Skip to content

Commit

Permalink
lua: add UnitPreDamaged callin.
Browse files Browse the repository at this point in the history
it's similar to UnitDamaged, but it's synced only and it can (should)
return new damage value.
  • Loading branch information
imbaczek committed Apr 11, 2009
1 parent c49d916 commit 535cff5
Show file tree
Hide file tree
Showing 5 changed files with 90 additions and 0 deletions.
14 changes: 14 additions & 0 deletions installer/builddata/springcontent/LuaGadgets/gadgets.lua
Expand Up @@ -108,6 +108,7 @@ local callInLists = {
'UnitExperience',
'UnitIdle',
'UnitCmdDone',
'UnitPreDamaged',
'UnitDamaged',
'UnitTaken',
'UnitGiven',
Expand Down Expand Up @@ -1257,6 +1258,19 @@ function gadgetHandler:UnitCmdDone(unitID, unitDefID, unitTeam, cmdID, cmdTag)
end


function gadgetHandler:UnitPreDamaged(unitID, unitDefID, unitTeam,
damage, paralyzer, weaponID,
attackerID, attackerDefID, attackerTeam)
local dam = damage
for _,g in ipairs(self.UnitPreDamagedList) do
dam = g:UnitPreDamaged(unitID, unitDefID, unitTeam,
dam, paralyzer, weaponID,
attackerID, attackerDefID, attackerTeam)
end
return dam
end


function gadgetHandler:UnitDamaged(unitID, unitDefID, unitTeam,
damage, paralyzer, weaponID,
attackerID, attackerDefID, attackerTeam)
Expand Down
64 changes: 64 additions & 0 deletions rts/Lua/LuaRules.cpp
Expand Up @@ -127,6 +127,7 @@ CLuaRules::CLuaRules()
haveTerraformComplete = HasCallIn("TerraformComplete");
haveDrawUnit = HasCallIn("DrawUnit");
haveAICallIn = HasCallIn("AICallIn");
haveUnitPreDamaged = HasCallIn("UnitPreDamaged");

SetupUnsyncedFunction("DrawUnit");
SetupUnsyncedFunction("AICallIn");
Expand Down Expand Up @@ -811,6 +812,69 @@ bool CLuaRules::TerraformComplete(const CUnit* unit, const CUnit* build)
}


/**
* called after every damage modification (even HitByWeaponId)
* but before the damage is applied
*
* expects a number returned by lua code; it is stored under *newDamage if
* newDamage != NULL.
*/
bool CLuaRules::UnitPreDamaged(const CUnit* unit, const CUnit* attacker,
float damage, int weaponID, bool paralyzer,
float* newDamage)
{
if (!haveUnitPreDamaged) {
return false;
}

LUA_CALL_IN_CHECK(L);
lua_checkstack(L, 11);

int errfunc = SetupTraceback();

static const LuaHashString cmdStr("UnitPreDamaged");
if (!cmdStr.GetGlobalFunc(L)) {
// remove error handler
if (errfunc) lua_pop(L, 1);
return false; // the call is not defined
}

int argCount = 5;
lua_pushnumber(L, unit->id);
lua_pushnumber(L, unit->unitDef->id);
lua_pushnumber(L, unit->team);
lua_pushnumber(L, damage);
lua_pushboolean(L, paralyzer);
if (fullRead) {
lua_pushnumber(L, weaponID);
argCount += 1;
if (attacker != NULL) {
lua_pushnumber(L, attacker->id);
lua_pushnumber(L, attacker->unitDef->id);
lua_pushnumber(L, attacker->team);
argCount += 3;
}
}

// call the routine
RunCallInTraceback(cmdStr, argCount, 1, errfunc);

// get the results
if (!lua_isnumber(L, -1)) {
logOutput.Print("%s() bad return value, expected number\n", cmdStr.GetString().c_str());
lua_pop(L, 1);
return false;
}

const float retval = lua_tonumber(L, -1);
lua_pop(L, 1);
if (newDamage) {
*newDamage = retval;
}
return true;
}


/******************************************************************************/

bool CLuaRules::DrawUnit(int unitID)
Expand Down
5 changes: 5 additions & 0 deletions rts/Lua/LuaRules.h
Expand Up @@ -66,6 +66,10 @@ class CLuaRules : public CLuaHandleSynced
void Cob2Lua(const LuaHashString& funcName, const CUnit* unit,
int& argsCount, int args[MAX_LUA_COB_ARGS]);

bool UnitPreDamaged(const CUnit* unit, const CUnit* attacker,
float damage, int weaponID, bool paralyzer,
float* newDamage);

// unsynced
bool DrawUnit(int unitID);
const char* AICallIn(const char* data, int inSize, int* outSize);
Expand Down Expand Up @@ -122,6 +126,7 @@ class CLuaRules : public CLuaHandleSynced
bool haveTerraformComplete;
bool haveDrawUnit;
bool haveAICallIn;
bool haveUnitPreDamaged;

map<string, string> infoMap;

Expand Down
6 changes: 6 additions & 0 deletions rts/Sim/Units/Unit.cpp
Expand Up @@ -1008,6 +1008,12 @@ void CUnit::DoDamage(const DamageArray& damages, CUnit *attacker,const float3& i
float experienceMod = expMultiplier;

const int paralyzeTime = damages.paralyzeDamageTime;
float newDamage = damage;

if (luaRules && luaRules->UnitPreDamaged(this, attacker, damage, weaponId,
!!damages.paralyzeDamageTime, &newDamage))
damage = newDamage;


if (paralyzeTime == 0) { // real damage
if (damage > 0.0f) {
Expand Down
1 change: 1 addition & 0 deletions rts/System/EventHandler.cpp
Expand Up @@ -134,6 +134,7 @@ CEventHandler::CEventHandler()
SetupEvent("AllowStartPosition", NULL, CONTROL_BIT);
SetupEvent("TerraformComplete", NULL, CONTROL_BIT);
SetupEvent("MoveCtrlNotify", NULL, CONTROL_BIT);
SetupEvent("UnitPreDamaged", NULL, CONTROL_BIT);
}


Expand Down

0 comments on commit 535cff5

Please sign in to comment.