Add areas_high_limit privilege for trusted players

This commit is contained in:
ShadowNinja 2014-11-14 13:21:09 -05:00
parent fe52664043
commit e4aef02cb9
4 changed files with 43 additions and 22 deletions

16
api.lua
View File

@ -41,17 +41,18 @@ end
--- Checks if the area intersects with an area that the player can't interact in. --- Checks if the area intersects with an area that the player can't interact in.
-- Note that this fails and returns false when the specified area is fully -- Note that this fails and returns false when the specified area is fully
-- owned by the player, but with miltiple protection zones, none of which -- owned by the player, but with multiple protection zones, none of which
-- cover the entire checked area. -- cover the entire checked area.
-- @param name (optional) player name. If not specified checks for any intersecting areas. -- @param name (optional) player name. If not specified checks for any intersecting areas.
-- @param allow_open Whether open areas should be counted as is they didn't exist.
-- @return Boolean indicating whether the player can interact in that area. -- @return Boolean indicating whether the player can interact in that area.
-- @return Un-owned intersecting area id, if found. -- @return Un-owned intersecting area id, if found.
function areas:canInteractInArea(pos1, pos2, name) function areas:canInteractInArea(pos1, pos2, name, allow_open)
if name and minetest.check_player_privs(name, self.adminPrivs) then if name and minetest.check_player_privs(name, self.adminPrivs) then
return true return true
end end
areas:sortPos(pos1, pos2) areas:sortPos(pos1, pos2)
-- First check for a fully enclosing owned area -- First check for a fully enclosing owned area.
if name then if name then
for id, area in pairs(self.areas) do for id, area in pairs(self.areas) do
-- A little optimization: isAreaOwner isn't necessary -- A little optimization: isAreaOwner isn't necessary
@ -62,14 +63,17 @@ function areas:canInteractInArea(pos1, pos2, name)
end end
end end
end end
-- Then check for intersecting (non-owned) areas -- Then check for intersecting (non-owned) areas.
for id, area in pairs(self.areas) do for id, area in pairs(self.areas) do
local p1, p2 = area.pos1, area.pos2 local p1, p2 = area.pos1, area.pos2
if (p1.x <= pos2.x and p2.x >= pos1.x) and if (p1.x <= pos2.x and p2.x >= pos1.x) and
(p1.y <= pos2.y and p2.y >= pos1.y) and (p1.y <= pos2.y and p2.y >= pos1.y) and
(p1.z <= pos2.z and p2.z >= pos1.z) then (p1.z <= pos2.z and p2.z >= pos1.z) then
-- Found an intersecting area -- Found an intersecting area.
if not name or not areas:isAreaOwner(id, name) then -- Return if the area is closed or open areas aren't
-- allowed, and the area isn't owned.
if (not allow_open or not area.open) and
(not name or not areas:isAreaOwner(id, name)) then
return false, id return false, id
end end
end end

View File

@ -19,11 +19,16 @@ dofile(areas.modpath.."/hud.lua")
areas:load() areas:load()
minetest.register_privilege("areas", {description = "Can administer areas"}) minetest.register_privilege("areas", {
description = "Can administer areas."
})
minetest.register_privilege("areas_high_limit", {
description = "Can can more, bigger areas."
})
if not minetest.registered_privileges[areas.self_protection_privilege] then if not minetest.registered_privileges[areas.self_protection_privilege] then
minetest.register_privilege(areas.self_protection_privilege, { minetest.register_privilege(areas.self_protection_privilege, {
description = "Can protect areas", description = "Can protect areas.",
}) })
end end

View File

