1
0
mirror of https://gitlab.com/echoes91/spears.git synced 2025-06-30 22:50:21 +02:00

7 Commits
2.4 ... fix

Author SHA1 Message Date
b888cda310 fix itemframes issue nalc/nalc-server-mods#103
fix deployer issue nalc/nalc-server-mods#104
fix deprecated function
fix bad/Nonexistent collision detection on mobs/players, use collision box for very good detection
add translation client side
2022-07-21 17:35:07 +02:00
e2182ca004 Delete depends.txt, add mod.conf 2022-07-02 21:36:09 +02:00
a5b33a6e9a Fix crash 2020-08-09 00:58:12 +02:00
8770387fbc Change craft recipes that conflict with throwing mod 2020-08-08 23:46:38 +02:00
66c69c5265 Fix undeclared global variable warning at startup
DISABLE_GOLD_SPEAR
2020-06-20 16:31:26 +02:00
662e637595 Merge remote-tracking branch 'upstream/master' into nalc-1.2-dev 2020-06-14 22:16:47 +02:00
63d339a686 Corrige avertissement sur variable globale 2018-12-24 01:14:12 +01:00
11 changed files with 170 additions and 163 deletions

View File

@ -1,8 +1,3 @@
Version 2.3:
- Updated to Minetest 5.6.0 API
- Changed receipts to avoid being confused with arrows
- Various cleansing and fixes
Version 2.2:
- "Hit detection" based on spearhead position
- Spears go through buildable_to nodes (snow)

7
README
View File

@ -12,17 +12,14 @@ How to install:
http://wiki.minetest.com/wiki/Installing_Mods
How to use the mod:
Craft a spear with | | | (material) |
| | stick | |
| stick | | |,
works also mirrored.
Craft a spear with | stick | stick | (material) |, works also mirrored.
Spears can be thrown using right mouse button, they either hurt someone or stick where they land on; damage depends on speed and material, flight trajectory is ballistic with (unrealistic) drag.
Spears can be used to fight, but are slower and weaker than swords.
Spears can be used to dig, but are slower and weaker and pickaxes.
If you miss the target it's your fault, the spear is fine.
You can grab a spear on the fly (or maybe wait until it falls?).
You can stick a spear into a block, but if you remove the block then the spear falls (obviously).
This mod contains the word "spear" more than 100 times, if you want the exact number you can count them.
This mod contains the word "spear" more than 100 times, if you want the exact number count them yourself.
If you feel clever, throw a spear right above you and look at it to see what happens.
You can even throw a spear from above down to your foes, it's even easier to hit.
Someone once reported to have hit its own foot but it takes practice to do that.

View File

@ -5,12 +5,3 @@ DISABLE_BRONZE_SPEAR = false
DISABLE_DIAMOND_SPEAR = false
DISABLE_OBSIDIAN_SPEAR = false
DISABLE_GOLD_SPEAR = false
DISABLE_IRON_SPEAR = false
SPEARS_THROW_SPEED = 13
SPEARS_V_ZERO = {x = 0, y = 0, z = 0}
SPEARS_DRAG_COEFF = 0.1
SPEARS_NODE_UNKNOWN = nil
SPEARS_NODE_THROUGH = 0
SPEARS_NODE_STICKY = 1
SPEARS_NODE_CRACKY = 2
SPEARS_NODE_CRACKY_LIMIT = 3

View File

