Compare commits

...

6 Commits
1.5.2 ... 1.5.4

7 changed files with 114 additions and 130 deletions

View File

@ -20,6 +20,7 @@ end
i3 = { i3 = {
settings = { settings = {
debug_mode = false,
max_favs = 6, max_favs = 6,
min_fs_version = 4, min_fs_version = 4,
item_btn_size = 1.1, item_btn_size = 1.1,
@ -66,13 +67,6 @@ i3 = {
model_alias = lf"/src/model_aliases.lua", model_alias = lf"/src/model_aliases.lua",
progressive = lf"/src/progressive.lua", progressive = lf"/src/progressive.lua",
styles = lf"/src/styles.lua", styles = lf"/src/styles.lua",
tests = {
tabs = lf"/tests/test_tabs.lua",
operators = lf"/tests/test_operators.lua",
compression = lf"/tests/test_compression.lua",
custom_recipes = lf"/tests/test_custom_recipes.lua",
}
}, },
-- Caches -- Caches
@ -121,10 +115,9 @@ local function get_formspec_version(info)
end end
local function outdated(name) local function outdated(name)
local fs = ("size[6.3,1.3]image[0,0;1,1;i3_book.png]label[1,0;%s]button_exit[2.6,0.8;1,1;;OK]"):format( core.show_formspec(name, "i3_outdated",
"Your Minetest client is outdated.\nGet the latest version on minetest.net to play the game.") ("size[6.5,1.3]image[0,0;1,1;i3_book.png]label[1,0;%s]button_exit[2.6,0.8;1,1;;OK]"):format(
"Your Minetest client is outdated.\nGet the latest version on minetest.net to play the game."))
core.show_formspec(name, "i3_outdated", fs)
end end
if rawget(_G, "armor") then if rawget(_G, "armor") then
@ -254,7 +247,9 @@ if i3.settings.progressive_mode then
i3.files.progressive() i3.files.progressive()
end end
--i3.files.tests.tabs() if i3.settings.debug_mode then
--i3.files.tests.operators() lf("/tests/test_tabs.lua")()
--i3.files.tests.compression() lf("/tests/test_operators.lua")()
--i3.files.tests.custom_recipes(http) lf("/tests/test_compression.lua")()
lf("/tests/test_custom_recipes.lua")()
end

View File

@ -1,5 +1,5 @@
local make_fs = i3.files.gui()
local http = ... local http = ...
local make_fs = i3.files.gui()
IMPORT("gmatch", "split") IMPORT("gmatch", "split")
IMPORT("S", "err", "fmt", "reg_items") IMPORT("S", "err", "fmt", "reg_items")
@ -22,7 +22,7 @@ end
function i3.register_craft(def) function i3.register_craft(def)
local width, c = 0, 0 local width, c = 0, 0
if true_str(def.url) then if http and true_str(def.url) then
http.fetch({url = def.url}, function(result) http.fetch({url = def.url}, function(result)
if result.succeeded then if result.succeeded then
local t = core.parse_json(result.data) local t = core.parse_json(result.data)
@ -51,7 +51,7 @@ function i3.register_craft(def)
def.result = nil def.result = nil
end end
if not true_str(def.output) then if not true_str(def.output) and not def.url then
return err "i3.register_craft: output missing" return err "i3.register_craft: output missing"
end end
@ -69,9 +69,7 @@ function i3.register_craft(def)
end end
local cp = copy(def.grid) local cp = copy(def.grid)
sort(cp, function(a, b) sort(cp, function(a, b) return #a > #b end)
return #a > #b
end)
width = #cp[1] width = #cp[1]
@ -86,26 +84,29 @@ function i3.register_craft(def)
def.items[c] = def.key[symbol] def.items[c] = def.key[symbol]
end end
else else
local items, len = def.items, #def.items local items = copy(def.items)
local lines = {}
def.items = {} def.items = {}
for i = 1, len do for i = 1, #items do
local rlen = #split(items[i], ",") lines[i] = split(items[i], ",", true)
if rlen > width then if #lines[i] > width then
width = rlen width = #lines[i]
end end
end end
for i = 1, len do for i = 1, #items do
while #split(items[i], ",") < width do while #lines[i] < width do
items[i] = fmt("%s,", items[i]) insert(lines[i], items[i])
end end
end end
for name in gmatch(concat(items, ","), "[%s%w_:]+") do for _, line in ipairs(lines) do
for _, v in ipairs(line) do
c++ c++
def.items[c] = clean_name(name) def.items[c] = clean_name(v)
end
end end
end end

View File

@ -229,6 +229,9 @@ i3.new_tab("inventory", {
}) })
data.scrbar_inv += 1000 data.scrbar_inv += 1000
elseif fields.hide_debug_grid then
data.hide_debug_grid = not data.hide_debug_grid
end end
return set_fs(player) return set_fs(player)
@ -376,13 +379,12 @@ local function rcp_fields(player, data, fields)
data.scrbar_usg = 1 data.scrbar_usg = 1
elseif fields.fav then elseif fields.fav then
local fav, i = is_fav(data.favs, data.query_item) local fav = is_fav(data)
local total = #data.favs
if total < i3.settings.max_favs and not fav then if #data.favs < i3.settings.max_favs and not fav then
data.favs[total + 1] = data.query_item insert(data.favs, data.query_item)
elseif fav then elseif fav then
remove(data.favs, i) remove(data.favs, fav)
end end
elseif fields.export_rcp or fields.export_usg then elseif fields.export_rcp or fields.export_usg then
@ -423,7 +425,8 @@ core.register_on_player_receive_fields(function(player, formname, fields)
local name = player:get_player_name() local name = player:get_player_name()
if formname == "i3_outdated" then if formname == "i3_outdated" then
return false, core.kick_player(name, S"Come back when your client is up-to-date.") return false, core.kick_player(name,
S"Come back when your Minetest client is up-to-date (www.minetest.net).")
elseif formname ~= "" then elseif formname ~= "" then
return false return false
end end

View File

@ -289,17 +289,12 @@ local function compressible(item, data)
return compression_active(data) and i3.compress_groups[item] return compression_active(data) and i3.compress_groups[item]
end end
local function is_fav(favs, query_item) local function is_fav(data)
local fav, i for i = 1, #data.favs do
for j = 1, #favs do if data.favs[i] == data.query_item then
if favs[j] == query_item then return i
fav = true
i = j
break
end end
end end
return fav, i
end end
local function sort_by_category(data) local function sort_by_category(data)

View File

@ -7,9 +7,9 @@ local PNG, styles, fs_elements, colors = i3.files.styles()
local sprintf = string.format local sprintf = string.format
local VoxelArea, VoxelManip = VoxelArea, VoxelManip local VoxelArea, VoxelManip = VoxelArea, VoxelManip
IMPORT("clr", "ESC", "check_privs")
IMPORT("find", "match", "sub", "upper") IMPORT("find", "match", "sub", "upper")
IMPORT("vec_new", "vec_sub", "vec_round") IMPORT("vec_new", "vec_sub", "vec_round")
IMPORT("clr", "ESC", "msg", "check_privs")
IMPORT("min", "max", "floor", "ceil", "round") IMPORT("min", "max", "floor", "ceil", "round")
IMPORT("reg_items", "reg_tools", "reg_entities") IMPORT("reg_items", "reg_tools", "reg_entities")
IMPORT("get_bag_description", "get_detached_inv") IMPORT("get_bag_description", "get_detached_inv")
@ -234,14 +234,14 @@ local function get_isometric_view(fs, pos, X, Y, t, cubes, depth, high)
local width = 8 local width = 8
local base_height = 4 local base_height = 4
local base_depth = depth == -1 local base_depth = depth == -1
local max_depth = -10 local max_depth = -7
local height = base_depth and (base_height - 1) or depth local height = base_depth and (base_height - 1) or depth
local pos1 = vec_new(pos.x - width, pos.y + depth, pos.z - width) local pos1 = vec_new(pos.x - width, pos.y + depth, pos.z - width)
local pos2 = vec_new(pos.x + width, pos.y + height, pos.z + width) local pos2 = vec_new(pos.x + width, pos.y + height, pos.z + width)
local vm = VoxelManip(pos1, pos2) local vm = VoxelManip(pos1, pos2)
local emin, emax = vm:read_from_map(pos1, pos2) local emin, emax = vm:get_emerged_area()
local area = VoxelArea:new{MinEdge = emin, MaxEdge = emax} local area = VoxelArea:new{MinEdge = emin, MaxEdge = emax}
local data = vm:get_data() local data = vm:get_data()
@ -276,8 +276,9 @@ local function get_isometric_view(fs, pos, X, Y, t, cubes, depth, high)
if cubes < maxc and depth > max_depth then if cubes < maxc and depth > max_depth then
-- if there's not enough map to preview, go deeper -- if there's not enough map to preview, go deeper
depth -= 1 depth -= 1
get_isometric_view(fs, pos, X, Y, t, cubes, depth, high) return get_isometric_view(fs, pos, X, Y, t, cubes, depth, high)
else end
local shift = -0.3 - high local shift = -0.3 - high
for i = max_depth, 0 do for i = max_depth, 0 do
@ -294,7 +295,6 @@ local function get_isometric_view(fs, pos, X, Y, t, cubes, depth, high)
shift += (base_depth and 0.45 or 0.95) shift += (base_depth and 0.45 or 0.95)
fs("image", 2.7, Y + shift, 0.3, 0.3, PNG.flag) fs("image", 2.7, Y + shift, 0.3, 0.3, PNG.flag)
end
end end
local function get_waypoint_fs(fs, data, player, yextra, ctn_len) local function get_waypoint_fs(fs, data, player, yextra, ctn_len)
@ -1093,8 +1093,7 @@ local function get_model_fs(fs, data, def, model_alias)
hex = "0" .. hex hex = "0" .. hex
end end
_name = fmt("%s^[multiply:%s", v.name, _name = fmt("%s^[multiply:%s", v.name, fmt("#%s%s", sub(hex, 3), sub(hex, 1, 2)))
fmt("#%s%s", sub(hex, 3), sub(hex, 1, 2)))
else else
_name = fmt("%s^[multiply:%s", v.name, v.color) _name = fmt("%s^[multiply:%s", v.name, v.color)
end end
@ -1115,7 +1114,7 @@ local function get_model_fs(fs, data, def, model_alias)
end end
local function get_header(fs, data) local function get_header(fs, data)
local fav = is_fav(data.favs, data.query_item) local fav = is_fav(data)
local nfavs = #data.favs local nfavs = #data.favs
local max_favs = i3.settings.max_favs local max_favs = i3.settings.max_favs
local star_x, star_y, size = data.inv_width + 0.3, data.yoffset + 0.2, 0.4 local star_x, star_y, size = data.inv_width + 0.3, data.yoffset + 0.2, 0.4
@ -1201,7 +1200,7 @@ local function get_export_fs(fs, data, is_recipe, is_usage, max_stacks_rcp, max_
fmt("craft_%s", name), ES("Craft (×@1)", stack_fs)) fmt("craft_%s", name), ES("Craft (×@1)", stack_fs))
end end
local function get_rcp_extra(fs, player, data, panel, is_recipe, is_usage) local function get_rcp_extra(fs, data, player, panel, is_recipe, is_usage)
fs"container[0,0.075]" fs"container[0,0.075]"
local rn = panel.rcp and #panel.rcp local rn = panel.rcp and #panel.rcp
@ -1270,7 +1269,7 @@ local function hide_items(player, data)
end end
end end
local function get_items_fs(fs, player, data, full_height) local function get_items_fs(fs, data, player, full_height)
hide_items(player, data) hide_items(player, data)
local items = data.alt_items or data.items or {} local items = data.alt_items or data.items or {}
@ -1278,6 +1277,8 @@ local function get_items_fs(fs, player, data, full_height)
local ipp = rows * lines local ipp = rows * lines
local size = 0.85 local size = 0.85
fs("bg9", data.inv_width + 0.1, 0, 7.9, full_height, PNG.bg_full, 10)
fs(fmt("box[%f,0.2;4.05,0.6;#bababa25]", data.inv_width + 0.3), fs(fmt("box[%f,0.2;4.05,0.6;#bababa25]", data.inv_width + 0.3),
"set_focus[filter]", "set_focus[filter]",
fmt("field[%f,0.2;2.95,0.6;filter;;%s]", data.inv_width + 0.35, ESC(data.filter)), fmt("field[%f,0.2;2.95,0.6;filter;;%s]", data.inv_width + 0.35, ESC(data.filter)),
@ -1363,43 +1364,23 @@ local function get_favs(fs, data)
end end
end end
local function get_panels(fs, player, data, full_height) local function get_panels(fs, data, player)
local _title = {name = "title", height = 1.4} local title = {name = "title", height = 1.4, func = get_header}
local _favs = {name = "favs", height = 2.23} local favs = {name = "favs", height = 2.23, func = get_favs}
local _items = {name = "items", height = full_height} local recipes = {name = "recipes", rcp = data.recipes, height = 4.045, func = get_rcp_extra}
local _recipes = {name = "recipes", rcp = data.recipes, height = 4.045} local usages = {name = "usages", rcp = data.usages, height = 4.045, func = get_rcp_extra}
local _usages = {name = "usages", rcp = data.usages, height = 4.045} local panels = {title, recipes, usages, favs}
local panels
if data.query_item then
panels = {_title, _recipes, _usages, _favs}
else
panels = {_items}
end
for idx = 1, #panels do
local panel = panels[idx]
data.yoffset = 0 data.yoffset = 0
if idx > 1 then for i, panel in ipairs(panels) do
for _idx = idx - 1, 1, -1 do if i > 1 then
data.yoffset = data.yoffset + panels[_idx].height + 0.1 data.yoffset += panels[i - 1].height + 0.1
end
end end
fs("bg9", data.inv_width + 0.1, data.yoffset, 7.9, panel.height, PNG.bg_full, 10) fs("bg9", data.inv_width + 0.1, data.yoffset, 7.9, panel.height, PNG.bg_full, 10)
local is_recipe, is_usage = panel.name == "recipes", panel.name == "usages" local is_recipe, is_usage = panel.name == "recipes", panel.name == "usages"
panel.func(fs, data, player, panel, is_recipe, is_usage)
if is_recipe or is_usage then
get_rcp_extra(fs, player, data, panel, is_recipe, is_usage)
elseif panel.name == "items" then
get_items_fs(fs, player, data, full_height)
elseif panel.name == "title" then
get_header(fs, data)
elseif panel.name == "favs" then
get_favs(fs, data)
end
end end
end end
@ -1452,6 +1433,10 @@ local function get_tabs_fs(fs, player, data, full_height)
end end
local function get_debug_grid(data, fs, full_height) local function get_debug_grid(data, fs, full_height)
fs"style[hide_debug_grid;noclip=true]"
fs("button", -2, full_height - 1, 2, 1, "hide_debug_grid", "Toggle grid")
if data.hide_debug_grid then return end
fs("style_type[label;font_size=8;noclip=true]") fs("style_type[label;font_size=8;noclip=true]")
local spacing, i = 0.2, 1 local spacing, i = 0.2, 1
@ -1475,7 +1460,7 @@ local function get_debug_grid(data, fs, full_height)
end end
local function make_fs(player, data) local function make_fs(player, data)
--local start = os.clock() local start = i3.settings.debug_mode and os.clock() or nil
local fs = setmetatable({}, { local fs = setmetatable({}, {
__call = function(t, ...) __call = function(t, ...)
@ -1493,26 +1478,32 @@ local function make_fs(player, data)
data.inv_width = 10.23 data.inv_width = 10.23
local full_height = 12 local full_height = 12
local tab = i3.tabs[data.tab]
fs(fmt("formspec_version[%u]size[%f,%f]no_prepend[]bgcolor[#0000]", fs(fmt("formspec_version[%u]size[%f,%f]no_prepend[]bgcolor[#0000]",
i3.settings.min_fs_version, data.inv_width + 8, full_height), styles) i3.settings.min_fs_version, data.inv_width + 8, full_height), styles)
fs("bg9", 0, 0, data.inv_width, full_height, PNG.bg_full, 10) fs("bg9", 0, 0, data.inv_width, full_height, PNG.bg_full, 10)
local tab = i3.tabs[data.tab]
if tab then if tab then
tab.formspec(player, data, fs) tab.formspec(player, data, fs)
end end
get_panels(fs, player, data, full_height) if data.query_item then
get_panels(fs, data, player)
else
get_items_fs(fs, data, player, full_height)
end
if #i3.tabs > 1 then if #i3.tabs > 1 then
get_tabs_fs(fs, player, data, full_height) get_tabs_fs(fs, player, data, full_height)
end end
--get_debug_grid(data, fs, full_height) if i3.settings.debug_mode then
--print("make_fs()", fmt("%.2f ms", (os.clock() - start) * 1000)) get_debug_grid(data, fs, full_height)
--print("#fs elements", #fs) msg(data.player_name, fmt("make_fs(): %.2f ms", (os.clock() - start) * 1000))
msg(data.player_name, fmt("#fs elements: %u", #fs))
end
return concat(fs) return concat(fs)
end end

View File

@ -34,7 +34,7 @@ local function init_hud(player)
}, },
} }
if not i3.legacy_inventory then if not i3.settings.legacy_inventory then
core.after(0, function() core.after(0, function()
player:hud_set_hotbar_itemcount(i3.settings.hotbar_len) player:hud_set_hotbar_itemcount(i3.settings.hotbar_len)
player:hud_set_hotbar_image"i3_hotbar.png" player:hud_set_hotbar_image"i3_hotbar.png"

View File

@ -38,6 +38,24 @@ i3.register_craft({
items = {"default:copper_ingot 7, default:tin_ingot, default:steel_ingot 2"}, items = {"default:copper_ingot 7, default:tin_ingot, default:steel_ingot 2"},
}) })
i3.register_craft {
result = "default:tree",
items = {
"default:wood",
"",
"default:wood"
},
}
i3.register_craft {
result = "default:cobble 16",
items = {
"default:stone, default:stone",
"default:stone, , default:stone",
", default:stone, default:stone",
}
}
i3.register_craft({ i3.register_craft({
grid = { grid = {
"X", "X",
@ -311,22 +329,3 @@ i3.register_craft({
}, },
result = "default:mese 3", result = "default:mese 3",
}) })
i3.register_craft({
grid = {
"X #",
" ## ",
"X#X#",
"#X#X#",
"X X##X#X",
" ## ",
"#X#X#",
"#X#X#",
"X #",
},
key = {
['#'] = "default:wood",
['X'] = "default:glass",
},
result = "default:mese 3",
})