fix mossy nodes list and add a rocket launcher

master
HybridDog 2014-01-01 18:03:10 +01:00
parent 953619efb4
commit 833f9ca3e5
2 changed files with 291 additions and 129 deletions

25
b.lua Normal file
View File

@ -0,0 +1,25 @@
local function throw_bomb(pos, range, particle_texture, sound)
local t1 = os.clock()
local dir = {x=math.random(-5,5)/10, y=-1, z=math.random(-5,5)/10}
local vel = {x=dir.x*nuke.rocket_speed, y=dir.y*nuke.rocket_speed, z=dir.z*nuke.rocket_speed}
minetest.add_particle(pos, vel, {x=0,y=0,z=0}, 30/nuke.rocket_speed, 2, false, particle_texture)
nuke.rocket_nodes(pos, dir, player, range)
print("[nuke] <rocket> my shot was calculated after "..tostring(os.clock()-t1).."s")
end
minetest.register_globalstep(function(dtime)
for _, player in ipairs(minetest.get_connected_players()) do
local pos = vector.round(player:getpos())
for i = -9,9 do
for j = -9,9 do
if math.random(1000) == 1 then
throw_bomb({x=pos.x+i, y=pos.y+15, z=pos.z+j}, 30, "nuke_firearms_rocket_entity.png")
end
end
end
end
end)

395
init.lua
View File

