2019-03-07 23:46:35 +00:00
local S = minetest.get_translator ( " mcl_tnt " )
2020-02-05 02:11:32 +00:00
local tnt_griefing = minetest.settings : get_bool ( " mcl_tnt_griefing " , true )
2019-03-07 23:46:35 +00:00
2017-08-09 11:38:47 +00:00
local mod_death_messages = minetest.get_modpath ( " mcl_death_messages " )
2017-01-16 13:59:16 +00:00
local function spawn_tnt ( pos , entname )
2020-04-06 22:55:45 +00:00
minetest.sound_play ( " tnt_ignite " , { pos = pos , gain = 1.0 , max_hear_distance = 15 , } , true )
2017-02-27 22:45:26 +00:00
local tnt = minetest.add_entity ( pos , entname )
tnt : set_armor_groups ( { immortal = 1 } )
2017-03-04 22:25:02 +00:00
return tnt
2015-06-29 17:55:56 +00:00
end
2017-01-16 13:59:16 +00:00
tnt = { }
tnt.ignite = function ( pos )
minetest.remove_node ( pos )
2020-06-07 18:39:19 +00:00
local e = spawn_tnt ( pos , " mcl_tnt:tnt " )
2020-02-05 11:45:29 +00:00
minetest.check_for_falling ( pos )
2020-06-07 18:39:19 +00:00
return e
2017-01-16 13:59:16 +00:00
end
2020-01-30 21:05:18 +00:00
-- Add smoke particle of entity at pos.
-- Intended to be called every step
tnt.smoke_step = function ( pos )
minetest.add_particle ( {
pos = { x = pos.x , y = pos.y + 0.5 , z = pos.z } ,
velocity = vector.new ( math.random ( ) * 0.2 - 0.1 , 1.0 + math.random ( ) , math.random ( ) * 0.2 - 0.1 ) ,
acceleration = vector.new ( 0 , - 0.1 , 0 ) ,
expirationtime = 0.15 + math.random ( ) * 0.25 ,
size = 1.0 + math.random ( ) ,
collisiondetection = false ,
2020-08-19 16:47:58 +00:00
texture = " mcl_particles_smoke.png "
2020-01-30 21:05:18 +00:00
} )
end
tnt.BOOMTIMER = 4
tnt.BLINKTIMER = 0.25
2017-03-11 19:54:27 +00:00
local TNT_RANGE = 3
2017-01-16 13:59:16 +00:00
2017-08-09 11:38:47 +00:00
local sounds
if minetest.get_modpath ( " mcl_sounds " ) then
sounds = mcl_sounds.node_sound_wood_defaults ( )
end
2019-03-17 08:33:44 +00:00
local tnt_mesecons
if minetest.get_modpath ( " mesecons " ) then
tnt_mesecons = { effector = {
action_on = tnt.ignite ,
rules = mesecon.rules . alldirs ,
} }
end
2020-02-05 02:11:32 +00:00
local longdesc
if tnt_griefing then
longdesc = S ( " An explosive device. When it explodes, it will hurt living beings and destroy blocks around it. TNT has an explosion radius of @1. With a small chance, blocks may drop as an item (as if being mined) rather than being destroyed. TNT can be ignited by tools, explosions, fire, lava and redstone signals. " , TNT_RANGE )
else
longdesc = S ( " An explosive device. When it explodes, it will hurt living beings. TNT has an explosion radius of @1. TNT can be ignited by tools, explosions, fire, lava and redstone signals. " , TNT_RANGE )
end
2017-01-26 10:23:09 +00:00
minetest.register_node ( " mcl_tnt:tnt " , {
2017-01-16 12:00:20 +00:00
tiles = { " default_tnt_top.png " , " default_tnt_bottom.png " ,
2015-06-29 17:55:56 +00:00
" default_tnt_side.png " , " default_tnt_side.png " ,
" default_tnt_side.png " , " default_tnt_side.png " } ,
2017-01-04 21:36:51 +00:00
is_ground_content = false ,
2015-06-29 17:55:56 +00:00
stack_max = 64 ,
2019-03-07 23:46:35 +00:00
description = S ( " TNT " ) ,
2017-06-13 12:46:21 +00:00
paramtype = " light " ,
sunlight_propagates = true ,
2020-03-12 00:35:11 +00:00
_tt_help = S ( " Ignited by tools, explosions, fire, lava, redstone power " ) .. " \n " .. S ( " Explosion radius: @1 " , tostring ( TNT_RANGE ) ) ,
2020-02-05 02:11:32 +00:00
_doc_items_longdesc = longdesc ,
2019-03-15 23:07:44 +00:00
_doc_items_usagehelp = S ( " Place the TNT and ignite it with one of the methods above. Quickly get in safe distance. The TNT will start to be affected by gravity and explodes in 4 seconds. " ) ,
2020-05-09 16:52:03 +00:00
groups = { dig_immediate = 3 , tnt = 1 , enderman_takable = 1 , flammable =- 1 } ,
2019-03-17 08:33:44 +00:00
mesecons = tnt_mesecons ,
2020-04-16 21:05:50 +00:00
on_blast = function ( pos )
2020-06-07 18:39:19 +00:00
local e = tnt.ignite ( pos )
2020-04-18 12:18:23 +00:00
e : get_luaentity ( ) . timer = tnt.BOOMTIMER - ( 0.5 + math.random ( ) )
2020-04-16 21:05:50 +00:00
end ,
2017-08-17 02:12:34 +00:00
_on_ignite = function ( player , pointed_thing )
tnt.ignite ( pointed_thing.under )
2017-09-19 13:45:23 +00:00
return true
2017-05-09 15:49:38 +00:00
end ,
2020-05-09 16:52:03 +00:00
_on_burn = function ( pos )
tnt.ignite ( pos )
return true
end ,
2018-02-01 21:45:19 +00:00
_on_dispense = function ( stack , pos , droppos , dropnode , dropdir )
-- Place and ignite TNT
if minetest.registered_nodes [ dropnode.name ] . buildable_to then
minetest.set_node ( droppos , { name = stack : get_name ( ) } )
tnt.ignite ( droppos )
end
end ,
2017-08-09 11:38:47 +00:00
sounds = sounds ,
2015-06-29 17:55:56 +00:00
} )
local TNT = {
-- Static definition
physical = true , -- Collides with things
--weight = -100,
collisionbox = { - 0.5 , - 0.5 , - 0.5 , 0.5 , 0.5 , 0.5 } ,
visual = " cube " ,
textures = { " default_tnt_top.png " , " default_tnt_bottom.png " ,
" default_tnt_side.png " , " default_tnt_side.png " ,
" default_tnt_side.png " , " default_tnt_side.png " } ,
-- Initial value for our timer
timer = 0 ,
blinktimer = 0 ,
2020-04-18 12:18:23 +00:00
tnt_knockback = true ,
2015-06-29 17:55:56 +00:00
blinkstatus = true , }
function TNT : on_activate ( staticdata )
2018-01-25 15:23:54 +00:00
local phi = math.random ( 0 , 65535 ) / 65535 * 2 * math.pi
local hdir_x = math.cos ( phi ) * 0.02
local hdir_z = math.sin ( phi ) * 0.02
2019-03-06 03:38:57 +00:00
self.object : set_velocity ( { x = hdir_x , y = 2 , z = hdir_z } )
self.object : set_acceleration ( { x = 0 , y =- 10 , z = 0 } )
self.object : set_texture_mod ( " ^mcl_tnt_blink.png " )
2015-06-29 17:55:56 +00:00
end
2017-05-29 23:27:45 +00:00
local function add_effects ( pos , radius , drops )
minetest.add_particlespawner ( {
amount = 64 ,
time = 0.5 ,
minpos = vector.subtract ( pos , radius / 2 ) ,
maxpos = vector.add ( pos , radius / 2 ) ,
minvel = { x = - 10 , y = - 10 , z = - 10 } ,
maxvel = { x = 10 , y = 10 , z = 10 } ,
minacc = vector.new ( ) ,
maxacc = vector.new ( ) ,
minexptime = 1 ,
maxexptime = 2.5 ,
minsize = radius * 1 ,
maxsize = radius * 3 ,
2020-08-19 16:47:58 +00:00
texture = " mcl_particles_smoke.png " ,
2017-05-29 23:27:45 +00:00
} )
-- we just dropped some items. Look at the items entities and pick
-- one of them to use as texture
2020-08-19 16:47:58 +00:00
local texture = " mcl_particles_smoke.png " --fallback texture
2017-05-29 23:27:45 +00:00
local most = 0
for name , stack in pairs ( drops ) do
local count = stack : get_count ( )
if count > most then
most = count
local def = minetest.registered_nodes [ name ]
if def and def.tiles and def.tiles [ 1 ] then
texture = def.tiles [ 1 ]
end
end
end
minetest.add_particlespawner ( {
amount = 32 ,
time = 0.1 ,
minpos = vector.subtract ( pos , radius / 2 ) ,
maxpos = vector.add ( pos , radius / 2 ) ,
minvel = { x = - 3 , y = 0 , z = - 3 } ,
maxvel = { x = 3 , y = 5 , z = 3 } ,
minacc = { x = 0 , y = - 10 , z = 0 } ,
minexptime = 0.8 ,
maxexptime = 2.0 ,
minsize = radius * 0.66 ,
maxsize = radius * 2 ,
texture = texture ,
collisiondetection = true ,
} )
end
2015-06-29 17:55:56 +00:00
function TNT : on_step ( dtime )
2019-02-01 05:33:07 +00:00
local pos = self.object : get_pos ( )
2020-01-30 21:05:18 +00:00
tnt.smoke_step ( pos )
2015-06-29 17:55:56 +00:00
self.timer = self.timer + dtime
self.blinktimer = self.blinktimer + dtime
2020-01-30 21:05:18 +00:00
if self.blinktimer > tnt.BLINKTIMER then
self.blinktimer = self.blinktimer - tnt.BLINKTIMER
2015-06-29 17:55:56 +00:00
if self.blinkstatus then
2019-03-06 03:38:57 +00:00
self.object : set_texture_mod ( " " )
2015-06-29 17:55:56 +00:00
else
2019-03-06 03:38:57 +00:00
self.object : set_texture_mod ( " ^mcl_tnt_blink.png " )
2015-06-29 17:55:56 +00:00
end
self.blinkstatus = not self.blinkstatus
end
2020-01-30 21:05:18 +00:00
if self.timer > tnt.BOOMTIMER then
2020-05-02 16:21:44 +00:00
mcl_explosions.explode ( self.object : get_pos ( ) , 4 , { drop_chance = 1.0 } , self.object )
2017-07-25 02:44:46 +00:00
self.object : remove ( )
end
end
2017-01-26 10:23:09 +00:00
minetest.register_entity ( " mcl_tnt:tnt " , TNT )
2015-06-29 17:55:56 +00:00
2017-08-09 11:38:47 +00:00
if minetest.get_modpath ( " mcl_mobitems " ) then
minetest.register_craft ( {
output = " mcl_tnt:tnt " ,
recipe = {
{ ' mcl_mobitems:gunpowder ' , ' group:sand ' , ' mcl_mobitems:gunpowder ' } ,
{ ' group:sand ' , ' mcl_mobitems:gunpowder ' , ' group:sand ' } ,
{ ' mcl_mobitems:gunpowder ' , ' group:sand ' , ' mcl_mobitems:gunpowder ' }
}
} )
end
2017-03-21 03:36:18 +00:00
if minetest.get_modpath ( " doc_identifier " ) then
doc.sub . identifier.register_object ( " mcl_tnt:tnt " , " nodes " , " mcl_tnt:tnt " )
end