This commit is contained in:
DustyBagel 2024-06-25 13:45:56 -05:00
commit eae9fa4e95
13 changed files with 223 additions and 189 deletions

@ -240,12 +240,15 @@ function math.factorial(x)
return v
end
function math.round(x)
if x >= 0 then
return math.floor(x + 0.5)
if x < 0 then
local int = math.ceil(x)
local frac = x - int
return int - ((frac <= -0.5) and 1 or 0)
end
return math.ceil(x - 0.5)
local int = math.floor(x)
local frac = x - int
return int + ((frac >= 0.5) and 1 or 0)
end
local formspec_escapes = {

@ -176,3 +176,17 @@ describe("formspec_escape", function()
assert.equal("\\[Hello\\\\\\[", core.formspec_escape("[Hello\\["))
end)
end)
describe("math", function()
it("round()", function()
assert.equal(0, math.round(0))
assert.equal(10, math.round(10.3))
assert.equal(11, math.round(10.5))
assert.equal(11, math.round(10.7))
assert.equal(-10, math.round(-10.3))
assert.equal(-11, math.round(-10.5))
assert.equal(-11, math.round(-10.7))
assert.equal(0, math.round(0.49999999999999994))
assert.equal(0, math.round(-0.49999999999999994))
end)
end)

@ -133,6 +133,8 @@ local function start_install(package, reason)
conf:set("release", package.release)
conf:write()
end
pkgmgr.reload_by_type(package.type)
end
end
@ -146,7 +148,6 @@ local function start_install(package, reason)
start_install(next.package, next.reason)
end
ui.update()
end
@ -427,8 +428,9 @@ end
function contentdb.update_paths()
pkgmgr.load_all()
local mod_hash = {}
pkgmgr.refresh_globals()
for _, mod in pairs(pkgmgr.global_mods:get_list()) do
local cdb_id = pkgmgr.get_contentdb_id(mod)
if cdb_id then
@ -437,7 +439,6 @@ function contentdb.update_paths()
end
local game_hash = {}
pkgmgr.update_gamelist()
for _, game in pairs(pkgmgr.games) do
local cdb_id = pkgmgr.get_contentdb_id(game)
if cdb_id then
@ -446,7 +447,7 @@ function contentdb.update_paths()
end
local txp_hash = {}
for _, txp in pairs(pkgmgr.get_texture_packs()) do
for _, txp in pairs(pkgmgr.texture_packs) do
local cdb_id = pkgmgr.get_contentdb_id(txp)
if cdb_id then
txp_hash[contentdb.aliases[cdb_id] or cdb_id] = txp

