1283 lines
38 KiB
Lua
1283 lines
38 KiB
Lua
minetest.register_tool("aliveai:book", {
|
|
description = "Ai Book",
|
|
range=15,
|
|
inventory_image = "aliveai_book.png",
|
|
on_use=function(itemstack, user, pointed_thing)
|
|
local pos=user:get_pos()
|
|
local name=user:get_player_name()
|
|
local pos2=pointed_thing.under
|
|
local item=itemstack:to_table()
|
|
local save
|
|
local meta=minetest.deserialize(item.metadata) or {bots={},selected="",pages=0,selected_num=0,user=name,description="Ai Book by ".. name}
|
|
|
|
if meta.user==name then
|
|
local bots={}
|
|
for i, b in ipairs(meta.bots) do
|
|
bots[b]=1
|
|
end
|
|
if pointed_thing.type=="node" and aliveai.group(pointed_thing.under,"aliveai")>0 and not bots[minetest.get_node(pointed_thing.under).name] then
|
|
bots[minetest.get_node(pointed_thing.under).name]=1
|
|
if meta.selected=="" then
|
|
meta.selected=minetest.get_node(pointed_thing.under).name
|
|
end
|
|
save=true
|
|
elseif pointed_thing.type=="object" and aliveai.is_bot(pointed_thing.ref) and not bots[pointed_thing.ref:get_luaentity().name] then
|
|
bots[pointed_thing.ref:get_luaentity().name]=1
|
|
meta.selected=pointed_thing.ref:get_luaentity().name
|
|
save=true
|
|
else
|
|
for _, ob in ipairs(minetest.get_objects_inside_radius(pos,5)) do
|
|
if aliveai.is_bot(ob) and not bots[ob:get_luaentity().name] and aliveai.visiable(pos,ob) then
|
|
bots[ob:get_luaentity().name]=1
|
|
meta.selected=ob:get_luaentity().name
|
|
save=true
|
|
end
|
|
end
|
|
end
|
|
if save then
|
|
local sbots={}
|
|
local num=0
|
|
for b, n in pairs(bots) do
|
|
num=num+1
|
|
table.insert(sbots,b)
|
|
if meta.selected_num==0 and b==meta.selected then
|
|
meta.selected_num=num
|
|
end
|
|
meta.pages=num
|
|
end
|
|
meta.bots=sbots
|
|
item.meta={description="Ai Book by ".. name}
|
|
minetest.chat_send_player(name, "Book: New content added")
|
|
|
|
if aliveai.grant_invisiable==true and not meta.finished and meta.pages>=aliveai.loaded_objects then
|
|
local p=minetest.get_player_privs(name)
|
|
p.aliveai_invisibility=true
|
|
minetest.set_player_privs(name, p)
|
|
meta.finished=1
|
|
minetest.chat_send_player(name, "Book: You have been granted aliveai_invisibility")
|
|
minetest.chat_send_player(name, "Book: Ai's will not detect you when you are sneaking")
|
|
end
|
|
|
|
item.metadata=minetest.serialize(meta)
|
|
itemstack:replace(item)
|
|
end
|
|
end
|
|
aliveai.view_book(user,meta)
|
|
return itemstack
|
|
end,
|
|
})
|
|
|
|
aliveai.view_book=function(user,meta)
|
|
table.sort(meta.bots)
|
|
local list=""
|
|
local c=""
|
|
local name=user:get_player_name()
|
|
local a=aliveai.registered_bots[meta.selected]
|
|
for i, bot in ipairs(meta.bots) do
|
|
list=list .. c .. bot
|
|
c=","
|
|
end
|
|
|
|
local gui="size[10,8]"
|
|
.."background[-0.2,-0.2;10.4,8.6;gui_formbg.png]"
|
|
.. "label[8,0;Page: " .. meta.selected_num.. "/" .. meta.pages .. " (" .. aliveai.loaded_objects ..")]"
|
|
.."dropdown[0,-0.1;3,1;list;" .. list.. ";" .. meta.selected_num .."]"
|
|
.."button[3,-0.2;1,1;bac;<]"
|
|
.."button[4,-0.2;1,1;fro;>]"
|
|
|
|
if a then
|
|
local light="light"
|
|
local flying="true"
|
|
local drops="none"
|
|
local aggressive="false"
|
|
if a.floating==0 then
|
|
flying="false"
|
|
end
|
|
if a.attacking==1 then
|
|
aggressive="true"
|
|
end
|
|
if a.light<0 then
|
|
light="darknes"
|
|
elseif a.light==0 then
|
|
light="light and darknes"
|
|
end
|
|
if type(a.start_with_items)=="table" then
|
|
drops=""
|
|
local rit
|
|
for it, c in pairs(a.start_with_items) do
|
|
rit=it
|
|
if minetest.registered_items[it] then
|
|
rit=minetest.registered_items[it].description
|
|
end
|
|
drops=drops .. rit .." " .. c ..", "
|
|
end
|
|
end
|
|
gui=gui
|
|
.. "label[0,0.5;"
|
|
.."Name: " .. a.name .."\n"
|
|
.."Type: " .. a.type .."\n"
|
|
.."Team: " .. a.team .."\n"
|
|
.."Health: " .. a.hp .."\n"
|
|
.."Damage: " .. a.dmg .."\n"
|
|
.."Durability: " .. a.mindamage .."\n"
|
|
.."Drops: " .. drops .."\n"
|
|
.."Flying: " .. flying .."\n"
|
|
.."Aggressive: " .. aggressive .."\n"
|
|
.."Thrive in " .. light .."\n\n"
|
|
.. a.description
|
|
.."]"
|
|
.."item_image[5.5,0.5;5,5;" .. a.item .. "]"
|
|
else
|
|
gui=gui .. "label[0,0.5;\nEmpty Ai Book\n\nPunch one or use the book near AI to add.\nBlocks too.]"
|
|
end
|
|
minetest.after(0, function(gui)
|
|
return minetest.show_formspec(name, "aliveai.book",gui)
|
|
end, gui)
|
|
end
|
|
|
|
|
|
aliveai.register_buildings_spawner=function(name,def)
|
|
aliveai.buildings_spawners[minetest.get_current_modname() .. "." .. name]={
|
|
name=name,
|
|
mod=minetest.get_current_modname(),
|
|
on_use=def.on_use,
|
|
on_place=def.on_place
|
|
}
|
|
end
|
|
|
|
minetest.register_tool("aliveai:buildings_spawner", {
|
|
description = "Buildings spawner",
|
|
range=15,
|
|
inventory_image = "aliveai_buildings_spawner.png",
|
|
on_use=function(itemstack, user, pointed_thing)
|
|
aliveai.show_buildings_spawner(itemstack, user, pointed_thing)
|
|
return itemstack
|
|
end,
|
|
on_place=function(itemstack, user, pointed_thing)
|
|
aliveai.show_buildings_spawner(itemstack, user, pointed_thing,true)
|
|
return itemstack
|
|
end,
|
|
})
|
|
|
|
aliveai.show_buildings_spawner=function(itemstack, user, pointed_thing,place)
|
|
if not user or type(user)~="userdata" then return end
|
|
local name=user:get_player_name()
|
|
if minetest.check_player_privs(name, {aliveai_buildings_spawning=true})==false then
|
|
if type(itemstack)=="userdata" then
|
|
itemstack:replace(nil)
|
|
end
|
|
minetest.chat_send_player(name,"You are unallowed to use this tool")
|
|
return itemstack
|
|
end
|
|
local use=":on_use"
|
|
if place then
|
|
use=":on_place"
|
|
end
|
|
local gui="size[10,8]"
|
|
local x,y=0,0
|
|
local l=0
|
|
for i, v in pairs(aliveai.buildings_spawners) do
|
|
if (not place and v.on_use) or (place and v.on_place) then
|
|
l=string.len(v.name)
|
|
if l<5 then
|
|
l=1
|
|
elseif l<15 then
|
|
l=2
|
|
else
|
|
l=3
|
|
end
|
|
gui=gui .. "tooltip[" .. v.mod .."." .. v.name .. use ..";" .. v.name .."]"
|
|
.. "button[" .. x .."," .. y .. ";" .. l ..",1;" .. v.mod .."." .. v.name .. use ..";" .. v.name .."]"
|
|
x=x+l
|
|
if x>10 then
|
|
x=0
|
|
y=y+1
|
|
end
|
|
|
|
end
|
|
end
|
|
aliveai.terminal_users[user:get_player_name()]={itemstack=itemstack,user=user,pointed_thing=pointed_thing}
|
|
minetest.after(0, function(gui)
|
|
return minetest.show_formspec(name, "aliveai.buildings_spawner",gui)
|
|
end, gui)
|
|
end
|
|
|
|
minetest.register_on_player_receive_fields(function(player, form, pressed)
|
|
if form=="aliveai.book" then
|
|
if pressed.quit then
|
|
return
|
|
end
|
|
local item=player:get_wielded_item():to_table()
|
|
local meta=minetest.deserialize(item.metadata) or {bots={},selected=""}
|
|
if not meta.pages or meta.pages==0 then return end
|
|
table.sort(meta.bots)
|
|
if pressed.fro then
|
|
meta.selected_num=meta.selected_num+1
|
|
if meta.selected_num>meta.pages then
|
|
meta.selected_num=1
|
|
end
|
|
meta.selected=meta.bots[meta.selected_num]
|
|
elseif pressed.bac then
|
|
meta.selected_num=meta.selected_num-1
|
|
if meta.selected_num<1 then
|
|
meta.selected_num=meta.pages
|
|
end
|
|
meta.selected=meta.bots[meta.selected_num]
|
|
elseif pressed.list then
|
|
meta.selected=pressed.list
|
|
for i, b in ipairs(meta.bots) do
|
|
if b==meta.selected then
|
|
meta.selected_num=i
|
|
break
|
|
end
|
|
end
|
|
end
|
|
item.metadata=minetest.serialize(meta)
|
|
player:get_inventory():set_stack("main", player:get_wield_index(),item)
|
|
aliveai.view_book(player,meta)
|
|
elseif form=="aliveai.buildings_spawner" then
|
|
local name=player:get_player_name()
|
|
if pressed.quit or not aliveai.terminal_users[name] then
|
|
aliveai.terminal_users[name]=nil
|
|
return
|
|
end
|
|
local na
|
|
local s
|
|
for name, v in pairs(pressed) do
|
|
na=name
|
|
break
|
|
end
|
|
s=na.split(na,":")
|
|
if s and s[2] and aliveai.buildings_spawners[s[1]] then
|
|
local a=aliveai.terminal_users[name]
|
|
aliveai.buildings_spawners[s[1]][s[2]](a.itemstack,a.user,a.pointed_thing)
|
|
end
|
|
end
|
|
end)
|
|
|
|
|
|
|
|
aliveai.crafttools=function(self,t)
|
|
if self.crafting~=1 or math.random(1,10)~=1 then return end
|
|
if type(self.tools)=="table" then return end
|
|
for name, s in pairs(aliveai.tools_handler) do
|
|
if s.try_to_craft and s.tools and not self.creative==1 then
|
|
for i, name2 in pairs(s.tools) do
|
|
if not self.inv[name ..":" ..name2] then
|
|
aliveai.crafting(self,name ..":" ..name2)
|
|
end
|
|
end
|
|
end
|
|
end
|
|
return self
|
|
end
|
|
|
|
aliveai.tool_handler=function(self,t)
|
|
if self.using_tool then return end
|
|
self.using_tool=true
|
|
if not minetest.registered_tools[t] then return end
|
|
local ts=t.split(t,":")
|
|
local tool=aliveai.tools_handler[ts[1]]
|
|
if not tool or not tool.use then return end
|
|
aliveai.showstatus(self,"tool handler")
|
|
if tool.tool_group and minetest.get_item_group(t, tool.tool_group)==0 and minetest.get_item_group(t, tool.tool_group)==0 then
|
|
return
|
|
end
|
|
if tool.tools then
|
|
local nm=true
|
|
for i, name in pairs(tool.tools) do
|
|
if ts[2]==name then nm=false break end
|
|
end
|
|
if nm then return end
|
|
end
|
|
if tool.amo and self.inv[tool.amo] then
|
|
if tool.amo_index and tool.tool_index then
|
|
if tool.amo_index<=tool.tool_index then
|
|
self.tools={tool.amo,t}
|
|
else
|
|
self.tools={t,tool.amo}
|
|
end
|
|
elseif tool.amo_index and tool.amo_index>1 then
|
|
self.tools={tool.amo,t}
|
|
elseif tool.tool_index and tool.tool_index>1 then
|
|
self.tools={t,tool.amo}
|
|
else
|
|
self.tools={tool.amo,t}
|
|
end
|
|
elseif tool.amo_group then
|
|
for name, s in pairs(self.inv) do
|
|
if minetest.get_item_group(name, tool.amo_group)>0
|
|
or minetest.get_item_group(name, tool.amo_group)>0 then
|
|
if tool.amo_index and tool.tool_index then
|
|
if tool.amo_index<=tool.tool_index then
|
|
self.tools={name,t}
|
|
else
|
|
self.tools={t,name}
|
|
end
|
|
elseif tool.amo_index and tool.amo_index>1 then
|
|
self.tools={name,t}
|
|
elseif tool.tool_index and tool.tool_index>1 then
|
|
self.tools={t,name}
|
|
else
|
|
self.tools={name,t}
|
|
end
|
|
end
|
|
end
|
|
else
|
|
return self
|
|
end
|
|
self.tool_index= tool.tool_index or self.self.tool_index
|
|
self.tool_reuse= tool.tool_reuse or self.tool_reuse
|
|
self.tool_near= tool.tool_near or self.tool_near
|
|
self.tool_see= tool.tool_see or self.tool_see
|
|
self.tool_chance= tool.tool_chance or self.tool_chance
|
|
end
|
|
|
|
aliveai.give_to_bot=function(self,clicker)
|
|
local stack=clicker:get_wielded_item()
|
|
if stack:get_name()=="" or stack:get_name()=="aliveai:team_gift" or stack:get_name()=="aliveai_minecontroller:controller" then
|
|
aliveai.on_spoken_to(self,self.botname,clicker:get_player_name(),"come")
|
|
return self
|
|
end
|
|
|
|
if stack:get_name()=="aliveai:hypnotics" then
|
|
local inv=clicker:get_inventory()
|
|
local i=clicker:get_wield_index()
|
|
stack:take_item(1)
|
|
inv:set_stack("main", i,stack)
|
|
if self.hp_max<101 and self.type=="npc" then
|
|
aliveai.sleep(self,2)
|
|
else
|
|
aliveai.punch(self,self.object,20)
|
|
end
|
|
return self
|
|
end
|
|
|
|
if stack:get_name()=="aliveai:relive" then
|
|
local inv=clicker:get_inventory()
|
|
local i=clicker:get_wield_index()
|
|
stack:take_item(1)
|
|
inv:set_stack("main", i,stack)
|
|
|
|
if self.dying or self.dead then
|
|
aliveai.dying(self,3)
|
|
elseif self.hp_max<101 and self.drop_dead_body==1 then
|
|
self.hp=-10
|
|
aliveai.dying(self,1)
|
|
else
|
|
aliveai.punch(self,self.object,20)
|
|
end
|
|
return self
|
|
end
|
|
|
|
if self.dead then return end
|
|
self.mood=self.mood+1
|
|
local inv=clicker:get_inventory()
|
|
local i=clicker:get_wield_index()
|
|
if self.hp<self.hp_max and minetest.get_item_group(stack:get_name(),"aliveai_eatable")>0 then
|
|
aliveai.known(self,clicker,"member")
|
|
self.mood=self.mood+2
|
|
aliveai.sayrnd(self,"thanks",clicker:get_player_name())
|
|
aliveai.invadd(self,stack:get_name(),stack:get_count())
|
|
inv:set_stack("main", i,nil)
|
|
return self
|
|
elseif self.dying then
|
|
return
|
|
end
|
|
|
|
if stack:get_name()=="aliveai_minecontroller:controller" then return end
|
|
|
|
aliveai.invadd(self,stack:get_name(),stack:get_count())
|
|
|
|
if stack:get_name()=="default:diamond" and aliveai.team(clicker)==self.team then
|
|
self.taskstep=3
|
|
self.task="..."
|
|
aliveai.task_build(self)
|
|
aliveai.say(self,"ok, im a guard")
|
|
self.namecolor="0000ff55"
|
|
aliveai.showtext(self,"Guard")
|
|
self.home=aliveai.roundpos(self.object:get_pos())
|
|
aliveai.showstatus(self,"guard")
|
|
inv:set_stack("main", i,nil)
|
|
return self
|
|
end
|
|
|
|
if self.need then
|
|
local name=stack:get_name()
|
|
for ii, vv in pairs(self.need) do
|
|
if vv.item==name or vv.search==name then
|
|
aliveai.known(self,clicker,"member")
|
|
self.mood=self.mood+2
|
|
aliveai.sayrnd(self,"thanks",clicker:get_player_name())
|
|
break
|
|
end
|
|
end
|
|
end
|
|
inv:set_stack("main", i,nil)
|
|
return self
|
|
end
|
|
|
|
aliveai.invadd=function(self,add,num,nfeedback)
|
|
-- inventory
|
|
if not (add and num) or add=="" or num=="" or add=="air" then return self end
|
|
if num>1 then self.mood=self.mood+1 end
|
|
|
|
if self.inv[add] then
|
|
self.inv[add]=self.inv[add]+num
|
|
self.lastitem_name=add
|
|
self.lastitem_count=self.inv[add]
|
|
else
|
|
self.inv[add]=num
|
|
end
|
|
if self.inv[add]<=0 then
|
|
self.inv[add]=nil
|
|
else
|
|
aliveai.eat(self)
|
|
end
|
|
-- needs
|
|
if self.need and self.need[add] then
|
|
if num<0 then num=num*-1 end
|
|
self.need[add].num=self.need[add].num-num
|
|
if self.need[add].num<=0 then self.need[add]=nil end
|
|
end
|
|
--feedback
|
|
|
|
if self.tools=="" then
|
|
if minetest.registered_tools[add] then
|
|
if minetest.registered_tools[add].tool_capabilities then
|
|
local tool=minetest.registered_tools[add].tool_capabilities
|
|
if tool.damage_groups and tool.damage_groups.fleshy and tool.damage_groups.fleshy> self.dmg then
|
|
self.dmg=tool.damage_groups.fleshy
|
|
end
|
|
elseif minetest.registered_tools[add].on_use then
|
|
self.tools={add}
|
|
self.tool_near=1
|
|
self.savetool=1
|
|
end
|
|
elseif minetest.registered_craftitems[add] then
|
|
if minetest.registered_craftitems[add].tool_capabilities then
|
|
local tool=minetest.registered_craftitems[add].tool_capabilities
|
|
if tool.damage_groups and tool.damage_groups.fleshy and tool.damage_groups.fleshy> self.dmg then
|
|
self.dmg=tool.damage_groups.fleshy
|
|
end
|
|
elseif minetest.registered_craftitems[add].on_use and minetest.get_item_group(add,"aliveai_eatable")==0 then
|
|
self.tools={add}
|
|
self.tool_near=1
|
|
self.savetool=1
|
|
end
|
|
end
|
|
end
|
|
|
|
|
|
|
|
|
|
if aliveai.armor then aliveai.armor(self,{item=add}) end
|
|
if aliveai.wieldviewr and not nfeedback then aliveai.wieldviewr(self,add) end
|
|
|
|
aliveai.crafttools(self,add)
|
|
if self.need and not nfeedback then aliveai.haveneed(self,true) end
|
|
return self
|
|
end
|
|
|
|
aliveai.invhave=function(self,name,n,getnum)
|
|
if self.creative==1 and getnum then
|
|
return n
|
|
elseif self.creative==1 then
|
|
self.need=nil
|
|
return true
|
|
end
|
|
local group=name
|
|
local count=0
|
|
if group~=name then-- only for namecuts
|
|
for nm, s in pairs(self.inv) do
|
|
if minetest.get_item_group(nm, group)>0 then
|
|
count=count+s
|
|
end
|
|
end
|
|
elseif self.need and self.crafting==1 then
|
|
-- if its a group, return an item/node
|
|
name=aliveai.crafttoneed(self,name,true)
|
|
end
|
|
if getnum then
|
|
if count>0 then return count end
|
|
return self.inv[name] or 0
|
|
end
|
|
if count>0 and count>=n then
|
|
return true
|
|
end
|
|
if self.inv[name]==nil then
|
|
return false
|
|
elseif n>self.inv[name] then
|
|
return false
|
|
end
|
|
return true
|
|
end
|
|
|
|
aliveai.newneed=function(self,item,num,search,type)
|
|
if self.creative==1 then return end
|
|
if not self.need then self.need={} end
|
|
search=search or ""
|
|
num=num or 1
|
|
if self.ignore_item[item] or (self.need[item] and self.need[item].search==search) or aliveai.invhave(self,item,num) then
|
|
return
|
|
end
|
|
if type==nil then
|
|
type="item"
|
|
if minetest.registered_items[item] then type="item" end
|
|
if minetest.registered_nodes[item] then type="node" end
|
|
end
|
|
-- some extra help for the bot
|
|
if item=="default:chest" then search="default:chest" type="node" end
|
|
if item=="default:chest_locked" then search="default:chest_locked" type="node" end
|
|
if item=="default:glass" then search="group:sand" type="node" end
|
|
if item=="default:wood" then search="group:tree" type="node" end
|
|
if item=="default:stone" then item="default:cobble" search="group:stone" type="node" end
|
|
if item=="default:bush_stem" then search="group:tree" item="default:wood" type="node" end
|
|
if item=="default:acacia_bush_stem" then search="group:tree" item="default:wood" type="node" end
|
|
if item=="default:iron_lump" then item="default:steel_ingot" end
|
|
if item=="default:copper_lump" then item="default:copper_ingot" end
|
|
if item=="default:gold_lump" then item="default:gold_ingot" end
|
|
if item=="default:stone" then search="group:stone" end
|
|
if item=="default:leaves" then search="group:leaves" end
|
|
if item=="default:dirt" then search="group:soil" end
|
|
if item=="wool:white" then search="farming:cotton_8" end
|
|
if item=="wool:blue" then search="farming:cotton_8" end
|
|
if item=="wool:red" then search="farming:cotton_8" end
|
|
if item=="air" then return self end
|
|
self.need[item]={num=num,item=item,search=search,type=type}
|
|
|
|
if not self.mine then
|
|
self.mine={target={},status="search"}
|
|
aliveai.showstatus(self,"mine",4)
|
|
end
|
|
return self
|
|
end
|
|
|
|
aliveai.haveneed=function(self,craft)
|
|
if self.creative==1 then return nil end
|
|
if self.need then
|
|
local have={}
|
|
local name2=""
|
|
local n=true
|
|
for name, need in pairs(self.need) do
|
|
n=false
|
|
if aliveai.invhave(self,need.item,need.num) then
|
|
self.need[name]=nil
|
|
for name2, count2 in pairs(self.need) do
|
|
return self
|
|
end
|
|
n=true
|
|
elseif craft and self.crafting==1 then
|
|
aliveai.crafting(self,need.item,1,need.num)
|
|
end
|
|
end
|
|
if n then
|
|
self.need=nil
|
|
return nil,self
|
|
end
|
|
return self
|
|
end
|
|
return nil
|
|
end
|
|
|
|
aliveai.place=function(self,pos,name)
|
|
local n=minetest.registered_nodes[minetest.get_node(pos).name]
|
|
if minetest.registered_nodes[name] and aliveai.invhave(self,name,1) and n and n.buildable_to and not aliveai.protected(pos,self) then
|
|
local name=name
|
|
if self.inv[name] or self.creative==1 then
|
|
--if minetest.registered_nodes[name] and
|
|
--(minetest.registered_nodes[name].after_place_node
|
|
--or minetest.registered_nodes[name].on_construct
|
|
--or minetest.registered_nodes[name].on_destruct) then
|
|
--minetest.registered_nodes[name].on_place(ItemStack(name), aliveai.createuser(self), {under=pos,above={x=pos.x,y=pos.y+0.5,z=pos.z}})
|
|
--minetest.place_node(pos, {name=name})
|
|
--else
|
|
minetest.set_node(pos, {name=name})
|
|
if aliveai.def(name,"on_construct") then minetest.registered_nodes[name].on_construct(pos) end
|
|
|
|
|
|
--end
|
|
|
|
if self.creative==0 then aliveai.showstatus(self,name .." left: " .. self.inv[name],4) end
|
|
aliveai.invadd(self,name,-1,true)
|
|
return self
|
|
end
|
|
for node, c in pairs(self.inv) do
|
|
if minetest.get_item_group(node, name)>0 then
|
|
minetest.set_node(pos, {name=node})
|
|
aliveai.showstatus(self,name .." left: " .. (self.inv[node]-1),4)
|
|
aliveai.invadd(self,node,-1)
|
|
return self
|
|
end
|
|
end
|
|
else
|
|
return nil
|
|
end
|
|
end
|
|
|
|
aliveai.dig=function(self,pos)
|
|
if minetest.is_protected(pos,"")==false and aliveai.protected(pos,self)==false and minetest.get_node(pos) then
|
|
local name=minetest.get_node(pos).name
|
|
if name=="air" then return true end
|
|
-- have inventory/owned
|
|
local meta = minetest.get_meta(pos)
|
|
local inv = meta:get_inventory()
|
|
local owner=meta:get_string("owner")
|
|
if meta:get_int("owner")==1 or owner=="" or owner==self.botname then
|
|
if inv and not inv:is_empty("main") then
|
|
for i=1,inv:get_size("main"),1 do
|
|
local it=inv:get_stack("main",i):get_name()
|
|
local co=inv:get_stack("main",i):get_count()
|
|
inv:set_stack("main",i,nil)
|
|
aliveai.spawnpickup(pos,it,co)
|
|
end
|
|
end
|
|
else
|
|
aliveai.ignorenode(self,pos)
|
|
return false
|
|
end
|
|
--dig + drops
|
|
local n=1
|
|
local drop=aliveai.digdrop(pos)
|
|
if drop==nil then
|
|
minetest.remove_node(pos)
|
|
minetest.check_for_falling(pos)
|
|
end
|
|
if not drop then return false end
|
|
if drop.name~=nil then
|
|
minetest.remove_node(pos)
|
|
minetest.check_for_falling(pos)
|
|
end
|
|
if minetest.get_node(pos).name~="air" then
|
|
aliveai.ignorenode(self,pos)
|
|
return self
|
|
end
|
|
aliveai.showstatus(self,"dig " .. name,4)
|
|
aliveai.invadd(self,drop.name,drop.n)
|
|
self.on_dig(self,pos,drop.name,drop.n)
|
|
-- if dug was added need
|
|
if self.need and self.need[name] and self.need[name]==1 then
|
|
self.need[name]=nil
|
|
end
|
|
return true
|
|
end
|
|
return false
|
|
end
|
|
|
|
aliveai.digdrop=function(pos)
|
|
local node
|
|
if minetest.registered_nodes[pos] then
|
|
node=minetest.registered_nodes[pos]
|
|
elseif pos and pos.x and pos.y and pos.z then
|
|
node=minetest.registered_nodes[minetest.get_node(pos).name]
|
|
else
|
|
return nil
|
|
end
|
|
-- have drop
|
|
if not node then
|
|
return nil
|
|
elseif node.drop then
|
|
local n=1
|
|
local name=node.name
|
|
-- string drop
|
|
if type(node.drop)=="string" then
|
|
if node.drop=="" or node.groups.unbreakable then return nil end
|
|
name=node.drop
|
|
if string.find(name," ")~=nil then
|
|
local sp=name.split(name," ")
|
|
name=sp[1]
|
|
n=tonumber(sp[2])
|
|
|
|
end
|
|
return {name=name,n=n}
|
|
end
|
|
-- advanced drop
|
|
if not (type(node.drop)=="table" and node.drop.items) then
|
|
return {name=name,n=n}
|
|
end
|
|
local maxitems=node.drop.max_items or 1
|
|
local items={}
|
|
n=0
|
|
for i, v in pairs(node.drop.items) do
|
|
n=n+1
|
|
items[n]={}
|
|
if v.rarity then
|
|
items[n].rnd=v.rarity
|
|
end
|
|
if v.items then
|
|
items[n].items={}
|
|
if type(v.items)=="table" then
|
|
items[n].name=v.items[1]
|
|
else
|
|
items[n].name=v.items
|
|
end
|
|
items[n].n=1
|
|
if string.find(items[n].name," ")~=nil then
|
|
local sp=items[n].name.split(items[n].name," ")
|
|
items[n].name=sp[1]
|
|
items[n].n=tonumber(sp[2])
|
|
end
|
|
end
|
|
end
|
|
local rr=0
|
|
for i=1,n,1 do
|
|
if items[i] and items[i].name and items[i].rnd and aliveai.random(1,items[i].rnd)==1 then
|
|
return {name=items[i].name,n=items[i].n}
|
|
elseif items[i] and items[i].name and not items[i].rnd then
|
|
return {name=items[i].name,n=items[i].n}
|
|
end
|
|
end
|
|
else
|
|
return {name=node.name,n=1}
|
|
end
|
|
end
|
|
|
|
aliveai.eat=function(self)
|
|
local hp=aliveai.gethp(self.object)
|
|
if hp<=0 or hp>=self.hp_max then
|
|
return nil
|
|
end
|
|
local ohp=hp
|
|
for i, h in pairs(self.inv) do
|
|
local eat=minetest.get_item_group(i,"aliveai_eatable")
|
|
if eat>0 then
|
|
for i2=1,h,1 do
|
|
hp=hp+eat
|
|
if hp>=self.hp_max then
|
|
self.inv[i]=h-i2
|
|
if self.inv[i]<=0 then self.inv[i]=nil end
|
|
self.object:set_hp(self.hp_max)
|
|
self.hp=self.hp_max
|
|
aliveai.showhp(self,true)
|
|
aliveai.showstatus(self,"ate, hp now " .. self.hp)
|
|
return
|
|
end
|
|
end
|
|
self.inv[i]=nil
|
|
end
|
|
end
|
|
if ohp~=hp then
|
|
self.object:set_hp(hp)
|
|
self.hp=hp
|
|
aliveai.showhp(self,true)
|
|
aliveai.showstatus(self,"ate, hp now " .. self.hp)
|
|
end
|
|
return self
|
|
end
|
|
|
|
aliveai.crafting=function(self,name,norecraft,neednum)
|
|
|
|
if self.crafting~=1 or name==nil or aliveai.enable_build==false then return false end
|
|
neednum=neednum or 1
|
|
if not norecraft then norecraft=0 end
|
|
norecraft=norecraft+1
|
|
if norecraft>5 then return self end
|
|
name=name
|
|
local c=minetest.get_craft_recipe(name)
|
|
local n=1
|
|
local relist1={}
|
|
local relist2={}
|
|
local list=c.items
|
|
local output=c.output
|
|
--if group or burn
|
|
if not c.output then
|
|
local group=name
|
|
output=group
|
|
local old=output
|
|
for i, s in pairs(self.inv) do
|
|
local from=minetest.get_craft_result({ method = "normal", width = 1, items = { ItemStack(i)}})
|
|
local burn=minetest.get_craft_result({ method = "cooking", width = 3, items = { ItemStack(i)}})
|
|
if (from and from.item) or (burn and burn.item) then
|
|
local a1=from.item:to_table()
|
|
local a2=burn.item:to_table()
|
|
if a2~=nil and a2.name and aliveai.invhave(self,i,neednum) then -- cooking
|
|
local have=s
|
|
local take=neednum
|
|
if take>have then
|
|
local l=s-take
|
|
take=take-l
|
|
end
|
|
aliveai.invadd(self,i,take*-1,true)
|
|
aliveai.invadd(self,a2.name,take, true)
|
|
return self
|
|
end
|
|
if a1~=nil and minetest.get_item_group(a1.name, group)>0 then
|
|
list={i}
|
|
output=a1.name
|
|
n=a1.count
|
|
break
|
|
end
|
|
end
|
|
end
|
|
if old==output then
|
|
return false
|
|
end
|
|
end
|
|
-- collect items to remove
|
|
if not list then return end
|
|
for i, v in pairs(list) do
|
|
local gr=v
|
|
if not relist1[gr] then relist1[gr]=0 end
|
|
relist1[gr]=relist1[gr]+1
|
|
end
|
|
if not relist1 then return end
|
|
-- check if list can be removed, or try to craft
|
|
local nothaveall=false
|
|
for i, v in pairs(relist1) do
|
|
local ii=i
|
|
if self.need and string.find(ii,"group:",1)~=nil then
|
|
ii=aliveai.crafttoneed(self,ii,true)
|
|
end
|
|
if not aliveai.invhave(self,ii,v) then
|
|
local getc
|
|
if self.need then getc=aliveai.crafttoneed(self,ii,false,v) end
|
|
if getc then aliveai.crafting(self,getc,norecraft,v) end
|
|
nothaveall=true
|
|
end
|
|
relist2[ii]=v
|
|
end
|
|
if nothaveall or not relist2 then return self end
|
|
-- remove list
|
|
for i, v in pairs(relist2) do
|
|
if self.inv[i]==nil then
|
|
for ii, vv in pairs(self.inv) do
|
|
if minetest.get_item_group(ii, i)>0 or minetest.get_item_group(ii, i)>0 then
|
|
aliveai.invadd(self,ii,v*-1,true)
|
|
end
|
|
end
|
|
else
|
|
aliveai.invadd(self,i,v*-1,true)
|
|
end
|
|
end
|
|
aliveai.invadd(self,name,n,true)
|
|
return self
|
|
end
|
|
|
|
aliveai.getmaxstack=function(a)
|
|
if a==nil or a=="" then return 1 end
|
|
local b
|
|
if minetest.registered_nodes[a] then
|
|
b=minetest.registered_nodes[a]
|
|
elseif minetest.registered_items[a] then
|
|
b=minetest.registered_items[a]
|
|
elseif minetest.registered_craftitems[a] then
|
|
b=minetest.registered_craftitems[a]
|
|
elseif minetest.registered_tools[a] then
|
|
b=minetest.registered_tools[a]
|
|
end
|
|
|
|
if not b then return 1 end
|
|
return b.stack_max
|
|
end
|
|
|
|
aliveai.spawnpickup=function(pos,name,n,self)
|
|
if (name==nil or name=="") or
|
|
(minetest.registered_nodes[name]==nil
|
|
and minetest.registered_items[name]==nil
|
|
and minetest.registered_craftitems[name]==nil
|
|
and minetest.registered_tools[name]==nil) then return end
|
|
if n==nil or tonumber(n)==nil or n==0 then n=1 end
|
|
local ob=minetest.add_item(pos, name .." ".. n)
|
|
if self then ob:get_luaentity().dropped_by=self.botname end
|
|
ob:set_velocity({x = math.random(-1, 1),y=5,z = math.random(-1, 1)})
|
|
minetest.after(3, function(ob)
|
|
if ob and ob:get_luaentity() then
|
|
local pos=ob:get_pos()
|
|
local n=minetest.get_node(pos)
|
|
local nr=minetest.registered_nodes[n.name]
|
|
if nr and (nr.damage_per_second>0 or minetest.get_item_group(n.name,"igniter")>0 or minetest.get_item_group(n.name,"lava")>0) then
|
|
ob:punch(ob, 1, "default:sword_wood", nil)
|
|
minetest.add_particlespawner({
|
|
amount = 1,
|
|
time =0.2,
|
|
minpos = {x=pos.x-1, y=pos.y, z=pos.z-1},
|
|
maxpos = {x=pos.x+1, y=pos.y, z=pos.z+1},
|
|
minvel = {x=0, y=0, z=0},
|
|
maxvel = {x=0, y=math.random(3,6), z=0},
|
|
minacc = {x=0, y=2, z=0},
|
|
maxacc = {x=0, y=0, z=0},
|
|
minexptime = 1,
|
|
maxexptime = 3,
|
|
minsize = 3,
|
|
maxsize = 8,
|
|
texture = "default_item_smoke.png",
|
|
collisiondetection = true,
|
|
})
|
|
end
|
|
end
|
|
end,ob)
|
|
|
|
end
|
|
|
|
aliveai.invdropall=function(self)
|
|
local pos=self.object:get_pos()
|
|
local c=0
|
|
local max
|
|
aliveai.showstatus(self,"drop all items")
|
|
if not self.inv then aliveai.kill(self) return self end
|
|
for i, itt in pairs(self.inv) do
|
|
max=aliveai.getmaxstack(i)
|
|
if i and itt<=max then
|
|
aliveai.spawnpickup(pos,i,itt,self)
|
|
else
|
|
local io=itt
|
|
for b=1,itt, 1 do
|
|
if io>max then
|
|
io=io-max
|
|
aliveai.spawnpickup(pos,i,max,self)
|
|
else
|
|
aliveai.spawnpickup(pos,i,io,self)
|
|
break
|
|
end
|
|
end
|
|
end
|
|
end
|
|
self.inv={}
|
|
return self
|
|
end
|
|
|
|
aliveai.pickup=function(self,rnd)
|
|
if self.pickuping~=1 then return self end
|
|
if not self.pickupgoto then
|
|
if not rnd and math.random(0,5)>1 then return self end
|
|
end
|
|
self.pickupgoto=nil
|
|
if self.isrnd and not rnd then
|
|
local pos=self.object:get_pos()
|
|
pos.y=pos.y-1
|
|
for _, ob in ipairs(minetest.get_objects_inside_radius(pos, self.distance)) do
|
|
if ob and ob:get_luaentity() and ob:get_luaentity().name=="__builtin:item" then
|
|
local pos2=ob:get_pos()
|
|
if aliveai.visiable(self,pos2) then
|
|
aliveai.lookat(self,pos2)
|
|
aliveai.walk(self)
|
|
self.pickupgoto=true
|
|
aliveai.showstatus(self,"goto item")
|
|
aliveai.showpath(pos2,3)
|
|
break
|
|
end
|
|
end
|
|
end
|
|
end
|
|
local pos=self.object:get_pos()
|
|
for _, ob in ipairs(minetest.get_objects_inside_radius(pos, self.arm)) do
|
|
if ob and ob:get_luaentity() and ob:get_luaentity().name=="__builtin:item" then
|
|
local item=ob:get_luaentity().itemstring
|
|
local droppedby=ob:get_luaentity().dropped_by
|
|
local n=1
|
|
if string.find(item," ")~=nil then
|
|
local sp=item.split(item," ")
|
|
item=sp[1]
|
|
n=tonumber(sp[2])
|
|
end
|
|
if item==nil then
|
|
ob:set_hp(0)
|
|
ob:punch(self.object, 1, "default:sword_wood", nil)
|
|
return self
|
|
end
|
|
if droppedby~=nil then
|
|
local player=minetest.get_player_by_name(droppedby)
|
|
if self.need and self.need[item] then
|
|
if not self.fight and not self.fly and player then
|
|
aliveai.known(self,player,"member")
|
|
aliveai.sayrnd(self,"thanks",droppedby)
|
|
end
|
|
if self.fight and aliveai.getknown(self,self.fight,"fight") then
|
|
aliveai.known(self,self.fight,"")
|
|
aliveai.sayrnd(self,"thanks",droppedby)
|
|
end
|
|
end
|
|
end
|
|
aliveai.invadd(self,item,n)
|
|
aliveai.punch(self,ob,1)
|
|
self.pickupgoto=nil
|
|
aliveai.showstatus(self,"picked up " .. item)
|
|
end
|
|
end
|
|
end
|
|
|
|
minetest.after(0, function()
|
|
aliveai.inventorycreate()
|
|
end)
|
|
aliveai.inventorycreate=function()
|
|
aliveai.inventory=minetest.create_detached_inventory("main", {
|
|
allow_move = function(inv, from_list, from_index, to_list, to_index, count, player)
|
|
return count
|
|
end,
|
|
allow_put = function(inv, listname, index, stack, player)
|
|
return stack:get_count()
|
|
end,
|
|
allow_take = function(inv, listname, index, stack, player)
|
|
return stack:get_count()
|
|
end,
|
|
})
|
|
aliveai.inventory:set_size("main", 16)
|
|
end
|
|
|
|
aliveai.clearinventory=function(self)
|
|
local pos
|
|
if self then pos=self.object:get_pos() end
|
|
local inv = minetest.get_inventory({type="detached", name="main"})
|
|
for i=1,inv:get_size("main"),1 do
|
|
local it=inv:get_stack("main",i):get_name()
|
|
local co=inv:get_stack("main",i):get_count()
|
|
inv:set_stack("main",i,nil)
|
|
if it~="" and pos and pos.x and type(self.tools)=="table" then
|
|
local nohaveit=true
|
|
for ii, name in pairs(self.tools) do
|
|
if name==it then
|
|
nohaveit=false
|
|
break
|
|
end
|
|
end
|
|
if nohaveit then aliveai.spawnpickup(pos,it,co,self) end
|
|
end
|
|
end
|
|
end
|
|
|
|
aliveai.re=function(a)
|
|
return (function() return a end)
|
|
end
|
|
|
|
aliveai.use=function(self)
|
|
if self.tools==nil or type(self.tools)~="table" then return self end
|
|
|
|
if self.tools[1] and not self.tools[2] then
|
|
aliveai.tool_handler(self,self.tools[1])
|
|
end
|
|
|
|
local inv=minetest.get_inventory({type="detached", name="main"})
|
|
local n=0
|
|
local tool=""
|
|
local pointed_thing={type="nothing"}
|
|
local pos=self.object:get_pos()
|
|
for i, name in pairs(self.tools) do
|
|
n=n+1
|
|
if n==self.tool_index then
|
|
if not (minetest.registered_tools[name] and minetest.registered_tools[name].on_use) then print("error: tried to use " .. name .." as a tool, but doesn't have the on_use() function") return self end
|
|
tool=name
|
|
end
|
|
inv:set_stack("main", n, ItemStack(name .. " " .. 1))
|
|
end
|
|
local user=aliveai.createuser(self,self.tool_index)
|
|
if self.fight then
|
|
local range=self.arm
|
|
if minetest.registered_tools[tool] and minetest.registered_tools[tool].range then range=minetest.registered_tools[tool].range end
|
|
local fpos=self.fight:get_pos()
|
|
local d=aliveai.distance(self,fpos)
|
|
if d<self.distance and aliveai.visiable(self,fpos) then
|
|
local dir=aliveai.get_dir(self,fpos)
|
|
user.get_look_dir=aliveai.re(dir)
|
|
if d<=range then
|
|
pointed_thing.type="object"
|
|
pointed_thing.ref=self.fight
|
|
end
|
|
end
|
|
end
|
|
local stack=ItemStack(inv:get_stack("main", self.tool_index))
|
|
aliveai.showstatus(self,"use tool: " .. stack:get_name())
|
|
if not minetest.registered_tools[tool] then return end
|
|
|
|
if aliveai.wieldviewr then aliveai.wieldviewr(self,tool) end
|
|
|
|
minetest.log("aliveai:" .. self.botname .." uses " .. tool)
|
|
|
|
local error
|
|
error,stack=pcall(minetest.registered_tools[tool].on_use,unpack{stack,user,pointed_thing})
|
|
|
|
if error==true and self.tool_reuse==1 then
|
|
tool=stack:get_name()
|
|
minetest.after(0.1, function(self,tool,inv,stack,user,pointed_thing)
|
|
minetest.registered_tools[tool].on_use(stack,user,pointed_thing)
|
|
aliveai.clearinventory(self)
|
|
end,self,tool,inv,stack,user,pointed_thing)
|
|
else
|
|
aliveai.clearinventory(self)
|
|
end
|
|
return self
|
|
end
|
|
|
|
aliveai.spawnbones=function(self)
|
|
if not self and self.object then return end
|
|
local pos=self.object:get_pos()
|
|
pos={x=pos.x,y=pos.y+0.5,z=pos.z}
|
|
if self.dropbones==1 and aliveai.set_bones and aliveai.bones and aliveai.def(pos,"buildable_to") and not minetest.is_protected(pos,"") then
|
|
minetest.set_node(pos,{name="bones:bones"})
|
|
local meta=minetest.get_meta(pos)
|
|
local inv=meta:get_inventory()
|
|
inv:set_size("main", 32)
|
|
meta:set_string("infotext", self.botname .."'s bones")
|
|
meta:set_string("formspec",
|
|
"size[8,8]" ..
|
|
"list[context;main;0,0;8,4;]" ..
|
|
"list[current_player;main;0,4;8,4;]" ..
|
|
"listring[current_player;main]" ..
|
|
"listring[current_name;main]")
|
|
for _, ob in ipairs(minetest.get_objects_inside_radius(pos, 3)) do
|
|
local en=ob:get_luaentity()
|
|
if en and en.name=="__builtin:item" and en.dropped_by==self.botname then
|
|
if inv:room_for_item("main", en.itemstring) then
|
|
inv:add_item("main", en.itemstring)
|
|
aliveai.kill(en)
|
|
else
|
|
return
|
|
end
|
|
end
|
|
end
|
|
end
|
|
end
|
|
|
|
|
|
|
|
aliveai.createuser=function(self,index)
|
|
index=index or 1
|
|
local yaw=self.object:get_yaw()
|
|
if type(yaw)~="number" then yaw=0 end
|
|
yaw=yaw+1.575
|
|
local pos=self.object:get_pos()
|
|
local inv=minetest.get_inventory({type="detached", name="main"})
|
|
return {
|
|
get_player_control=aliveai.re({sneak=false,up=false,down=false,left=false,right=false}),
|
|
get_inventory=aliveai.re({contains_item=aliveai.re(true)}),
|
|
get_luaentity=aliveai.re(self.object),
|
|
get_player_name=aliveai.re(self.botname),
|
|
get_look_horizontal=aliveai.re(0),
|
|
set_look_horizontal=aliveai.re(0),
|
|
set_animation=aliveai.re(),
|
|
set_eye_offset=aliveai.re(),
|
|
get_look_dir=aliveai.re(aliveai.get_dir(self,aliveai.pointat(self))),
|
|
get_look_pitch=aliveai.re(math.pi/2),
|
|
get_look_yaw=aliveai.re(self.object:get_yaw()),
|
|
get_player_control=aliveai.re({jump=false,right=false,left=false,LMB=false,RMB=false,sneak=false,aux1=false,down=false,up=false}),
|
|
get_player_control_bits=aliveai.re(0),
|
|
is_player=aliveai.re(true),
|
|
set_hp=aliveai.re(),
|
|
get_hp=aliveai.re(self.object:get_hp()),
|
|
get_breath=aliveai.re(11),
|
|
get_inventory_formspec=aliveai.re(""),
|
|
set_inventory_formspec=aliveai.re(0),
|
|
get_inventory=aliveai.re(inv),
|
|
get_wielded_item=aliveai.re(inv:get_stack("main", index)),
|
|
get_wield_index=aliveai.re(self.tool_index),
|
|
get_wield_list=aliveai.re("main"),
|
|
set_wielded_item=function(self, item)
|
|
items=item
|
|
inv:set_stack("main", items, item)
|
|
end,
|
|
setpos=aliveai.re(),
|
|
set_pos=aliveai.re(),
|
|
getpos=aliveai.re(pos),
|
|
get_pos=aliveai.re(pos),
|
|
moveto=aliveai.re(),
|
|
punch=aliveai.re(),
|
|
remove=aliveai.re(),
|
|
right_click=aliveai.re(),
|
|
set_properties=aliveai.re(),
|
|
set_animation=aliveai.re(),
|
|
get_attach=aliveai.re(),
|
|
set_attach=aliveai.re(),
|
|
set_detach=aliveai.re(),
|
|
set_bone_position=aliveai.re(),
|
|
hud_change=aliveai.re(),
|
|
}
|
|
end
|
|
|
|
|
|
aliveai.register_buildings_spawner("Copy building",{
|
|
on_use = function(itemstack, user, pointed_thing)
|
|
if pointed_thing.type=="node" then
|
|
aliveai.form(user:get_player_name())
|
|
end
|
|
return itemstack
|
|
end,
|
|
on_place = function(itemstack, user, pointed_thing)
|
|
if pointed_thing.type=="node" then
|
|
local name=user:get_player_name()
|
|
if not aliveai.buildingtool then
|
|
aliveai.form(name)
|
|
return itemstack
|
|
end
|
|
local pos=pointed_thing.under
|
|
local last=""
|
|
local node=""
|
|
local nodes=""
|
|
local count=0
|
|
local need={}
|
|
local dir=minetest.dir_to_facedir(user:get_look_dir())
|
|
local z1=1
|
|
local x1=1
|
|
if dir==1 then x1=1 z1=1 end
|
|
if dir==3 then x1=-1 z1=-1 end
|
|
if dir==0 then x1=-1 z1=1 end
|
|
if dir==2 then x1=1 z1=-1 end
|
|
local toy=aliveai.buildingtool.y
|
|
local tox=aliveai.buildingtool.x*x1
|
|
local toz=aliveai.buildingtool.z*z1
|
|
local status=false
|
|
if aliveai.status==false then status=true end
|
|
aliveai.status=true
|
|
|
|
for y=0,toy,1 do
|
|
for x=0,tox,x1 do
|
|
for z=0,toz,z1 do
|
|
local p={x=pos.x+x,y=pos.y+y,z=pos.z+z}
|
|
node=minetest.get_node(p).name
|
|
if last=="" then last=node end
|
|
if node~="a" then
|
|
if not need[node] then need[node]=0 end
|
|
need[node]=need[node]+1
|
|
end
|
|
if (y==0 or y==toy) or (x==0 or x==tox) or (z==0 or z==toz) then
|
|
aliveai.showpath(p,2)
|
|
end
|
|
|
|
if node~=last then
|
|
nodes=nodes ..last .." " .. count .. "!"
|
|
count=0
|
|
end
|
|
count=count+1
|
|
last=node
|
|
if y==toy and x==tox and z==toz and last~="a" then
|
|
nodes=nodes ..last .." " .. count .. "!"
|
|
count=0
|
|
end
|
|
end
|
|
end
|
|
end
|
|
if status then aliveai.status=false end
|
|
local t=""
|
|
for n, v in pairs(need) do
|
|
t=t .. n.." " ..v .."!"
|
|
end
|
|
nodes=aliveai.buildingtool.x .." " .. aliveai.buildingtool.y .." " .. aliveai.buildingtool.z .. "+++" .. t .."+" .. nodes
|
|
aliveai.form(name,nodes)
|
|
return itemstack
|
|
end
|
|
end
|
|
})
|
|
|
|
aliveai.register_buildings_spawner("Generate building",{
|
|
on_use=function(itemstack, user, pointed_thing)
|
|
if pointed_thing.type=="node" then
|
|
local pos=pointed_thing.above
|
|
local name=user:get_player_name()
|
|
for y=0,7,1 do
|
|
for x=0,10,1 do
|
|
for z=0,10,1 do
|
|
local p={x=pos.x+x,y=pos.y+y,z=pos.z+z}
|
|
local node=minetest.get_node(p)
|
|
if not node then
|
|
minetest.set_node(p,{name="air"})
|
|
node=minetest.get_node(p)
|
|
end
|
|
if minetest.registered_nodes[node.name].buildable_to==false or minetest.is_protected(p,name) then
|
|
minetest.chat_send_player(name, "aliveai: area not able: " .. node.name)
|
|
return itemstack
|
|
end
|
|
end
|
|
end
|
|
end
|
|
aliveai.generate_house(pos)
|
|
end
|
|
end
|
|
}) |