mirror of
https://github.com/luanti-org/luanti.git
synced 2026-01-01 10:45:32 +01:00
Clarify that punch toolcaps are not optional (#16720)
This commit is contained in:
@@ -1791,8 +1791,8 @@ bool GenericCAO::directReportPunch(v3f dir, const ItemStack *punchitem,
|
||||
const ItemStack *hand_item, float time_from_last_punch)
|
||||
{
|
||||
assert(punchitem); // pre-condition
|
||||
const ToolCapabilities *toolcap =
|
||||
&punchitem->getToolCapabilities(m_client->idef(), hand_item);
|
||||
const ToolCapabilities &toolcap =
|
||||
punchitem->getToolCapabilities(m_client->idef(), hand_item);
|
||||
PunchDamageResult result = getPunchDamage(
|
||||
m_armor_groups,
|
||||
toolcap,
|
||||
|
||||
@@ -1046,7 +1046,7 @@ void Server::handleCommand_Interact(NetworkPacket *pkt)
|
||||
|
||||
ItemStack selected_item, hand_item;
|
||||
ItemStack tool_item = playersao->getWieldedItem(&selected_item, &hand_item);
|
||||
ToolCapabilities toolcap =
|
||||
const ToolCapabilities &toolcap =
|
||||
tool_item.getToolCapabilities(m_itemdef, &hand_item);
|
||||
v3f dir = (pointed_object->getBasePosition() -
|
||||
(playersao->getBasePosition() + playersao->getEyeOffset())
|
||||
@@ -1054,7 +1054,7 @@ void Server::handleCommand_Interact(NetworkPacket *pkt)
|
||||
float time_from_last_punch =
|
||||
playersao->resetTimeFromLastPunch();
|
||||
|
||||
u32 wear = pointed_object->punch(dir, &toolcap, playersao,
|
||||
u32 wear = pointed_object->punch(dir, toolcap, playersao,
|
||||
time_from_last_punch, tool_item.wear);
|
||||
|
||||
// Callback may have changed item, so get it again
|
||||
|
||||
@@ -1665,9 +1665,11 @@ ToolCapabilities read_tool_capabilities(
|
||||
lua_State *L, int table)
|
||||
{
|
||||
ToolCapabilities toolcap;
|
||||
luaL_checktype(L, table, LUA_TTABLE);
|
||||
getfloatfield(L, table, "full_punch_interval", toolcap.full_punch_interval);
|
||||
getintfield(L, table, "max_drop_level", toolcap.max_drop_level);
|
||||
getintfield(L, table, "punch_attack_uses", toolcap.punch_attack_uses);
|
||||
|
||||
lua_getfield(L, table, "groupcaps");
|
||||
if(lua_istable(L, -1)){
|
||||
int table_groupcaps = lua_gettop(L);
|
||||
@@ -1686,7 +1688,7 @@ ToolCapabilities read_tool_capabilities(
|
||||
float maxwear = 0;
|
||||
if (getfloatfield(L, table_groupcap, "maxwear", maxwear)){
|
||||
if (maxwear != 0)
|
||||
groupcap.uses = 1.0/maxwear;
|
||||
groupcap.uses = 1.0f/maxwear;
|
||||
else
|
||||
groupcap.uses = 0;
|
||||
warningstream << "Field \"maxwear\" is deprecated; "
|
||||
@@ -1748,7 +1750,7 @@ PointabilityType read_pointability_type(lua_State *L, int index)
|
||||
return PointabilityType::POINTABLE_BLOCKING;
|
||||
}
|
||||
}
|
||||
throw LuaError("Invalid pointable type.");
|
||||
throw LuaError("Invalid pointable type");
|
||||
}
|
||||
|
||||
/******************************************************************************/
|
||||
@@ -1756,6 +1758,7 @@ Pointabilities read_pointabilities(lua_State *L, int index)
|
||||
{
|
||||
Pointabilities pointabilities;
|
||||
|
||||
luaL_checktype(L, index, LUA_TTABLE);
|
||||
lua_getfield(L, index, "nodes");
|
||||
if(lua_istable(L, -1)){
|
||||
int ti = lua_gettop(L);
|
||||
@@ -1815,6 +1818,9 @@ void push_pointability_type(lua_State *L, PointabilityType pointable)
|
||||
case PointabilityType::POINTABLE_BLOCKING:
|
||||
lua_pushliteral(L, "blocking");
|
||||
break;
|
||||
default:
|
||||
assert(false);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -247,7 +247,7 @@ void ScriptApiEntity::luaentity_Step(u16 id, float dtime,
|
||||
// tool_capabilities, direction, damage)
|
||||
bool ScriptApiEntity::luaentity_Punch(u16 id,
|
||||
ServerActiveObject *puncher, float time_from_last_punch,
|
||||
const ToolCapabilities *toolcap, v3f dir, s32 damage)
|
||||
const ToolCapabilities &toolcap, v3f dir, s32 damage)
|
||||
{
|
||||
SCRIPTAPI_PRECHECKHEADER
|
||||
|
||||
@@ -270,7 +270,7 @@ bool ScriptApiEntity::luaentity_Punch(u16 id,
|
||||
else
|
||||
lua_pushnil(L);
|
||||
lua_pushnumber(L, time_from_last_punch);
|
||||
push_tool_capabilities(L, *toolcap);
|
||||
push_tool_capabilities(L, toolcap);
|
||||
push_v3f(L, dir);
|
||||
lua_pushnumber(L, damage);
|
||||
|
||||
|
||||
@@ -28,7 +28,7 @@ public:
|
||||
const collisionMoveResult *moveresult);
|
||||
bool luaentity_Punch(u16 id,
|
||||
ServerActiveObject *puncher, float time_from_last_punch,
|
||||
const ToolCapabilities *toolcap, v3f dir, s32 damage);
|
||||
const ToolCapabilities &toolcap, v3f dir, s32 damage);
|
||||
bool luaentity_on_death(u16 id, ServerActiveObject *killer);
|
||||
void luaentity_Rightclick(u16 id, ServerActiveObject *clicker);
|
||||
void luaentity_on_attach_child(u16 id, ServerActiveObject *child);
|
||||
|
||||
@@ -42,7 +42,7 @@ void ScriptApiPlayer::on_dieplayer(ServerActiveObject *player, const PlayerHPCha
|
||||
bool ScriptApiPlayer::on_punchplayer(ServerActiveObject *player,
|
||||
ServerActiveObject *hitter,
|
||||
float time_from_last_punch,
|
||||
const ToolCapabilities *toolcap,
|
||||
const ToolCapabilities &toolcap,
|
||||
v3f dir,
|
||||
s32 damage)
|
||||
{
|
||||
@@ -57,7 +57,7 @@ bool ScriptApiPlayer::on_punchplayer(ServerActiveObject *player,
|
||||
else
|
||||
lua_pushnil(L);
|
||||
lua_pushnumber(L, time_from_last_punch);
|
||||
push_tool_capabilities(L, *toolcap);
|
||||
push_tool_capabilities(L, toolcap);
|
||||
push_v3f(L, dir);
|
||||
lua_pushnumber(L, damage);
|
||||
runCallbacks(6, RUN_CALLBACKS_MODE_OR);
|
||||
|
||||
@@ -30,7 +30,7 @@ public:
|
||||
void on_leaveplayer(ServerActiveObject *player, bool timeout);
|
||||
void on_cheat(ServerActiveObject *player, const std::string &cheat_type);
|
||||
bool on_punchplayer(ServerActiveObject *player, ServerActiveObject *hitter,
|
||||
float time_from_last_punch, const ToolCapabilities *toolcap,
|
||||
float time_from_last_punch, const ToolCapabilities &toolcap,
|
||||
v3f dir, s32 damage);
|
||||
void on_rightclickplayer(ServerActiveObject *player, ServerActiveObject *clicker);
|
||||
s32 on_player_hpchange(ServerActiveObject *player, s32 hp_change,
|
||||
|
||||
@@ -204,7 +204,7 @@ int ObjectRef::l_punch(lua_State *L)
|
||||
return 0;
|
||||
|
||||
float time_from_last_punch = readParam<float>(L, 3, 1000000.0f);
|
||||
ToolCapabilities toolcap = read_tool_capabilities(L, 4);
|
||||
ToolCapabilities toolcap = read_tool_capabilities(L, 4); // not optional!
|
||||
v3f dir;
|
||||
if (puncher) {
|
||||
dir = readParam<v3f>(L, 5, sao->getBasePosition() - puncher->getBasePosition());
|
||||
@@ -213,7 +213,7 @@ int ObjectRef::l_punch(lua_State *L)
|
||||
dir = readParam<v3f>(L, 5, v3f(0));
|
||||
}
|
||||
|
||||
u32 wear = sao->punch(dir, &toolcap, puncher, time_from_last_punch);
|
||||
u32 wear = sao->punch(dir, toolcap, puncher, time_from_last_punch);
|
||||
lua_pushnumber(L, wear);
|
||||
|
||||
return 1;
|
||||
|
||||
@@ -195,12 +195,12 @@ int ModApiUtil::l_get_dig_params(lua_State *L)
|
||||
int ModApiUtil::l_get_hit_params(lua_State *L)
|
||||
{
|
||||
NO_MAP_LOCK_REQUIRED;
|
||||
std::unordered_map<std::string, int> groups;
|
||||
ItemGroupList groups;
|
||||
read_groups(L, 1, groups);
|
||||
ToolCapabilities tp = read_tool_capabilities(L, 2);
|
||||
float time_from_last_punch = readParam<float>(L, 3, 1000000);
|
||||
int wear = readParam<int>(L, 4, 0);
|
||||
push_hit_params(L, getHitParams(groups, &tp,
|
||||
push_hit_params(L, getHitParams(groups, tp,
|
||||
time_from_last_punch, wear));
|
||||
return 1;
|
||||
}
|
||||
|
||||
@@ -323,7 +323,7 @@ void LuaEntitySAO::getStaticData(std::string *result) const
|
||||
}
|
||||
|
||||
u32 LuaEntitySAO::punch(v3f dir,
|
||||
const ToolCapabilities *toolcap,
|
||||
const ToolCapabilities &toolcap,
|
||||
ServerActiveObject *puncher,
|
||||
float time_from_last_punch,
|
||||
u16 initial_wear)
|
||||
|
||||
@@ -29,7 +29,7 @@ public:
|
||||
bool shouldUnload() const { return true; }
|
||||
void getStaticData(std::string *result) const;
|
||||
|
||||
u32 punch(v3f dir, const ToolCapabilities *toolcap = nullptr,
|
||||
u32 punch(v3f dir, const ToolCapabilities &toolcap,
|
||||
ServerActiveObject *puncher = nullptr,
|
||||
float time_from_last_punch = 1000000.0f,
|
||||
u16 initial_wear = 0);
|
||||
|
||||
@@ -450,14 +450,11 @@ void PlayerSAO::setLookPitchAndSend(const float pitch)
|
||||
}
|
||||
|
||||
u32 PlayerSAO::punch(v3f dir,
|
||||
const ToolCapabilities *toolcap,
|
||||
const ToolCapabilities &toolcap,
|
||||
ServerActiveObject *puncher,
|
||||
float time_from_last_punch,
|
||||
u16 initial_wear)
|
||||
{
|
||||
if (!toolcap)
|
||||
return 0;
|
||||
|
||||
// No effect if PvP disabled or if immortal
|
||||
if (isImmortal() || !g_settings->getBool("enable_pvp")) {
|
||||
if (puncher && puncher->getType() == ACTIVEOBJECT_TYPE_PLAYER) {
|
||||
|
||||
@@ -101,7 +101,7 @@ public:
|
||||
Interaction interface
|
||||
*/
|
||||
|
||||
u32 punch(v3f dir, const ToolCapabilities *toolcap, ServerActiveObject *puncher,
|
||||
u32 punch(v3f dir, const ToolCapabilities &toolcap, ServerActiveObject *puncher,
|
||||
float time_from_last_punch, u16 initial_wear = 0) override;
|
||||
void rightClick(ServerActiveObject *clicker) override;
|
||||
void setHP(s32 hp, const PlayerHPChangeReason &reason) override
|
||||
@@ -141,7 +141,7 @@ public:
|
||||
float resetTimeFromLastPunch()
|
||||
{
|
||||
float r = m_time_from_last_punch;
|
||||
m_time_from_last_punch = 0.0;
|
||||
m_time_from_last_punch = 0;
|
||||
return r;
|
||||
}
|
||||
void noCheatDigStart(const v3s16 &p)
|
||||
|
||||
@@ -129,7 +129,7 @@ public:
|
||||
|
||||
// Returns added tool wear
|
||||
virtual u32 punch(v3f dir,
|
||||
const ToolCapabilities *toolcap = nullptr,
|
||||
const ToolCapabilities &toolcap,
|
||||
ServerActiveObject *puncher = nullptr,
|
||||
float time_from_last_punch = 1000000.0f,
|
||||
u16 initial_wear = 0)
|
||||
|
||||
42
src/tool.cpp
42
src/tool.cpp
@@ -421,21 +421,21 @@ DigParams getDigParams(const ItemGroupList &groups,
|
||||
}
|
||||
|
||||
HitParams getHitParams(const ItemGroupList &armor_groups,
|
||||
const ToolCapabilities *tp, float time_from_last_punch,
|
||||
const ToolCapabilities &tp, float time_from_last_punch,
|
||||
u16 initial_wear)
|
||||
{
|
||||
s32 damage = 0;
|
||||
float result_wear = 0.0f;
|
||||
float punch_interval_multiplier =
|
||||
rangelim(time_from_last_punch / tp->full_punch_interval, 0.0f, 1.0f);
|
||||
rangelim(time_from_last_punch / tp.full_punch_interval, 0.0f, 1.0f);
|
||||
|
||||
for (const auto &damageGroup : tp->damageGroups) {
|
||||
for (const auto &damageGroup : tp.damageGroups) {
|
||||
s16 armor = itemgroup_get(armor_groups, damageGroup.first);
|
||||
damage += damageGroup.second * punch_interval_multiplier * armor / 100.0;
|
||||
}
|
||||
|
||||
if (tp->punch_attack_uses > 0) {
|
||||
result_wear = calculateResultWear(tp->punch_attack_uses, initial_wear);
|
||||
if (tp.punch_attack_uses > 0) {
|
||||
result_wear = calculateResultWear(tp.punch_attack_uses, initial_wear);
|
||||
result_wear *= punch_interval_multiplier;
|
||||
}
|
||||
// Keep damage in sane bounds for simplicity
|
||||
@@ -445,36 +445,30 @@ HitParams getHitParams(const ItemGroupList &armor_groups,
|
||||
return {damage, wear_i};
|
||||
}
|
||||
|
||||
HitParams getHitParams(const ItemGroupList &armor_groups,
|
||||
const ToolCapabilities *tp)
|
||||
{
|
||||
return getHitParams(armor_groups, tp, 1000000);
|
||||
}
|
||||
|
||||
PunchDamageResult getPunchDamage(
|
||||
const ItemGroupList &armor_groups,
|
||||
const ToolCapabilities *toolcap,
|
||||
const ToolCapabilities &toolcap,
|
||||
const ItemStack *punchitem,
|
||||
float time_from_last_punch,
|
||||
u16 initial_wear
|
||||
){
|
||||
bool do_hit = true;
|
||||
{
|
||||
if (do_hit && punchitem) {
|
||||
if (itemgroup_get(armor_groups, "punch_operable") &&
|
||||
(toolcap == NULL || punchitem->name.empty()))
|
||||
do_hit = false;
|
||||
}
|
||||
if (do_hit && punchitem) {
|
||||
// FIXME: punch_operable is supposed to apply to "non-tool" items too
|
||||
// 1. We don't have the itemdef available here to check
|
||||
// 2. how is this supposed to interact with overridable toolcaps?
|
||||
if (itemgroup_get(armor_groups, "punch_operable") &&
|
||||
punchitem->name.empty())
|
||||
do_hit = false;
|
||||
}
|
||||
|
||||
if (do_hit) {
|
||||
if(itemgroup_get(armor_groups, "immortal"))
|
||||
do_hit = false;
|
||||
}
|
||||
if (do_hit) {
|
||||
if (itemgroup_get(armor_groups, "immortal"))
|
||||
do_hit = false;
|
||||
}
|
||||
|
||||
PunchDamageResult result;
|
||||
if(do_hit)
|
||||
{
|
||||
if (do_hit) {
|
||||
HitParams hitparams = getHitParams(armor_groups, toolcap,
|
||||
time_from_last_punch,
|
||||
punchitem ? punchitem->wear : 0);
|
||||
|
||||
12
src/tool.h
12
src/tool.h
@@ -149,11 +149,14 @@ struct HitParams
|
||||
};
|
||||
|
||||
HitParams getHitParams(const ItemGroupList &armor_groups,
|
||||
const ToolCapabilities *tp, float time_from_last_punch,
|
||||
const ToolCapabilities &tp, float time_from_last_punch,
|
||||
u16 initial_wear = 0);
|
||||
|
||||
HitParams getHitParams(const ItemGroupList &armor_groups,
|
||||
const ToolCapabilities *tp);
|
||||
inline HitParams getHitParams(const ItemGroupList &armor_groups,
|
||||
const ToolCapabilities &tp)
|
||||
{
|
||||
return getHitParams(armor_groups, tp, 1000000);
|
||||
}
|
||||
|
||||
struct PunchDamageResult
|
||||
{
|
||||
@@ -168,12 +171,13 @@ struct ItemStack;
|
||||
|
||||
PunchDamageResult getPunchDamage(
|
||||
const ItemGroupList &armor_groups,
|
||||
const ToolCapabilities *toolcap,
|
||||
const ToolCapabilities &toolcap,
|
||||
const ItemStack *punchitem,
|
||||
float time_from_last_punch,
|
||||
u16 initial_wear = 0
|
||||
);
|
||||
|
||||
u32 calculateResultWear(const u32 uses, const u16 initial_wear);
|
||||
|
||||
f32 getToolRange(const ItemStack &wielded_item, const ItemStack &hand_item,
|
||||
const IItemDefManager *itemdef_manager);
|
||||
|
||||
Reference in New Issue
Block a user