@ -1,30 +1,39 @@
local time_load_start = os.clock()
print("[nuke] loading...")
local nuke_preserve_items = false
local nuke_drop_items = false --this will only cause lags
nuke = nuke or {}
--nuke.preserve_items = false
--nuke.drop_items = false --this will only cause lags
local MESE_TNT_RANGE = 12
local IRON_TNT_RANGE = 6
local nuke_seed = 12
nuke.seed = 12
nuke.bombs_list = {
{"iron", "Iron"},
{"mese", "Mese"},
{"mossy", "Mossy"}
}
if minetest.get_modpath("extrablocks") then
nuke_mossy_nodes = {
{"default:cobble", "default:mossycobble"},
{"default:stonebrick", "extrablocks:mossystonebrick"},
{"extrablocks:wall", "extrablocks:mossywall"}
}
else
nuke_mossy_nodes = {
{"default:cobble", "default:mossycobble"}
}
end
minetest.after(3, function()
if minetest.get_modpath("extrablocks") then
nuke.mossy_nodes = {
{"default:cobble", "default:mossycobble"},
{"default:stonebrick", "extrablocks:mossystonebrick"},
{"extrablocks:wall", "extrablocks:mossywall"}
}
else
nuke.mossy_nodes = {
{"default:cobble", "default:mossycobble"}
}
end
local num = 1
local nuke_mossy_nds = {}
for _,node in ipairs(nuke_mossy_nodes) do
nuke_mossy_nds[num] = {minetest.get_content_id(node[1]), minetest.get_content_id(node[2])}
num = num+1
end
local num = 1
nuke.mossy_nds = {}
for _,node in ipairs(nuke.mossy_nodes) do
nuke.mossy_nds[num] = {minetest.get_content_id(node[1]), minetest.get_content_id(node[2])}
num = num+1
end
end)
local function r_area(manip, size, pos)
local emerged_pos1, emerged_pos2 = manip:read_from_map(
@ -38,9 +47,11 @@ local function set_vm_data(manip, nodes, pos, t1, msg)
manip:set_data(nodes)
manip:write_to_map()
print(string.format("[nuke] "..msg.." at ("..pos.x.."|"..pos.y.."|"..pos.z..") after ca. %.2fs", os.clock() - t1))
local t1 = os.clock()
manip:update_map()
print(string.format("[nuke] map updated after ca. %.2fs", os.clock() - t1))
if not nuke.no_map_update then
local t1 = os.clock()
manip:update_map()
print(string.format("[nuke] map updated after ca. %.2fs", os.clock() - t1))
end
end
function spawn_tnt(pos, entname)
@ -54,7 +65,11 @@ function do_tnt_physics(tnt_np,tntr)
local oname = obj:get_entity_name()
local v = obj:getvelocity()
local p = obj:getpos()
if oname == "experimental:tnt" or oname == "nuke:iron_tnt" or oname == "nuke:mese_tnt" or oname == "nuke:hardcore_iron_tnt" or oname == "nuke:hardcore_mese_tnt" then
if oname == "experimental:tnt"
or oname == "nuke:iron_tnt"
or oname == "nuke:mese_tnt"
or oname == "nuke:hardcore_iron_tnt"
or oname == "nuke:hardcore_mese_tnt" then
obj:setvelocity({x=(p.x - tnt_np.x) + (tntr / 2) + v.x, y=(p.y - tnt_np.y) + tntr + v.y, z=(p.z - tnt_np.z) + (tntr / 2) + v.z})
else
if v ~= nil then
@ -74,7 +89,7 @@ end
local function get_nuke_random(pos)
return PseudoRandom(math.abs(pos.x+pos.y*3+pos.z*5)+nuke_seed)
return PseudoRandom(math.abs(pos.x+pos.y*3+pos.z*5)+nuke.seed)
end
@ -109,7 +124,7 @@ local c_chest = minetest.get_content_id("default:chest")
local function explode(pos, tab, range)
local t1 = os.clock()
minetest.sound_play("nuke_explode", {pos = pos, gain = 1, max_hear_distance = range*2})
minetest.sound_play("nuke_explode", {pos = pos, gain = 1, max_hear_distance = range*200})
local manip = minetest.get_voxel_manip()
local area = r_area(manip, range+1, pos)
@ -139,7 +154,8 @@ end
local function expl_moss(pos, range)
local t1 = os.clock()
minetest.sound_play("nuke_explode", {pos = pos, gain = 1, max_hear_distance = range*2})
minetest.sound_play("nuke_explode", {pos = pos, gain = 1, max_hear_distance = range*200})
local manip = minetest.get_voxel_manip()
local area = r_area(manip, range+1, pos)
@ -162,10 +178,8 @@ local function expl_moss(pos, range)
if pr:next(1,5) >= 4 then
nodes[p_np] = c_air
--destroy_node(np)
elseif pr:next(1,50) == 1 then
minetest.sound_play("default_glass_footstep", {pos = np, gain = 0.5, max_hear_distance = 4})
else
for _,node in ipairs(nuke_mossy_nds) do
for _,node in ipairs(nuke.mossy_nds) do
if d_p_np == node[1] then
nodes[p_np] = node[2]
break
@ -186,74 +200,79 @@ local function expl_moss(pos, range)
end
minetest.register_chatcommand('nuke_switch_map_update',{
description = 'Switch map update',
params = "",
privs = {},
func = function()
if not nuke.no_map_update then
nuke.no_map_update = true
msg = "nuke map_update disabled"
else
nuke.no_map_update = false
msg = "nuke map_update enabled"
end
print("[nuke] "..name..": "..msg)
minetest.chat_send_player(name, msg)
end
})
--Crafting:
local w = 'default:wood'
local c = 'default:coal_lump'
local s = 'default:steel_ingot'
local m = 'default:mese_crystal'
minetest.register_craft({
output = 'nuke:iron_tnt 4',
recipe = {
{'', w, ''},
{ s, c, s },
{'', w, ''}
}
})
for _,i in ipairs({
{"mese", "mese_crystal"},
{"iron", "steel_ingot"}
}) do
local s = "default"..i[2]
minetest.register_craft({
output = 'nuke:mese_tnt 4',
recipe = {
{'', w, ''},
{ m, c, m },
{'', w, ''}
}
})
minetest.register_craft({
output = 'nuke:'..i[1]..'_tnt 4',
recipe = {
{'', w, ''},
{ s, c, s },
{'', w, ''}
}
})
minetest.register_craft({
output = 'nuke:hardcore_iron_tnt',
recipe = {
{'', c, ''},
{c, 'nuke:iron_tnt', c},
{'', c, ''}
}
})
minetest.register_craft({
output = 'nuke:hardcore_'..i[1]..'_tnt',
recipe = {
{'', c, ''},
{c, 'nuke:'..i[1]..'_tnt', c},
{'', c, ''}
}
})
end
minetest.register_craft({
output = 'nuke:hardcore_mese_tnt',
recipe = {
{'', c, ''},
{c, 'nuke:mese_tnt', c},
{'', c, ''}
}
})
function nuke.lit_tnt(pos, name, puncher)
minetest.remove_node(pos)
spawn_tnt(pos, "nuke:"..name.."_tnt")
nodeupdate(pos)
nuke_puncher = puncher
end
for _,i in ipairs(nuke.bombs_list) do
local nnam = "nuke:"..i[1].."_tnt"
minetest.register_node(nnam, {
description = i[2].." Bomb",
tiles = {"nuke_"..i[1].."_tnt_top.png", "nuke_"..i[1].."_tnt_bottom.png", "nuke_"..i[1].."_tnt_side.png"},
dug_item = '', -- Get nothing
material = {diggability = "not"},
})
minetest.register_on_punchnode(function(p, node, puncher)
if node.name == nnam then
nuke.lit_tnt(p, i[1], puncher)
end
end)
end
-- Iron TNT
minetest.register_node("nuke:iron_tnt", {
tiles = {"nuke_iron_tnt_top.png", "nuke_iron_tnt_bottom.png",
"nuke_iron_tnt_side.png", "nuke_iron_tnt_side.png",
"nuke_iron_tnt_side.png", "nuke_iron_tnt_side.png"},
inventory_image = minetest.inventorycube("nuke_iron_tnt_top.png",
"nuke_iron_tnt_side.png", "nuke_iron_tnt_side.png"),
dug_item = '', -- Get nothing
material = {
diggability = "not",
},
description = "Iron Bomb",
})
minetest.register_on_punchnode(function(p, node, puncher)
if node.name == "nuke:iron_tnt" then
minetest.remove_node(p)
spawn_tnt(p, "nuke:iron_tnt")
nodeupdate(p)
nuke_puncher = puncher
end
end)
local IRON_TNT = {
-- Static definition
physical = true, -- Collides with things
@ -329,22 +348,6 @@ minetest.register_entity("nuke:iron_tnt", IRON_TNT)
-- Mese TNT
minetest.register_node("nuke:mese_tnt", {
description = "Mese Bomb",
tiles = {"nuke_mese_tnt_top.png", "nuke_mese_tnt_bottom.png", "nuke_mese_tnt_side.png"},
inventory_image = minetest.inventorycube("nuke_mese_tnt_top.png", "nuke_mese_tnt_side.png", "nuke_mese_tnt_side.png"),
dug_item = '', -- Get nothing?
material = {diggability = "not"},
})
minetest.register_on_punchnode(function(p, node, puncher)
if node.name == "nuke:mese_tnt" then
minetest.remove_node(p)
spawn_tnt(p, "nuke:mese_tnt")
nodeupdate(p)
nuke_puncher = puncher
end
end)
local MESE_TNT = {
-- Static definition
@ -420,28 +423,6 @@ minetest.register_entity("nuke:mese_tnt", MESE_TNT)
-- Mossy TNT
minetest.register_node("nuke:mossy_tnt", {
tiles = {"nuke_mossy_tnt_top.png", "nuke_mossy_tnt_bottom.png",
"nuke_mossy_tnt_side.png", "nuke_mossy_tnt_side.png",
"nuke_mossy_tnt_side.png", "nuke_mossy_tnt_side.png"},
inventory_image = minetest.inventorycube("nuke_mossy_tnt_top.png",
"nuke_mossy_tnt_side.png", "nuke_mossy_tnt_side.png"),
dug_item = '', -- Get nothing
material = {
diggability = "not",
},
description = "Mossy Bomb",
})
minetest.register_on_punchnode(function(p, node, puncher)
if node.name == "nuke:mossy_tnt" then
minetest.remove_node(p)
spawn_tnt(p, "nuke:mossy_tnt")
nodeupdate(p)
nuke_puncher = puncher
end
end)
local MOSSY_TNT_RANGE = 2
local MOSSY_TNT = {
-- Static definition
@ -491,7 +472,8 @@ function MOSSY_TNT:on_step(dtime)
pos.y = math.floor(pos.y+0.5)
pos.z = math.floor(pos.z+0.5)
do_tnt_physics(pos, MOSSY_TNT_RANGE)
if minetest.get_node(pos).name == "default:water_source" or minetest.get_node(pos).name == "default:water_flowing" then
if minetest.get_node(pos).name == "default:water_source"
or minetest.get_node(pos).name == "default:water_flowing" then
-- Cancel the Explosion
self.object:remove()
return
@ -516,8 +498,7 @@ minetest.register_entity("nuke:mossy_tnt", MOSSY_TNT)
minetest.register_node("nuke:hardcore_iron_tnt", {
tiles = {"nuke_iron_tnt_top.png", "nuke_iron_tnt_bottom.png",
"nuke_hardcore_iron_tnt_side.png", "nuke_hardcore_iron_tnt_side.png",
"nuke_hardcore_iron_tnt_side.png", "nuke_hardcore_iron_tnt_side.png"},
"nuke_hardcore_iron_tnt_side.png"},
inventory_image = minetest.inventorycube("nuke_iron_tnt_top.png",
"nuke_hardcore_iron_tnt_side.png", "nuke_hardcore_iron_tnt_side.png"),
dug_item = '', -- Get nothing
@ -610,8 +591,7 @@ minetest.register_entity("nuke:hardcore_iron_tnt", HARDCORE_IRON_TNT)
minetest.register_node("nuke:hardcore_mese_tnt", {
tiles = {"nuke_mese_tnt_top.png", "nuke_mese_tnt_bottom.png",
"nuke_hardcore_mese_tnt_side.png", "nuke_hardcore_mese_tnt_side.png",
"nuke_hardcore_mese_tnt_side.png", "nuke_hardcore_mese_tnt_side.png"},
"nuke_hardcore_mese_tnt_side.png"},
inventory_image = minetest.inventorycube("nuke_mese_tnt_top.png",
"nuke_hardcore_mese_tnt_side.png", "nuke_hardcore_mese_tnt_side.png"),
dug_item = '', -- Get nothing
@ -700,4 +680,161 @@ end
minetest.register_entity("nuke:hardcore_mese_tnt", HARDCORE_MESE_TNT)
-- Rocket Launcher
--license LGPLv2+
nuke.rocket_speed = 2
nuke.rocket_a = 200
local r_corr = 0.25 --sth like antialiasing
local f_1 = 0.5-r_corr
local f_2 = 0.5+r_corr
-- Taken from the Flowers mod by erlehmann.
local function table_contains(t, v)
for _,i in ipairs(t) do
if i == v then
return true
end
end
return false
end
local function rocket_expl(pos, player, pos2)
local nodenam = minetest.get_node(pos).name
if nodenam == "air"
or nodenam == "default:water_source"
or nodenam == "default:water_flowing" then
return false
end
local delay = nuke.timeacc(vector.distance(pos,pos2), nuke.rocket_speed, nuke.rocket_a)
minetest.after(delay, function(pos)
do_tnt_physics(pos, MOSSY_TNT_RANGE)
expl_moss(pos, MOSSY_TNT_RANGE)
end, pos)
return true
end
local function get_used_dir(dir)
local abs_dir = {x=math.abs(dir.x), y=math.abs(dir.y), z=math.abs(dir.z)}
local dir_max = math.max(abs_dir.x, abs_dir.y, abs_dir.z)
if dir_max == abs_dir.x then
local tab = {"x", {x=1, y=dir.y/dir.x, z=dir.z/dir.x}}
if dir.x >= 0 then
tab[3] = "+"
end
return tab
end
if dir_max == abs_dir.y then
local tab = {"y", {x=dir.x/dir.y, y=1, z=dir.z/dir.y}}
if dir.y >= 0 then
tab[3] = "+"
end
return tab
end
local tab = {"z", {x=dir.x/dir.z, y=dir.y/dir.z, z=1}}
if dir.z >= 0 then
tab[3] = "+"
end
return tab
end
local function node_tab(z, d)
local n1 = math.floor(z*d+f_1)
local n2 = math.floor(z*d+f_2)
if n1 == n2 then
return {n1}
end
return {n1, n2}
end
function nuke.rocket_nodes(pos, dir, player, range)
local t_dir = get_used_dir(dir)
local dir_typ = t_dir[1]
if t_dir[3] == "+" then
f_tab = {0, range, 1}
else
f_tab = {0, -range, -1}
end
local d_ch = t_dir[2]
if dir_typ == "x" then
for d = f_tab[1],f_tab[2],f_tab[3] do
local x = d
local ytab = node_tab(d_ch.y, d)
local ztab = node_tab(d_ch.z, d)
for _,y in ipairs(ytab) do
for _,z in ipairs(ztab) do
if rocket_expl({x=pos.x+x, y=pos.y+y, z=pos.z+z}, player, pos) then
return
end
end
end
end
return
end
if dir_typ == "y" then
for d = f_tab[1],f_tab[2],f_tab[3] do
local xtab = node_tab(d_ch.x, d)
local y = d
local ztab = node_tab(d_ch.z, d)
for _,x in ipairs(xtab) do
for _,z in ipairs(ztab) do
if rocket_expl({x=pos.x+x, y=pos.y+y, z=pos.z+z}, player, pos) then
return
end
end
end
end
return
end
for d = f_tab[1],f_tab[2],f_tab[3] do
local xtab = node_tab(d_ch.x, d)
local ytab = node_tab(d_ch.y, d)
local z = d
for _,x in ipairs(xtab) do
for _,y in ipairs(ytab) do
if rocket_expl({x=pos.x+x, y=pos.y+y, z=pos.z+z}, player, pos) then
return
end
end
end
end
end
function nuke.timeacc(s, v, a)
return (math.sqrt(v*v+2*a*s)-v)/a
end
function nuke.rocket_shoot(player, range, particle_texture, sound)
local t1 = os.clock()
local playerpos=player:getpos()
local dir=player:get_look_dir()
local startpos = {x=playerpos.x, y=playerpos.y+1.6, z=playerpos.z}
minetest.add_particle(startpos,
{x=dir.x*nuke.rocket_speed, y=dir.y*nuke.rocket_speed, z=dir.z*nuke.rocket_speed},
{x=dir.x*nuke.rocket_a, y=dir.y*nuke.rocket_a, z=dir.z*nuke.rocket_a},
nuke.timeacc(range, nuke.rocket_speed, nuke.rocket_a),
1, false, particle_texture
)
nuke.rocket_nodes(vector.round(startpos), dir, player, range)
minetest.sound_play(sound, {pos = playerpos, gain = 1.0, max_hear_distance = range})
print("[nuke] <rocket> my shot was calculated after "..tostring(os.clock()-t1).."s")
end
minetest.register_tool("nuke:rocket_launcher", {
description = "Rocket Launcher",
inventory_image = "firearms_bazooka.png",
stack_max = 1,
on_use = function(itemstack, user)
nuke.rocket_shoot(user, 30, "firearms_rocket_entity.png", "firearms_m79_shot")
end,
})
--dofile(minetest.get_modpath("nuke").."/b.lua")
print(string.format("[nuke] loaded after ca. %.2fs", os.clock() - time_load_start))