Name | Type | is_array | initial_value |
AfterDamageEvent | real | No | |
ClearDamageEvent | trigger | No | |
DAMAGE_FACTOR_BRACERS | real | No | |
DAMAGE_FACTOR_ELUNES | real | No | |
DAMAGE_FACTOR_ETHEREAL | real | No | |
DamageBlockingAbility | abilcode | No | |
DamageEvent | real | No | |
DamageEventAmount | real | No | |
DamageEventOverride | boolean | No | |
DamageEventPrevAmt | real | No | |
DamageEventSource | unit | No | |
DamageEventsWasted | integer | No | |
DamageEventTarget | unit | No | |
DamageEventTrigger | trigger | No | |
DamageEventType | integer | No | |
DamageModifierEvent | real | No | |
DamageTypeBlocked | integer | No | |
DamageTypeCriticalStrike | integer | No | |
DamageTypeExplosive | integer | No | |
DamageTypeHeal | integer | No | |
DamageTypeReduced | integer | No | |
DmgEvBracers | itemcode | No | |
DmgEvRecursionN | integer | No | |
DmgEvRunning | boolean | No | |
DmgEvStarted | boolean | No | |
DmgEvTimer | timer | No | |
DmgEvTrig | trigger | No | |
GDD__LeftMapGroup | group | No | |
HideDamageFrom | boolean | Yes | |
IsDamageSpell | boolean | No | |
LastDamageHP | real | No | |
LastDmgPrevAmount | real | Yes | |
LastDmgPrevType | integer | Yes | |
LastDmgSource | unit | Yes | |
LastDmgTarget | unit | Yes | |
LastDmgValue | real | Yes | |
LastDmgWasSpell | boolean | Yes | |
NextDamageOverride | boolean | No | |
NextDamageType | integer | No | |
SourceName | string | No | |
SpellDamageAbility | abilcode | No | |
TargetName | string | No | |
TempInt | integer | No | |
TempKey | integer | No | |
TI_Allies | boolean | No | |
TI_AllowSpellAsTrigger | boolean | No | |
TI_AT | attacktype | Yes | |
TI_AttachPoint | string | Yes | |
TI_AttackType | attacktype | No | |
TI_DamageCapBase | real | Yes | |
TI_DamageCapPerLevel | real | Yes | |
TI_DamageStackBase | real | No | |
TI_DamageStackPerLevel | real | No | |
TI_DamageType | damagetype | No | |
TI_DCapBase | real | No | |
TI_DCapPerLevel | real | No | |
TI_DPABase | real | Yes | |
TI_DPAPerLevel | real | Yes | |
TI_DT | damagetype | Yes | |
TI_DummyID | integer | Yes | |
TI_DurationBase | real | Yes | |
TI_DurationPerLevel | real | Yes | |
TI_DurBase | real | No | |
TI_DurPerLevel | real | No | |
TI_EffectAttachment | string | No | |
TI_EffectModel1 | string | No | |
TI_EffectModel2 | string | No | |
TI_EXAOEBase | real | No | |
TI_EXAOEPerLevel | real | No | |
TI_ExplodeAOEBase | real | Yes | |
TI_ExplodeAOEPerLevel | real | Yes | |
TI_ExplodeSmallDAOEBase | real | Yes | |
TI_ExplodeSmallDAOEPerLev | real | Yes | |
TI_ExplodeSmallDFactorBase | real | Yes | |
TI_ExplodeSmallDFactorPerLev | real | Yes | |
TI_EXSmallAOEBase | real | No | |
TI_EXSmallAOEPerLevel | real | No | |
TI_EXSmallDamageFactorBase | real | No | |
TI_EXSmallDamageFactorPerLevel | real | No | |
TI_Hash | hashtable | No | |
TI_Illusions | boolean | No | |
TI_IsUnitAlly | boolean | Yes | |
TI_IsUnitIllusion | boolean | Yes | |
TI_IsUnitMagicImmune | boolean | Yes | |
TI_IsUnitMechanical | boolean | Yes | |
TI_IsUnitStructure | boolean | Yes | |
TI_MagicImmune | boolean | No | |
TI_Mechanicals | boolean | No | |
TI_SFXModel1 | string | Yes | |
TI_SFXModel2 | string | Yes | |
TI_Spell | abilcode | No | |
TI_SpellAsTrigger | boolean | Yes | |
TI_SpellID | abilcode | Yes | |
TI_SpellIndex | integer | No | |
TI_Structures | boolean | No | |
TI_TempGroup | group | No | |
TI_Trig | trigger | No | |
UDex | integer | No | |
UDexGen | integer | No | |
UDexNext | integer | Yes | |
UDexPrev | integer | Yes | |
UDexRecycle | integer | No | |
UDexUnits | unit | Yes | |
UDexWasted | integer | No | |
UnitDamageRegistered | boolean | Yes | |
UnitIndexerEnabled | boolean | No | |
UnitIndexEvent | real | No | |
UnitIndexLock | integer | Yes |
//TESH.scrollpos=284
//TESH.alwaysfold=0
///////////////////////////////////////////////////////////////////////////////////////////////////////
//===================================================================================================//
//============================= *** **** *** **** * * **** ==============================//
//============================= * * * * * * * ** ** * ==============================//
//============================= *** *** ***** * * * * * *** ==============================//
//============================= * * * * * * * * * * ==============================//
//============================= * * **** * * **** * * **** ==============================//
//===================================================================================================//
///////////////////////////////////////////////////////////////////////////////////////////////////////
// //
// ***************************** //
// * Triggered Incinerate v1.2 * //
// * by: AGD * //
// ***************************** //
// //
// Credits: //
// - Bribe ( Damage Engine ) //
// //
// //
// How to Import: //
// - Copy the dummy model in the import manager //
// - Copy the dummy unit //
// - Copy the custom abilities //
// - Copy the "Triggered Incinerate by AGD" trigger category //
// //
// But first, check "automatically create unknown variables while pasting trigger data" so that the //
// "TI Variable Creator" will create the necessary variables in your map. //
// //
// //
// Spell Summary: //
// //
// The spell's effect is passive. It activates everytime the unit deals damage to its target. This //
// spell causes the unit to deal increasing damage (additionally) per attack. The damage stacking //
// has a duration after which if the target takes no damage from a unit with incinerate spell, it //
// will be reset back to zero. Upon the target unit's death, it will explode and deal damage equal //
// to the damage stacked to a certain AOE. //
// //
// //
// Spell Info (Please Read): //
// //
// For those who don't know yet, the Incinerate spell of Fire Lord which was made by Blizzard is //
// actually buggy if you're not using the original spell ( i.e. if you're using a custom ability //
// based on that spell ). In this case, even if you change the stats of the custom spell, the stats //
// of the original spell will persist and it's almost impossible or atleast difficult to make //
// many incinerate spells with different stats and sometimes you will be forced to use triggers to //
// do this. //
// //
// For this reason I made this spell hoping that this will help you with your difficulties regarding //
// the buggy Incinerate. In this spell, you can make as many incinerate spells as you like, all with //
// different stats and spellIDs. The spell's effects is also not limited by the unit's weapon type //
// which, unlike Blizzard's Incinerate, will only work with missile attacks. And lastly, one //
// POSSIBLE advantage of this sytem is that it works together with other buff placers and orb //
// effects. //
// //
// Please share your feedback and suggestions about this spell at Hive Workshop or you can PM AGD //
// at Hive. Please also report bugs and glitches if you found some. //
// //
// //
// Note: If you use this resource in your map, please don't forget to give credits to AGD. And if //
// you're having problem regarding how to import or in configuring the spell, you can PM him //
// or post your comment at Hive Workshop. //
// //
// //
///////////////////////////////////////////////////////////////////////////////////////////////////////
//===================================================================================================//
//===================================================================================================//
//===================================================================================================//
///////////////////////////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////
// This function indexes the spell's stats listed //
// in the Incinerate spells list one by one //
////////////////////////////////////////////////////
function TI_InitSpellIndex takes nothing returns nothing
local integer i = udg_TI_SpellIndex + 1
set udg_TI_SpellID[i] = udg_TI_Spell
set udg_TI_SpellAsTrigger[i] = udg_TI_AllowSpellAsTrigger
set udg_TI_DPABase[i] = udg_TI_DamageStackBase
set udg_TI_DPAPerLevel[i] = udg_TI_DamageStackPerLevel
set udg_TI_DurationBase[i] = udg_TI_DurBase
set udg_TI_DurationPerLevel[i] = udg_TI_DurPerLevel
set udg_TI_DamageCapBase[i] = udg_TI_DCapBase
set udg_TI_DamageCapPerLevel[i] = udg_TI_DCapPerLevel
set udg_TI_ExplodeAOEBase[i] = udg_TI_EXAOEBase
set udg_TI_ExplodeAOEPerLevel[i] = udg_TI_EXAOEPerLevel
set udg_TI_ExplodeSmallDAOEBase[i] = udg_TI_EXSmallAOEBase
set udg_TI_ExplodeSmallDAOEPerLev[i] = udg_TI_EXSmallAOEPerLevel
set udg_TI_ExplodeSmallDFactorBase[i] = udg_TI_EXSmallDamageFactorBase
set udg_TI_ExplodeSmallDFactorPerLev[i] = udg_TI_EXSmallDamageFactorPerLevel
set udg_TI_AT[i] = udg_TI_AttackType
set udg_TI_DT[i] = udg_TI_DamageType
set udg_TI_SFXModel1[i] = udg_TI_EffectModel1
set udg_TI_SFXModel2[i] = udg_TI_EffectModel2
set udg_TI_AttachPoint[i] = udg_TI_EffectAttachment
set udg_TI_IsUnitStructure[i] = udg_TI_Structures
set udg_TI_IsUnitMechanical[i] = udg_TI_Mechanicals
set udg_TI_IsUnitMagicImmune[i] = udg_TI_MagicImmune
set udg_TI_IsUnitAlly[i] = udg_TI_Allies
set udg_TI_IsUnitIllusion[i] = udg_TI_Illusions
set udg_TI_SpellIndex = i
endfunction
/////////////////////////////////////////////////////
// This function filters unwanted units from being //
// affected by the spell //
/////////////////////////////////////////////////////
function TI_TargetFilter takes unit target, player p, integer i returns boolean
return ( ( not IsUnitType( target, UNIT_TYPE_STRUCTURE ) ) or udg_TI_IsUnitStructure[i] ) and ( ( not IsUnitType( target, UNIT_TYPE_MECHANICAL ) ) or udg_TI_IsUnitMechanical[i] ) and ( ( not IsUnitType( target, UNIT_TYPE_MAGIC_IMMUNE ) ) or udg_TI_IsUnitMagicImmune[i] ) and ( IsUnitEnemy( target, p ) or udg_TI_IsUnitAlly[i] ) and ( ( not IsUnitIllusion( target ) ) or udg_TI_IsUnitIllusion[i] )
endfunction
/////////////////////////////////////////////////////
// This function debuffs the target unit when not //
// damaged for a certain duration //
/////////////////////////////////////////////////////
function TI_Debuff takes nothing returns nothing
local timer t = GetExpiredTimer()
local integer timerkey = GetHandleId( t )
local integer i = LoadInteger( udg_TI_Hash, timerkey, 0 )
local unit u = LoadUnitHandle( udg_TI_Hash, timerkey, 1 )
local integer key = GetHandleId( u )
local string I = I2S( i )
call DestroyEffect( LoadEffectHandle( udg_TI_Hash, key, StringHash( "SFX" + I ) ) )
call DestroyTimer( t )
call SaveBoolean( udg_TI_Hash, key, i, false )
call SaveReal( udg_TI_Hash, key, StringHash( "Damage" + I ), 0 )
call FlushChildHashtable( udg_TI_Hash, timerkey )
set t = null
set u = null
set I = null
endfunction
//////////////////////////////////////////////////////
// This function triggers the dead unit's explosion //
//////////////////////////////////////////////////////
function TI_Incinerate takes nothing returns boolean
local unit dying = GetTriggerUnit()
local integer key = GetHandleId( dying )
local real x = GetUnitX( dying )
local real y = GetUnitY( dying )
local integer i = 0
local unit target
local player p
local real dx
local real dy
local real damage
local real smalldfactor
local unit buffplacer
local string I
loop
set i = i + 1
set I = I2S( i )
if LoadBoolean( udg_TI_Hash, key, i ) then
set damage = LoadReal( udg_TI_Hash, key, StringHash( "Damage" + I ) )
set smalldfactor = LoadReal( udg_TI_Hash, key, StringHash( "SmallDFactor" + I ) )
set buffplacer = LoadUnitHandle( udg_TI_Hash, key, StringHash( "BuffPlacer" + I ) )
set p = GetOwningPlayer( buffplacer )
call SaveReal( udg_TI_Hash, key, StringHash( "Damage" + I ), 0 )
call DestroyEffect( LoadEffectHandle( udg_TI_Hash, key, StringHash( "SFX" + I ) ) )
call DestroyEffect( AddSpecialEffect( udg_TI_SFXModel2[i], x, y ) )
call GroupEnumUnitsInRange( udg_TI_TempGroup, x, y, LoadReal( udg_TI_Hash, key, StringHash( "SmallDAOE" + I ) ), null )
loop
set target = FirstOfGroup( udg_TI_TempGroup )
exitwhen target == null
call GroupRemoveUnit( udg_TI_TempGroup, target )
set dx = GetUnitX( target ) - x
set dy = GetUnitY( target ) - y
if ( target != buffplacer ) and TI_TargetFilter( target, p, i ) then
if SquareRoot( dx*dx + dy*dy ) > LoadReal( udg_TI_Hash, key, StringHash( "AOE" + I ) ) then
call UnitDamageTarget( buffplacer, target, damage*smalldfactor, true, false, udg_TI_AT[i], udg_TI_DT[i], null )
else
call UnitDamageTarget( buffplacer, target, damage, true, false, udg_TI_AT[i], udg_TI_DT[i], null )
endif
endif
endloop
endif
exitwhen i == udg_TI_SpellIndex
endloop
call FlushChildHashtable( udg_TI_Hash, key )
set dying = null
set buffplacer = null
set p = null
set I = null
return false
endfunction
///////////////////////////////////////////////////////////
// This function checks if the level of incinerate spell //
// for the damage source is greater than zero in order //
// run the main actions of the spell. //
///////////////////////////////////////////////////////////
function TI_MainAction takes nothing returns boolean
local trigger trig = GetTriggeringTrigger()
local integer key = GetHandleId( udg_DamageEventTarget )
local integer i = 0
local integer level
local integer timerkey
local real dcap
local string I
loop
set i = i + 1
set level = GetUnitAbilityLevel( udg_DamageEventSource, udg_TI_SpellID[i] )
if level > 0 then
if not udg_IsDamageSpell or udg_TI_SpellAsTrigger[i] then
set I = I2S( i )
set dcap = udg_TI_DamageCapBase[i] + udg_TI_DamageCapPerLevel[i]*level
if TI_TargetFilter( udg_DamageEventTarget, GetOwningPlayer( udg_DamageEventSource ), i ) then
call DestroyEffect( LoadEffectHandle( udg_TI_Hash, key, StringHash( "SFX" + I ) ) )
call SaveEffectHandle( udg_TI_Hash, key, StringHash( "SFX" + I ), AddSpecialEffectTarget( udg_TI_SFXModel1[i], udg_DamageEventTarget, udg_TI_AttachPoint[i] ) )
call DestroyTimer( LoadTimerHandle( udg_TI_Hash, key, StringHash( "Timer" + I ) ) )
call SaveTimerHandle( udg_TI_Hash, key, StringHash( "Timer" + I ), CreateTimer() )
set timerkey = GetHandleId( LoadTimerHandle( udg_TI_Hash, key, StringHash( "Timer" + I ) ) )
call SaveUnitHandle( udg_TI_Hash, timerkey, 1, udg_DamageEventTarget )
call SaveUnitHandle( udg_TI_Hash, key, StringHash( "BuffPlacer" + I ), udg_DamageEventSource )
call SaveReal( udg_TI_Hash, key, StringHash( "Damage" + I ), LoadReal( udg_TI_Hash, key, StringHash( "Damage" + I ) ) + udg_TI_DPABase[i] + udg_TI_DPAPerLevel[i]*level )
call SaveReal( udg_TI_Hash, key, StringHash( "AOE" + I ), udg_TI_ExplodeAOEBase[i] + udg_TI_ExplodeAOEPerLevel[i]*level )
call SaveReal( udg_TI_Hash, key, StringHash( "SmallDAOE" + I ), udg_TI_ExplodeSmallDAOEBase[i] + udg_TI_ExplodeSmallDAOEPerLev[i]*level )
call SaveReal( udg_TI_Hash, key, StringHash( "SmallDFactor" + I ), udg_TI_ExplodeSmallDFactorBase[i] + udg_TI_ExplodeSmallDFactorPerLev[i]*level )
call SaveInteger( udg_TI_Hash, timerkey, 0, i )
call SaveBoolean( udg_TI_Hash, key, i, true )
if dcap != 0 then
if LoadReal( udg_TI_Hash, key, StringHash( "Damage" + I ) ) > dcap then
call SaveReal( udg_TI_Hash, key, StringHash( "Damage" + I ), dcap )
endif
endif
call DisableTrigger( trig )
call UnitDamageTarget( udg_DamageEventSource, udg_DamageEventTarget, udg_DamageEventAmount + LoadReal( udg_TI_Hash, key, StringHash( "Damage" + I ) ), true, false, udg_TI_AT[i], udg_TI_DT[i], null )
call EnableTrigger( trig )
set udg_DamageEventAmount = 0
call TimerStart( LoadTimerHandle( udg_TI_Hash, key, StringHash( "Timer" + I ) ), udg_TI_DurationBase[i] + udg_TI_DurationPerLevel[i]*level, false, function TI_Debuff )
endif
endif
endif
exitwhen i == udg_TI_SpellIndex
endloop
set trig = null
set I = null
return false
endfunction
/////////////////////////////
// Initialization function //
/////////////////////////////
function InitTrig_Triggered_Incinerate takes nothing returns nothing
local trigger t1 = CreateTrigger()
local trigger t2 = CreateTrigger()
set udg_TI_Hash = InitHashtable()
call TriggerRegisterAnyUnitEventBJ( t1, EVENT_PLAYER_UNIT_DEATH )
call TriggerAddCondition( t1, Filter( function TI_Incinerate ) )
call TriggerRegisterVariableEvent( t2, "udg_DamageEvent", EQUAL, 1 )
call TriggerAddCondition( t2, Filter( function TI_MainAction ) )
call ExecuteFunc( "Trig_Incinerate_SpellsList_Actions" )
endfunction
//////////////////////
//******************//
//** End of Spell **//
//******************//
//////////////////////
//TESH.scrollpos=262
//TESH.alwaysfold=0
//===========================================================================
// Damage Engine lets you detect, amplify, block or nullify damage. It even
// lets you detect if the damage was physical or from a spell. Just reference
// DamageEventAmount/Source/Target or the boolean IsDamageSpell, to get the
// necessary damage event data.
//
// - Detect damage: use the event "DamageEvent Equal to 1.00"
// - To change damage before it's dealt: use the event "DamageModifierEvent Equal to 1.00"
// - Detect damage after it was applied, use the event "AfterDamageEvent Equal to 1.00"
// - Detect spell damage: use the condition "IsDamageSpell Equal to True"
// - Detect zero-damage: use the event "DamageEvent Equal to 2.00" (an AfterDamageEvent will not fire for this)
//
// You can specify the DamageEventType before dealing triggered damage. To prevent an already-improbable error, I recommend running the trigger "ClearDamageEvent (Checking Conditions)" after dealing triggered damage from within a damage event:
// - Set NextDamageType = DamageTypeWhatever
// - Unit - Cause...
// - Trigger - Run ClearDamageEvent (Checking Conditions)
//
// You can modify the DamageEventAmount and the DamageEventType from a "DamageModifierEvent Equal to 1.00" trigger.
// - If the amount is modified to negative, it will count as a heal.
// - If the amount is set to 0, no damage will be dealt.
//
// If you need to reference the original in-game damage, use the variable "DamageEventPrevAmt".
//
//===========================================================================
// Programming note about "integer i" and "udg_DmgEvRecursionN": integer i
// ranges from -1 upwards. "udg_DmgEvRecursionN" ranges from 0 upwards.
// "integer i" is always 1 less than "udg_DmgEvRecursionN"
//
function DmgEvResetVars takes nothing returns nothing
local integer i = udg_DmgEvRecursionN - 2
set udg_DmgEvRecursionN = i + 1
if i >= 0 then
set udg_DamageEventPrevAmt = udg_LastDmgPrevAmount[i]
set udg_DamageEventAmount = udg_LastDmgValue[i]
set udg_DamageEventSource = udg_LastDmgSource[i]
set udg_DamageEventTarget = udg_LastDmgTarget[i]
set udg_IsDamageSpell = udg_LastDmgWasSpell[i]
set udg_DamageEventType = udg_LastDmgPrevType[i]
endif
endfunction
function CheckDamagedLifeEvent takes boolean clear returns nothing
if clear then
set udg_NextDamageOverride = false
set udg_NextDamageType = 0
endif
if udg_DmgEvTrig != null then
call DestroyTrigger(udg_DmgEvTrig)
set udg_DmgEvTrig = null
if udg_IsDamageSpell then
call SetWidgetLife(udg_DamageEventTarget, RMaxBJ(udg_LastDamageHP, 0.41))
if udg_LastDamageHP <= 0.405 then
if udg_DamageEventType < 0 then
call SetUnitExploded(udg_DamageEventTarget, true)
endif
//Kill the unit
call DisableTrigger(udg_DamageEventTrigger)
call UnitDamageTarget(udg_DamageEventSource, udg_DamageEventTarget, -999, false, false, null, DAMAGE_TYPE_UNIVERSAL, null)
call EnableTrigger(udg_DamageEventTrigger)
endif
elseif GetUnitAbilityLevel(udg_DamageEventTarget, udg_DamageBlockingAbility) > 0 then
call UnitRemoveAbility(udg_DamageEventTarget, udg_DamageBlockingAbility)
call SetWidgetLife(udg_DamageEventTarget, udg_LastDamageHP)
endif
if udg_DamageEventAmount != 0.00 and not udg_HideDamageFrom[GetUnitUserData(udg_DamageEventSource)] then
set udg_AfterDamageEvent = 0.00
set udg_AfterDamageEvent = 1.00
set udg_AfterDamageEvent = 0.00
endif
call DmgEvResetVars()
endif
endfunction
function DmgEvOnExpire takes nothing returns nothing
set udg_DmgEvStarted = false
call CheckDamagedLifeEvent(true)
endfunction
function PreCheckDamagedLifeEvent takes nothing returns boolean
call CheckDamagedLifeEvent(true)
return false
endfunction
function OnUnitDamage takes nothing returns boolean
local boolean override = udg_DamageEventOverride
local integer i = udg_DmgEvRecursionN - 1
local string s
local real prevAmount
local real life
local real prevLife
local unit u
call CheckDamagedLifeEvent(false) //in case the unit state event failed and the 0.00 second timer hasn't yet expired
if i >= 0 then
if i < 16 then
set udg_LastDmgPrevAmount[i]= udg_DamageEventPrevAmt
set udg_LastDmgValue[i] = udg_DamageEventAmount
set udg_LastDmgSource[i] = udg_DamageEventSource
set udg_LastDmgTarget[i] = udg_DamageEventTarget
set udg_LastDmgWasSpell[i] = udg_IsDamageSpell
set udg_LastDmgPrevType[i] = udg_DamageEventType
else
//set s = "WARNING: Recursion error when dealing damage! Make sure when you deal damage from within a DamageEvent trigger, do it like this:\n\n"
//set s = s + "Trigger - Turn off (This Trigger)\n"
//set s = s + "Unit - Cause...\n"
//set s = s + "Trigger - Turn on (This Trigger)"
//Delete the next couple of lines to disable the in-game recursion crash warnings
//call ClearTextMessages()
//call DisplayTimedTextToPlayer(GetLocalPlayer(), 0.00, 0.00, 999.00, s)
return false
endif
endif
set udg_DmgEvRecursionN = i + 2
set u = GetTriggerUnit()
set prevAmount = GetEventDamage()
set udg_DamageEventSource = GetEventDamageSource()
set udg_DamageEventAmount = prevAmount
set udg_DamageEventTarget = u
set udg_DamageEventType = udg_NextDamageType
set udg_NextDamageType = 0
set udg_DamageEventOverride = udg_NextDamageOverride
set udg_NextDamageOverride = false
if prevAmount == 0.00 then
if not udg_HideDamageFrom[GetUnitUserData(udg_DamageEventSource)] then
set udg_DamageEventPrevAmt = 0.00
set udg_DamageEvent = 0.00
set udg_DamageEvent = 2.00
set udg_DamageEvent = 0.00
endif
call DmgEvResetVars()
else
if not udg_DmgEvStarted then
set udg_DmgEvStarted = true
call TimerStart(udg_DmgEvTimer, 0.00, false, function DmgEvOnExpire)
endif
set udg_IsDamageSpell = prevAmount < 0.00
if udg_IsDamageSpell then
set prevAmount = -udg_DamageEventAmount
set life = 1.00
if IsUnitType(u, UNIT_TYPE_ETHEREAL) and not IsUnitType(u, UNIT_TYPE_HERO) then
set life = life*udg_DAMAGE_FACTOR_ETHEREAL //1.67
endif
if GetUnitAbilityLevel(u, 'Aegr') > 0 then
set life = life*udg_DAMAGE_FACTOR_ELUNES //0.80
endif
if udg_DmgEvBracers != 0 and IsUnitType(u, UNIT_TYPE_HERO) then
//Inline of UnitHasItemOfTypeBJ without the potential handle ID leak.
set i = 6
loop
set i = i - 1
if GetItemTypeId(UnitItemInSlot(u, i)) == udg_DmgEvBracers then
set life = life*udg_DAMAGE_FACTOR_BRACERS //0.67
exitwhen true
endif
exitwhen i == 0
endloop
endif
set udg_DamageEventAmount = prevAmount*life
endif
set udg_DamageEventPrevAmt = prevAmount
set udg_DamageModifierEvent = 0.00
if not udg_DamageEventOverride then
set udg_DamageModifierEvent = 1.00
if not udg_DamageEventOverride then
set udg_DamageModifierEvent = 2.00
set udg_DamageModifierEvent = 3.00
endif
endif
set udg_DamageEventOverride = override
if udg_DamageEventAmount > 0.00 then
set udg_DamageModifierEvent = 4.00
endif
set udg_DamageModifierEvent = 0.00
if not udg_HideDamageFrom[GetUnitUserData(udg_DamageEventSource)] then
set udg_DamageEvent = 0.00
set udg_DamageEvent = 1.00
set udg_DamageEvent = 0.00
endif
call CheckDamagedLifeEvent(true) //in case the unit state event failed from a recursive damage event
//All events have run and the damage amount is finalized.
set life = GetWidgetLife(u)
set udg_DmgEvTrig = CreateTrigger()
call TriggerAddCondition(udg_DmgEvTrig, Filter(function PreCheckDamagedLifeEvent))
if not udg_IsDamageSpell then
if udg_DamageEventAmount != prevAmount then
set life = life + prevAmount - udg_DamageEventAmount
if GetUnitState(u, UNIT_STATE_MAX_LIFE) < life then
set udg_LastDamageHP = life - prevAmount
call UnitAddAbility(u, udg_DamageBlockingAbility)
endif
call SetWidgetLife(u, RMaxBJ(life, 0.42))
endif
call TriggerRegisterUnitStateEvent(udg_DmgEvTrig, u, UNIT_STATE_LIFE, LESS_THAN, RMaxBJ(0.41, life - prevAmount/2.00))
else
set udg_LastDamageHP = GetUnitState(u, UNIT_STATE_MAX_LIFE)
set prevLife = life
if life + prevAmount*0.75 > udg_LastDamageHP then
set life = RMaxBJ(udg_LastDamageHP - prevAmount/2.00, 1.00)
call SetWidgetLife(u, life)
set life = (life + udg_LastDamageHP)/2.00
else
set life = life + prevAmount*0.50
endif
set udg_LastDamageHP = prevLife - (prevAmount - (prevAmount - udg_DamageEventAmount))
call TriggerRegisterUnitStateEvent(udg_DmgEvTrig, u, UNIT_STATE_LIFE, GREATER_THAN, life)
endif
set u = null
endif
return false
endfunction
function CreateDmgEvTrg takes nothing returns nothing
set udg_DamageEventTrigger = CreateTrigger()
call TriggerAddCondition(udg_DamageEventTrigger, Filter(function OnUnitDamage))
endfunction
function SetupDmgEv takes nothing returns boolean
local integer i = udg_UDex
local unit u
if udg_UnitIndexEvent == 1.00 then
set u = udg_UDexUnits[i]
if GetUnitAbilityLevel(u, 'Aloc') == 0 and TriggerEvaluate(gg_trg_Damage_Engine_Config) then
set udg_UnitDamageRegistered[i] = true
call TriggerRegisterUnitEvent(udg_DamageEventTrigger, u, EVENT_UNIT_DAMAGED)
call UnitAddAbility(u, udg_SpellDamageAbility)
call UnitMakeAbilityPermanent(u, true, udg_SpellDamageAbility)
endif
set u = null
else
set udg_HideDamageFrom[i] = false
if udg_UnitDamageRegistered[i] then
set udg_UnitDamageRegistered[i] = false
set udg_DamageEventsWasted = udg_DamageEventsWasted + 1
if udg_DamageEventsWasted == 32 then //After 32 registered units have been removed...
set udg_DamageEventsWasted = 0
//Rebuild the mass EVENT_UNIT_DAMAGED trigger:
call DestroyTrigger(udg_DamageEventTrigger)
call CreateDmgEvTrg()
set i = udg_UDexNext[0]
loop
exitwhen i == 0
if udg_UnitDamageRegistered[i] then
call TriggerRegisterUnitEvent(udg_DamageEventTrigger, udg_UDexUnits[i], EVENT_UNIT_DAMAGED)
endif
set i = udg_UDexNext[i]
endloop
endif
endif
endif
return false
endfunction
//===========================================================================
function InitTrig_Damage_Engine takes nothing returns nothing
local unit u = CreateUnit(Player(15), 'uloc', 0, 0, 0)
local integer i = 16
//Create this trigger with UnitIndexEvents in order add and remove units
//as they are created or removed.
local trigger t = CreateTrigger()
call TriggerRegisterVariableEvent(t, "udg_UnitIndexEvent", EQUAL, 1.00)
call TriggerRegisterVariableEvent(t, "udg_UnitIndexEvent", EQUAL, 2.00)
call TriggerAddCondition(t, Filter(function SetupDmgEv))
set t = null
//Run the configuration trigger to set all configurables:
if gg_trg_Damage_Engine_Config == null then
//It's possible this InitTrig_ function ran first, in which case use ExecuteFunc.
call ExecuteFunc("Trig_Damage_Engine_Config_Actions")
else
call TriggerExecute(gg_trg_Damage_Engine_Config)
endif
//Create trigger for storing all EVENT_UNIT_DAMAGED events.
call CreateDmgEvTrg()
//Create GUI-friendly trigger for cleaning up after UnitDamageTarget.
set udg_ClearDamageEvent = CreateTrigger()
call TriggerAddCondition(udg_ClearDamageEvent, Filter(function PreCheckDamagedLifeEvent))
//Disable SpellDamageAbility for every player.
loop
set i = i - 1
call SetPlayerAbilityAvailable(Player(i), udg_SpellDamageAbility, false)
exitwhen i == 0
endloop
//Preload abilities.
call UnitAddAbility(u, udg_DamageBlockingAbility)
call UnitAddAbility(u, udg_SpellDamageAbility)
call RemoveUnit(u)
set u = null
endfunction
//TESH.scrollpos=-1
//TESH.alwaysfold=0
function Cond takes nothing returns boolean
return IsUnitType( GetTriggerUnit(), UNIT_TYPE_HERO )
endfunction
function A takes nothing returns nothing
local unit u = GetTriggerUnit()
local integer ID = GetUnitTypeId( u )
local player p = GetOwningPlayer( u )
local real facing = GetRandomReal( 0, 360 )
local real wait = 2
if not IsUnitType( u, UNIT_TYPE_HERO ) then
call CreateUnit( p, ID, GetRandomReal( GetRectMinX( bj_mapInitialPlayableArea ), GetRectMaxX( bj_mapInitialPlayableArea ) ), GetRandomReal( GetRectMinY( bj_mapInitialPlayableArea ), GetRectMaxY( bj_mapInitialPlayableArea ) ), facing )
call TriggerSleepAction( wait )
call RemoveUnit( u )
else
call TriggerSleepAction( wait )
call ReviveHero( u, GetRectCenterX( bj_mapInitialPlayableArea ), GetRectCenterY( bj_mapInitialPlayableArea ), false )
endif
set u = null
set p = null
endfunction
function B takes nothing returns nothing
local unit u = GetTriggerUnit()
local player p = GetOwningPlayer( u )
local integer i = GetHeroLevel( u )
if IsUnitAlly( u, p ) then
call SetHeroLevel( u, ( i + 1 ), true )
endif
set u = null
set p = null
endfunction
function InitTrig_Init takes nothing returns nothing
local real centerX = GetRectCenterX( bj_mapInitialPlayableArea )
local real centerY = GetRectCenterY( bj_mapInitialPlayableArea )
local player p = Player(1)
local real dist = 1300
local integer creepcount = 20
local integer campcount = 15
local integer i = 0
local integer f = 360
local real x
local real y
local integer a = 1
local real facing
local integer index = 0
local trigger t1 = CreateTrigger()
local trigger t2 = CreateTrigger()
call FogEnable( false )
call FogMaskEnable( false )
call SetHeroLevel( CreateUnit( Player(0), 'H000', centerX - 200, centerY, 270 ), 10, false )
call SetHeroLevel( CreateUnit( Player(0), 'H001', centerX + 200, centerY, 270 ), 10, false )
call SetPlayerState( p, PLAYER_STATE_GIVES_BOUNTY, 1 )
loop
exitwhen i > f
set i = i + ( f / campcount )
set x = centerX + dist * Cos( i * bj_DEGTORAD )
set y = centerY + dist * Sin( i * bj_DEGTORAD )
set facing = bj_RADTODEG * Atan2(centerY - y, centerX - x)
loop
exitwhen a > creepcount
set a = a + 1
call CreateUnit( p, 'hpea', x, y, facing )
endloop
set a = 1
endloop
set p = null
loop
call TriggerRegisterPlayerUnitEvent( t1, Player(index), EVENT_PLAYER_UNIT_DEATH, null )
call TriggerRegisterPlayerUnitEvent( t2, Player(index), EVENT_PLAYER_UNIT_SELECTED, null )
set index = index + 1
exitwhen index == 16
endloop
call TriggerAddAction( t1, function A )
call TriggerAddCondition( t2, Filter( function Cond ) )
call TriggerAddAction( t2, function B )
set t1 = null
set t2 = null
endfunction