@ -7,39 +7,36 @@ function spears_throw (itemstack, player, pointed_thing)
local pitch = player:get_look_vertical()
local yaw = player:get_look_horizontal()
local rotation = vector.new(0, yaw + math.pi/2, pitch + math.pi/6)
local wear = itemstack:get_wear()
local pointed_a = pointed_thing.above
local pointed_b = pointed_thing.under
if pointed_thing.type == "node" and vector.distance(pointed_a, throw_pos) < 1 then -- Stick into node
local node = minetest.get_node(pointed_b)
local check_node = spears_check_node(node.name)
if check_node == SPEARS_NODE_UNKNOWN then
return false
elseif check_node == SPEARS_NODE_CRACKY then
minetest.sound_play("default_metal_footstep", {pos = pointed_a}, true)
return false
elseif check_node == SPEARS_NODE_STICKY then
local spear_object = minetest.add_entity(vector.divide(vector.add(vector.multiply(pointed_a, 2), pointed_b), 3), spear)
-- Plant into node
if pointed_thing.type == "node" then
local node = minetest.get_node(pointed_thing.under)
if minetest.registered_nodes[node.name].walkable and vector.distance(pointed_thing.above, throw_pos) < 1 then
local spear_object = minetest.add_entity(vector.divide(vector.add(vector.multiply(pointed_thing.above, 2), pointed_thing.under), 3), spear)
spear_object:set_rotation(rotation)
spear_object:get_luaentity()._wear = wear
spear_object:get_luaentity()._stickpos = pointed_b
minetest.sound_play("default_place_node", {pos = pointed_a}, true)
return false
spear_object:get_luaentity()._wear = itemstack:get_wear()
spear_object:get_luaentity()._stickpos = pointed_thing.under
return
end
else -- Avoid hitting yourself and throw
local throw_speed = SPEARS_THROW_SPEED
end
-- Avoid hitting yourself and throw
local throw_speed = 12
while vector.distance(player_pos, throw_pos) < 1.2 do
throw_pos = vector.add(throw_pos, vector.multiply(direction, 0.1))
end
local player_vel = player:get_velocity()
local player_vel
if player.is_fake_player then
player_vel = {x=0,y=0,z=0}
else
player_vel = player:get_velocity()
end
local spear_object = minetest.add_entity(throw_pos, spear)
spear_object:set_velocity(vector.add(player_vel, vector.multiply(direction, throw_speed)))
spear_object:set_rotation(rotation)
minetest.sound_play("spears_throw", {pos = player_pos}, true)
spear_object:get_luaentity()._wear = wear
spear_object:get_luaentity()._wear = itemstack:get_wear()
spear_object:get_luaentity().lastpos = throw_pos
spear_object:get_luaentity()._stickpos = nil
return true
end
end
function spears_set_entity(spear_type, base_damage, toughness)
@ -50,6 +47,7 @@ function spears_set_entity(spear_type, base_damage, toughness)
visual_size = {x = 0.3, y = 0.3, z = 0.3},
wield_item = "spears:spear_" .. spear_type,
collisionbox = {-0.3, -0.3, -0.3, 0.3, 0.3, 0.3},
lastpos={},
},
on_activate = function (self, staticdata, dtime_s)
@ -68,98 +66,116 @@ function spears_set_entity(spear_type, base_damage, toughness)
end,
on_step = function(self, dtime)
local wear = self._wear
if wear == nil then
if not self._wear then
self.object:remove()
return false
return
end
local pos = self.object:get_pos()
local velocity = self.object:get_velocity()
local speed = vector.length(velocity)
if self._stickpos ~= nil then -- Spear is stuck
-- Spear is stuck ?
if self._stickpos then
local node = minetest.get_node(self._stickpos)
local check_node = spears_check_node(node.name)
if check_node ~= SPEARS_NODE_STICKY then -- Fall when node is removed
local node_cracky = minetest.registered_nodes[node.name].groups.cracky
local pos = self.object:get_pos()
if node_cracky and node_cracky < 3 then
minetest.sound_play("default_metal_footstep", {pos = pos}, true)
self.object:remove()
minetest.add_item(pos, {name='spears:spear_' .. spear_type, wear = wear})
return false
minetest.add_item(pos, {name='spears:spear_' .. spear_type, wear = self._wear})
elseif not self._node_walkable then
minetest.sound_play("default_place_node", {pos = self._stickpos}, true)
end
self._node_walkable = minetest.registered_nodes[node.name].walkable
if not node or not self._node_walkable then -- Fall when node is removed
self.object:remove()
minetest.add_item(pos, {name='spears:spear_' .. spear_type, wear = self._wear})
return
end
else -- Spear is flying
local newpos = self.object:get_pos()
for _, pos in pairs(spears_get_trajectoire(self, newpos)) do
local direction = vector.normalize(velocity)
local yaw = minetest.dir_to_yaw(direction)
local pitch = math.acos(velocity.y/speed) - math.pi/3
local spearhead_pos = vector.add(pos, vector.multiply(direction, 0.5))
local node = minetest.get_node(spearhead_pos)
self.object:set_rotation({x = 0, y = yaw + math.pi/2, z = pitch})
-- Hit someone?
local objects_in_radius = minetest.get_objects_inside_radius(spearhead_pos, 0.6)
local objects_in_radius = minetest.get_objects_inside_radius(spearhead_pos, 2.5)
for _,object in ipairs(objects_in_radius) do
if object:get_luaentity() ~= self and object:get_armor_groups().fleshy then
local objpos = object:get_pos()
local collisionbox = object:get_properties().collisionbox or {-0.5, -0.5, -0.5, 0.5, 0.5, 0.5}
if spears_touch(spearhead_pos, objpos, collisionbox) then
local damage = (speed + base_damage)^1.15 - 20
object:punch(self.object, 1.0, {full_punch_interval = 1.0, damage_groups = {fleshy=damage},}, direction)
self.object:remove()
minetest.sound_play("spears_hit", {pos = pos}, true)
wear = spears_wear(wear, toughness)
minetest.add_item(pos, {name='spears:spear_' .. spear_type, wear = wear})
return true
minetest.add_item(pos, {name='spears:spear_' .. spear_type, wear = self._wear + 65535/toughness})
return
end
end
end
-- Hit a node?
local node = minetest.get_node(spearhead_pos)
local check_node = spears_check_node(node.name)
if check_node == SPEARS_NODE_UNKNOWN then
self.object:remove()
minetest.add_item(pos, {name='spears:spear_' .. spear_type, wear = wear})
elseif check_node ~= SPEARS_NODE_THROUGH then
wear = spears_wear(wear, toughness)
if wear >= 65535 then
if node and minetest.registered_nodes[node.name].walkable
and not minetest.registered_nodes[node.name].buildable_to
and not (minetest.registered_nodes[node.name].groups.slab and spearhead_pos.y % 1 < 0.5)
then -- Stick
self.object:set_acceleration({x = 0, y = 0, z = 0})
self.object:set_velocity({x = 0, y = 0, z = 0})
self._wear = self._wear + 65535/toughness
if self._wear >= 65535 then
minetest.sound_play("default_tool_breaks", {pos = pos}, true)
self.object:remove()
minetest.add_item(pos, {name='defaut:stick'})
return false
elseif check_node == SPEARS_NODE_CRACKY then
minetest.sound_play("default_metal_footstep", {pos = pos}, true)
self.object:remove()
minetest.add_item(pos, {name='spears:spear_' .. spear_type, wear = wear})
return false
elseif check_node == SPEARS_NODE_STICKY then
self.object:set_acceleration(SPEARS_V_ZERO)
self.object:set_velocity(SPEARS_V_ZERO)
minetest.sound_play("default_place_node", {pos = pos}, true)
self._stickpos = spearhead_pos
self._wear = wear
return
end
self._stickpos = spearhead_pos
self.lastpos = pos
return
else -- Get drag
local viscosity = minetest.registered_nodes[node.name].liquid_viscosity
local drag = math.max(viscosity, SPEARS_DRAG_COEFF)
local drag = math.max(minetest.registered_nodes[node.name].liquid_viscosity, 0.1)
local acceleration = vector.multiply(velocity, -drag)
acceleration.y = acceleration.y - 10 * ((7 - drag) / 7)
self.object:set_acceleration(acceleration)
end
end
self.lastpos = newpos
end
end,
}
return SPEAR_ENTITY
end
function spears_check_node(node_name)
local node = minetest.registered_nodes[node_name]
if node == nil then
return SPEARS_NODE_UNKNOWN
elseif node.groups.cracky ~= nil and node.groups.cracky < SPEARS_NODE_CRACKY_LIMIT then
return SPEARS_NODE_CRACKY
elseif node.walkable and not node.buildable then
return SPEARS_NODE_STICKY
else
return SPEARS_NODE_THROUGH
function spears_get_trajectoire(self, newpos)
if self.lastpos.x == nil then
return {newpos}
end
local coord = {}
local dx = vector.distance({x=newpos["x"], y=0, z=0}, {x=self.lastpos["x"], y=0, z=0} )/2
local dy = vector.distance({x=0, y=newpos["y"], z=0}, {x=0, y=self.lastpos["y"], z=0} )/2
local dz = vector.distance({x=0, y=0, z=newpos["z"]}, {x=0, y=0, z=self.lastpos["z"]} )/2
if newpos["x"] < self.lastpos["x"] then
dx = -dx
end
if newpos["y"] < self.lastpos["y"] then
dy = -dy
end
if newpos["z"] < self.lastpos["z"] then
dz = -dz
end
table.insert(coord, {x=self.lastpos["x"]+dx, y=self.lastpos["y"]+dy ,z=self.lastpos["z"]+dz })
table.insert(coord, newpos)
return coord
end
function spears_wear(initial_wear, toughness)
if not minetest.settings:get_bool("creative_mode") then
local wear = initial_wear + 65535/toughness
return wear
else
local wear = initial_wear
return wear
function spears_touch(pos, objpos, cbox)
--colbox format {x1, y1, z1, x2, y2, z2}
if (pos.x < objpos.x + math.max(cbox[1], cbox[4]) and pos.x > objpos.x + math.min(cbox[1], cbox[4]))
and (pos.y < objpos.y + math.max(cbox[2], cbox[5]) and pos.y > objpos.y + math.min(cbox[2], cbox[5]))
and (pos.z < objpos.z + math.max(cbox[3], cbox[6]) and pos.z > objpos.z + math.min(cbox[3], cbox[6])) then
return true
end
return false
end