@ -110,7 +110,7 @@ pkgmgr = {}
-- @param modpack Currently processing modpack or nil/"" if none (recursion)
function pkgmgr.get_mods(path, virtual_path, listing, modpack)
local mods = core.get_dir_list(path, true)
local added = {}
for _, name in ipairs(mods) do
if name:sub(1, 1) ~= "." then
local mod_path = path .. DIR_DELIM .. name
@ -120,6 +120,7 @@ function pkgmgr.get_mods(path, virtual_path, listing, modpack)
parent_dir = path,
}
listing[#listing + 1] = toadd
added[#added + 1] = toadd
-- Get config file
local mod_conf
@ -150,8 +151,6 @@ function pkgmgr.get_mods(path, virtual_path, listing, modpack)
toadd.virtual_path = mod_virtual_path
toadd.type = "mod"
pkgmgr.update_translations({ toadd })
-- Check modpack.txt
-- Note: modpack.conf is already checked above
local modpackfile = io.open(mod_path .. DIR_DELIM .. "modpack.txt")
@ -171,6 +170,8 @@ function pkgmgr.get_mods(path, virtual_path, listing, modpack)
end
end
pkgmgr.update_translations(added)
if not modpack then
-- Sort all when the recursion is done
table.sort(listing, function(a, b)
@ -180,12 +181,13 @@ function pkgmgr.get_mods(path, virtual_path, listing, modpack)
end
--------------------------------------------------------------------------------
function pkgmgr.get_texture_packs()
function pkgmgr.reload_texture_packs()
local txtpath = core.get_texturepath()
local txtpath_system = core.get_texturepath_share()
local retval = {}
load_texture_packs(txtpath, retval)
-- on portable versions these two paths coincide. It avoids loading the path twice
if txtpath ~= txtpath_system then
load_texture_packs(txtpath_system, retval)
@ -197,11 +199,13 @@ function pkgmgr.get_texture_packs()
return a.title:lower() < b.title:lower()
end)
return retval
pkgmgr.texture_packs = retval
end
--------------------------------------------------------------------------------
function pkgmgr.get_all()
pkgmgr.load_all()
local result = {}
for _, mod in pairs(pkgmgr.global_mods:get_list()) do
@ -210,7 +214,7 @@ function pkgmgr.get_all()
for _, game in pairs(pkgmgr.games) do
result[#result + 1] = game
end
for _, txp in pairs(pkgmgr.get_texture_packs()) do
for _, txp in pairs(pkgmgr.texture_packs) do
result[#result + 1] = txp
end
@ -288,7 +292,7 @@ end
function pkgmgr.render_packagelist(render_list, use_technical_names, with_icon)
if not render_list then
if not pkgmgr.global_mods then
pkgmgr.refresh_globals()
pkgmgr.reload_global_mods()
end
render_list = pkgmgr.global_mods
end
@ -549,6 +553,7 @@ function pkgmgr.get_worldconfig(worldpath)
end
--------------------------------------------------------------------------------
-- Caller is responsible for reloading content types (see reload_by_type)
function pkgmgr.install_dir(expected_type, path, basename, targetpath)
assert(type(expected_type) == "string")
assert(type(path) == "string")
@ -615,12 +620,6 @@ function pkgmgr.install_dir(expected_type, path, basename, targetpath)
fgettext_ne("Failed to install $1 to $2", basename, targetpath)
end
if basefolder.type == "game" then
pkgmgr.update_gamelist()
else
pkgmgr.refresh_globals()
end
return targetpath, nil
end
@ -742,7 +741,7 @@ function pkgmgr.comparemod(elem1,elem2)
end
--------------------------------------------------------------------------------
function pkgmgr.refresh_globals()
function pkgmgr.reload_global_mods()
local function is_equal(element,uid) --uid match
if element.name == uid then
return true
@ -774,7 +773,7 @@ function pkgmgr.get_game_mods(gamespec, retval)
end
--------------------------------------------------------------------------------
function pkgmgr.update_gamelist()
function pkgmgr.reload_games()
pkgmgr.games = core.get_games()
table.sort(pkgmgr.games, function(a, b)
return a.title:lower() < b.title:lower()
@ -782,6 +781,32 @@ function pkgmgr.update_gamelist()
pkgmgr.update_translations(pkgmgr.games)
end
--------------------------------------------------------------------------------
function pkgmgr.reload_by_type(type)
if type == "game" then
pkgmgr.reload_games()
elseif type == "txp" then
pkgmgr.reload_texture_packs()
elseif type == "mod" or type == "modpack" then
pkgmgr.reload_global_mods()
else
error("Unknown package type: " .. type)
end
end
--------------------------------------------------------------------------------
function pkgmgr.load_all()
if not pkgmgr.global_mods then
pkgmgr.reload_global_mods()
end
if not pkgmgr.games then
pkgmgr.reload_games()
end
if not pkgmgr.texture_packs then
pkgmgr.reload_texture_packs()
end
end
--------------------------------------------------------------------------------
function pkgmgr.update_translations(list)
for _, item in ipairs(list) do
@ -831,4 +856,4 @@ end
--------------------------------------------------------------------------------
-- read initial data
--------------------------------------------------------------------------------
pkgmgr.update_gamelist()
pkgmgr.reload_games()

@ -46,6 +46,9 @@ local function reset()
function core.get_texturepath()
return txp_dir
end
function core.get_texturepath_share()
return txp_dir
end
function core.get_modpath()
return mods_dir
end
@ -59,13 +62,6 @@ local function reset()
setfenv(loadfile("builtin/common/misc_helpers.lua"), env)()
setfenv(loadfile("builtin/mainmenu/content/pkgmgr.lua"), env)()
function env.pkgmgr.update_gamelist()
table.insert(calls, { "update_gamelist" })
end
function env.pkgmgr.refresh_globals()
table.insert(calls, { "refresh_globals" })
end
function env.assert_calls(list)
assert.are.same(list, calls)
end
@ -113,7 +109,6 @@ describe("install_dir", function()
env.assert_calls({
{ "delete_dir", mods_dir .. "/mymod" },
{ "copy_dir", "/tmp/123", mods_dir .. "/mymod", false },
{ "refresh_globals" },
})
end)
@ -129,7 +124,6 @@ describe("install_dir", function()
env.assert_calls({
{ "delete_dir", mods_dir .. "/mymod" },
{ "copy_dir", "/tmp/123", mods_dir .. "/mymod", false },
{ "refresh_globals" },
})
end)
@ -145,7 +139,6 @@ describe("install_dir", function()
env.assert_calls({
{ "delete_dir", games_dir .. "/mygame" },
{ "copy_dir", "/tmp/123", games_dir .. "/mygame", false },
{ "update_gamelist" },
})
end)
@ -161,7 +154,6 @@ describe("install_dir", function()
env.assert_calls({
{ "delete_dir", mods_dir .. "/123" },
{ "copy_dir", "/tmp/123", mods_dir .. "/123", false },
{ "refresh_globals" },
})
end)
@ -188,7 +180,6 @@ describe("install_dir", function()
env.assert_calls({
{ "delete_dir", "/tmp/alt-target" },
{ "copy_dir", "/tmp/123", "/tmp/alt-target", false },
{ "refresh_globals" },
})
end)
@ -238,6 +229,5 @@ describe("install_dir", function()
path, message = env.pkgmgr.install_dir("txp", "/tmp/123", "name", nil)
assert.is._not._nil(path)
assert.is._nil(message)
end)
end)

@ -72,9 +72,6 @@ end
local function has_packages_from_cdb()
pkgmgr.refresh_globals()
pkgmgr.update_gamelist()
for _, content in pairs(pkgmgr.get_all()) do
if pkgmgr.get_contentdb_id(content) then
return true
@ -127,9 +124,6 @@ function update_detector.get_all()
return {}
end
pkgmgr.refresh_globals()
pkgmgr.update_gamelist()
local ret = {}
local all_content = pkgmgr.get_all()
for _, content in ipairs(all_content) do

@ -37,11 +37,7 @@ local function delete_content_buttonhandler(this, fields)
gamedata.errormessage = fgettext_ne("pkgmgr: failed to delete \"$1\"", this.data.content.path)
end
if this.data.content.type == "game" then
pkgmgr.update_gamelist()
else
pkgmgr.refresh_globals()
end
pkgmgr.reload_by_type(this.data.content.type)
else
gamedata.errormessage = fgettext_ne("pkgmgr: invalid path \"$1\"", this.data.content.path)
end

@ -45,7 +45,7 @@ local function rename_modpack_buttonhandler(this, fields)
local oldpath = this.data.mod.path
local targetpath = this.data.mod.parent_dir .. DIR_DELIM .. fields["te_modpack_name"]
os.rename(oldpath, targetpath)
pkgmgr.refresh_globals()
pkgmgr.reload_global_mods()
pkgmgr.selected_mod = pkgmgr.global_mods:get_current_index(
pkgmgr.global_mods:raw_index_by_uid(fields["te_modpack_name"]))

@ -22,16 +22,27 @@ local component_funcs = dofile(core.get_mainmenu_path() .. DIR_DELIM ..
local shadows_component = dofile(core.get_mainmenu_path() .. DIR_DELIM ..
"settings" .. DIR_DELIM .. "shadows_component.lua")
local full_settings = settingtypes.parse_config_file(false, true)
local loaded = false
local full_settings
local info_icon_path = core.formspec_escape(defaulttexturedir .. "settings_info.png")
local reset_icon_path = core.formspec_escape(defaulttexturedir .. "settings_reset.png")
local all_pages = {}
local page_by_id = {}
local filtered_pages = all_pages
local filtered_page_by_id = page_by_id
local function get_setting_info(name)
for _, entry in ipairs(full_settings) do
if entry.type ~= "category" and entry.name == name then
return entry
end
end
return nil
end
local function add_page(page)
assert(type(page.id) == "string")
assert(type(page.title) == "string")
@ -46,49 +57,6 @@ local function add_page(page)
end
local change_keys = {
query_text = "Controls",
requires = {
keyboard_mouse = true,
},
get_formspec = function(self, avail_w)
local btn_w = math.min(avail_w, 3)
return ("button[0,0;%f,0.8;btn_change_keys;%s]"):format(btn_w, fgettext("Controls")), 0.8
end,
on_submit = function(self, fields)
if fields.btn_change_keys then
core.show_keys_menu()
end
end,
}
add_page({
id = "accessibility",
title = fgettext_ne("Accessibility"),
content = {
"language",
{ heading = fgettext_ne("General") },
"font_size",
"chat_font_size",
"gui_scaling",
"hud_scaling",
"show_nametag_backgrounds",
{ heading = fgettext_ne("Chat") },
"console_height",
"console_alpha",
"console_color",
{ heading = fgettext_ne("Controls") },
"autojump",
"safe_dig_and_place",
{ heading = fgettext_ne("Movement") },
"arm_inertia",
"view_bobbing_amount",
"fall_bobbing_amount",
},
})
local function load_settingtypes()
local page = nil
local section = nil
@ -129,94 +97,134 @@ local function load_settingtypes()
end
end
end
load_settingtypes()
table.insert(page_by_id.controls_keyboard_and_mouse.content, 1, change_keys)
do
local content = page_by_id.graphics_and_audio_shaders.content
local idx = table.indexof(content, "enable_dynamic_shadows")
table.insert(content, idx, shadows_component)
end
local function get_setting_info(name)
for _, entry in ipairs(full_settings) do
if entry.type ~= "category" and entry.name == name then
return entry
end
local function load()
if loaded then
return
end
loaded = true
full_settings = settingtypes.parse_config_file(false, true)
local change_keys = {
query_text = "Controls",
requires = {
keyboard_mouse = true,
},
get_formspec = function(self, avail_w)
local btn_w = math.min(avail_w, 3)
return ("button[0,0;%f,0.8;btn_change_keys;%s]"):format(btn_w, fgettext("Controls")), 0.8
end,
on_submit = function(self, fields)
if fields.btn_change_keys then
core.show_keys_menu()
end
end,
}
add_page({
id = "accessibility",
title = fgettext_ne("Accessibility"),
content = {
"language",
{ heading = fgettext_ne("General") },
"font_size",
"chat_font_size",
"gui_scaling",
"hud_scaling",
"show_nametag_backgrounds",
{ heading = fgettext_ne("Chat") },
"console_height",
"console_alpha",
"console_color",
{ heading = fgettext_ne("Controls") },
"autojump",
"safe_dig_and_place",
{ heading = fgettext_ne("Movement") },
"arm_inertia",
"view_bobbing_amount",
"fall_bobbing_amount",
},
})
load_settingtypes()
table.insert(page_by_id.controls_keyboard_and_mouse.content, 1, change_keys)
do
local content = page_by_id.graphics_and_audio_shaders.content
local idx = table.indexof(content, "enable_dynamic_shadows")
table.insert(content, idx, shadows_component)
end
return nil
-- These must not be translated, as they need to show in the local
-- language no matter the user's current language.
-- This list must be kept in sync with src/unsupported_language_list.txt.
get_setting_info("language").option_labels = {
[""] = fgettext_ne("(Use system language)"),
--ar = " [ar]", blacklisted
be = "Беларуская [be]",
bg = "Български [bg]",
ca = "Català [ca]",
cs = "Česky [cs]",
cy = "Cymraeg [cy]",
da = "Dansk [da]",
de = "Deutsch [de]",
--dv = " [dv]", blacklisted
el = "Ελληνικά [el]",
en = "English [en]",
eo = "Esperanto [eo]",
es = "Español [es]",
et = "Eesti [et]",
eu = "Euskara [eu]",
fi = "Suomi [fi]",
fil = "Wikang Filipino [fil]",
fr = "Français [fr]",
gd = "Gàidhlig [gd]",
gl = "Galego [gl]",
--he = " [he]", blacklisted
--hi = " [hi]", blacklisted
hu = "Magyar [hu]",
id = "Bahasa Indonesia [id]",
it = "Italiano [it]",
ja = "日本語 [ja]",
jbo = "Lojban [jbo]",
kk = "Қазақша [kk]",
--kn = " [kn]", blacklisted
ko = "한국어 [ko]",
ky = "Kırgızca / Кыргызча [ky]",
lt = "Lietuvių [lt]",
lv = "Latviešu [lv]",
mn = "Монгол [mn]",
mr = "मराठी [mr]",
ms = "Bahasa Melayu [ms]",
--ms_Arab = " [ms_Arab]", blacklisted
nb = "Norsk Bokmål [nb]",
nl = "Nederlands [nl]",
nn = "Norsk Nynorsk [nn]",
oc = "Occitan [oc]",
pl = "Polski [pl]",
pt = "Português [pt]",
pt_BR = "Português do Brasil [pt_BR]",
ro = "Română [ro]",
ru = "Русский [ru]",
sk = "Slovenčina [sk]",
sl = "Slovenščina [sl]",
sr_Cyrl = "Српски [sr_Cyrl]",
sr_Latn = "Srpski (Latinica) [sr_Latn]",
sv = "Svenska [sv]",
sw = "Kiswahili [sw]",
--th = " [th]", blacklisted
tr = "Türkçe [tr]",
tt = "Tatarça [tt]",
uk = "Українська [uk]",
vi = "Tiếng Việt [vi]",
zh_CN = "中文 (简体) [zh_CN]",
zh_TW = "正體中文 (繁體) [zh_TW]",
}
end
-- These must not be translated, as they need to show in the local
-- language no matter the user's current language.
-- This list must be kept in sync with src/unsupported_language_list.txt.
get_setting_info("language").option_labels = {
[""] = fgettext_ne("(Use system language)"),
--ar = " [ar]", blacklisted
be = "Беларуская [be]",
bg = "Български [bg]",
ca = "Català [ca]",
cs = "Česky [cs]",
cy = "Cymraeg [cy]",
da = "Dansk [da]",
de = "Deutsch [de]",
--dv = " [dv]", blacklisted
el = "Ελληνικά [el]",
en = "English [en]",
eo = "Esperanto [eo]",
es = "Español [es]",
et = "Eesti [et]",
eu = "Euskara [eu]",
fi = "Suomi [fi]",
fil = "Wikang Filipino [fil]",
fr = "Français [fr]",
gd = "Gàidhlig [gd]",
gl = "Galego [gl]",
--he = " [he]", blacklisted
--hi = " [hi]", blacklisted
hu = "Magyar [hu]",
id = "Bahasa Indonesia [id]",
it = "Italiano [it]",
ja = "日本語 [ja]",
jbo = "Lojban [jbo]",
kk = "Қазақша [kk]",
--kn = " [kn]", blacklisted
ko = "한국어 [ko]",
ky = "Kırgızca / Кыргызча [ky]",
lt = "Lietuvių [lt]",
lv = "Latviešu [lv]",
mn = "Монгол [mn]",
mr = "मराठी [mr]",
ms = "Bahasa Melayu [ms]",
--ms_Arab = " [ms_Arab]", blacklisted
nb = "Norsk Bokmål [nb]",
nl = "Nederlands [nl]",
nn = "Norsk Nynorsk [nn]",
oc = "Occitan [oc]",
pl = "Polski [pl]",
pt = "Português [pt]",
pt_BR = "Português do Brasil [pt_BR]",
ro = "Română [ro]",
ru = "Русский [ru]",
sk = "Slovenčina [sk]",
sl = "Slovenščina [sl]",
sr_Cyrl = "Српски [sr_Cyrl]",
sr_Latn = "Srpski (Latinica) [sr_Latn]",
sv = "Svenska [sv]",
sw = "Kiswahili [sw]",
--th = " [th]", blacklisted
tr = "Türkçe [tr]",
tt = "Tatarça [tt]",
uk = "Українська [uk]",
vi = "Tiếng Việt [vi]",
zh_CN = "中文 (简体) [zh_CN]",
zh_TW = "正體中文 (繁體) [zh_TW]",
}
-- See if setting matches keywords
local function get_setting_match_weight(entry, query_keywords)
local setting_score = 0
@ -734,6 +742,7 @@ end
function create_settings_dlg()
load()
local dlg = dialog_create("dlg_settings", get_formspec, buttonhandler, eventhandler)
dlg.data.page_id = update_filtered_pages("")

@ -439,9 +439,9 @@ function settingtypes.parse_config_file(read_all, parse_mods)
end
-- Parse mods
pkgmgr.load_all()
local mods_category_initialized = false
local mods = {}
pkgmgr.get_mods(core.get_modpath(), "mods", mods)
local mods = pkgmgr.global_mods:get_list()
table.sort(mods, function(a, b) return a.name < b.name end)
for _, mod in ipairs(mods) do

@ -29,16 +29,11 @@ end
local packages_raw, packages
local function update_packages()
if not pkgmgr.global_mods then
pkgmgr.refresh_globals()
end
if not pkgmgr.games then
pkgmgr.update_gamelist()
end
pkgmgr.load_all()
packages_raw = {}
table.insert_all(packages_raw, pkgmgr.games)
table.insert_all(packages_raw, pkgmgr.get_texture_packs())
table.insert_all(packages_raw, pkgmgr.texture_packs)
table.insert_all(packages_raw, pkgmgr.global_mods:get_list())
local function get_data()
@ -207,6 +202,7 @@ local function handle_doubleclick(pkg)
core.settings:set("texture_path", pkg.path)
end
packages = nil
pkgmgr.reload_texture_packs()
mm_game_theme.init()
mm_game_theme.set_engine()
@ -271,6 +267,7 @@ local function handle_buttons(tabview, fields, tabname, tabdata)
core.settings:set("texture_path", txp_path)
packages = nil
pkgmgr.reload_texture_packs()
mm_game_theme.init()
mm_game_theme.set_engine()

@ -314,7 +314,8 @@ Minetest namespace reference
Call these functions only at load time!
* `minetest.register_globalstep(function(dtime))`
* Called every client environment step, usually interval of 0.1s
* Called every client environment step
* `dtime` is the time since last execution in seconds.
* `minetest.register_on_mods_loaded(function())`
* Called just after mods have finished loading.
* `minetest.register_on_shutdown(function())`

@ -4007,8 +4007,9 @@ Helper functions
* X1, Y1, ... Z2 are coordinates
* `relative_to`: Optional. If set to a position, each coordinate
can use the tilde notation for relative positions
* Tilde notation: "~": Relative coordinate
"~<number>": Relative coordinate plus <number>
* Tilde notation
* `"~"`: Relative coordinate
* `"~<number>"`: Relative coordinate plus `<number>`
* Example: `minetest.string_to_area("(1,2,3) (~5,~-5,~)", {x=10,y=10,z=10})`
returns `{x=1,y=2,z=3}, {x=15,y=5,z=10}`
* `minetest.formspec_escape(string)`: returns a string
@ -4346,6 +4347,8 @@ the previous octave.
This may need to be tuned when altering `lacunarity`; when doing so consider
that a common medium value is 1 / lacunarity.
Instead of `persistence`, the key `persist` may be used to the same effect.
### `lacunarity`
Each additional octave has a 'wavelength' that is the 'wavelength' of the
@ -5714,7 +5717,8 @@ Global callback registration functions
Call these functions only at load time!
* `minetest.register_globalstep(function(dtime))`
* Called every server step, usually interval of 0.1s
* Called every server step, usually interval of 0.1s.
* `dtime` is the time since last execution in seconds.
* `minetest.register_on_mods_loaded(function())`
* Called after mods have finished loading and before the media is cached or the
aliases handled.