TNT: Allow mods to override entity physics.
Introduces an `on_blast(luaobj, damage)` callback that mods can attach to an entity def. The function will get called with the damage that TNT would make. The function should return three values: bool do_damage, bool do_knockback, table drops do_damage allows the mod to tell the TNT code to perform damage on the entity for the mod. The mod code should not do anything with the entity HP. The entity should not be immortal. If false, then the entity will not be damaged by the TNT mod. do_knockback allows the mod to tell the TNT mod to perform an entity knockback effect. If false, no knockback effect is applied to the entity. the drops table is a list of items to drop. It may be nil. E.g. { "wool:red" }. I've documented both on_blast() API methods in game_api.txt. It is a better place than lua_api.txt.
This commit is contained in:
parent
b56c7c0703
commit
43cf4a4984
39
init.lua
39
init.lua
@ -138,7 +138,7 @@ local function calc_velocity(pos1, pos2, old_vel, power)
|
|||||||
return vel
|
return vel
|
||||||
end
|
end
|
||||||
|
|
||||||
local function entity_physics(pos, radius)
|
local function entity_physics(pos, radius, drops)
|
||||||
local objs = minetest.get_objects_inside_radius(pos, radius)
|
local objs = minetest.get_objects_inside_radius(pos, radius)
|
||||||
for _, obj in pairs(objs) do
|
for _, obj in pairs(objs) do
|
||||||
local obj_pos = obj:getpos()
|
local obj_pos = obj:getpos()
|
||||||
@ -157,14 +157,31 @@ local function entity_physics(pos, radius)
|
|||||||
|
|
||||||
obj:set_hp(obj:get_hp() - damage)
|
obj:set_hp(obj:get_hp() - damage)
|
||||||
else
|
else
|
||||||
local obj_vel = obj:getvelocity()
|
local do_damage = true
|
||||||
obj:setvelocity(calc_velocity(pos, obj_pos,
|
local do_knockback = true
|
||||||
obj_vel, radius * 10))
|
local entity_drops = {}
|
||||||
if not obj:get_armor_groups().immortal then
|
local luaobj = obj:get_luaentity()
|
||||||
obj:punch(obj, 1.0, {
|
local objdef = minetest.registered_entities[luaobj.name]
|
||||||
full_punch_interval = 1.0,
|
|
||||||
damage_groups = {fleshy = damage},
|
if objdef and objdef.on_blast then
|
||||||
}, nil)
|
do_damage, do_knockback, entity_drops = objdef.on_blast(luaobj, damage)
|
||||||
|
end
|
||||||
|
|
||||||
|
if do_knockback then
|
||||||
|
local obj_vel = obj:getvelocity()
|
||||||
|
obj:setvelocity(calc_velocity(pos, obj_pos,
|
||||||
|
obj_vel, radius * 10))
|
||||||
|
end
|
||||||
|
if do_damage then
|
||||||
|
if not obj:get_armor_groups().immortal then
|
||||||
|
obj:punch(obj, 1.0, {
|
||||||
|
full_punch_interval = 1.0,
|
||||||
|
damage_groups = {fleshy = damage},
|
||||||
|
}, nil)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
for _, item in ipairs(entity_drops) do
|
||||||
|
add_drop(drops, item)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
@ -303,7 +320,9 @@ function tnt.boom(pos, def)
|
|||||||
minetest.set_node(pos, {name = "tnt:boom"})
|
minetest.set_node(pos, {name = "tnt:boom"})
|
||||||
local drops = tnt_explode(pos, def.radius, def.ignore_protection,
|
local drops = tnt_explode(pos, def.radius, def.ignore_protection,
|
||||||
def.ignore_on_blast)
|
def.ignore_on_blast)
|
||||||
entity_physics(pos, def.damage_radius)
|
-- append entity drops
|
||||||
|
entity_physics(pos, def.damage_radius, drops)
|
||||||
|
|
||||||
if not def.disable_drops then
|
if not def.disable_drops then
|
||||||
eject_drops(drops, pos, def.radius)
|
eject_drops(drops, pos, def.radius)
|
||||||
end
|
end
|
||||||
|
Loading…
Reference in New Issue
Block a user