View File

@ -11,8 +11,5 @@ dofile(minetest.get_modpath("spears").."/functions.lua")
dofile(minetest.get_modpath("spears").."/tools.lua")
local log_mods = minetest.settings:get_bool("log_mods")
if minetest.settings:get_bool("log_mods") then
minetest.log("action", "[MOD] Spears loaded")
end
minetest.log("action", "[spears] loaded.")

9
locale/spears.fr.tr Normal file
View File

@ -0,0 +1,9 @@
# textdomain: spears
Stone spear=Lance en pierre
Steel spear=Lance en acier
Copper spear=Lance en cuivre
Bronze spear=Lance en bronze
Obsidian spear=Lance en obsidienne
Diamond spear=Lance en diamant
Golden spear=Lance en or

11
locale/template.txt Normal file
View File

@ -0,0 +1,11 @@
# textdomain: spears
Stone spear=
Steel spear=
Copper spear=
Bronze spear=
Obsidian spear=
Diamond spear=
Golden spear=

View File

@ -1,7 +1,4 @@
name = spears
title = Separs
description = Add spears to Minetest
depends = default
description = Add spears to Minetest, versatile weapons that can be thrown
author = Echoes91
title = Spears
min_minetest_version = 5.4

View File

@ -4,5 +4,3 @@ DISABLE_COPPER_SPEAR = true
DISABLE_BRONZE_SPEAR = true
DISABLE_DIAMOND_SPEAR = true
DISABLE_OBSIDIAN_SPEAR = true
DISABLE_GOLD_SPEAR = true
SPEARS_THROW_SPEED = 13