@ -52,12 +52,12 @@ end
-- Remove a area, and optionally it's children recursively. -- Remove a area, and optionally it's children recursively.
-- If a area is deleted non-recursively the children will -- If a area is deleted non-recursively the children will
-- have the removed area's parent as their new parent. -- have the removed area's parent as their new parent.
function areas:remove(id, recurse, secondrun) function areas:remove(id, recurse)
if recurse then if recurse then
-- Recursively find child entries and remove them -- Recursively find child entries and remove them
local cids = self:getChildren(id) local cids = self:getChildren(id)
for _, cid in pairs(cids) do for _, cid in pairs(cids) do
self:remove(cid, true, true) self:remove(cid, true)
end end
else else
-- Update parents -- Update parents
@ -109,22 +109,26 @@ end
-- Also checks the size of the area and if the user already -- Also checks the size of the area and if the user already
-- has more than max_areas. -- has more than max_areas.
function areas:canPlayerAddArea(pos1, pos2, name) function areas:canPlayerAddArea(pos1, pos2, name)
if minetest.check_player_privs(name, self.adminPrivs) then local privs = minetest.get_player_privs(name)
if privs.areas then
return true return true
end end
-- Check self protection privilege, if it is enabled, -- Check self protection privilege, if it is enabled,
-- and if the area is too big. -- and if the area is too big.
if (not self.self_protection) or if not self.self_protection or
(not minetest.check_player_privs(name, not privs[areas.self_protection_privilege] then
{[areas.self_protection_privilege]=true})) then
return false, "Self protection is disabled or you do not have" return false, "Self protection is disabled or you do not have"
.." the necessary privilege." .." the necessary privilege."
end end
if (pos2.x - pos1.x) > self.self_protection_max_size.x or local max_size = privs.areas_high_limit and
(pos2.y - pos1.y) > self.self_protection_max_size.y or self.self_protection_max_size_high or
(pos2.z - pos1.z) > self.self_protection_max_size.z then self.self_protection_max_size
if
(pos2.x - pos1.x) > max_size.x or
(pos2.y - pos1.y) > max_size.y or
(pos2.z - pos1.z) > max_size.z then
return false, "Area is too big." return false, "Area is too big."
end end
@ -135,7 +139,10 @@ function areas:canPlayerAddArea(pos1, pos2, name)
count = count + 1 count = count + 1
end end
end end
if count >= self.self_protection_max_areas then local max_areas = privs.areas_high_limit and
self.self_protection_max_areas_high or
self.self_protection_max_areas
if count >= max_areas then
return false, "You have reached the maximum amount of" return false, "You have reached the maximum amount of"
.." areas that you are allowed to protect." .." areas that you are allowed to protect."
end end
@ -144,7 +151,7 @@ function areas:canPlayerAddArea(pos1, pos2, name)
local can, id = self:canInteractInArea(pos1, pos2, name) local can, id = self:canInteractInArea(pos1, pos2, name)
if not can then if not can then
local area = self.areas[id] local area = self.areas[id]
return false, ("The area intersects with %s [%u] owned by %s.") return false, ("The area intersects with %s [%u] (%s).")
:format(area.name, id, area.owner) :format(area.name, id, area.owner)
end end

View File

@ -12,16 +12,21 @@ areas.filename =
minetest.setting_get("areas.filename") or worldpath.."/areas.dat" minetest.setting_get("areas.filename") or worldpath.."/areas.dat"
-- Allow players with a privilege create their own areas -- Allow players with a privilege create their own areas
-- within the max_size and number -- within the maximum size and number
areas.self_protection = areas.self_protection =
setting_getbool_default("areas.self_protection", false) setting_getbool_default("areas.self_protection", false)
areas.self_protection_privilege = areas.self_protection_privilege =
minetest.setting_get("areas.self_protection_privilege") or "interact" minetest.setting_get("areas.self_protection_privilege") or "interact"
areas.self_protection_max_size = areas.self_protection_max_size =
minetest.setting_get_pos("areas.self_protection_max_size") or minetest.setting_get_pos("areas.self_protection_max_size") or
{x=50, y=100, z=50} {x=64, y=128, z=64}
areas.self_protection_max_size_high =
minetest.setting_get_pos("areas.self_protection_max_size_high") or
{x=512, y=512, z=512}
areas.self_protection_max_areas = areas.self_protection_max_areas =
tonumber(minetest.setting_get("areas.self_protection_max_areas")) or 3 tonumber(minetest.setting_get("areas.self_protection_max_areas")) or 4
areas.self_protection_max_areas_high =
tonumber(minetest.setting_get("areas.self_protection_max_areas_high")) or 32
-- Register compatability functions for node_ownership. -- Register compatability functions for node_ownership.
-- legacy_table (owner_defs) compatibility is untested -- legacy_table (owner_defs) compatibility is untested