- Joined
- Feb 18, 2014
- Messages
- 3,709
Hi, I wanted to optimize the old creep respawn system in my custom campaign so I asked ChatGPT to help me with that and it said that I should replace the Wait with a Timer instead to improve performance. Here are my triggers:
Everything seem to work as intended during my tests but I'm not sure if these triggers are leaking or cause issues on the long run. Can someone tell me if these triggers are okay? Thanks.
JASS:
function InitCreepRespawn takes nothing returns nothing
local group g = CreateGroup()
local unit u
local integer id
call GroupEnumUnitsOfPlayer(g, Player(PLAYER_NEUTRAL_AGGRESSIVE), null)
loop
set u = FirstOfGroup(g)
exitwhen u == null
call GroupRemoveUnit(g, u)
set udg_CreepIndex = udg_CreepIndex + 1
set id = udg_CreepIndex
call SetUnitUserData(u, id)
set udg_CreepX[id] = GetUnitX(u)
set udg_CreepY[id] = GetUnitY(u)
set udg_CreepType[id] = GetUnitTypeId(u)
set udg_CreepTimer[id] = CreateTimer()
endloop
call DestroyGroup(g)
endfunction
//===========================================================================
function InitTrig_Respawn_Setup takes nothing returns nothing
set gg_trg_Respawn_Setup = CreateTrigger( )
call TriggerAddAction( gg_trg_Respawn_Setup, function InitCreepRespawn )
endfunction
JASS:
function RespawnCheck takes nothing returns nothing
local timer t = GetExpiredTimer()
local integer id = 1
local group g
local boolean nearby = false
local unit u
loop
exitwhen id > udg_CreepIndex
if udg_CreepTimer[id] == t then
set g = CreateGroup()
call GroupEnumUnitsOfPlayer(g, Player(0), null)
loop
set u = FirstOfGroup(g)
exitwhen u == null
call GroupRemoveUnit(g, u)
if IsUnitAliveBJ(u) and IsUnitInRangeXY(u, udg_CreepX[id], udg_CreepY[id], 1400) then
set nearby = true
exitwhen true
endif
endloop
call DestroyGroup(g)
// Delay respawn if player nearby
if nearby then
call TimerStart(t, 5.0, false, function RespawnCheck)
return
endif
// Respawn creep
call SetUnitUserData(CreateUnit(Player(PLAYER_NEUTRAL_AGGRESSIVE),udg_CreepType[id],udg_CreepX[id],udg_CreepY[id],GetRandomReal(0,360)),id)
return
endif
set id = id + 1
endloop
endfunction
function CreepDies takes nothing returns nothing
local unit u = GetTriggerUnit()
local integer lvl = GetUnitLevel(u)
local integer id = GetUnitUserData(u)
local integer low
local integer high
local integer chance
// Item Table
if lvl <= 3 then
set low = 1
set high = 3
set chance = 15
elseif lvl <= 6 then
set low = 4
set high = 6
set chance = 20
else
set low = 7
set high = 9
set chance = 25
endif
if GetRandomInt(1, 100) <= chance then
call CreateItem( udg_CreepTable[GetRandomInt(low,high)], GetUnitX(u),GetUnitY(u) )
endif
// Respawn Timer
if id > 0 then
call TimerStart(udg_CreepTimer[id], 15.0, false, function RespawnCheck)
endif
set u = null
endfunction
//===========================================================================
function InitTrig_Respawn_Creep takes nothing returns nothing
set gg_trg_Respawn_Creep = CreateTrigger( )
call TriggerRegisterPlayerUnitEventSimple( gg_trg_Respawn_Creep, Player(PLAYER_NEUTRAL_AGGRESSIVE), EVENT_PLAYER_UNIT_DEATH )
call TriggerAddAction( gg_trg_Respawn_Creep, function CreepDies )
endfunction
JASS:
function FilterNeutralHostile takes nothing returns boolean
return GetOwningPlayer(GetFilterUnit()) == Player(PLAYER_NEUTRAL_AGGRESSIVE)
endfunction
function CreepWanderLoop takes nothing returns nothing
local integer i = 1
local unit h
local group g
local unit u
local integer id
local real hx
local real hy
local real angle
local real dist
local real tx
local real ty
loop
exitwhen i > udg_NHeroes
set h = udg_Hero[i]
if h != null and IsUnitAliveBJ(h) then
set hx = GetUnitX(h)
set hy = GetUnitY(h)
set g = CreateGroup()
call GroupEnumUnitsInRange(g,hx,hy,1000,Condition(function FilterNeutralHostile))
loop
set u = FirstOfGroup(g)
exitwhen u == null
call GroupRemoveUnit(g, u)
if IsUnitAliveBJ(u) and GetUnitCurrentOrder(u) == 0 and GetUnitLevel(u) < 6 then
set id = GetUnitUserData(u)
// random point inside leash radius
set angle = GetRandomReal(0, 6.283)
set dist = GetRandomReal(100, 400)
set tx = udg_CreepX[id] + dist * Cos(angle)
set ty = udg_CreepY[id] + dist * Sin(angle)
if not IsTerrainPathable(tx,ty,PATHING_TYPE_WALKABILITY) and GetRandomInt(1, 100) <= 40 then
call IssuePointOrder(u, "attack", tx, ty)
endif
endif
endloop
call DestroyGroup(g)
endif
set i = i + 1
endloop
set h = null
set u = null
endfunction
//===========================================================================
function InitTrig_Respawn_Roam takes nothing returns nothing
set gg_trg_Respawn_Roam = CreateTrigger( )
call TriggerRegisterTimerEvent( gg_trg_Respawn_Roam, 3.0, true )
call TriggerAddAction( gg_trg_Respawn_Roam, function CreepWanderLoop )
endfunction
JASS:
function Respawn_Table takes nothing returns nothing
// Runes
set udg_CreepTable[1] = 'rhe2' //Rune of Healing
set udg_CreepTable[2] = 'rman' //Rune of Mana
set udg_CreepTable[3] = 'rspd' //Rune of Speed
// Scrolls
set udg_CreepTable[4] = 'shea' //Scroll of Healing
set udg_CreepTable[5] = 'sman' //Scroll of Mana
set udg_CreepTable[6] = 'spro' //Scroll of Protection
// Tomes
set udg_CreepTable[7] = 'tdex' //Tome of Agility
set udg_CreepTable[8] = 'tstr' //Tome of Strength
set udg_CreepTable[9] = 'tint' //Tome of Intelligence
endfunction
//===========================================================================
function InitTrig_Respawn_Table takes nothing returns nothing
set gg_trg_Respawn_Table = CreateTrigger( )
call TriggerRegisterTimerEvent( gg_trg_Respawn_Table, 0.0, false )
call TriggerAddAction( gg_trg_Respawn_Table, function Respawn_Table )
endfunction
Last edited:


