• There is NO official Otland's Discord server and NO official Otland's server list. The Otland's Staff does not manage any Discord server or server list. Moderators or administrator of any Discord server or server lists have NO connection to the Otland's Staff. Do not get scammed!

Lua Function Condition Suppressions in Lua

Crevasse

惡名昭彰
Joined
Jan 13, 2017
Messages
149
Solutions
16
Reaction score
109
Location
Washington, D.C.
Pretty straightforward, here is a method to manage condition suppressions in Lua. I have seen this come up before in threads in the past, and it doesn't seem like anyone's posted the answer here and from what I can tell all TFS and TFS-based distros dont come with this. Anyways, here it is:

To luascript.h, at the end of the "player" class functions:
C++:
static int luaPlayerAddConditionSuppression(lua_State* L);
static int luaPlayerRemoveConditionSuppression(lua_State* L);

Then, in luascript.cpp, at the end of the "player" method registrations:

C++:
registerMethod("Player", "addConditionSuppression", LuaScriptInterface::luaPlayerAddConditionSuppression);
registerMethod("Player", "removeConditionSuppression", LuaScriptInterface::luaPlayerRemoveConditionSuppression);

Finally, also in luascript.cpp, the actual functions themselves (again, after the final existing player related function):
C++:
int LuaScriptInterface::luaPlayerAddConditionSuppression(lua_State* L)
{
    // player:addConditionSuppression(conditions)
    Player* player = getUserdata<Player>(L, 1);
    uint32_t conditions = luaL_checkinteger(L, 2);

    if (player) {
        player->addConditionSuppressions(conditions); //Leverage the existing function from player.cpp
        pushBoolean(L, true); // Indicate success
    } else {
        pushBoolean(L, false); // Indicate failure
    }

    return 1; // Number of return values
}

int LuaScriptInterface::luaPlayerRemoveConditionSuppression(lua_State* L)
{
    // player:removeConditionSuppression(conditions)
    Player* player = getUserdata<Player>(L, 1);
    uint32_t conditions = luaL_checkinteger(L, 2);

    if (player) {
        player->removeConditionSuppressions(conditions);
        pushBoolean(L, true); // Indicate success
    } else {
        pushBoolean(L, false); // Indicate failure
    }

    return 1; // Number of return values
}

When would this be necessary? Well, take my own use case for an example:

I had an item that suppressed the drowning condition. The movement in movements.xml for this item would simply be like this:
XML:
<movevent event="Equip" itemid="5460" slot="head" function="onEquipItem" />
<movevent event="DeEquip" itemid="5460" slot="head" function="onDeEquipItem" />

That's fine, but now let's say I need the player to get a specific storage value when they equip this item? Well, there's no built-in "function" for that, instead the movement needs to look like this:
XML:
<movevent event="Equip" itemid="5460" slot="head" script="script.lua" />
<movevent event="DeEquip" itemid="5460" slot="head" script="script.lua" />
If you do this, the suppression attribute of the item will no longer be applied since movements.xml is only going to look at whatever is called in "script.lua".

After making these source code changes, you can do both at the same time:
Lua:
function onEquip(player, item, slot)
    player:setStorageValue(1234, 1)
    player:addConditionSuppression(CONDITION_DROWN)
    return true
end

function onDeEquip(player, item, slot)
    player:setStorageValue(1234, 0)
    player:removeConditionSuppression(CONDITION_DROWN)
    return true
end
 
Back
Top