22 Commits

Author SHA1 Message Date
7f277db7ac Optimize openfarming check 2025-03-20 00:08:37 +01:00
b129fb9494 Merge remote-tracking branch 'upstream/master' 2025-03-19 19:37:57 +01:00
2184118a4b Fix crash 2024-09-15 23:09:05 +02:00
0c9815460a Merge remote-tracking branch 'upstream/master' 2024-09-15 08:24:21 +02:00
2fda1adbd7 Merge remote-tracking branch 'upstream/master' 2023-11-22 23:04:43 +01:00
64b19c2594 Merge remote-tracking branch 'upstream/master' 2023-06-04 23:07:43 +02:00
a8cacee8cc Fixed a minor bug introduced when I created openfarming, which skips the faction test if an area is openfarming.
And not return false if not a player(ie:mobs api) or unknown node, continue iterate on others areas(minor bug, generaly if 1 area it's protected).
2022-07-09 02:49:12 +02:00
76f8ccf8ab Add morefarming and improve farming support on openfarming areas 2020-10-14 22:33:09 +02:00
02b23b0371 Merge remote-tracking branch 'upstream/master' 2020-09-08 18:45:48 +02:00
4eeb2a9d11 Merge remote-tracking branch 'upstream/master' 2020-08-29 20:29:29 +02:00
99408df96a Delete unused textures 2020-07-05 17:10:03 +02:00
42cde6a494 Merge branch 'nalc-1.2-dev' 2020-07-05 17:02:34 +02:00
e0783cf8bf Corrige crash au démarrage 2020-06-15 01:10:47 +02:00
0b2baacb92 Merge remote-tracking branch 'upstream/master' into nalc-1.2-dev 2020-06-14 23:38:20 +02:00
54c504fa0d [areas] Remet le HUD comme avant la modif du feae996 2019-12-30 01:02:36 +01:00
26d6f56485 Ajoute description privilège \"megabuilder\" pour admins d'areas 2019-12-28 15:26:21 +01:00
57f20bb25f Ajoute infos privilège "megabuilder" dans la commande /area_info 2019-12-28 15:07:13 +01:00
feae9967dc Ajoute certaines modifications venant de MFF + ajustement HUD
* Aires openfarming
* Privilège megabuilder
* HUD légèrement modifié pour laisser de la place à celui de factions
2019-12-28 02:43:12 +01:00
c4d0fe020f Corrige lecture de paramètre de configuration 2018-12-24 02:22:29 +01:00
b0c229d80a Restore upstream default config 2016-08-23 15:43:33 +02:00
d7fba610a1 Don't use auth_table, use get_auth_handler().get_auth instead
No guarantee is made auth_table contains auth entries or even exists.
Using this table directly is incompatible with auth handlers that don't
cache auth entries (e.g. when they are stored in an SQL database
supposed to be concurrently accessed and modified).
2016-08-23 14:31:59 +02:00
2a56743f65 Apply MFF edits 2016-08-23 14:28:49 +02:00
9 changed files with 130 additions and 105 deletions

View File

@ -101,10 +101,10 @@ Commands
* `/area_pos {set,set1,set2,get}` -- Sets the area positions by punching
nodes or shows the current area positions.
* `/area_pos1 [X,Y,Z|X Y Z|X, Y, Z]` -- Sets area position one to your position or
* `/area_pos1 [X,Y,Z|X Y Z]` -- Sets area position one to your position or
the one supplied.
* `/area_pos2 [X,Y,Z|X Y Z|X, Y, Z]` -- Sets area position two to your position or
* `/area_pos2 [X,Y,Z|X Y Z]` -- Sets area position two to your position or
the one supplied.
* `/areas_cleanup` -- Removes all ownerless areas.

37
api.lua
View File

@ -1,5 +1,24 @@
local hudHandlers = {}
---plants to place in openfarming
local plants = {
["farming:beetroot"]="air", ["farming:blueberries"]="air", ["farming:cabbage"]="air",
["farming:carrot"]="air", ["farming:chili_pepper"]="air", ["farming:coffee_beans"]="air",
["farming:corn"]="air", ["farming:cucumber"]="air", ["farming:garlic_clove"]="air",
["farming:melon_slice"]="air", ["farming:onion"]="air", ["default:papyrus"]="air",
["farming:pea_pod"]="air", ["farming:peppercorn"]="air", ["farming:pineapple_top"]="air",
["farming:potato"]="air", ["farming:pumpkin_slice"]="air", ["farming:raspberries"]="air",
["farming:rhubarb"]="air",
["farming:seed_barley"]="air", ["farming:seed_cotton"]="air", ["farming:seed_hemp"]="air",
["farming:seed_mint"]="air", ["farming:seed_oat"]="air", ["farming:seed_rice"]="air",
["farming:seed_rye"]="air", ["farming:seed_wheat"]="air",
["farming:tomato"]="air",
["farming:trellis"]="air", ["farming:grapes"]="farming:trellis",
["farming:beanpole"]="air", ["farming:beans"]="farming:beanpole",
["morefarming:seed_wildcarrot"]="air", ["morefarming:seed_teosinte"]="air",
["morefarming:seed_carrot"]="air", ["morefarming:seed_corn"]="air",
}
areas.registered_protection_conditions = {}
areas.registered_on_adds = {}
areas.registered_on_removes = {}
@ -113,7 +132,7 @@ function areas:getSmallestAreaAtPos(pos)
return smallest_area, smallest_id
end
-- Checks if the area is unprotected, open, owned by player
-- Checks if the area is unprotected, open[farming], owned by player
-- or player is part of faction of [smallest] area at position.
function areas:canInteract(pos, name)
if minetest.check_player_privs(name, self.adminPrivs) then
@ -127,10 +146,26 @@ function areas:canInteract(pos, name)
areas_list = self:getAreasAtPos(pos)
end
local owned = false
local player = minetest.get_player_by_name(name)
local node = minetest.get_node(pos).name
for _, area in pairs(areas_list) do
-- Player owns the area or area is open
if area.owner == name or area.open then
return true
elseif area.openfarming then -- If area is openfarming
if player and minetest.registered_nodes[node] then
local wstack = player:get_wielded_item():get_name()
if wstack == "" then wstack = "hand" end
-- on_dig
if minetest.get_item_group(node, "plant") == 1
and (wstack == "hand" or minetest.registered_tools[wstack]) then
return true
end
-- on_place
if plants[wstack] ~= nil and plants[wstack] == node then
return true
end
end
elseif areas.factions_available and area.faction_open then
if (factions.version or 0) < 2 then
local faction_name = factions.get_player_faction(name)

View File

@ -317,6 +317,28 @@ minetest.register_chatcommand("area_open", {
})
minetest.register_chatcommand(
"area_openfarming", {
params = "<ID>",
description = "Toggle an area as open farming (anyone can harvest and plant) or closed",
func = function(name, param)
local id = tonumber(param)
if not id then
return false, "Invalid usage, see /help area_openfarming."
end
if not areas:isAreaOwner(id, name) then
return false, "Area "..id.." does not exist"
.." or is not owned by you."
end
local open = not areas.areas[id].openfarming
-- Save false as nil to avoid inflating the DB.
areas.areas[id].openfarming = open or nil
areas:save()
return true, ("Area %s to farming."):format(open and "opened" or "closed")
end
})
if areas.factions_available then
minetest.register_chatcommand("area_faction_open", {
params = S("<ID> [faction_name]"),
@ -426,7 +448,9 @@ minetest.register_chatcommand("area_info", {
elseif has_high_limit then
table.insert(lines,
S("You have extended area protection"..
" limits (\"areas_high_limit\" privilege)."))
" limits (\"areas_high_limit\" privilege)."))
elseif privs.megabuilder then
table.insert(lines, "You are a megabuilder (\"megabuilder\" privilege).")
end
-- Area count
@ -439,7 +463,7 @@ minetest.register_chatcommand("area_info", {
table.insert(lines, S("You have @1 areas.", area_num))
-- Area limit
local area_limit_line = privs.areas and
local area_limit_line = (privs.areas or privs.megabuilder) and
S("Limit: no area count limit") or
S("Limit: @1 areas", max_count)
table.insert(lines, area_limit_line)
@ -460,6 +484,9 @@ minetest.register_chatcommand("area_info", {
limit, size_limit)
priv_limit_info("areas_high_limit",
limit_high, size_limit_high)
table.insert(lines, "Players with the \"megabuilder\" privilege can protect unlimited areas in size and number.")
elseif privs.megabuilder then
table.insert(lines, "You can protect areas unlimited in size and number.")
elseif has_prot_priv then
size_info(S("You can protect areas"), max_size)
end

View File

@ -44,8 +44,8 @@ minetest.register_globalstep(function(dtime)
table.insert(areaStrings, ("%s [%u] (%s%s%s)")
:format(area.name, id, area.owner,
area.open and S(":open") or "",
faction_info and ": "..faction_info or ""))
area.open and S(":open") or area.openfarming and ":openfarming" or "",
faction_info and ":"..faction_info or ""))
end
for i, area in pairs(areas:getExternalHudEntries(pos)) do

View File

@ -35,6 +35,10 @@ minetest.register_privilege("areas_high_limit", {
description = S("Can protect more, bigger areas."),
give_to_singleplayer = false
})
-- Mega_builder privilege -- MFF
minetest.register_privilege("megabuilder", {
description = "Can protect an infinite amount of areas."
})
if not minetest.registered_privileges[areas.config.self_protection_privilege] then
minetest.register_privilege(areas.config.self_protection_privilege, {

View File

@ -60,8 +60,6 @@ function areas:load()
end
file:close()
self:populateStore()
areas:_checkHierarchy()
end
--- Checks an AreaStore ID.
@ -209,7 +207,6 @@ function areas:isSubarea(pos1, pos2, id)
end
-- Returns a table (list) of children of an area given its identifier
-- This is not recursive, meaning that only children and not grand-children are returned.
function areas:getChildren(id)
local children = {}
for cid, area in pairs(self.areas) do
@ -264,16 +261,19 @@ areas:registerProtectionCondition(function(pos1, pos2, name)
end)
-- check if the area is too big
-- NALC: megabuilders skip checks on size and number of areas
areas:registerProtectionCondition(function(pos1, pos2, name)
local privs = minetest.get_player_privs(name)
local max_size = privs.areas_high_limit and
if not privs.megabuilder then
local max_size = privs.areas_high_limit and
areas.config.self_protection_max_size_high or
areas.config.self_protection_max_size
if
if
(pos2.x - pos1.x + 1) > max_size.x or
(pos2.y - pos1.y + 1) > max_size.y or
(pos2.z - pos1.z + 1) > max_size.z then
return false, S("Area is too big.")
return false, S("Area is too big.")
end
end
end)
@ -345,13 +345,10 @@ function areas:isAreaOwner(id, name)
if cur and minetest.check_player_privs(name, self.adminPrivs) then
return true
end
local seen = {}
while cur and not seen[cur] do
while cur do
if cur.owner == name then
return true
elseif cur.parent then
-- Prevent lock-ups
seen[cur] = true
cur = self.areas[cur.parent]
else
return false
@ -359,56 +356,3 @@ function areas:isAreaOwner(id, name)
end
return false
end
local function get_parent_chain_if_recursive(area, completed)
-- Get uppermost parent
local affected = {}
while area do
if affected[area] then
-- List of affected areas
return affected
end
if completed[area] then
-- Already checked by another function call --> all OK
return nil
end
affected[area] = true
completed[area] = true
area = areas.areas[area.parent]
end
return nil -- all OK
end
--- Internal function to ensure there are no circular parent/children occurrences
function areas:_checkHierarchy()
local needs_save = false
local completed = {}
for _, area_1 in pairs(self.areas) do
local chain = get_parent_chain_if_recursive(area_1, completed)
if chain then
-- How can it be fixed if there is a longer chain?
local list = {}
for area, _ in pairs(chain) do
list[#list + 1] = area.parent
end
local instruction
if #list == 1 then
-- Trivial case, can be resolved in-place
instruction = "The issue was corrected automatically."
area_1.parent = nil
needs_save = true
else
instruction = "Please resolve this conflict manually. Expect issues."
end
core.log("error", "[areas] LOGIC ERROR! Detected a circular area hierarchy in the "
.. "following area ID(s): " .. table.concat(list, ", ") .. ". " .. instruction)
end
end
if needs_save then
-- Prevent repetitive spam upon startup
self:save()
end
end

85
pos.lua
View File

@ -69,53 +69,68 @@ minetest.register_chatcommand("select_area", {
end,
})
local function area_pos_handler(name, param, nr)
local pos
local player = minetest.get_player_by_name(name)
if player then
pos = vector.round(player:get_pos())
end
-- Input parsing
local error_msg
local found, _, x_str, y_str, z_str = param:find(
"^(~?-?%d*)[, ] *(~?-?%d*)[, ] *(~?-?%d*)$")
if found then
pos, error_msg = parse_relative_pos(x_str, y_str, z_str, pos)
elseif param ~= "" then
return false, S("Invalid usage, see /help @1.", "area_pos" .. nr)
end
if not pos then
return false, error_msg or S("Unable to get position.")
end
-- Assign the position
pos = posLimit(vector.round(pos))
if nr == 1 then
areas:setPos1(name, pos)
else
areas:setPos2(name, pos)
end
return true, S("Area position @1 set to @2", tostring(nr),
minetest.pos_to_string(pos))
end
minetest.register_chatcommand("area_pos1", {
params = "[X Y Z|X,Y,Z|X, Y, Z]",
params = "[X Y Z|X,Y,Z]",
description = S("Set area protection region position @1 to your"
.." location or the one specified", "1"),
privs = {},
func = function(name, param)
return area_pos_handler(name, param, 1)
local pos
local player = minetest.get_player_by_name(name)
if player then
pos = vector.round(player:get_pos())
end
local found, _, x_str, y_str, z_str = param:find(
"^(~?-?%d*)[, ](~?-?%d*)[, ](~?-?%d*)$")
if found then
local get_pos, reason = parse_relative_pos(x_str, y_str, z_str, pos)
if get_pos then
pos = get_pos
elseif not get_pos and reason then
return false, reason
end
elseif param ~= "" then
return false, S("Invalid usage, see /help @1.", "area_pos1")
end
if not pos then
return false, S("Unable to get position.")
end
pos = posLimit(vector.round(pos))
areas:setPos1(name, pos)
return true, S("Area position @1 set to @2", "1",
minetest.pos_to_string(pos))
end,
})
minetest.register_chatcommand("area_pos2", {
params = "[X Y Z|X,Y,Z|X, Y, Z]",
params = "[X Y Z|X,Y,Z]",
description = S("Set area protection region position @1 to your"
.." location or the one specified", "2"),
func = function(name, param)
return area_pos_handler(name, param, 2)
local pos
local player = minetest.get_player_by_name(name)
if player then
pos = vector.round(player:get_pos())
end
local found, _, x_str, y_str, z_str = param:find(
"^(~?-?%d*)[, ](~?-?%d*)[, ](~?-?%d*)$")
if found then
local get_pos, reason = parse_relative_pos(x_str, y_str, z_str, pos)
if get_pos then
pos = get_pos
elseif not get_pos and reason then
return false, reason
end
elseif param ~= "" then
return false, S("Invalid usage, see /help @1.", "area_pos2")
end
if not pos then
return false, S("Unable to get position.")
end
pos = posLimit(vector.round(pos))
areas:setPos2(name, pos)
return true, S("Area position @1 set to @2", "2",
minetest.pos_to_string(pos))
end,
})

Binary file not shown.

Before

Width:  |  Height:  |  Size: 142 B

After

Width:  |  Height:  |  Size: 123 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 157 B

After

Width:  |  Height:  |  Size: 134 B