diff -Nru minetest-mod-craftguide-1.13/debian/changelog minetest-mod-craftguide-1.14/debian/changelog --- minetest-mod-craftguide-1.13/debian/changelog 2020-04-30 05:53:46.000000000 +0000 +++ minetest-mod-craftguide-1.14/debian/changelog 2020-07-12 11:01:38.000000000 +0000 @@ -1,3 +1,14 @@ +minetest-mod-craftguide (1.14-1) unstable; urgency=medium + + * New upstream release. + * Update team mailing list address. + * Bump dh compat to 13. + * Declare d/rules doesn't require root. + * Add basic upstream metadata. + * Point to the https uri in d/copyright. + + -- Julien Puydt Sun, 12 Jul 2020 13:01:38 +0200 + minetest-mod-craftguide (1.13-1) unstable; urgency=medium * New upstream release. @@ -77,8 +88,8 @@ * New upstream release. * Refresh packaging: - Update dates in d/copyright. - - Use my debian.org mail address. - - Drop the upstreamed patch. + - Use my debian.org mail address. + - Drop the upstreamed patch. -- Julien Puydt Thu, 28 Jun 2018 22:51:24 +0200 diff -Nru minetest-mod-craftguide-1.13/debian/control minetest-mod-craftguide-1.14/debian/control --- minetest-mod-craftguide-1.13/debian/control 2020-04-30 05:53:46.000000000 +0000 +++ minetest-mod-craftguide-1.14/debian/control 2020-07-12 11:01:38.000000000 +0000 @@ -1,10 +1,11 @@ Source: minetest-mod-craftguide Section: games Priority: optional -Maintainer: Debian Games Team +Maintainer: Debian Games Team Uploaders: Julien Puydt -Build-Depends: debhelper-compat (= 12) +Build-Depends: debhelper-compat (= 13) Standards-Version: 4.5.0 +Rules-Requires-Root: no Homepage: https://github.com/minetest-mods/craftguide Vcs-Git: https://salsa.debian.org/games-team/minetest-mod-craftguide.git Vcs-Browser: https://salsa.debian.org/games-team/minetest-mod-craftguide diff -Nru minetest-mod-craftguide-1.13/debian/copyright minetest-mod-craftguide-1.14/debian/copyright --- minetest-mod-craftguide-1.13/debian/copyright 2020-04-30 05:53:46.000000000 +0000 +++ minetest-mod-craftguide-1.14/debian/copyright 2020-07-12 11:01:38.000000000 +0000 @@ -1,4 +1,4 @@ -Format: http://www.debian.org/doc/packaging-manuals/copyright-format/1.0/ +Format: https://www.debian.org/doc/packaging-manuals/copyright-format/1.0/ Upstream-Name: craftguide Source: https://github.com/minetest-mods/craftguide diff -Nru minetest-mod-craftguide-1.13/debian/upstream/metadata minetest-mod-craftguide-1.14/debian/upstream/metadata --- minetest-mod-craftguide-1.13/debian/upstream/metadata 1970-01-01 00:00:00.000000000 +0000 +++ minetest-mod-craftguide-1.14/debian/upstream/metadata 2020-07-12 11:01:38.000000000 +0000 @@ -0,0 +1,4 @@ +Homepage: https://github.com/minetest-mods/craftguide +Repository: https://github.com/minetest-mods/craftguide +Repository-Browse: https://github.com/minetest-mods/craftguide +Bug-Database: https://github.com/minetest-mods/craftguide/issues diff -Nru minetest-mod-craftguide-1.13/init.lua minetest-mod-craftguide-1.14/init.lua --- minetest-mod-craftguide-1.13/init.lua 2020-04-16 16:39:39.000000000 +0000 +++ minetest-mod-craftguide-1.14/init.lua 2020-07-10 13:55:20.000000000 +0000 @@ -7,15 +7,13 @@ local recipes_cache = {} local usages_cache = {} local fuel_cache = {} - local toolrepair local progressive_mode = core.settings:get_bool "craftguide_progressive_mode" local sfinv_only = core.settings:get_bool "craftguide_sfinv_only" and rawget(_G, "sfinv") -local autocache = core.settings:get_bool "craftguide_autocache" local http = core.request_http_api() -local storage = core.get_mod_storage() +local singleplayer = core.is_singleplayer() local reg_items = core.registered_items local reg_tools = core.registered_tools @@ -40,6 +38,7 @@ local on_mods_loaded = core.register_on_mods_loaded local on_leaveplayer = core.register_on_leaveplayer local get_player_info = core.get_player_information +local get_translation = minetest.get_translated_string local on_receive_fields = core.register_on_player_receive_fields local ESC = core.formspec_escape @@ -57,20 +56,24 @@ string.format, string.find, string.gmatch, string.match, string.sub, string.split, string.upper, string.lower -local min, max, floor, ceil = math.min, math.max, math.floor, math.ceil -local pairs, next, type, tostring, unpack = pairs, next, type, tostring, unpack +local min, max, floor, ceil, abs = math.min, math.max, math.floor, math.ceil, math.abs +local pairs, next, type, unpack = pairs, next, type, unpack local vec_add, vec_mul = vector.add, vector.multiply -local FORMSPEC_MINIMAL_VERSION = 3 - local ROWS = 9 -local LINES = sfinv_only and 5 or 9 +local LINES = sfinv_only and 5 or 10 local IPP = ROWS * LINES -local WH_LIMIT = 8 +local WH_LIMIT = 10 +local MAX_FAVS = 6 +local ITEM_BTN_SIZE = 1.1 local XOFFSET = sfinv_only and 3.83 or 11.2 local YOFFSET = sfinv_only and 4.9 or 1 +-- Progressive mode +local POLL_FREQ = 0.25 +local HUD_TIMER_MAX = 1.5 + local PNG = { bg = "craftguide_bg.png", bg_full = "craftguide_bg_full.png", @@ -106,9 +109,23 @@ arrow = "image_button[%f,%f;0.8,0.8;%s;%s;;;false;%s]", } -local function get_fs_version(name) +local function get_lang_code(name) local info = get_player_info(name) - return info and info.formspec_version or 1 + return info and info.lang_code +end + +local function outdated(name) + local fs = fmt([[ + size[6.6,1.3] + image[0,0;1,1;%s] + label[1,0;%s] + button_exit[2.8,0.8;1,1;;OK] + ]], + PNG.book, + "Your Minetest client is outdated.\n" .. + "Get the latest version on minetest.net to use the Crafting Guide.") + + return show_formspec(name, "craftguide", fs) end local function mul_elem(elem, n) @@ -135,14 +152,18 @@ } local group_names = { + carpet = S"Any carpet", coal = S"Any coal", - wool = S"Any wool", - wood = S"Any wood planks", + dye = S"Any dye", + flower = S"Any flower", + mushroom = S"Any mushroom", sand = S"Any sand", stick = S"Any stick", stone = S"Any kind of stone block", tree = S"Any tree", vessel = S"Any vessel", + wool = S"Any wool", + wood = S"Any wood planks", ["color_red,flower"] = S"Any red flower", ["color_blue,flower"] = S"Any blue flower", @@ -429,12 +450,12 @@ end end - local output = match(def.output, "%S+") - recipes_cache[output] = recipes_cache[output] or {} + local item = match(def.output, "%S+") + recipes_cache[item] = recipes_cache[item] or {} def.custom = true def.width = width - insert(recipes_cache[output], def) + insert(recipes_cache[item], def) end local recipe_filters = {} @@ -505,35 +526,8 @@ end local function extract_groups(str) - return split(sub(str, 7), ",") -end - -local function item_in_recipe(item, recipe) - local clean_item = reg_aliases[item] or item - - for _, recipe_item in pairs(recipe.items) do - local clean_recipe_item = reg_aliases[recipe_item] or recipe_item - if clean_recipe_item == clean_item then - return true - end - end -end - -local function groups_item_in_recipe(item, recipe) - local def = reg_items[item] - if not def then return end - local item_groups = def.groups - - for _, recipe_item in pairs(recipe.items) do - if is_group(recipe_item) then - local groups = extract_groups(recipe_item) - - if item_has_groups(item_groups, groups) then - local usage = copy(recipe) - table_replace(usage.items, recipe_item, item) - return usage - end - end + if sub(str, 1, 6) == "group:" then + return split(sub(str, 7), ",") end end @@ -546,7 +540,7 @@ local usages = usages_cache[item] recipes = #apply_recipe_filters(recipes or {}, player) - usages = #apply_recipe_filters(usages or {}, player) + usages = #apply_recipe_filters(usages or {}, player) if recipes > 0 or usages > 0 then c = c + 1 @@ -565,58 +559,151 @@ return items end -local function get_usages(item) - local usages, c = {}, 0 +local function get_burntime(item) + return get_craft_result{method = "fuel", items = {item}}.time +end - for _, recipes in pairs(recipes_cache) do - for i = 1, #recipes do - local recipe = recipes[i] - if item_in_recipe(item, recipe) then - c = c + 1 - usages[c] = recipe - else - recipe = groups_item_in_recipe(item, recipe) - if recipe then - c = c + 1 - usages[c] = recipe +local function cache_fuel(item) + local burntime = get_burntime(item) + if burntime > 0 then + fuel_cache[item] = burntime + end +end + +local function show_item(def) + return def and not (def.groups.not_in_craft_guide == 1 or + def.groups.not_in_creative_inventory == 1) and + def.description and def.description ~= "" +end + +local function get_usages(recipe) + local added = {} + + for _, item in pairs(recipe.items) do + item = reg_aliases[item] or item + if not added[item] then + local groups = extract_groups(item) + if groups then + for name, def in pairs(reg_items) do + if not added[name] and show_item(def) and + item_has_groups(def.groups, groups) then + local usage = copy(recipe) + table_replace(usage.items, item, name) + usages_cache[name] = usages_cache[name] or {} + insert(usages_cache[name], 1, usage) + added[name] = true + end + end + elseif show_item(reg_items[item]) then + usages_cache[item] = usages_cache[item] or {} + insert(usages_cache[item], 1, recipe) end + + added[item] = true end end +end + +local function cache_usages(item) + local recipes = recipes_cache[item] or {} + + for i = 1, #recipes do + get_usages(recipes[i]) end if fuel_cache[item] then - usages[#usages + 1] = { + local fuel = { type = "fuel", items = {item}, replacements = fuel_cache.replacements[item], } - end - return usages + usages_cache[item] = table_merge(usages_cache[item] or {}, {fuel}) + end end -local function get_burntime(item) - return get_craft_result{method = "fuel", items = {item}}.time -end +local function drop_table(name, drop) + local drop_sure, drop_maybe = {}, {} + local drop_items = drop.items or {} -local function cache_fuel(item) - local burntime = get_burntime(item) - if burntime > 0 then - fuel_cache[item] = burntime + for i = 1, #drop_items do + local di = drop_items[i] + + for j = 1, #di.items do + local dstack = ItemStack(di.items[j]) + local dname = dstack:get_name() + local dcount = dstack:get_count() + + if not dstack:is_empty() and (dname ~= name or + (dname == name and dcount > 1)) then + if #di.items == 1 and (not di.rarity or di.rarity <= 1) then + if drop_sure[dname] then + if dcount > drop_sure[dname].output then + dcount = dcount + drop_sure[dname].output + else + dcount = drop_sure[dname].output + end + end + + drop_sure[dname] = { + output = dcount, + tools = di.tools, + } + else + drop_maybe[#drop_maybe + 1] = { + item = dname, + output = dcount, + rarity = di.rarity, + tools = di.tools, + } + end + end + end + end + + for item, data in pairs(drop_sure) do + craftguide.register_craft{ + type = "digging", + items = {name}, + output = fmt("%s %u", item, data.output), + tools = data.tools, + } + end + + for _, data in ipairs(drop_maybe) do + craftguide.register_craft{ + type = "digging_chance", + items = {name}, + output = fmt("%s %u", data.item, data.output), + rarity = data.rarity, + tools = data.tools, + } end end -local function cache_usages(item) - local usages = get_usages(item) - if #usages > 0 then - usages_cache[item] = table_merge(usages, usages_cache[item] or {}) +local function cache_drops(name, drop) + if true_str(drop) then + local dstack = ItemStack(drop) + if not dstack:is_empty() and dstack:get_name() ~= name then + craftguide.register_craft{ + type = "digging", + items = {name}, + output = drop, + } + end + elseif is_table(drop) then + drop_table(name, drop) end end -local function cache_recipes(output) - local recipes = get_all_recipes(output) or {} - if #recipes > 0 then - recipes_cache[output] = recipes +local function cache_recipes(item) + item = reg_aliases[item] or item + local def = reg_items[item] + if not def then return end + local recipes = get_all_recipes(item) or {} + + for i = 1, #recipes do + recipes_cache[item] = table_merge(recipes_cache[item] or {}, recipes[i]) end end @@ -657,6 +744,7 @@ local def_gr = "default:" .. group local stereotypes = craftguide.group_stereotypes local stereotype = stereotypes and stereotypes[group] + stereotype = reg_items[stereotype] and stereotype if stereotype then return stereotype @@ -684,10 +772,10 @@ return toolrepair and def and def.groups and def.groups.disable_repair ~= 1 end -local function is_fav(data) +local function is_fav(favs, query_item) local fav, i - for j = 1, #data.favs do - if data.favs[j] == data.query_item then + for j = 1, #favs do + if favs[j] == query_item then fav = true i = j break @@ -697,19 +785,29 @@ return fav, i end -local function get_desc(name) - if sub(name, 1, 1) == "_" then - name = sub(name, 2) +local function str_newline(str) + return find(str, "\n") +end + +local function get_desc(item, lang_code) + if sub(item, 1, 1) == "_" then + item = sub(item, 2) end - local def = reg_items[name] + local def = reg_items[item] - return def and (match(def.description, "%)([%w%s]*)") or def.description) or - (def and match(name, ":.*"):gsub("%W%l", upper):sub(2):gsub("_", " ") or - S("Unknown Item (@1)", name)) + if def then + if true_str(def.description) then + return match(get_translation(lang_code, def.description), "[^\n]*") + elseif true_str(item) then + return match(item, ":.*"):gsub("%W%l", upper):sub(2):gsub("_", " ") + end + end + + return S("Unknown Item (@1)", item) end -local function get_tooltip(name, info) +local function get_tooltip(item, info, lang_code) local tooltip if info.groups then @@ -717,18 +815,17 @@ tooltip = group_names[concat(info.groups, ",")] if not tooltip then - local groupstr, c = {}, 0 + local groupstr = {} for i = 1, #info.groups do - c = c + 1 - groupstr[c] = clr("#ff0", info.groups[i]) + insert(groupstr, clr("#ff0", info.groups[i])) end groupstr = concat(groupstr, ", ") tooltip = S("Any item belonging to the group(s): @1", groupstr) end else - tooltip = get_desc(name) + tooltip = get_desc(item, lang_code) end local function add(str) @@ -744,14 +841,17 @@ end if info.replace then - local desc = clr("#ff0", get_desc(info.replace)) - - if info.cooktime then - tooltip = add(S("Replaced by @1 on smelting", desc)) - elseif info.burntime then - tooltip = add(S("Replaced by @1 on burning", desc)) - else - tooltip = add(S("Replaced by @1 on crafting", desc)) + for i = 1, #info.replace do + local rpl = info.replace[i] + local desc = clr("#ff0", get_desc(rpl, lang_code)) + + if info.cooktime then + tooltip = add(S("Replaced by @1 on smelting", desc)) + elseif info.burntime then + tooltip = add(S("Replaced by @1 on burning", desc)) + else + tooltip = add(S("Replaced by @1 on crafting", desc)) + end end end @@ -760,26 +860,44 @@ end if info.rarity then - local chance = (1 / info.rarity) * 100 + local chance = (1 / max(1, info.rarity)) * 100 tooltip = add(S("@1 of chance to drop", clr("#ff0", chance .. "%"))) end - return fmt("tooltip[%s;%s]", name, ESC(tooltip)) + if info.tools then + local several = #info.tools > 1 + local names = several and "\n" or "" + + if several then + for i = 1, #info.tools do + names = fmt("%s\t\t- %s\n", + names, clr("#ff0", get_desc(info.tools[i], lang_code))) + end + + tooltip = add(S("Only drop if using one of these tools: @1", + sub(names, 1, -2))) + else + tooltip = add(S("Only drop if using this tool: @1", + clr("#ff0", get_desc(info.tools[1], lang_code)))) + end + end + + return fmt("tooltip[%s;%s]", item, ESC(tooltip)) end -local function get_output_fs(data, fs, L) - local custom_recipe = craft_types[L.recipe.type] +local function get_output_fs(lang_code, fs, rcp, shapeless, right, btn_size, _btn_size, spacing) + local custom_recipe = craft_types[rcp.type] - if custom_recipe or L.shapeless or L.recipe.type == "cooking" then + if custom_recipe or shapeless or rcp.type == "cooking" then local icon = custom_recipe and custom_recipe.icon or - L.shapeless and "shapeless" or "furnace" + shapeless and "shapeless" or "furnace" if not custom_recipe then icon = fmt("craftguide_%s.png^[resize:16x16", icon) end - local pos_x = L.rightest + L.btn_size + 0.1 - local pos_y = YOFFSET + (sfinv_only and 0.25 or -0.45) + L.spacing + local pos_x = right + btn_size + 0.1 + local pos_y = YOFFSET + (sfinv_only and 1.55 or -0.45) + spacing if sub(icon, 1, 18) == "craftguide_furnace" then fs[#fs + 1] = fmt(FMT.animated_image, @@ -789,59 +907,66 @@ end local tooltip = custom_recipe and custom_recipe.description or - L.shapeless and S"Shapeless" or S"Cooking" + shapeless and S"Shapeless" or S"Cooking" fs[#fs + 1] = fmt(FMT.tooltip, pos_x, pos_y, 0.5, 0.5, ESC(tooltip)) end - local arrow_X = L.rightest + (L._btn_size or 1.1) + local arrow_X = right + (_btn_size or ITEM_BTN_SIZE) local output_X = arrow_X + 0.9 - local Y = YOFFSET + (sfinv_only and 0.7 or 0) + L.spacing + local Y = YOFFSET + (sfinv_only and 2 or 0) + spacing fs[#fs + 1] = fmt(FMT.image, arrow_X, Y + 0.2, 0.9, 0.7, PNG.arrow) - if L.recipe.type == "fuel" then - fs[#fs + 1] = fmt(FMT.animated_image, output_X, Y, 1.1, 1.1, PNG.fire_anim, 8, 180) + if rcp.type == "fuel" then + fs[#fs + 1] = fmt(FMT.animated_image, output_X, Y, + ITEM_BTN_SIZE, ITEM_BTN_SIZE, PNG.fire_anim, 8, 180) else - local item = L.recipe.output + local item = rcp.output item = clean_name(item) local name = match(item, "%S*") - fs[#fs + 1] = fmt(FMT.image, output_X, Y, 1.1, 1.1, PNG.selected) + fs[#fs + 1] = fmt(FMT.image, output_X, Y, + ITEM_BTN_SIZE, ITEM_BTN_SIZE, PNG.selected) local _name = sfinv_only and name or fmt("_%s", name) fs[#fs + 1] = fmt("item_image_button[%f,%f;%f,%f;%s;%s;%s]", - output_X, Y, 1.1, 1.1, item, _name, "") + output_X, Y, ITEM_BTN_SIZE, ITEM_BTN_SIZE, item, _name, "") + + local def = reg_items[name] + local unknown = not def or nil + local weird_desc = name ~= "" and def and + (not true_str(def.description) or str_newline(def.description)) or nil local infos = { - unknown = not reg_items[name] or nil, - burntime = fuel_cache[name], - repair = repairable(name), - rarity = L.rarity, + unknown = unknown, + weird_desc = weird_desc, + burntime = fuel_cache[name], + repair = repairable(name), + rarity = rcp.rarity, + tools = rcp.tools, } if next(infos) then - fs[#fs + 1] = get_tooltip(_name, infos) + fs[#fs + 1] = get_tooltip(_name, infos, lang_code) end if infos.burntime then fs[#fs + 1] = fmt(FMT.image, - output_X + 1, YOFFSET + (sfinv_only and 0.7 or 0.1) + L.spacing, + output_X + 1, YOFFSET + (sfinv_only and 2 or 0.1) + spacing, 0.6, 0.4, PNG.arrow) fs[#fs + 1] = fmt(FMT.animated_image, - output_X + 1.6, YOFFSET + (sfinv_only and 0.55 or 0) + L.spacing, + output_X + 1.6, YOFFSET + (sfinv_only and 1.85 or 0) + spacing, 0.6, 0.6, PNG.fire_anim, 8, 180) end end end -local function get_grid_fs(data, fs, rcp, spacing) +local function get_grid_fs(lang_code, fs, rcp, spacing) local width = rcp.width or 1 - local replacements = rcp.replacements - local rarity = rcp.rarity - local rightest, btn_size, _btn_size = 0, 1.1 + local right, btn_size, _btn_size = 0, ITEM_BTN_SIZE local cooktime, shapeless if rcp.type == "cooking" then @@ -878,22 +1003,17 @@ local Y = ceil(i / width) + YOFFSET - min(2, rows) + spacing if large_recipe then - local xof = 1 - 4 / width - local yof = 1 - 4 / rows - local x_y = width > rows and xof or yof - - btn_size = width > rows and - (3.5 + (xof * 2)) / width or (3.5 + (yof * 2)) / rows + btn_size = (width > 3 and 3 / width or 3 / rows) + 0.1 _btn_size = btn_size + local xi = (i - 1) % width + local yi = floor((i - 1) / width) - X = (btn_size * ((i - 1) % width) + XOFFSET - - (sfinv_only and 2.83 or 0)) * (0.83 - (x_y / 5)) - Y = (btn_size * floor((i - 1) / width) + - (sfinv_only and 5.81 or 3.92) + x_y) * (0.86 - (x_y / 5)) + X = btn_size * xi + XOFFSET - 2.65 - (xi * 0.15) + Y = btn_size * yi + spacing + (sfinv_only and 4 or 0) - (yi * 0.1) end - if X > rightest then - rightest = X + if X > right then + right = X end local groups @@ -906,17 +1026,19 @@ local label = groups and "\nG" or "" local replace - if replacements then - for j = 1, #replacements do - local replacement = replacements[j] + if rcp.replacements then + replace = {} + label = fmt("%s%s\nR", label ~= "" and "\n" or "", label) + + for j = 1, #rcp.replacements do + local replacement = rcp.replacements[j] if replacement[1] == name then - label = (label ~= "" and "\n" or "") .. label .. "\nR" - replace = replacement[2] + replace[#replace + 1] = replacement[2] end end end - Y = Y + (sfinv_only and 0.7 or 0) + Y = Y + (sfinv_only and 2 or 0) if not large_recipe then fs[#fs + 1] = fmt(FMT.image, X, Y, btn_size, btn_size, PNG.selected) @@ -925,16 +1047,23 @@ fs[#fs + 1] = fmt(FMT.item_image_button, X, Y, btn_size, btn_size, item, item, label) + local def = reg_items[name] + local unknown = not def or nil + unknown = not groups and unknown or nil + local weird_desc = name ~= "" and def and + (not true_str(def.description) or str_newline(def.description)) or nil + local infos = { - unknown = not reg_items[name] or nil, - groups = groups, - burntime = fuel_cache[name], - cooktime = cooktime, - replace = replace, + unknown = unknown, + weird_desc = weird_desc, + groups = groups, + burntime = fuel_cache[name], + cooktime = cooktime, + replace = replace, } if next(infos) then - fs[#fs + 1] = get_tooltip(item, infos) + fs[#fs + 1] = get_tooltip(item, infos, lang_code) end end @@ -942,70 +1071,129 @@ fs[#fs + 1] = "style_type[item_image_button;border=false]" end - get_output_fs(data, fs, { - recipe = rcp, - shapeless = shapeless, - rightest = rightest, - btn_size = btn_size, - _btn_size = _btn_size, - spacing = spacing, - rarity = rarity, - }) + get_output_fs(lang_code, fs, rcp, shapeless, right, btn_size, _btn_size, spacing) end -local function get_panels(data, fs) - local start_y = sfinv_only and 0.33 or 0 +local function get_rcp_lbl(lang_code, show_usages, unum, rnum, fs, panel, spacing, rn, is_recipe) + local lbl - local panels = { - {dat = data.usages or {}, height = 3.5}, - {dat = data.recipes or {}, height = 3.5}, - } + if (not sfinv_only and is_recipe) or (sfinv_only and not show_usages) then + lbl = ES("Recipe @1 of @2", rnum, rn) - if not sfinv_only then - panels.favs = {height = 2.19} + elseif not sfinv_only or (sfinv_only and show_usages) then + lbl = ES("Usage @1 of @2", unum, rn) + + elseif sfinv_only then + lbl = show_usages and ES("Usage @1 of @2", unum, rn) or + ES("Recipe @1 of @2", rnum, rn) + end + + lbl = get_translation(lang_code, lbl) + local shift = min(0.9, abs(13 - max(13, #lbl)) * 0.1) + + fs[#fs + 1] = fmt(FMT.label, + XOFFSET + (sfinv_only and 2.3 or 1.6) - shift, + YOFFSET + (sfinv_only and 3.4 or 1.5 + spacing), lbl) + + if rn > 1 then + local btn_suffix = is_recipe and "recipe" or "usage" + local prev_name = fmt("prev_%s", btn_suffix) + local next_name = fmt("next_%s", btn_suffix) + local x_arrow = XOFFSET + (sfinv_only and 1.7 or 1) + local y_arrow = YOFFSET + (sfinv_only and 3.3 or 1.4 + spacing) + + fs[#fs + 1] = fmt([[ + style[%s;fgimg=%s;fgimg_hovered=%s;fgimg_pressed=%s] + style[%s;fgimg=%s;fgimg_hovered=%s;fgimg_pressed=%s] + ]], + prev_name, PNG.prev, PNG.prev_hover, PNG.prev_hover, + next_name, PNG.next, PNG.next_hover, PNG.next_hover) + + fs[#fs + 1] = fmt(mul_elem(FMT.arrow, 2), + x_arrow - shift, y_arrow, PNG.prev, prev_name, "", + x_arrow + 1.8, y_arrow, PNG.next, next_name, "") + end + + local rcp = is_recipe and panel.rcp[rnum] or panel.rcp[unum] + get_grid_fs(lang_code, fs, rcp, spacing) +end + +local function get_title_fs(query_item, lang_code, favs, fs, spacing) + local desc = ESC(get_desc(query_item, lang_code)) + desc = #desc > 33 and fmt("%s...", sub(desc, 1, 30)) or desc + local t_desc = query_item + t_desc = #t_desc > 40 and fmt("%s...", sub(t_desc, 1, 37)) or t_desc + + fs[#fs + 1] = fmt("hypertext[9.05,%f;5.85,1.2;item_title;%s]", + spacing - 0.1, + fmt("" .. + "%s\n", + query_item, desc, t_desc)) + + local fav = is_fav(favs, query_item) + local nfavs = #favs + + if nfavs < MAX_FAVS or (nfavs == MAX_FAVS and fav) then + local fav_marked = fmt("craftguide_fav%s.png", fav and "_off" or "") + + fs[#fs + 1] = fmt( + "style[fav;fgimg=%s;fgimg_hovered=%s;fgimg_pressed=%s]", + fmt("craftguide_fav%s.png", fav and "" or "_off"), fav_marked, fav_marked) + + fs[#fs + 1] = fmt(FMT.image_button, 8.25, spacing + 0.15, 0.5, 0.45, "", "fav", "") + + fs[#fs + 1] = fmt("tooltip[fav;%s]", + fav and ES"Unmark this item" or ES"Mark this item") else - panels = data.show_usages and {{dat = data.usages}} or {{dat = data.recipes}} + fs[#fs + 1] = fmt( + "style[fav_no;fgimg=%s;fgimg_hovered=%s;fgimg_pressed=%s]", + "craftguide_fav_off.png", PNG.nothing, PNG.nothing) + + fs[#fs + 1] = fmt(FMT.image_button, + 8.25, spacing + 0.15, 0.5, 0.45, "", "fav_no", "") + + fs[#fs + 1] = fmt("tooltip[fav_no;%s]", + ES"Cannot mark this item. Limit of bookmarks reached.") end +end - for k, v in pairs(panels) do - start_y = start_y + 1 - local spacing = (start_y - 1) * 3.6 - - if not sfinv_only then - fs[#fs + 1] = fmt("background9[8.1,%f;6.6,%f;%s;false;%d]", - -0.2 + spacing, v.height, PNG.bg_full, 10) - - if k == 2 then - local fav = is_fav(data) - local nfavs = #data.favs - - fs[#fs + 1] = fmt( - "style[fav;fgimg=%s;fgimg_hovered=%s;fgimg_pressed=%s]", - fmt("craftguide_fav%s.png", fav and "" or "_off"), - fmt("craftguide_fav%s.png", fav and "_off" or ""), - fmt("craftguide_fav%s.png", fav and "_off" or "")) - - if nfavs < 6 or (nfavs >= 6 and fav) then - fs[#fs + 1] = fmt(FMT.image_button, - 14, spacing, 0.5, 0.45, "", "fav", "") - end +local function get_panels(lang_code, query_item, recipes, usages, show_usages, + favs, unum, rnum, fs) + + local _title = {name = "title", height = 1.2} + local _favs = {name = "favs", height = 1.91} + local _recipes = {name = "recipes", rcp = recipes, height = 3.5} + local _usages = {name = "usages", rcp = usages, height = 3.5} + local panels = {_title, _recipes, _usages, _favs} - fs[#fs + 1] = fmt("tooltip[fav;%s]", - fav and ES"Unmark this item" or ES"Mark this item") + if sfinv_only then + panels = {show_usages and _usages or _recipes} + end + + for idx = 1, #panels do + local panel, spacing = panels[idx], 0 + + if idx > 1 then + for _idx = idx - 1, 1, -1 do + spacing = spacing + panels[_idx].height + 0.1 end end - local rn = v.dat and #v.dat or -1 - local _rn = tostring(rn) - local xu = tostring(data.unum) .. _rn - local xr = tostring(data.rnum) .. _rn - xu = max(-0.3, -((#xu - 3) * 0.05)) - xr = max(-0.3, -((#xr - 3) * 0.05)) + local rn = panel.rcp and #panel.rcp + local is_recipe = sfinv_only and not show_usages or panel.name == "recipes" + local recipe_or_usage = panel.name == "recipes" or panel.name == "usages" + + if rn then + get_rcp_lbl(lang_code, show_usages, unum, rnum, fs, panel, + spacing, rn, is_recipe) + end + + if sfinv_only then return end - local is_recipe = sfinv_only and not data.show_usages or k == 2 - local lbl = "" + fs[#fs + 1] = fmt("background9[8.1,%f;6.6,%f;%s;false;%d]", + -0.2 + spacing, panel.height, PNG.bg_full, 10) - if not sfinv_only and rn == 0 then + if recipe_or_usage and not rn then local X = XOFFSET - 0.7 local Y = YOFFSET - 0.4 + spacing @@ -1014,55 +1202,24 @@ fs[#fs + 1] = fmt(FMT.tooltip, X, Y, 2, 2, is_recipe and ES"No recipes" or ES"No usages") - elseif (not sfinv_only and is_recipe) or - (sfinv_only and not data.show_usages) then - lbl = ES("Recipe @1 of @2", data.rnum, rn) - - elseif not sfinv_only or (sfinv_only and data.show_usages) then - lbl = ES("Usage @1 of @2", data.unum, rn) - - elseif sfinv_only then - lbl = data.show_usages and - ES("Usage @1 of @2", data.unum, rn) or - ES("Recipe @1 of @2", data.rnum, rn) - end - - fs[#fs + 1] = fmt(FMT.label, - XOFFSET + (sfinv_only and 2.3 or 1.6) + (is_recipe and xr or xu), - YOFFSET + (sfinv_only and 3.4 or 1.5 + spacing), lbl) + elseif panel.name == "title" then + get_title_fs(query_item, lang_code, favs, fs, spacing) - if rn > 1 then - local btn_suffix = is_recipe and "recipe" or "usage" - local prev_name = fmt("prev_%s", btn_suffix) - local next_name = fmt("next_%s", btn_suffix) - local x_arrow = XOFFSET + (sfinv_only and 1.7 or 1) - local y_arrow = YOFFSET + (sfinv_only and 3.3 or 1.4 + spacing) + elseif panel.name == "favs" then + fs[#fs + 1] = fmt(FMT.label, 8.3, spacing - 0.15, ES"Bookmarks") - fs[#fs + 1] = fmt(mul_elem(FMT.arrow, 2), - x_arrow + (is_recipe and xr or xu), y_arrow, - PNG.prev, prev_name, "", - x_arrow + 1.8, y_arrow, PNG.next, next_name, "") - end - - local rcp = v.dat and (is_recipe and v.dat[data.rnum] or v.dat[data.unum]) - if rcp then - get_grid_fs(data, fs, rcp, spacing) - end - - if k == "favs" and not sfinv_only then - fs[#fs + 1] = fmt(FMT.label, 8.3, spacing - 0.1, ES"Bookmarks") - - for i = 1, #data.favs do - local item = data.favs[i] + for i = 1, #favs do + local item = favs[i] local X = 7.85 + (i - 0.5) - local Y = spacing + 0.45 + local Y = spacing + 0.4 - if data.query_item == item then - fs[#fs + 1] = fmt(FMT.image, X, Y, 1.1, 1.1, PNG.selected) + if query_item == item then + fs[#fs + 1] = fmt(FMT.image, X, Y, + ITEM_BTN_SIZE, ITEM_BTN_SIZE, PNG.selected) end fs[#fs + 1] = fmt(FMT.item_image_button, - X, Y, 1.1, 1.1, item, item, "") + X, Y, ITEM_BTN_SIZE, ITEM_BTN_SIZE, item, item, "") end end end @@ -1085,9 +1242,9 @@ fs[#fs + 1] = fmt([[ style[filter;border=false] - field[0.4,0.2;2.5,1;filter;;%s] + field[0.4,0.2;2.6,1;filter;;%s] field_close_on_enter[filter;false] - box[0,0;2.4,0.6;#bababa25] + box[0,0;2.5,0.6;#bababa25] ]], ESC(data.filter)) @@ -1098,6 +1255,7 @@ style[clear;fgimg=%s;fgimg_hovered=%s] style[prev_page;fgimg=%s;fgimg_hovered=%s;fgimg_pressed=%s] style[next_page;fgimg=%s;fgimg_hovered=%s;fgimg_pressed=%s] + style[pagenum;border=false] ]], PNG.selected, PNG.selected, PNG.search, PNG.search_hover, @@ -1105,17 +1263,27 @@ PNG.prev, PNG.prev_hover, PNG.prev_hover, PNG.next, PNG.next_hover, PNG.next_hover) - fs[#fs + 1] = fmt(mul_elem(FMT.image_button, 4), - sfinv_only and 2.6 or 2.54, -0.06, 0.85, 0.85, "", "search", "", - sfinv_only and 3.3 or 3.25, -0.06, 0.85, 0.85, "", "clear", "", - sfinv_only and 5.45 or (9 * 6.83) / 11, -0.06, 0.85, 0.85, "", "prev_page", "", - sfinv_only and 7.2 or (9 * 8.75) / 11, -0.06, 0.85, 0.85, "", "next_page", "") + fs[#fs + 1] = fmt(mul_elem(FMT.image_button, 2), + 2.6, -0.06, 0.85, 0.85, "", "search", "", + 3.3, -0.06, 0.85, 0.85, "", "clear", "") + + if sfinv_only then + fs[#fs + 1] = "container[0.2,0]" + end + + fs[#fs + 1] = fmt(mul_elem(FMT.image_button, 2), + 5.35, -0.06, 0.85, 0.85, "", "prev_page", "", + 7.1, -0.06, 0.85, 0.85, "", "next_page", "") data.pagemax = max(1, ceil(#data.items / IPP)) - fs[#fs + 1] = fmt("label[%f,%f;%s / %u]", - sfinv_only and 6.35 or (9 * 7.85) / 11, - 0.06, clr("#ff0", data.pagenum), data.pagemax) + fs[#fs + 1] = fmt(FMT.button, + 5.97, -0.06, 1.36, 0.85, "pagenum", + fmt("%s / %u", clr("#ff0", data.pagenum), data.pagemax)) + + if sfinv_only then + fs[#fs + 1] = "container_end[]" + end if #data.items == 0 then local no_item = ES"No item to show" @@ -1149,7 +1317,8 @@ end if (data.recipes and #data.recipes > 0) or (data.usages and #data.usages > 0) then - get_panels(data, fs) + get_panels(data.lang_code, data.query_item, data.recipes, data.usages, + data.show_usages, data.favs, data.unum, data.rnum, fs) end return concat(fs) @@ -1166,12 +1335,12 @@ craftguide.register_craft_type("digging", { description = ES"Digging", - icon = "default_tool_steelpick.png", + icon = "craftguide_steelpick.png", }) craftguide.register_craft_type("digging_chance", { - description = ES"Digging Chance", - icon = "default_tool_mesepick.png", + description = ES"Digging (by chance)", + icon = "craftguide_mesepick.png", }) local function search(data) @@ -1338,91 +1507,7 @@ end end -local function handle_drops_table(name, drop) - -- Code borrowed and modified from unified_inventory - -- https://github.com/minetest-mods/unified_inventory/blob/master/api.lua - local drop_sure, drop_maybe = {}, {} - local drop_items = drop.items or {} - local max_items_left = drop.max_items - local max_start = true - - for i = 1, #drop_items do - if max_items_left and max_items_left <= 0 then break end - local di = drop_items[i] - - for j = 1, #di.items do - local dstack = ItemStack(di.items[j]) - local dname = dstack:get_name() - - if not dstack:is_empty() and dname ~= name then - local dcount = dstack:get_count() - - if #di.items == 1 and di.rarity == 1 and max_start then - if not drop_sure[dname] then - drop_sure[dname] = 0 - end - - drop_sure[dname] = drop_sure[dname] + dcount - - if max_items_left then - max_items_left = max_items_left - 1 - if max_items_left <= 0 then break end - end - else - if max_items_left then - max_start = false - end - - if not drop_maybe[dname] then - drop_maybe[dname] = {} - end - - if not drop_maybe[dname].output then - drop_maybe[dname].output = 0 - end - - drop_maybe[dname] = { - output = drop_maybe[dname].output + dcount, - rarity = di.rarity, - } - end - end - end - end - - for item, count in pairs(drop_sure) do - craftguide.register_craft{ - type = "digging", - items = {name}, - output = fmt("%s %u", item, count), - } - end - - for item, data in pairs(drop_maybe) do - craftguide.register_craft{ - type = "digging_chance", - items = {name}, - output = fmt("%s %u", item, data.output), - rarity = data.rarity, - } - end -end - -local function register_drops(name, drop) - local dstack = ItemStack(drop) - - if not dstack:is_empty() and dstack:get_name() ~= name then - craftguide.register_craft{ - type = "digging", - items = {name}, - output = drop, - } - elseif is_table(drop) then - handle_drops_table(name, drop) - end -end - -local function handle_aliases(hash) +local function resolve_aliases(hash) for oldname, newname in pairs(reg_aliases) do cache_recipes(oldname) local recipes = recipes_cache[oldname] @@ -1460,53 +1545,33 @@ end end -local function show_item(def) - return not (def.groups.not_in_craft_guide == 1 or - def.groups.not_in_creative_inventory == 1) and - def.description and def.description ~= "" -end - local function get_init_items() - local init_items_bak = storage:get "init_items" + local _select, _preselect = {}, {} - if autocache == false and init_items_bak then - init_items = dslz(init_items_bak) - fuel_cache = dslz(storage:get "fuel_cache") - usages_cache = dslz(storage:get "usages_cache") - recipes_cache = dslz(storage:get "recipes_cache") - else - print "[craftguide] Caching data (this may take a while)" - local hash = {} - - for name, def in pairs(reg_items) do - if show_item(def) then - if not fuel_cache[name] then - cache_fuel(name) - end - - if not recipes_cache[name] then - cache_recipes(name) - end - - cache_usages(name) - register_drops(name, def.drop) + for name, def in pairs(reg_items) do + if name ~= "" and show_item(def) then + cache_recipes(name) + cache_drops(name, def.drop) + cache_fuel(name) - if name ~= "" and recipes_cache[name] or usages_cache[name] then - init_items[#init_items + 1] = name - hash[name] = true - end - end + _preselect[name] = true end + end - handle_aliases(hash) - sort(init_items) + for name in pairs(_preselect) do + cache_usages(name) + end - storage:set_string("init_items", slz(init_items)) - storage:set_string("fuel_cache", slz(fuel_cache)) - storage:set_string("usages_cache", slz(usages_cache)) - storage:set_string("recipes_cache", slz(recipes_cache)) + for name in pairs(_preselect) do + if recipes_cache[name] or usages_cache[name] then + init_items[#init_items + 1] = name + _select[name] = true + end end + resolve_aliases(_select) + sort(init_items) + if http and true_str(craftguide.export_url) then local post_data = { recipes = recipes_cache, @@ -1523,12 +1588,12 @@ local function init_data(name) pdata[name] = { - filter = "", - pagenum = 1, - items = init_items, - items_raw = init_items, - favs = {}, - fs_version = get_fs_version(name), + filter = "", + pagenum = 1, + items = init_items, + items_raw = init_items, + favs = {}, + lang_code = get_lang_code(name), } end @@ -1549,6 +1614,10 @@ on_joinplayer(function(player) local name = player:get_player_name() init_data(name) + + if not pdata[name].lang_code then + outdated(name) + end end) local function fields(player, _f) @@ -1579,7 +1648,7 @@ data.pagenum = 1 search(data) - elseif _f.prev_page or _f.next_page then + elseif _f.prev_page or _f.next_page or _f.pagenum then if data.pagemax == 1 then return end data.pagenum = data.pagenum - (_f.prev_page and 1 or -1) @@ -1590,10 +1659,10 @@ end elseif _f.fav then - local fav, i = is_fav(data) + local fav, i = is_fav(data.favs, data.query_item) local total = #data.favs - if total < 6 and not fav then + if total < MAX_FAVS and not fav then data.favs[total + 1] = data.query_item elseif fav then remove(data.favs, i) @@ -1647,15 +1716,14 @@ is_in_nav = function(self, player, context) local name = player:get_player_name() - return get_fs_version(name) >= FORMSPEC_MINIMAL_VERSION + return get_lang_code(name) end, get = function(self, player, context) local name = player:get_player_name() local data = pdata[name] - local formspec = make_fs(data) - return sfinv.make_formspec(player, context, formspec) + return sfinv.make_formspec(player, context, make_fs(data)) end, on_enter = function(self, player, context) @@ -1683,18 +1751,8 @@ local name = user:get_player_name() local data = pdata[name] - if data.fs_version < FORMSPEC_MINIMAL_VERSION then - local fs = fmt([[ - size[6.6,1.3] - image[0,0;1,1;%s] - label[1,0;%s] - button_exit[2.8,0.8;1,1;;OK] - ]], - PNG.nothing, - "Your Minetest client is outdated.\n" .. - "Get the latest version on minetest.net to use the Crafting Guide.") - - return show_formspec(name, "craftguide", fs) + if not data.lang_code then + return outdated(name) end if next(recipe_filters) then @@ -1725,7 +1783,12 @@ paramtype = "light", paramtype2 = "wallmounted", sunlight_propagates = true, - groups = {choppy = 1, attached_node = 1, oddly_breakable_by_hand = 1, flammable = 3}, + groups = { + choppy = 1, + attached_node = 1, + oddly_breakable_by_hand = 1, + flammable = 3, + }, node_box = { type = "wallmounted", wall_top = {-0.5, 0.4375, -0.5, 0.5, 0.5, 0.5}, @@ -1770,7 +1833,7 @@ if rawget(_G, "sfinv_buttons") then sfinv_buttons.register_button("craftguide", { title = S"Crafting Guide", - tooltip = S"Shows a list of available crafting recipes, cooking recipes and fuels", + tooltip = S"Shows a list of available crafting recipes", image = PNG.book, action = function(player) on_use(player) @@ -1780,10 +1843,6 @@ end if progressive_mode then - local PLAYERS = {} - local POLL_FREQ = 0.25 - local HUD_TIMER_MAX = 1.5 - local function item_in_inv(item, inv_items) local inv_items_size = #inv_items @@ -1867,6 +1926,37 @@ return inv_items end + local function init_hud(player, data) + data.hud = { + bg = player:hud_add{ + hud_elem_type = "image", + position = {x = 0.78, y = 1}, + alignment = {x = 1, y = 1}, + scale = {x = 370, y = 112}, + text = PNG.bg, + z_index = 0xDEAD, + }, + + book = player:hud_add{ + hud_elem_type = "image", + position = {x = 0.79, y = 1.02}, + alignment = {x = 1, y = 1}, + scale = {x = 4, y = 4}, + text = PNG.book, + z_index = 0xDEAD, + }, + + text = player:hud_add{ + hud_elem_type = "text", + position = {x = 0.84, y = 1.04}, + alignment = {x = 1, y = 1}, + number = 0xffffff, + text = "", + z_index = 0xDEAD, + }, + } + end + local function show_hud_success(player, data) -- It'd better to have an engine function `hud_move` to only need -- 2 calls for the notification's back and forth. @@ -1914,8 +2004,9 @@ -- Workaround. Need an engine call to detect when the contents of -- the player inventory changed, instead. local function poll_new_items() - for i = 1, #PLAYERS do - local player = PLAYERS[i] + local players = get_players() + for i = 1, #players do + local player = players[i] local name = player:get_player_name() local data = pdata[name] @@ -1948,12 +2039,13 @@ poll_new_items() globalstep(function() - for i = 1, #PLAYERS do - local player = PLAYERS[i] + local players = get_players() + for i = 1, #players do + local player = players[i] local name = player:get_player_name() local data = pdata[name] - if data.show_hud ~= nil then + if data.show_hud ~= nil and singleplayer then show_hud_success(player, data) end end @@ -1962,8 +2054,6 @@ craftguide.add_recipe_filter("Default progressive filter", progressive_filter) on_joinplayer(function(player) - PLAYERS = get_players() - local name = player:get_player_name() local data = pdata[name] @@ -1971,31 +2061,9 @@ data.inv_items = dslz(meta:get_string "inv_items") or {} data.known_recipes = dslz(meta:get_string "known_recipes") or 0 - data.hud = { - bg = player:hud_add{ - hud_elem_type = "image", - position = {x = 0.78, y = 1}, - alignment = {x = 1, y = 1}, - scale = {x = 370, y = 112}, - text = PNG.bg, - }, - - book = player:hud_add{ - hud_elem_type = "image", - position = {x = 0.79, y = 1.02}, - alignment = {x = 1, y = 1}, - scale = {x = 4, y = 4}, - text = PNG.book, - }, - - text = player:hud_add{ - hud_elem_type = "text", - position = {x = 0.84, y = 1.04}, - alignment = {x = 1, y = 1}, - number = 0xffffff, - text = "", - }, - } + if singleplayer then + init_hud(player, data) + end end) local to_save = {"inv_items", "known_recipes"} @@ -2011,14 +2079,12 @@ end end - on_leaveplayer(function(player) - PLAYERS = get_players() - save_meta(player) - end) + on_leaveplayer(save_meta) on_shutdown(function() - for i = 1, #PLAYERS do - local player = PLAYERS[i] + local players = get_players() + for i = 1, #players do + local player = players[i] save_meta(player) end end) @@ -2047,12 +2113,12 @@ if not recipes_cache[item] and not usages_cache[item] then return false, msg(name, fmt("%s: %s", S"No recipe or usage for this item", - get_desc(item))) + get_desc(item, data.lang_code))) end return false, msg(name, fmt("%s: %s", S"You don't know a recipe or usage for this item", - get_desc(item))) + get_desc(item, data.lang_code))) end data.query_item = item diff -Nru minetest-mod-craftguide-1.13/locale/craftguide.fr.tr minetest-mod-craftguide-1.14/locale/craftguide.fr.tr --- minetest-mod-craftguide-1.13/locale/craftguide.fr.tr 2020-04-16 16:39:39.000000000 +0000 +++ minetest-mod-craftguide-1.14/locale/craftguide.fr.tr 2020-07-10 13:55:20.000000000 +0000 @@ -56,5 +56,10 @@ You don't know a recipe or usage for this item=Tu ne connais aucune recette pour ce bloc No recipe or usage for this item=Aucune recette pour ce bloc Digging=Destruction -Digging Chance=Destruction chanceuse +Digging (by chance)=Destruction (par chance) @1 of chance to drop=@1 de chance de tomber +Mark this item=Mettre en favori. +Unmark this item=Enlever des favoris. +Cannot mark this item. Limit of bookmarks reached.=Impossible de mettre cet item en favori. Limite des favoris atteinte. +Only drop if using one of these tools: @1=Tombe seulement si détruit avec un de ces outils: @1 +Only drop if using this tool: @1=Tombe seulement si détruit avec cet outil: @1 diff -Nru minetest-mod-craftguide-1.13/locale/template minetest-mod-craftguide-1.14/locale/template --- minetest-mod-craftguide-1.13/locale/template 2020-04-16 16:39:39.000000000 +0000 +++ minetest-mod-craftguide-1.14/locale/template 2020-07-10 13:55:20.000000000 +0000 @@ -56,5 +56,10 @@ You don't know a recipe or usage for this item= No recipe or usage for this item= Digging= -Digging Chance= +Digging (by chance)= @1 of chance to drop= +Mark this item= +Unmark this item= +Cannot mark this item. Limit of bookmarks reached.= +Only drop if using one of these tools: @1= +Only drop if using this tool: @1= diff -Nru minetest-mod-craftguide-1.13/README.md minetest-mod-craftguide-1.14/README.md --- minetest-mod-craftguide-1.13/README.md 2020-04-16 16:39:39.000000000 +0000 +++ minetest-mod-craftguide-1.14/README.md 2020-07-10 13:55:20.000000000 +0000 @@ -14,9 +14,11 @@ Use the command `/craft` to show the recipe(s) of the pointed node. -For developers, `craftguide` also has a [modding API](https://github.com/minetest-mods/craftguide/blob/master/API.md). +For developers, `craftguide` also has a [modding API](https://github.com/minetest-mods/craftguide/blob/master/API.md). + +For the best visuals, it is recommended to enable `inventory_items_animations` in `minetest.conf`. Love this mod? Donations are appreciated: https://www.paypal.me/jpg84240 -![Preview2](https://content.minetest.net/uploads/wAGr5rE3fI.png) +![Preview2](https://i.imgur.com/TrBouDq.png) diff -Nru minetest-mod-craftguide-1.13/settingtypes.txt minetest-mod-craftguide-1.14/settingtypes.txt --- minetest-mod-craftguide-1.13/settingtypes.txt 2020-04-16 16:39:39.000000000 +0000 +++ minetest-mod-craftguide-1.14/settingtypes.txt 2020-07-10 13:55:20.000000000 +0000 @@ -3,10 +3,3 @@ # Integration in the default Minetest Game inventory. craftguide_sfinv_only (Crafting Guide in inventory only) bool false - -# Enable pre-caching of item recipes. -# Do NOT disable the first time the mod loads. -# Disabling the auto-caching will result in faster mod loading. -# If you enable or disable mods, or edit the current mod recipes in your setup, you SHOULD re-enable this setting until the next caching at least. -# Usage at your own risk. -craftguide_autocache (Auto-caching of recipes) bool true Binary files /tmp/tmp5ofejI/nX4m0q0xIu/minetest-mod-craftguide-1.13/textures/craftguide_mesepick.png and /tmp/tmp5ofejI/SWW8sFlqwm/minetest-mod-craftguide-1.14/textures/craftguide_mesepick.png differ Binary files /tmp/tmp5ofejI/nX4m0q0xIu/minetest-mod-craftguide-1.13/textures/craftguide_steelpick.png and /tmp/tmp5ofejI/SWW8sFlqwm/minetest-mod-craftguide-1.14/textures/craftguide_steelpick.png differ