diff --git a/shooter/api.lua b/shooter/api.lua index 512fb30..0ae0e77 100644 --- a/shooter/api.lua +++ b/shooter/api.lua @@ -80,12 +80,22 @@ function shooter:spawn_particles(pos, texture) texture = config.explosion_texture end local spread = {x=0.1, y=0.1, z=0.1} - minetest.add_particlespawner(15, 0.3, - vector.subtract(pos, spread), vector.add(pos, spread), - {x=-1, y=1, z=-1}, {x=1, y=2, z=1}, - {x=-2, y=-2, z=-2}, {x=2, y=-2, z=2}, - 0.1, 0.75, 1, 2, false, texture - ) + minetest.add_particlespawner({ + amount = 15, + time = 0.3, + minpos = vector.subtract(pos, spread), + maxpos = vector.add(pos, spread), + minvel = {x=-1, y=1, z=-1}, + maxvel = {x=1, y=2, z=1}, + minacc = {x=-2, y=-2, z=-2}, + maxacc = {x=2, y=-2, z=2}, + minexptime = 0.1, + maxexptime = 0.75, + minsize = 1, + maxsize = 2, + collisiondetection = false, + texture = texture, + }) end end @@ -261,21 +271,32 @@ function shooter:blast(pos, radius, fleshy, distance, user) end end if config.enable_particle_fx == true then - minetest.add_particlespawner(50, 0.1, - p1, p2, {x=-0, y=-0, z=-0}, {x=0, y=0, z=0}, - {x=-0.5, y=5, z=-0.5}, {x=0.5, y=5, z=0.5}, - 0.1, 1, 8, 15, false, "tnt_smoke.png" - ) + minetest.add_particlespawner({ + amount = 50, + time = 0.1, + minpos = p1, + maxpos = p2, + minvel = {x=0, y=0, z=0}, + maxvel = {x=0, y=0, z=0}, + minacc = {x=-0.5, y=5, z=-0.5}, + maxacc = {x=0.5, y=5, z=0.5}, + minexptime = 0.1, + maxexptime = 1, + minsize = 8, + maxsize = 15, + collisiondetection = false, + texture = "tnt_smoke.png", + }) end local objects = minetest.get_objects_inside_radius(pos, distance) for _,obj in ipairs(objects) do if shooter:is_valid_object(obj) then - local obj_pos = obj:getpos() + local obj_pos = obj:get_pos() local dist = vector.distance(obj_pos, pos) local damage = (fleshy * 0.5 ^ dist) * 2 if dist ~= 0 then obj_pos.y = obj_pos.y + 1 - blast_pos = {x=pos.x, y=pos.y + 4, z=pos.z} + local blast_pos = {x=pos.x, y=pos.y + 4, z=pos.z} if minetest.line_of_sight(obj_pos, blast_pos, 1) then obj:punch(user, 1.0, { full_punch_interval = 1.0, diff --git a/shooter_crossbow/init.lua b/shooter_crossbow/init.lua index 460e783..a6beb1c 100644 --- a/shooter_crossbow/init.lua +++ b/shooter_crossbow/init.lua @@ -1,6 +1,7 @@ local config = { crossbow_uses = 50, arrow_lifetime = 180, + arrow_object_attach = false, } -- Legacy Config Support @@ -21,12 +22,14 @@ if minetest.global_exists("SHOOTER_ARROW_TOOL_CAPS") then arrow_tool_caps = table.copy(SHOOTER_ARROW_TOOL_CAPS) end -minetest.register_alias("shooter_crossbow:arrow", "shooter_crossbow:arrow_white") -minetest.register_alias("shooter:crossbow_loaded", "shooter:crossbow_loaded_white") - local dye_basecolors = (dye and dye.basecolors) or {"white", "grey", "black", "red", "yellow", "green", "cyan", "blue", "magenta"} +-- name is the overlay texture name, colour is used to select the wool texture +local function get_texture(name, colour) + return "wool_"..colour..".png^shooter_"..name..".png^[makealpha:255,126,126" +end + local function get_animation_frame(dir) local angle = math.atan(dir.y) local frame = 90 - math.floor(angle * 360 / math.pi) @@ -38,15 +41,55 @@ local function get_animation_frame(dir) return frame end -local function get_target_pos(p1, p2, dir, offset) - local d = vector.distance(p1, p2) - offset - local td = vector.multiply(dir, {x=d, y=d, z=d}) - return vector.add(p1, td) +local function get_pointed_thing(pos, dir, dist) + local p1 = vector.add(pos, dir) + local p2 = vector.add(pos, vector.multiply(dir, dist)) + local ray = minetest.raycast(p1, p2, true, true) + return ray:next() end --- name is the overlay texture name, colour is used to select the wool texture -local function get_texture(name, colour) - return "wool_"..colour..".png^shooter_"..name..".png^[makealpha:255,126,126" +local function strike(arrow, pointed_thing, name) + local puncher = minetest.get_player_by_name(name) + if not puncher then + return + end + local object = arrow.object + local hit_pos = pointed_thing.intersection_point or object:get_pos() + local dir = vector.normalize(object:get_velocity()) + if pointed_thing.type == "object" then + local target = pointed_thing.ref + if shooter:is_valid_object(target) then + local puncher = minetest.get_player_by_name(name) + if puncher and puncher ~= target then + local groups = target:get_armor_groups() or {} + if groups.fleshy then + shooter:spawn_particles(hit_pos, + shooter.config.explosion_texture) + end + target:punch(object, nil, arrow_tool_caps, dir) + if config.arrow_object_attach then + local pos = vector.multiply(vector.subtract(target:get_pos(), + hit_pos), -10) + local rot = vector.new() + rot.y = (target:get_yaw() - object:get_yaw()) * 57.2958 + object:set_attach(target, "", pos, rot) + arrow.state = "stuck" + else + arrow.state = "dropped" + end + end + end + elseif pointed_thing.type == "node" then + local pos = minetest.get_pointed_thing_position(pointed_thing, false) + local node = minetest.get_node(pos) + hit_pos = vector.subtract(hit_pos, vector.multiply(dir, 0.25)) + arrow.node_pos = pos + arrow.state = "stuck" + shooter:play_node_sound(node, pos) + else + return + end + arrow:stop(hit_pos) end minetest.register_entity("shooter_crossbow:arrow_entity", { @@ -60,14 +103,14 @@ minetest.register_entity("shooter_crossbow:arrow_entity", { color = "white", timer = 0, lifetime = config.arrow_lifetime, - player = nil, + user = nil, state = "init", node_pos = nil, collisionbox = {0,0,0, 0,0,0}, stop = function(self, pos) local acceleration = {x=0, y=-10, z=0} if self.state == "stuck" then - pos = pos or self.object:getpos() + pos = pos or self.object:get_pos() acceleration = {x=0, y=0, z=0} end if pos then @@ -77,22 +120,8 @@ minetest.register_entity("shooter_crossbow:arrow_entity", { physical = true, collisionbox = {-1/8,-1/8,-1/8, 1/8,1/8,1/8}, }) - self.object:setvelocity({x=0, y=0, z=0}) - self.object:setacceleration(acceleration) - end, - strike = function(self, object) - local puncher = self.player - if puncher and shooter:is_valid_object(object) then - if puncher ~= object then - local dir = puncher:get_look_dir() - local p1 = puncher:getpos() - local p2 = object:getpos() - local tpos = get_target_pos(p1, p2, dir, 0) - shooter:spawn_particles(tpos, shooter.config.explosion_texture) - object:punch(puncher, nil, arrow_tool_caps, dir) - end - end - self:stop(object:getpos()) + self.object:set_velocity({x=0, y=0, z=0}) + self.object:set_acceleration(acceleration) end, on_activate = function(self, staticdata) self.object:set_armor_groups({immortal=1}) @@ -143,25 +172,12 @@ minetest.register_entity("shooter_crossbow:arrow_entity", { return end if self.timer > 0.2 then - local dir = vector.normalize(self.object:getvelocity()) + local dir = vector.normalize(self.object:get_velocity()) local frame = get_animation_frame(dir) - local p1 = vector.add(self.object:getpos(), dir) - local p2 = vector.add(p1, vector.multiply(dir, 4)) - local ray = minetest.raycast(p1, p2, true, true) - local pointed_thing = ray:next() or {} - if pointed_thing.type == "object" then - local obj = pointed_thing.ref - if shooter:is_valid_object(obj) then - self:strike(obj) - end - elseif pointed_thing.type == "node" then - local pos = minetest.get_pointed_thing_position(pointed_thing, false) - local node = minetest.get_node(pos) - local target_pos = get_target_pos(p1, pos, dir, 0.66) - self.node_pos = pos - self.state = "stuck" - self:stop(target_pos) - shooter:play_node_sound(node, pos) + local pos = self.object:get_pos() + local pointed_thing = get_pointed_thing(pos, dir, 5) + if pointed_thing then + strike(self, pointed_thing, self.user) end self.object:set_animation({x=frame, y=frame}, 0) self.timer = 0 @@ -184,55 +200,37 @@ for _, color in pairs(dye_basecolors) do on_use = function(itemstack, user, pointed_thing) minetest.sound_play("shooter_click", {object=user}) if not minetest.setting_getbool("creative_mode") then - itemstack:add_wear(65535/config.crossbow_uses) + itemstack:add_wear(65535 / config.crossbow_uses) end itemstack = "shooter_crossbow:crossbow 1 "..itemstack:get_wear() - local pos = user:getpos() + local pos = user:get_pos() local dir = user:get_look_dir() - local yaw = user:get_look_yaw() + local yaw = user:get_look_horizontal() if pos and dir and yaw then pos.y = pos.y + shooter.config.camera_height - pos = vector.add(pos, dir) - local obj = minetest.add_entity(pos, "shooter_crossbow:arrow_entity") + local obj = minetest.add_entity(pos, + "shooter_crossbow:arrow_entity") local ent = nil if obj then ent = obj:get_luaentity() end if ent then - ent.player = ent.player or user + ent.user = user:get_player_name() ent.state = "flight" ent.color = color obj:set_properties({ textures = {get_texture("arrow_uv", color)} }) - minetest.sound_play("shooter_throw", {object=obj}) + minetest.sound_play("shooter_throw", {object=obj}) local frame = get_animation_frame(dir) - obj:setyaw(yaw + math.pi) + obj:set_yaw(yaw - math.pi / 2) obj:set_animation({x=frame, y=frame}, 0) - obj:setvelocity({x=dir.x * 14, y=dir.y * 14, z=dir.z * 14}) - if pointed_thing.type ~= "nothing" then - local ppos = minetest.get_pointed_thing_position(pointed_thing, false) - local _, npos = minetest.line_of_sight(pos, ppos, 1) - if npos then - ppos = npos - pointed_thing.type = "node" - end - if pointed_thing.type == "object" then - ent:strike(pointed_thing.ref) - return itemstack - elseif pointed_thing.type == "node" then - local node = minetest.get_node(ppos) - local tpos = get_target_pos(pos, ppos, dir, 0.66) - minetest.after(0.2, function(object, pos, npos) - ent.node_pos = npos - ent.state = "stuck" - ent:stop(pos) - shooter:play_node_sound(node, npos) - end, obj, tpos, ppos) - return itemstack - end + obj:set_velocity({x=dir.x * 14, y=dir.y * 14, z=dir.z * 14}) + obj:set_acceleration({x=dir.x * -3, y=-5, z=dir.z * -3}) + pointed_thing = get_pointed_thing(pos, dir, 5) + if pointed_thing then + strike(ent, pointed_thing, ent.user) end - obj:setacceleration({x=dir.x * -3, y=-5, z=dir.z * -3}) end end return itemstack diff --git a/shooter_crossbow/models/shooter_arrow.b3d b/shooter_crossbow/models/shooter_arrow.b3d index d24be3c..a3de778 100644 Binary files a/shooter_crossbow/models/shooter_arrow.b3d and b/shooter_crossbow/models/shooter_arrow.b3d differ diff --git a/shooter_flaregun/init.lua b/shooter_flaregun/init.lua index 7cd9270..f26e4f1 100644 --- a/shooter_flaregun/init.lua +++ b/shooter_flaregun/init.lua @@ -12,7 +12,7 @@ minetest.register_node("shooter_flaregun:flare_light", { walkable = false, buildable_to = true, sunlight_propagates = true, - light_source = LIGHT_MAX, + light_source = 14, pointable = false, }) @@ -47,7 +47,7 @@ minetest.register_entity("shooter_flaregun:flare_entity", { "shooter_flare.png", "shooter_flare.png", }, - player = nil, + glow = 14, collisionbox = {-1/16,-1/16,-1/16, 1/16,1/16,1/16}, on_activate = function(self, staticdata) if staticdata == "expired" then @@ -57,29 +57,41 @@ minetest.register_entity("shooter_flaregun:flare_entity", { on_step = function(self, dtime) self.timer = self.timer + dtime if self.timer > 0.2 then - local pos = self.object:getpos() + local pos = self.object:get_pos() local below = {x=pos.x, y=pos.y - 1, z=pos.z} local node = minetest.get_node(below) if node.name ~= "air" then - self.object:setvelocity({x=0, y=-10, z=0}) - self.object:setacceleration({x=0, y=0, z=0}) + self.object:set_velocity({x=0, y=-10, z=0}) + self.object:set_acceleration({x=0, y=0, z=0}) if minetest.get_node(pos).name == "air" and node.name ~= "default:water_source" and node.name ~= "default:water_flowing" then minetest.place_node(pos, {name="shooter_flaregun:flare_light"}) local meta = minetest.get_meta(pos) pos.y = pos.y - 0.1 - local id = minetest.add_particlespawner( - 1000, 30, pos, pos, - {x=-1, y=1, z=-1}, {x=1, y=1, z=1}, - {x=2, y=-2, z=-2}, {x=2, y=-2, z=2}, - 0.1, 0.75, 1, 8, false, "shooter_flare_particle.png" - ) + local id = minetest.add_particlespawner({ + amount = 1000, + time = 30, + minpos = pos, + maxpos = pos, + minvel = {x=-1, y=1, z=-1}, + maxvel = {x=1, y=1, z=1}, + minacc = {x=2, y=-2, z=-2}, + maxacc = {x=2, y=-2, z=2}, + minexptime = 0.1, + maxexptime = 0.75, + minsize = 1, + maxsize = 8, + collisiondetection = false, + texture = "shooter_flare_particle.png", + glow = 14, + }) meta:set_int("particle_id", id) meta:set_int("init_time", os.time()) local sound = minetest.sound_play("shooter_flare_burn", { - object = self.player, + pos = pos, loop = true, + max_hear_distance = 8, }) minetest.after(30, function(sound) minetest.sound_stop(sound) @@ -106,23 +118,19 @@ minetest.register_tool("shooter_flaregun:flaregun", { end if not minetest.setting_getbool("creative_mode") then inv:remove_item("main", "shooter:flare 1") - itemstack:add_wear(65535/100) + itemstack:add_wear(65535 / 100) end - local pos = user:getpos() + local pos = user:get_pos() local dir = user:get_look_dir() - local yaw = user:get_look_yaw() + local yaw = user:get_look_horizontal() if pos and dir and yaw then pos.y = pos.y + 1.5 local obj = minetest.add_entity(pos, "shooter_flaregun:flare_entity") if obj then minetest.sound_play("shooter_flare_fire", {object=obj}) - obj:setvelocity({x=dir.x * 16, y=dir.y * 16, z=dir.z * 16}) - obj:setacceleration({x=dir.x * -3, y=-10, z=dir.z * -3}) - obj:setyaw(yaw + math.pi) - local ent = obj:get_luaentity() - if ent then - ent.player = ent.player or user - end + obj:set_velocity(vector.multiply(dir, 16)) + obj:set_acceleration({x=dir.x * -3, y=-10, z=dir.z * -3}) + obj:set_yaw(yaw + math.pi / 2) end end return itemstack diff --git a/shooter_grenade/init.lua b/shooter_grenade/init.lua index e674be3..7d08d50 100644 --- a/shooter_grenade/init.lua +++ b/shooter_grenade/init.lua @@ -11,7 +11,7 @@ minetest.register_entity("shooter_grenade:grenade_entity", { "shooter_grenade.png", "shooter_grenade.png", }, - player = nil, + user = nil, collisionbox = {0,0,0, 0,0,0}, on_activate = function(self, staticdata) if staticdata == "expired" then @@ -21,11 +21,16 @@ minetest.register_entity("shooter_grenade:grenade_entity", { on_step = function(self, dtime) self.timer = self.timer + dtime if self.timer > 0.2 then - local pos = self.object:getpos() + local pos = self.object:get_pos() local above = {x=pos.x, y=pos.y + 1, z=pos.z} if minetest.get_node(pos).name ~= "air" then + if self.user then + local player = minetest.get_player_by_name(self.user) + if player then + shooter:blast(above, 2, 25, 5, player) + end + end self.object:remove() - shooter:blast(above, 2, 25, 5, self.player) end self.timer = 0 end @@ -40,28 +45,29 @@ minetest.register_tool("shooter_grenade:grenade", { inventory_image = "shooter_hand_grenade.png", on_use = function(itemstack, user, pointed_thing) if not minetest.setting_getbool("creative_mode") then - itemstack = "" + itemstack:clear() end if pointed_thing.type ~= "nothing" then local pointed = minetest.get_pointed_thing_position(pointed_thing) - if vector.distance(user:getpos(), pointed) < 8 then + if vector.distance(user:get_pos(), pointed) < 8 then shooter:blast(pointed, 1, 25, 5) return end end - local pos = user:getpos() + local pos = user:get_pos() local dir = user:get_look_dir() - local yaw = user:get_look_yaw() + local yaw = user:get_look_horizontal() if pos and dir then - pos.y = pos.y + 1.5 + pos.y = pos.y + shooter.config.camera_height local obj = minetest.add_entity(pos, "shooter_grenade:grenade_entity") if obj then - obj:setvelocity({x=dir.x * 15, y=dir.y * 15, z=dir.z * 15}) - obj:setacceleration({x=dir.x * -3, y=-10, z=dir.z * -3}) - obj:setyaw(yaw + math.pi) + minetest.sound_play("shooter_throw", {object=obj}) + obj:set_velocity(vector.multiply(dir, 15)) + obj:set_acceleration({x=dir.x * -3, y=-10, z=dir.z * -3}) + obj:set_yaw(yaw + math.pi / 2) local ent = obj:get_luaentity() if ent then - ent.player = ent.player or user + ent.user = user:get_player_name() end end end diff --git a/shooter_hook/init.lua b/shooter_hook/init.lua index 671f6d7..5e8639d 100644 --- a/shooter_hook/init.lua +++ b/shooter_hook/init.lua @@ -1,22 +1,22 @@ local function throw_hook(itemstack, user, vel) local inv = user:get_inventory() - local pos = user:getpos() + local pos = user:get_pos() local dir = user:get_look_dir() - local yaw = user:get_look_yaw() + local yaw = user:get_look_horizontal() if pos and dir and yaw then if not minetest.setting_getbool("creative_mode") then - itemstack:add_wear(65535/100) + itemstack:add_wear(65535 / 100) end pos.y = pos.y + 1.5 local obj = minetest.add_entity(pos, "shooter_hook:hook") if obj then minetest.sound_play("shooter_throw", {object=obj}) - obj:setvelocity({x=dir.x * vel, y=dir.y * vel, z=dir.z * vel}) - obj:setacceleration({x=dir.x * -3, y=-10, z=dir.z * -3}) - obj:setyaw(yaw + math.pi) + obj:set_velocity(vector.multiply(dir, vel)) + obj:set_acceleration({x=dir.x * -3, y=-10, z=dir.z * -3}) + obj:set_yaw(yaw + math.pi / 2) local ent = obj:get_luaentity() if ent then - ent.player = ent.player or user + ent.user = user:get_player_name() ent.itemstack = itemstack end end @@ -29,7 +29,7 @@ minetest.register_entity("shooter_hook:hook", { visual = "wielditem", visual_size = {x=1/2, y=1/2}, textures = {"shooter_hook:grapple_hook"}, - player = nil, + user = nil, itemstack = "", collisionbox = {-1/4,-1/4,-1/4, 1/4,1/4,1/4}, on_activate = function(self, staticdata) @@ -39,20 +39,23 @@ minetest.register_entity("shooter_hook:hook", { end end, on_step = function(self, dtime) - if not self.player then + if not self.user then return end self.timer = self.timer + dtime if self.timer > 0.25 then - local pos = self.object:getpos() + local pos = self.object:get_pos() local below = {x=pos.x, y=pos.y - 1, z=pos.z} local node = minetest.get_node(below) if node.name ~= "air" then - self.object:setvelocity({x=0, y=-10, z=0}) - self.object:setacceleration({x=0, y=0, z=0}) + self.object:set_velocity({x=0, y=-10, z=0}) + self.object:set_acceleration({x=0, y=0, z=0}) if minetest.get_item_group(node.name, "liquid") == 0 and minetest.get_node(pos).name == "air" then - self.player:moveto(pos) + local player = minetest.get_player_by_name(self.user) + if player then + player:moveto(pos) + end end if minetest.get_item_group(node.name, "lava") == 0 then minetest.add_item(pos, self.itemstack) diff --git a/shooter_rocket/init.lua b/shooter_rocket/init.lua index 45d1bcc..d4ea153 100644 --- a/shooter_rocket/init.lua +++ b/shooter_rocket/init.lua @@ -17,7 +17,7 @@ minetest.register_entity("shooter_rocket:rocket_entity", { "shooter_bullet.png", "shooter_bullet.png", }, - player = nil, + user = nil, collisionbox = {0,0,0, 0,0,0}, on_activate = function(self, staticdata) if staticdata == "expired" then @@ -27,11 +27,16 @@ minetest.register_entity("shooter_rocket:rocket_entity", { on_step = function(self, dtime) self.timer = self.timer + dtime if self.timer > 0.2 then - local pos = self.object:getpos() + local pos = self.object:get_pos() local above = {x=pos.x, y=pos.y + 1, z=pos.z} if minetest.get_node(pos).name ~= "air" then + if self.user then + local player = minetest.get_player_by_name(self.user) + if player then + shooter:blast(above, 4, 50, 8, player) + end + end self.object:remove() - shooter:blast(above, 4, 50, 8, self.player) end self.timer = 0 end @@ -47,30 +52,30 @@ minetest.register_tool("shooter_rocket:rocket_gun_loaded", { groups = {not_in_creative_inventory=1}, on_use = function(itemstack, user, pointed_thing) if not minetest.setting_getbool("creative_mode") then - itemstack:add_wear(65535/50) + itemstack:add_wear(65535 / 50) end itemstack = "shooter_rocket:rocket_gun 1 "..itemstack:get_wear() if pointed_thing.type ~= "nothing" then local pointed = minetest.get_pointed_thing_position(pointed_thing) - if vector.distance(user:getpos(), pointed) < 8 then + if vector.distance(user:get_pos(), pointed) < 8 then shooter:blast(pointed, 2, 50, 7) return itemstack end end - local pos = user:getpos() + local pos = user:get_pos() local dir = user:get_look_dir() - local yaw = user:get_look_yaw() + local yaw = user:get_look_horizontal() if pos and dir and yaw then - pos.y = pos.y + 1.5 + pos.y = pos.y + shooter.config.camera_height local obj = minetest.add_entity(pos, "shooter_rocket:rocket_entity") if obj then minetest.sound_play("shooter_rocket_fire", {object=obj}) - obj:setvelocity({x=dir.x * 20, y=dir.y * 20, z=dir.z * 20}) - obj:setacceleration({x=dir.x * -3, y=-10, z=dir.z * -3}) - obj:setyaw(yaw + math.pi) + obj:set_velocity(vector.multiply(dir, 20)) + obj:set_acceleration({x=dir.x * -3, y=-10, z=dir.z * -3}) + obj:set_yaw(yaw + math.pi / 2) local ent = obj:get_luaentity() if ent then - ent.player = ent.player or user + ent.user = user:get_player_name() end end end diff --git a/shooter_turret/depends.txt b/shooter_turret/depends.txt index 91ee42b..554434c 100644 --- a/shooter_turret/depends.txt +++ b/shooter_turret/depends.txt @@ -1 +1,2 @@ -shooter +shooter_rocket +player_api? diff --git a/shooter_turret/init.lua b/shooter_turret/init.lua index 645e828..e66376d 100644 --- a/shooter_turret/init.lua +++ b/shooter_turret/init.lua @@ -1,3 +1,5 @@ +local use_player_api = minetest.get_modpath("player_api") + local function get_turret_entity(pos) local entity = nil local objects = minetest.get_objects_inside_radius(pos, 1) @@ -17,42 +19,6 @@ local function get_turret_entity(pos) return entity end -minetest.register_entity("shooter_turret:tnt_entity", { - physical = false, - timer = 0, - visual = "cube", - visual_size = {x=1/4, y=1/4}, - textures = { - "tnt_top.png", - "tnt_bottom.png", - "tnt_side.png", - "tnt_side.png", - "tnt_side.png", - "tnt_side.png", - }, - player = nil, - collisionbox = {0,0,0, 0,0,0}, - on_activate = function(self, staticdata) - if staticdata == "expired" then - self.object:remove() - end - end, - on_step = function(self, dtime) - self.timer = self.timer + dtime - if self.timer > 0.2 then - local pos = self.object:getpos() - if minetest.get_node(pos).name ~= "air" then - self.object:remove() - shooter:blast(pos, 4, 80, 10, self.player) - end - self.timer = 0 - end - end, - get_staticdata = function(self) - return "expired" - end, -}) - minetest.register_entity("shooter_turret:turret_entity", { physical = true, visual = "mesh", @@ -63,13 +29,13 @@ minetest.register_entity("shooter_turret:turret_entity", { "shooter_turret_uv.png", }, timer = 0, - player = nil, + user = nil, pitch = 40, yaw = 0, firing = false, on_activate = function(self, staticdata) - self.pos = self.object:getpos() - self.yaw = self.object:getyaw() + self.pos = self.object:get_pos() + self.yaw = self.object:get_yaw() if minetest.get_node(self.pos).name ~= "shooter_turret:turret" then self.object:remove() return @@ -80,23 +46,36 @@ minetest.register_entity("shooter_turret:turret_entity", { get_turret_entity(self.pos) end, on_rightclick = function(self, clicker) - if self.player then - self.player:set_detach() - self.player = nil + if self.user then + local player = minetest.get_player_by_name(self.user) + if player then + player:set_detach() + if use_player_api then + player_api.player_attached[self.user] = false + end + end + self.user = nil else - clicker:set_attach(self.object, "", {x=0,y=5,z=-8}, {x=0,y=0,z=0}) - self.player = clicker + clicker:set_attach(self.object, "", {x=0,y=-5,z=-8}, {x=0,y=0,z=0}) + self.user = clicker:get_player_name() + if use_player_api then + player_api.player_attached[self.user] = true + end end end, on_step = function(self, dtime) - self.timer = self.timer + dtime - if self.timer < 0.1 then + if not self.user then return - end - if self.player then + end + self.timer = self.timer + dtime + if self.timer < 0.2 then + return + end + local player = minetest.get_player_by_name(self.user) + if player then local pitch = self.pitch - local yaw = self.object:getyaw() - local ctrl = self.player:get_player_control() + local yaw = self.object:get_yaw() + local ctrl = player:get_player_control() local step = 2 if ctrl then if ctrl.sneak then @@ -130,7 +109,7 @@ minetest.register_entity("shooter_turret:turret_entity", { self.pitch = pitch end if self.yaw ~= yaw then - self.object:setyaw(yaw) + self.object:set_yaw(yaw) self.yaw = yaw end end @@ -138,19 +117,20 @@ minetest.register_entity("shooter_turret:turret_entity", { self.timer = 0 end, fire = function(self) + if not self.user then + return + end local meta = minetest.get_meta(self.pos) local inv = meta:get_inventory() if not inv then return end - if not inv:contains_item("main", "tnt:tnt") then + if not inv:contains_item("main", "shooter_rocket:rocket") then minetest.sound_play("shooter_click", {object=self.object}) return end + inv:remove_item("main", "shooter_rocket:rocket") minetest.sound_play("shooter_shotgun", {object=self.object}) - if not minetest.setting_getbool("creative_mode") then - inv:remove_item("main", "tnt:tnt") - end local pitch = math.rad(self.pitch - 40) local len = math.cos(pitch) local dir = vector.normalize({ @@ -159,26 +139,35 @@ minetest.register_entity("shooter_turret:turret_entity", { z = len * math.cos(self.yaw), }) local pos = {x=self.pos.x, y=self.pos.y + 0.87, z=self.pos.z} - pos = vector.add(pos, {x=dir.x * 1.5, y=dir.y * 1.5, z=dir.z * 1.5}) - local obj = minetest.add_entity(pos, "shooter_turret:tnt_entity") + pos = vector.add(pos, vector.multiply(dir, 1.5)) + local obj = minetest.add_entity(pos, "shooter_rocket:rocket_entity") if obj then local ent = obj:get_luaentity() if ent then minetest.sound_play("shooter_rocket_fire", {object=obj}) - ent.player = self.player - obj:setyaw(self.yaw) - obj:setvelocity({x=dir.x * 20, y=dir.y * 20, z=dir.z * 20}) - obj:setacceleration({x=dir.x * -3, y=-10, z=dir.z * -3}) + ent.user = self.user + obj:set_yaw(self.yaw) + obj:set_velocity(vector.multiply(dir, 30)) + obj:set_acceleration({x=dir.x * -3, y=-10, z=dir.z * -3}) end end if shooter.config.enable_particle_fx == true then - minetest.add_particlespawner(10, 0.1, - {x=pos.x - 1, y=pos.y - 1, z=pos.z - 1}, - {x=pos.x + 1, y=pos.y + 1, z=pos.z + 1}, - {x=0, y=0, z=0}, {x=0, y=0, z=0}, - {x=-0.5, y=-0.5, z=-0.5}, {x=0.5, y=0.5, z=0.5}, - 0.1, 1, 8, 15, false, "tnt_smoke.png" - ) + minetest.add_particlespawner({ + amount = 10, + time = 0.1, + minpos = {x=pos.x - 1, y=pos.y - 1, z=pos.z - 1}, + maxpos = {x=pos.x + 1, y=pos.y + 1, z=pos.z + 1}, + minvel = {x=0, y=0, z=0}, + maxvel = {x=0, y=0, z=0}, + minacc = {x=-0.5, y=-0.5, z=-0.5}, + maxacc = {x=0.5, y=0.5, z=0.5}, + minexptime = 0.1, + maxexptime = 1, + minsize = 8, + maxsize = 15, + collisiondetection = false, + texture = "tnt_smoke.png", + }) end end }) @@ -191,7 +180,7 @@ minetest.register_node("shooter_turret:turret", { drawtype = "nodebox", paramtype = "light", paramtype2 = "facedir", - groups = {snappy=2,choppy=2,oddly_breakable_by_hand=3}, + groups = {snappy=2, choppy=2, oddly_breakable_by_hand=3}, node_box = { type = "fixed", fixed = { @@ -207,7 +196,8 @@ minetest.register_node("shooter_turret:turret", { local meta = minetest.get_meta(pos) meta:set_string("formspec", "size[8,9]".. "list[current_name;main;2,0;4,4;]".. - "list[current_player;main;0,5;8,4;]" + "list[current_player;main;0,5;8,4;]".. + "listring[]" ) meta:set_string("infotext", "Turret Gun") local inv = meta:get_inventory() diff --git a/shooter_turret/models/shooter_turret.b3d b/shooter_turret/models/shooter_turret.b3d index 8aa291c..da63011 100644 Binary files a/shooter_turret/models/shooter_turret.b3d and b/shooter_turret/models/shooter_turret.b3d differ