diff --git a/ess/settingtypes.txt b/ess/settingtypes.txt new file mode 100644 index 0000000..7c546ba --- /dev/null +++ b/ess/settingtypes.txt @@ -0,0 +1,6 @@ + +# Save death position so that the player can return to it via /back +ess_save_death (Save death position) bool false + +# /tpa request timeout in seconds +ess_tpa_timeout (tpask request timeout in seconds) int 120 diff --git a/ess/teleport.lua b/ess/teleport.lua index c3c76fa..9ff320b 100644 --- a/ess/teleport.lua +++ b/ess/teleport.lua @@ -1,8 +1,10 @@ +local ess_save_death = minetest.settings:get_bool("ess_save_death", false) +local ess_tpa_timeout = tonumber(minetest.settings:get("ess_tpa_timeout")) or 120 + local tpask = { requests = {}, muted = {}, - timeout = 120, } local function cmd_top(name) @@ -29,7 +31,9 @@ local function cmd_back(name) if not pos then return false, "Could not return to previous position." end - minetest.get_player_by_name(name):set_pos(pos) + local p = minetest.get_player_by_name(name) + ess.save_player_pos(p) + p:set_pos(pos) return true, "Teleported back." end @@ -43,7 +47,7 @@ local function cmd_tpcommon(name,tname,direction) return false, "Could not find player." end - if tpask.requests[tname] and tpask.requests[tname].when > minetest.get_us_time() - tpask.timeout * 100000 then + if tpask.requests[tname] and tpask.requests[tname].when > minetest.get_us_time() - ess_tpa_timeout * 100000 then return false, "There are currently pending requests regarding this player. Please wait." end @@ -56,10 +60,10 @@ local function cmd_tpcommon(name,tname,direction) minetest.chat_send_player(tname, name .. " has requested "..message..".") minetest.chat_send_player(tname, "Run /tpaccept to accept or /tpadeny to deny.") - if tpask.timeout > 0 then - minetest.chat_send_player(tname, "You have "..tpask.timeout.." seconds to respond.") + if ess_tpa_timeout > 0 then + minetest.chat_send_player(tname, "You have "..ess_tpa_timeout.." seconds to respond.") end - tpask.requests[tname] = {when = minetest.get_us_time()} + tpask.requests[tname] = {when = minetest.get_gametime()} if direction == 1 then tpask.requests[tname].who = name else @@ -81,7 +85,7 @@ end local function cmd_tpaconfirm(name) local reqs = tpask.requests[name] local me = minetest.get_player_by_name(name) - if not reqs or (tpask.timeout > 0 and tpask.requests[name].when < minetest.get_us_time() - tpask.timeout * 100000) then + if not reqs or (tpask.timeout > 0 and tpask.requests[name].when < minetest.get_gametime() - ess_tpa_timeout) then return false, "You have no pending teleport requests." end @@ -94,9 +98,11 @@ local function cmd_tpaconfirm(name) if reqs.to then minetest.chat_send_player(name, "Teleporting..") + ess.save_player_pos(me) me:set_pos(whoplayer:get_pos()) else minetest.chat_send_player(who, "Teleporting..") + ess.save_player_pos(whoplayer) whoplayer:set_pos(me:get_pos()) end @@ -107,7 +113,7 @@ end local function cmd_tpadeny(name) local reqs = tpask.requests[name] - if not reqs or tpask.requests[name].when < minetest.get_us_time() - tpask.timeout * 1000 then + if not reqs or tpask.requests[name].when < minetest.get_gametime() - tpask.timeout then return false, "You have no pending teleport requests." end @@ -137,7 +143,6 @@ local commands = { privs = { ["ess.teleport.tpa"] = true, }, - save_player_pos = true, func = cmd_tpask, }, ["tpaskhere"] = { @@ -147,14 +152,12 @@ local commands = { privs = { ["ess.teleport.tpahere"] = true, }, - save_player_pos = true, func = cmd_tpaskhere, }, ["tpaccept"] = { description = "Accept a teleport request.", aliases = {"tpayes"}, func = cmd_tpaconfirm, - save_player_pos = true, }, ["tpdeny"] = { description = "Reject a teleport request.", @@ -169,7 +172,6 @@ local commands = { description = "Teleports you to your location prior to tp/spawn/warp.", aliases = {"return"}, privs = true, - save_player_pos = true, func = cmd_back, }, ["top"] = { @@ -193,3 +195,10 @@ local commands = { } ess.autoregister(commands, "teleport") + +-- Save death point for use with /back +if ess_save_death then + minetest.register_on_dieplayer(function(player) + ess.save_player_pos(player) + end) +end diff --git a/ess/tools.lua b/ess/tools.lua index 9fab806..0b88498 100644 --- a/ess/tools.lua +++ b/ess/tools.lua @@ -35,7 +35,6 @@ local function cmd_repair(name, params, splitparams) commit = 1 end - if commit == 1 and player then local held = player:get_wielded_item() if held:get_wear() > 0 then diff --git a/ess/warp.lua b/ess/warp.lua index 5f3c3a4..f8c876e 100644 --- a/ess/warp.lua +++ b/ess/warp.lua @@ -67,6 +67,7 @@ local function cmd_warp(name,params,splitparams) return false, "No such user." end + ess.save_player_pos(user) user:set_pos(exists) return true, "Warped to "..location.."." end @@ -98,7 +99,6 @@ local commands = { ["ess.warp.warp"] = true, ["ess.warp.warp.other"] = true, }, - save_player_pos = true, func = cmd_warp, }, ["setwarp"] = { diff --git a/ess_core/init.lua b/ess_core/init.lua index 2084e9e..c7ef7f1 100644 --- a/ess_core/init.lua +++ b/ess_core/init.lua @@ -3,11 +3,11 @@ local storage = minetest.get_mod_storage() ess = { + modules = {}, commands = {}, privileges = {}, - modules = {}, - player_meta = {}, world_meta = nil, + player_meta = {}, } --------------------- @@ -54,7 +54,7 @@ end -- WORLD METADATA -- -------------------- --- Load player metadata +-- Load world metadata local function worlddata_load() local decoded = minetest.deserialize(storage:get_string("_data")) if not decoded then @@ -66,21 +66,21 @@ local function worlddata_load() return decoded end --- Save player metadata +-- Save world metadata local function worlddata_save() if not ess.world_meta then return end local encoded = minetest.serialize(ess.world_meta) storage:set_string("_data", encoded) end --- Set a player metadata value +-- Set a world metadata value function ess.set_world_meta(flag, value) if not ess.world_meta then worlddata_load() end ess.world_meta[flag] = value worlddata_save() end --- Get a player's metadata value +-- Get a world metadata value function ess.get_world_meta(flag) if not ess.world_meta then worlddata_load() end return ess.world_meta[flag] @@ -95,31 +95,52 @@ function ess.reject_permission() return false, "You don't have permission to run this command." end --- Match a single privilege, but also check ".all" privileges -function ess.priv_match(name, priv) - local parts = string.split(priv, ".") - if #parts > 1 then - if minetest.check_player_privs(name, {[parts[1] .. ".all"] = true}) then - return true - end - if #parts > 2 then - if minetest.check_player_privs(name, {[parts[1] .. "." .. parts[2] .. ".all"] = true}) then +-- Match a single privilege, but also check ".all" privileges (optional) +function ess.priv_match(name, priv, skip_alls) + if not skip_alls then + local parts = string.split(priv, ".") + if #parts > 1 then + if parts[1] ~= "ess" and minetest.check_player_privs(name, {["ess.all"] = true}) then return true end + + if minetest.check_player_privs(name, {[parts[1] .. ".all"] = true}) then + return true + end + + if #parts > 2 then + if minetest.check_player_privs(name, {[parts[1] .. "." .. parts[2] .. ".all"] = true}) then + return true + end + end end end return minetest.check_player_privs(name, {[priv] = true}) end --- Save a player's position for use with /back -local function save_player_pos(player, commit) - local pobj = minetest.get_player_by_name(player) - if not pobj then return end +-- Save a player's position +-- If commit is not defined or true, we save current position +-- If commit is false, just the player's position is returned +-- If commit is a position, we save that position +function ess.save_player_pos(player, commit) + local pobj + local name = player + if type(player) ~= "userdata" then + pobj = minetest.get_player_by_name(player) + if not pobj then return end + else + name = player:get_player_name() + pobj = player + end local pos = pobj:get_pos() + if commit == nil or commit == true then + commit = pos + end + if commit then - ess.set_player_meta(player, "position", minetest.pos_to_string(commit)) + ess.set_player_meta(name, "position", minetest.pos_to_string(commit)) end return pos @@ -142,6 +163,7 @@ local function handle_command_privileges(privileges, description, default) end perms[perm] = true + -- Make sure .all privileges are registered if #parts > 1 then for i,p in ipairs(parts) do if i == 1 then @@ -154,23 +176,20 @@ local function handle_command_privileges(privileges, description, default) }) ess.privileges[a] = true end - perms[a] = true elseif i == 2 then local a = parts[1] .. "." .. p .. ".all" if not ess.privileges[a] then minetest.register_privilege(a, { - description = "icyess all commands in module " .. p .. " category "..p, + description = "icyess all commands in module " .. parts[1] .. " category "..p, give_to_singleplayer = false, give_to_admin = false }) ess.privileges[a] = true end - perms[a] = true end end end end - perms["ess.all"] = true return perms end @@ -205,7 +224,7 @@ local function register_chatcommand(command, def) -- If this command is a teleport, save the player position local player_pos if def.save_player_pos then - player_pos = save_player_pos(name) + player_pos = ess.save_player_pos(name, false) end local splitparams = string.split(params, " ") @@ -215,7 +234,7 @@ local function register_chatcommand(command, def) -- If we saved player position and the command succeeded, commit the last position save if ret and player_pos then - save_player_pos(name, player_pos) + ess.save_player_pos(name, player_pos) end return ret,mesg @@ -295,7 +314,8 @@ end default = false, -- If this command modifies player's position in some way, - -- save their current position before running the command + -- save their current position before running the command. + -- Use this only when its is certain that the player will teleport. save_player_pos = false } ]]