Binary file not shown.

Before

Width:  |  Height:  |  Size: 223 B

View File

@ -1,7 +1,10 @@
local S = minetest.get_translator("spears")
function spears_register_spear(spear_type, desc, base_damage, toughness, material)
minetest.register_tool("spears:spear_" .. spear_type, {
description = desc .. " spear",
description = S(desc .. " spear"),
wield_image = "spears_spear_" .. spear_type .. ".png^[transform4",
inventory_image = "spears_spear_" .. spear_type .. ".png",
wield_scale= {x = 1.5, y = 1.5, z = 1.5},
@ -13,6 +16,13 @@ function spears_register_spear(spear_type, desc, base_damage, toughness, materia
return itemstack
end,
on_place = function(itemstack, user, pointed_thing)
if pointed_thing.type == "node" then
local node = minetest.get_node(pointed_thing.under)
if minetest.registered_nodes[node.name] and (node.name == "itemframes:pedestal" or node.name == "itemframes:frame") then
minetest.registered_nodes[node.name].on_rightclick(pointed_thing.under, node, user, itemstack)
return itemstack
end
end
spears_throw(itemstack, user, pointed_thing)
if not minetest.settings:get_bool("creative_mode") then
itemstack:take_item()
@ -38,18 +48,18 @@ function spears_register_spear(spear_type, desc, base_damage, toughness, materia
minetest.register_craft({
output = 'spears:spear_' .. spear_type,
recipe = {
{"", "", material},
{"", "group:stick", ""},
{"group:stick", "", ""}
{'', '', material},
{'', 'group:stick', ''},
{'group:stick', '', ''},
}
})
minetest.register_craft({
output = 'spears:spear_' .. spear_type,
recipe = {
{material, "", ""},
{"", "group:stick", ""},
{"", "", "group:stick"}
{material, '', ''},
{'', 'group:stick', ''},
{'', '', 'group:stick'},
}
})
end
@ -58,31 +68,17 @@ if not DISABLE_STONE_SPEAR then
spears_register_spear('stone', 'Stone', 4, 20, 'group:stone')
end
if minetest.get_modpath("pigiron") then
if not DISABLE_IRON_SPEAR then
spears_register_spear('iron', 'Iron', 5.5, 30, 'pigiron:iron_ingot')
end
if not DISABLE_STEEL_SPEAR then
spears_register_spear('steel', 'Steel', 6, 35, 'default:steel_ingot')
end
if not DISABLE_COPPER_SPEAR then
spears_register_spear('copper', 'Copper', 4.8, 30, 'default:copper_ingot')
end
if not DISABLE_BRONZE_SPEAR then
spears_register_spear('bronze', 'Bronze', 5.5, 35, 'default:bronze_ingot')
end
else
if not DISABLE_STEEL_SPEAR then
if not DISABLE_STEEL_SPEAR then
spears_register_spear('steel', 'Steel', 6, 30, 'default:steel_ingot')
end
if not DISABLE_COPPER_SPEAR then
spears_register_spear('copper', 'Copper', 5, 30, 'default:copper_ingot')
end
if not DISABLE_BRONZE_SPEAR then
spears_register_spear('bronze', 'Bronze', 6, 35, 'default:bronze_ingot')
end
end
if not DISABLE_COPPER_SPEAR then
spears_register_spear('copper', 'Copper', 5, 35, 'default:copper_ingot')
end
if not DISABLE_BRONZE_SPEAR then
spears_register_spear('bronze', 'Bronze', 6, 35, 'default:bronze_ingot')
end
if not DISABLE_OBSIDIAN_SPEAR then
spears_register_spear('obsidian', 'Obsidian', 8, 30, 'default:obsidian')