359 lines
10 KiB
Lua
359 lines
10 KiB
Lua
aliveai_electric={player={}}
|
|
|
|
aliveai_electric.pos_between=function(pos1,pos2,density)
|
|
if not ((pos1 and pos1.x and pos1.y and pos1.z) or (pos2 and pos2.x and pos2.y and pos2.z)) then return end
|
|
local d=aliveai.distance(pos1,pos2)
|
|
density=density or 1
|
|
local allpos={}
|
|
local v = {x = pos1.x - pos2.x, y = pos1.y - pos2.y-1, z = pos1.z - pos2.z}
|
|
local amount = (v.x ^ 2 + v.y ^ 2 + v.z ^ 2) ^ 0.5
|
|
local d=math.sqrt((pos1.x-pos2.x)*(pos1.x-pos2.x) + (pos1.y-pos2.y)*(pos1.y-pos2.y)+(pos1.z-pos2.z)*(pos1.z-pos2.z))
|
|
v.x = (v.x / amount)*-1
|
|
v.y = (v.y / amount)*-1
|
|
v.z = (v.z / amount)*-1
|
|
for i=1,d,density do
|
|
local posn={x=pos1.x+(v.x*i),y=pos1.y+(v.y*i),z=pos1.z+(v.z*i)}
|
|
if not aliveai.def(posn,"buildable_to") then
|
|
return allpos
|
|
end
|
|
table.insert(allpos,posn)
|
|
end
|
|
return allpos
|
|
end
|
|
|
|
aliveai_electric.getobjects=function(pos1,pos2)
|
|
if not ((pos1 and pos1.x and pos1.y and pos1.z) or (pos2 and pos2.x and pos2.y and pos2.z)) then return end
|
|
local d=aliveai.distance(pos1,pos2)
|
|
local p={}
|
|
local obs2={}
|
|
local obs1=minetest.get_objects_inside_radius(pos1, d)
|
|
local allpos={}
|
|
local v = {x = pos1.x - pos2.x, y = pos1.y - pos2.y-1, z = pos1.z - pos2.z}
|
|
local amount = (v.x ^ 2 + v.y ^ 2 + v.z ^ 2) ^ 0.5
|
|
local d=math.sqrt((pos1.x-pos2.x)*(pos1.x-pos2.x) + (pos1.y-pos2.y)*(pos1.y-pos2.y)+(pos1.z-pos2.z)*(pos1.z-pos2.z))
|
|
v.x = (v.x / amount)*-1
|
|
v.y = (v.y / amount)*-1
|
|
v.z = (v.z / amount)*-1
|
|
for i=1,d,1 do
|
|
local posn={x=pos1.x+(v.x*i),y=pos1.y+(v.y*i),z=pos1.z+(v.z*i)}
|
|
if not aliveai.def(posn,"buildable_to") then
|
|
return obs2,allpos,posn
|
|
else
|
|
for _, ob in ipairs(obs1) do
|
|
if aliveai.samepos(aliveai.roundpos(posn),aliveai.roundpos(ob:get_pos())) then
|
|
table.insert(obs2,ob)
|
|
end
|
|
end
|
|
end
|
|
table.insert(allpos,posn)
|
|
end
|
|
return obs2,allpos
|
|
end
|
|
|
|
|
|
minetest.register_on_dieplayer(function(player)
|
|
aliveai_electric.player[player:get_player_name()]=nil
|
|
end)
|
|
|
|
|
|
aliveai_electric.hit=function(ob,level,dmg1)
|
|
if not ob or aliveai.team(ob)=="nuke" then return end
|
|
level=level or 2
|
|
dmg1=dmg1 or 2
|
|
local hp=aliveai.gethp(ob)
|
|
if aliveai.is_bot(ob) then
|
|
hp=hp+(ob:get_luaentity().hp_max*2)
|
|
end
|
|
local en=0
|
|
if ob:get_luaentity() then en=1 end
|
|
|
|
local playername
|
|
if ob:is_player() then
|
|
playername=ob:get_player_name()
|
|
aliveai_electric.player[playername]=1
|
|
end
|
|
|
|
minetest.sound_play("aliveai_electric", {pos=ob:get_pos(), gain = 0.1, max_hear_distance = 10})
|
|
local time=0
|
|
for i=0,level,1 do
|
|
local dmg=math.random(1,dmg1)
|
|
hp=hp-dmg
|
|
minetest.after((i*0.3)+time, function(ob,playername)
|
|
if playername and not aliveai_electric.player[playername] then return end
|
|
if aliveai.gethp(ob,1)>0 then
|
|
local p=ob:get_pos()
|
|
minetest.add_particlespawner({
|
|
amount = 8,
|
|
time =0.2,
|
|
maxpos = {x=p.x+0.5,y=p.y+1.5,z=p.z+0.5},
|
|
minpos = {x=p.x-0.5,y=p.y+0.5,z=p.z-0.5},
|
|
minvel = {x=-0.01, y=-0.01, z=-0.01},
|
|
maxvel = {x=0.01, y=0.01, z=0.01},
|
|
minacc = {x=0, y=0, z=0},
|
|
maxacc = {x=0, y=0, z=0},
|
|
minexptime = 0.5,
|
|
maxexptime = 1,
|
|
minsize = 1,
|
|
maxsize = 4,
|
|
texture = "aliveai_electric_vol.png^[colorize:#ffffffff",
|
|
glow=13,
|
|
})
|
|
if aliveai.def(p,"buildable_to") then
|
|
minetest.set_node(p,{name="aliveai_electric:chock"})
|
|
elseif aliveai.def({x=p.x,y=p.y+1,z=p.z},"buildable_to") then
|
|
minetest.set_node({x=p.x,y=p.y+1,z=p.z},{name="aliveai_electric:chock"})
|
|
end
|
|
aliveai.punchdmg(ob,dmg)
|
|
if en==1 and ob then
|
|
ob:set_velocity({x=math.random(-1,1)*0.1, y=ob:get_velocity().y, z=math.random(-1,1)*0.1})
|
|
end
|
|
elseif aliveai_nitroglycerine and dmg>4 and math.random(1,5)==1 then
|
|
aliveai_nitroglycerine.explode(ob:get_pos(),{radius=2,blow_nodes=0})
|
|
end
|
|
|
|
|
|
if playername and i>=level then
|
|
aliveai_electric.player[playername]=nil
|
|
end
|
|
|
|
end, ob,playername)
|
|
time=math.random(1,5)*0.1
|
|
if hp<=0 then return false end
|
|
end
|
|
end
|
|
|
|
aliveai_electric.dir=function(user,pointed)
|
|
if user:get_luaentity() then user=user:get_luaentity() end
|
|
local type=pointed.type
|
|
local pos1=user:get_pos()
|
|
pos1.y=pos1.y+1.5
|
|
local pos2
|
|
if type=="object" then
|
|
pos2=pointed.ref:get_pos()
|
|
elseif type=="node" then
|
|
pos2=pointed.under
|
|
elseif type=="nothing" then
|
|
local dir
|
|
if user:get_luaentity() then
|
|
if user:get_luaentity().aliveai and user:get_luaentity().fight then
|
|
local dir=aliveai.get_dir(user:get_luaentity(),user:get_luaentity().fight)
|
|
pos2={x=pos1.x+(dir.x*30),y=pos1.y+(dir.y*30),z=pos1.z+(dir.z*30)}
|
|
else
|
|
pos2=aliveai.pointat(user:get_luaentity(),30)
|
|
end
|
|
else
|
|
local dir=user:get_look_dir()
|
|
pos2={x=pos1.x+(dir.x*30),y=pos1.y+(dir.y*30),z=pos1.z+(dir.z*30)}
|
|
end
|
|
else
|
|
return
|
|
end
|
|
if aliveai.def(pos1,"walkable") then return end
|
|
return pos1,pos2
|
|
end
|
|
|
|
|
|
aliveai_electric.lightning2=function(obs,pos,hit)
|
|
if not (obs and pos) then return end
|
|
|
|
if pos[1] then
|
|
minetest.sound_play("aliveai_electric_lightning", {
|
|
pos = pos[1],
|
|
max_hear_distance = 5,
|
|
gain = 0.1,
|
|
})
|
|
end
|
|
if pos[#pos] then
|
|
minetest.sound_play("aliveai_electric_lightning", {
|
|
pos = pos[#pos],
|
|
max_hear_distance = 5,
|
|
gain = 0.1,
|
|
})
|
|
end
|
|
|
|
local oo
|
|
for _, ob in ipairs(obs) do
|
|
if aliveai.is_bot(ob) then aliveai.dying(ob:get_luaentity(),1) end
|
|
aliveai.punchdmg(ob,15)
|
|
aliveai_electric.hit(ob)
|
|
minetest.sound_play("aliveai_electric_lightning", {
|
|
pos=ob:get_pos(),
|
|
max_hear_distance = 5,
|
|
gain = 0.1,
|
|
})
|
|
oo=1
|
|
end
|
|
if not oo and pos[#pos] then
|
|
for i, ob2 in pairs(minetest.get_objects_inside_radius(pos[#pos], 2)) do
|
|
if aliveai.is_bot(ob2) then aliveai.dying(ob2:get_luaentity(),1) end
|
|
aliveai.punchdmg(ob2,15)
|
|
aliveai_electric.hit(ob2)
|
|
end
|
|
end
|
|
|
|
for _, p in ipairs(pos) do
|
|
minetest.set_node(p,{name="aliveai_electric:lightning"})
|
|
end
|
|
if aliveai_nitroglycerine and hit then
|
|
aliveai_nitroglycerine.explode(hit,{radius=2})
|
|
end
|
|
end
|
|
|
|
aliveai_electric.lightning1=function(obs,pos,hit)
|
|
if not (obs and pos) then return end
|
|
if pos[1] then
|
|
minetest.sound_play("aliveai_electric_lightning", {
|
|
pos = pos[1],
|
|
max_hear_distance = 5,
|
|
gain = 0.1,
|
|
})
|
|
end
|
|
if pos[#pos] then
|
|
minetest.sound_play("aliveai_electric_lightning", {
|
|
pos = pos[#pos],
|
|
max_hear_distance = 5,
|
|
gain = 0.1,
|
|
})
|
|
end
|
|
for _, ob in ipairs(obs) do
|
|
minetest.set_node(ob:get_pos(), {name="aliveai_electric:lightning_clump"})
|
|
aliveai_electric.hit(ob,math.random(2,7))
|
|
minetest.sound_play("aliveai_electric_lightning", {
|
|
pos=ob:get_pos(),
|
|
max_hear_distance = 5,
|
|
gain = 0.1,
|
|
})
|
|
end
|
|
for _, p in ipairs(pos) do
|
|
minetest.add_particlespawner({
|
|
amount = 20,
|
|
time =0.2,
|
|
minpos = {x=p.x-0.3,y=p.y-0.3,z=p.z-0.3},
|
|
maxpos = {x=p.x+0.3,y=p.y+0.3,z=p.z+0.3},
|
|
minvel = {x=-0.1, y=-0.1, z=-0.1},
|
|
maxvel = {x=0.1, y=0.1, z=0.1},
|
|
minacc = {x=0, y=0, z=0},
|
|
maxacc = {x=0, y=0, z=0},
|
|
minexptime = 0.1,
|
|
maxexptime = 0.5,
|
|
minsize = 1,
|
|
maxsize = 3,
|
|
texture = "aliveai_electric_vol.png",
|
|
glow=13,
|
|
})
|
|
minetest.set_node(p,{name="aliveai_electric:chock"})
|
|
end
|
|
if hit and pos[#pos] then minetest.set_node(pos[#pos],{name="aliveai_electric:lightning_clump"}) end
|
|
end
|
|
|
|
minetest.register_node("aliveai_electric:lightning_clump", {
|
|
description = "Lightning clump",
|
|
groups = {not_in_creative_inventory=1},
|
|
drops="",
|
|
tiles = {
|
|
{
|
|
name = "aliveai_electric_clump.png",
|
|
animation = {
|
|
type = "vertical_frames",
|
|
aspect_w = 16,
|
|
aspect_h = 16,
|
|
length = 0.4,
|
|
},
|
|
},
|
|
},
|
|
pointable=false,
|
|
post_effect_color = {a = 210, r =10, g = 80, b = 230},
|
|
drawtype="plantlike",
|
|
light_source = 8,
|
|
paramtype = "light",
|
|
alpha = 50,
|
|
sunlight_propagates = true,
|
|
liquid_viscosity = 8,
|
|
liquid_renewable = false,
|
|
liquid_range = 0,
|
|
liquid_alternative_flowing="aliveai_electric:lightning_clump",
|
|
liquid_alternative_source="aliveai_electric:lightning_clump",
|
|
liquidtype = "source",
|
|
walkable=false,
|
|
is_ground_content = false,
|
|
on_construct=function(pos)
|
|
minetest.get_node_timer(pos):start(1)
|
|
end,
|
|
on_timer=function(pos, elapsed)
|
|
local rnd=math.random(1,3)
|
|
local sp=0
|
|
for i, ob in pairs(minetest.get_objects_inside_radius(pos, 3)) do
|
|
local p=ob:get_pos()
|
|
if aliveai.team(ob)~="nuke" and aliveai.def(p,"buildable_to") then
|
|
minetest.set_node(p, {name="aliveai_electric:lightning_clump"})
|
|
aliveai_electric.hit(ob)
|
|
minetest.sound_play("aliveai_electric", {pos=pos, gain = 0.1, max_hear_distance = 10,})
|
|
p.y=p.y+1
|
|
if aliveai.def(p,"buildable_to") then
|
|
minetest.set_node(p, {name="aliveai_electric:lightning_clump"})
|
|
end
|
|
end
|
|
sp=sp+1
|
|
if sp>2 then break end
|
|
end
|
|
if rnd>=2 then
|
|
minetest.set_node(pos, {name = "air"})
|
|
return false
|
|
else
|
|
local np=minetest.find_node_near(pos, 2,{"air"})
|
|
if np~=nil then
|
|
minetest.set_node(np, {name="aliveai_electric:lightning_clump"})
|
|
minetest.sound_play("aliveai_electric", {pos=pos, gain = 0.1, max_hear_distance = 10})
|
|
end
|
|
end
|
|
return true
|
|
end
|
|
})
|
|
|
|
|
|
|
|
|
|
minetest.register_node("aliveai_electric:lightning", {
|
|
description = "lightning",
|
|
drawtype="glasslike",
|
|
tiles = {"default_cloud.png^[colorize:#ff3fd7ff"},
|
|
drop="",
|
|
light_source = default.LIGHT_MAX - 1,
|
|
paramtype = "light",
|
|
walkable=false,
|
|
sunlight_propagates = true,
|
|
pointable=false,
|
|
buildable_to = true,
|
|
groups = {not_in_creative_inventory=1},
|
|
post_effect_color = {a = 255, r=255, g=255, b=255},
|
|
walkable=false,
|
|
damage_per_second = 10,
|
|
on_construct = function(pos)
|
|
minetest.get_node_timer(pos):start(0.3)
|
|
end,
|
|
on_timer = function (pos, elapsed)
|
|
minetest.set_node(pos,{name="air"})
|
|
end,
|
|
})
|
|
|
|
minetest.register_node("aliveai_electric:chock", {
|
|
drawtype="airlike",
|
|
tiles = {"aliveai_air.png"},
|
|
drop="",
|
|
light_source = default.LIGHT_MAX - 1,
|
|
walkable=false,
|
|
sunlight_propagates = true,
|
|
pointable=false,
|
|
buildable_to = true,
|
|
groups = {not_in_creative_inventory=1},
|
|
post_effect_color = {a = 200, r=255, g=255, b=255},
|
|
walkable=false,
|
|
on_construct = function(pos)
|
|
minetest.get_node_timer(pos):start(0.1)
|
|
end,
|
|
on_timer = function (pos, elapsed)
|
|
minetest.set_node(pos,{name="air"})
|
|
end,
|
|
})
|
|
|