2 Mod Gestor para Minetest
3 Gestor v1.0 Copyright (C) 2016 BrunoMine (https://github.com/BrunoMine)
5 Recebeste uma cópia da GNU Lesser General
6 Public License junto com esse software,
7 se não, veja em <http://www.gnu.org/licenses/>.
13 local modpath
= minetest
.get_modpath("gestor")
15 -- Variavel global de estruturador
16 gestor
.estruturador
= {}
20 local arredondar
= function(pos
)
22 if pos
.x
> (math
.floor(pos
.x
)+0.5) then
23 r
.x
= math
.ceil(pos
.x
)
25 r
.x
= math
.floor(pos
.x
)
27 if pos
.y
> (math
.floor(pos
.y
)+0.5) then
28 r
.y
= math
.ceil(pos
.y
)
30 r
.y
= math
.floor(pos
.y
)
32 if pos
.z
> (math
.floor(pos
.z
)+0.5) then
33 r
.z
= math
.ceil(pos
.z
)
35 r
.z
= math
.floor(pos
.z
)
40 -- Restaurar as refenrencias em relacao a uma pos
41 local restaurar_pos
= function(pos
, ref
)
43 r
.x
, r
.y
, r
.z
= (pos
.x
+ref
.x
), (pos
.y
+ref
.y
), (pos
.z
+ref
.z
)
47 -- calcular o deslocamento de ref em relacao a pos
48 local ref_pos
= function(pos
, ref
)
50 r
.x
, r
.y
, r
.z
= (ref
.x
-pos
.x
), (ref
.y
-pos
.y
), (ref
.z
-pos
.z
)
54 -- metodo melhorado para pegar nodes (pega nodes ainda nao carregados)
55 local function pegar_node(pos
)
57 local node
= minetest
.get_node(pos
)
58 if node
.name
== "ignore" then
59 minetest
.get_voxel_manip():read_from_map(pos
, pos
)
60 node
= minetest
.get_node(pos
)
64 Para salvar os metadados é criada um valor meta (node.meta)
65 para que alguns dados possam ser mantidos de forma serializada
66 no node e posteriormente serem restaurados quando a estrutura
69 local meta
= minetest
.get_meta(pos
)
70 if node
.name
== "placa_terreno:livre" then -- placas de terreno
73 if meta
:get_string("ref1") ~= "" then
74 -- Mantem os antigos ref's caso existam no metadado
75 ref1
= minetest
.deserialize(meta
:get_string("ref1"))
76 ref2
= minetest
.deserialize(meta
:get_string("ref2"))
79 ref1
= minetest
.serialize(ref_pos(pos
, minetest
.deserialize(meta
:get_string("pos1"))))
80 ref2
= minetest
.serialize(ref_pos(pos
, minetest
.deserialize(meta
:get_string("pos2"))))
82 local custo
= meta
:get_string("custo")
83 local altura
= meta
:get_string("altura")
84 resp
= {node
=node
,meta
={ref1
=ref1
,ref2
=ref2
,custo
=custo
,altura
=altura
}}
85 elseif node
.name
== "default:sign_wall" then -- placas normais de parede
86 local text
= meta
:get_string("text")
87 local infotext
= meta
:get_string("infotext")
88 resp
= {node
=node
,meta
={text
=text
,infotext
=infotext
}}
94 -- Serializar estrutura
95 gestor
.estruturador
.salvar
= function(pos
, nome
, largura
, altura
, modp
, silencio
)
96 if not pos
or not nome
then return false end
103 largura
= largura
or gestor
.diretrizes
.estruturas
[nome
][1]
104 altura
= altura
or gestor
.diretrizes
.estruturas
[nome
][1]
105 if not largura
or not altura
then return false end
107 if silencio
== nil or silencio
== false then minetest
.chat_send_all("Serializando estrutura. Aguarde...") end
109 local ix
, iy
, iz
= 1, 1, 1
110 local x
, y
, z
= pos
.x
, pos
.y
, pos
.z
111 local limx
, limy
, limz
= (pos
.x
+largura
-1), (pos
.y
+altura
-1), (pos
.z
+largura
-1)
116 estrutura
[ix
.." "..iy
.." "..iz
] = pegar_node({x
= x
, y
= y
, z
= z
})
133 local output
= io
.open(modp
.. "/estruturas/"..nome
, "w")
134 output
:write(minetest
.serialize(estrutura
))
137 -- Estrutura serializada com sucesso
138 if silencio
== nil or silencio
== false then minetest
.chat_send_all("Serializacao concluida.") end
142 -- Deserializar uma estrutura
143 gestor
.estruturador
.carregar
= function(pos
, nome
, largura
, altura
, modp
, silencio
)
144 if pos
== nil or nome
== nil then return false end
145 if silencio
== nil or silencio
== false then minetest
.chat_send_all("Criando estrutura. Aguarde...") end
149 dados
= gestor
.diretrizes
.estruturas
[nome
] or {}
150 largura
= dados
[1] or largura
151 altura
= dados
[2] or altura
154 if largura
== nil or altura
== nil or nome
== nil then return false end
155 local input
= io
.open(modp
.. "/estruturas/"..nome
, "r")
157 dados
.estrutura
= minetest
.deserialize(input
:read("*l"))
163 local ix
, iy
, iz
= 1, 1, 1
164 local x
, y
, z
= pos
.x
, pos
.y
, pos
.z
165 local limx
, limy
, limz
= (pos
.x
+largura
-1), (pos
.y
+altura
-1), (pos
.z
+largura
-1)
170 local PosNode
= dados
.estrutura
[ix
.." "..iy
.." "..iz
] or {node
={name
="air"}}
171 minetest
.set_node({x
= x
, y
= y
, z
= z
}, PosNode
.node
)
173 if PosNode
.node
.name
== "placa_terreno:livre" then
174 local meta
= minetest
.get_meta({x
= x
, y
= y
, z
= z
})
176 Tenta restaurar pos1 e pos2 mas devido a um erro
177 desconhecido as vezes desloca 1 node de distancia
180 meta
:set_string("pos1",
181 minetest
.serialize(restaurar_pos(minetest
.deserialize(PosNode
.meta
.ref1
),
182 {x
= x
, y
= y
, z
= z
}))
184 meta
:set_string("pos2",
185 minetest
.serialize(restaurar_pos(minetest
.deserialize(PosNode
.meta
.ref2
),
186 {x
= x
, y
= y
, z
= z
}))
189 Mantes ref1 e ref2 no meto do bloco para evitar distorções maiores
190 usando sempre esses ref's a distorção pode ser no maximo 1 node
192 meta
:set_string("ref1", minetest
.serialize(PosNode
.meta
.ref1
))
193 meta
:set_string("ref2", minetest
.serialize(PosNode
.meta
.ref2
))
194 meta
:set_string("custo", PosNode
.meta
.custo
)
195 meta
:set_string("altura", PosNode
.meta
.altura
)
196 meta
:set_string("status", "livre")
197 meta
:set_string("infotext", "Terreno a Venda")
198 elseif PosNode
.node
.name
== "default:sign_wall" then
199 local meta
= minetest
.get_meta({x
= x
, y
= y
, z
= z
})
200 meta
:set_string("text", PosNode
.meta
.text
)
201 meta
:set_string("infotext", PosNode
.meta
.infotext
)
219 -- Estrutura construida com sucesso
220 if silencio
== nil or silencio
== false then minetest
.chat_send_all("Estrutura construida. Aguarde o mapa ser renderizado.") end
227 -- Nodes restaurador de escadarias
228 local criar_nivel_escadaria
= function(pos
, largura
, name
)
229 local limx
, limz
= pos
.x
+(largura
/2), pos
.z
+(largura
/2)
230 local x
, z
= pos
.x
-(largura
/2), pos
.z
-(largura
/2)
232 z
= pos
.z
-(largura
/2)
234 local npos
= {x
=x
,y
=pos
.y
,z
=z
}
235 local node
= minetest
.get_node(npos
)
236 if node
.name
== "ignore" then
237 minetest
.get_voxel_manip():read_from_map(npos
, npos
)
238 node
= minetest
.get_node(npos
)
240 if node
.name
== "air" then
241 minetest
.set_node(npos
, {name
=name
})
248 local criar_escadaria
= function(pos
, node
)
249 local npos
= {x
=pos
.x
,y
=pos
.y
-10,z
=pos
.z
}
250 local altura
= pos
.y
- 8
251 while altura
<= pos
.y
do
252 criar_nivel_escadaria({x
=pos
.x
,y
=altura
,z
=pos
.z
}, (math
.abs(pos
.y
-altura
)*4)+7, node
)
256 minetest
.register_node("gestor:escadaria", {
257 description
= "Restaurador de escadaria",
259 "default_pine_wood.png",
260 "default_pine_wood.png",
261 "default_pine_wood.png",
262 "default_pine_wood.png",
263 "default_pine_wood.png",
264 "default_pine_wood.png"
266 groups
= {choppy
=2,oddly_breakable_by_hand
=2,wood
=1},
267 sounds
= default
.node_sound_wood_defaults(),
268 on_rightclick
= function(pos
)
269 local node
= minetest
.get_node({x
=pos
.x
,y
=pos
.y
+1,z
=pos
.z
})
270 criar_escadaria({x
=pos
.x
,y
=pos
.y
-1,z
=pos
.z
}, node
.name
)
271 minetest
.set_node(pos
, {name
="air"})
272 minetest
.set_node({x
=pos
.x
,y
=pos
.y
+1,z
=pos
.z
}, {name
="air"})