• 🏆 Texturing Contest #33 is OPEN! Contestants must re-texture a SD unit model found in-game (Warcraft 3 Classic), recreating the unit into a peaceful NPC version. 🔗Click here to enter!
  • It's time for the first HD Modeling Contest of 2024. Join the theme discussion for Hive's HD Modeling Contest #6! Click here to post your idea!

Complex trigger, need leak check for pure JASS

Status
Not open for further replies.
Level 12
Joined
Sep 4, 2007
Messages
407
Ok, i need a leak check for jass... xD check this out:

This is a cluster organizer (there are more triggers for such, but i'll only put this one, if i solve this one, i solve the rest.) basically it will send units from a cluster with more than 5 untis to a cluster with less than that. It is MUI and stuff. A00X is an dummy ability I use to separate the klusters, it has like 100 levels (100 clusters are possible). This trigger has other effects but i'll only exeplain if needed to =). help?

JASS:
function Trig_SP_TA_Func001A takes nothing returns boolean
    return ( GetUnitAbilityLevelSwapped('A00X', GetFilterUnit()) == GetForLoopIndexB())
endfunction

function Trig_SP_TA_Func001B takes nothing returns boolean
    return ( GetUnitAbilityLevelSwapped('A00X', GetFilterUnit()) == GetForLoopIndexA())
endfunction

function Trig_SP_TA_Actions takes nothing returns nothing
    local unit newpackunit
    local group packs
    local group overpack
    local integer LoopD
    local integer xlvl
    local integer packnumb
    set LoopD = 1
    loop
        exitwhen LoopD > 12
        if (udg_CC_SocialBehavior[LoopD] == 3) then
                  set bj_forLoopBIndex = 1
                  set bj_forLoopBIndexEnd = 10
                  loop
                      exitwhen bj_forLoopBIndex > bj_forLoopBIndexEnd
                      set packs = GetUnitsOfPlayerMatching(ConvertedPlayer(LoopD), Condition(function Trig_SP_TA_Func001A))
                      if (GetBooleanAnd((CountUnitsInGroup(packs) < 5), (CountUnitsInGroup(packs) != 0 ))) then
                         set packnumb = CountUnitsInGroup(packs)
                         set xlvl = GetForLoopIndexB()
                         set bj_forLoopAIndex = 1
                         set bj_forLoopAIndexEnd = 10
                         loop
                             exitwhen bj_forLoopAIndex > bj_forLoopAIndexEnd
                             set overpack = GetUnitsOfPlayerMatching(ConvertedPlayer(LoopD), Condition(function Trig_SP_TA_Func001B))
                             if (CountUnitsInGroup(overpack) > 5 ) then
                                 set newpackunit = GroupPickRandomUnit(overpack)
                                 call SetUnitAbilityLevelSwapped( 'A00X', newpackunit, xlvl )
                                 if ( CountUnitsInGroup(packs) >= 5 ) then
                                     set bj_forLoopAIndex = 10
                                     set newpackunit = null                                     
                                 else
                                 endif
                             else
                                 if (CountUnitsInGroup(overpack) == (5 - packnumb)) then
                                 set newpackunit = GroupPickRandomUnit(overpack)
                                 call SetUnitAbilityLevelSwapped( 'A00X', newpackunit, xlvl )
                                     if ( CountUnitsInGroup(packs) >= 5 ) then
                                        set bj_forLoopAIndex = 10
                                        set newpackunit = null                                     
                                     else
                                     endif
                                 else
                                 endif
                             endif
                             set bj_forLoopAIndex = bj_forLoopAIndex + 1
                         endloop
                      else
                      endif
                      set bj_forLoopBIndex = bj_forLoopBIndex + 1
                  endloop  
        else
        endif
        set LoopD = LoopD + 1
    endloop
    set newpackunit = null
    call DestroyGroup(packs)
    call DestroyGroup(overpack) 
endfunction

//===========================================================================
function InitTrig_SP_TogetherAdjustment takes nothing returns nothing
    set gg_trg_SP_TogetherAdjustment = CreateTrigger(  )
    call TriggerRegisterTimerEventPeriodic( gg_trg_SP_TogetherAdjustment, 0.20 )
    call TriggerAddAction( gg_trg_SP_TogetherAdjustment, function Trig_SP_TA_Actions )
endfunction

since there are so many loops, i suppose it will leak when changin the loop integer number and the variables are not destroy or cleaned. the problem is, if I destroy the variables I won't be able to use them again in the next integer number of the loop. got it? how do I solve this?

Oh, and any help improving the effect of it will be welcome with +rep
 
Here is it a bit more optimized:
JASS:
function SPPackCond takes nothing returns boolean
    return GetUnitAbilityLevel(GetFilterUnit(),'A00X') == bj_forLoopBIndex
endfunction

function SPOverPackCond takes nothing returns boolean
    return GetUnitAbilityLevel(GetFilterUnit(),'A00X') == bj_forLoopAIndex
endfunction

function SPTA_Act takes nothing returns nothing
    local unit newpackunit  = null
    local group packs       = CreateGroup()
    local group overpack    = CreateGroup()
    local integer LoopD     = 0
    local integer xlvl      = 0
    local integer Pcount    = 0
    local integer overCount = 0 
    
    set bj_forLoopAIndex = 0
    set bj_forLoopBIndex = 0
    
    loop
        exitwhen LoopD > 11
        if (udg_CC_SocialBehavior[LoopD] == 3) then
            loop
                exitwhen bj_forLoopBIndex > 9
                call GroupEnumUnitsOfPlayer(packs,Player(LoopD),Condition(function SPPackCond))
                set Pcount = CountUnitsInGroup(packs)
                if Pcount<5 and not (Pcount == 0) then
                    set xlvl = bj_forLoopAIndex
                    loop
                        exitwhen bj_forLoopAIndex > 9
                        call GroupEnumUnitsOfPlayer(overpack,Player(LoopD),Condition(function SPOverPackCond))
                        set overCount = CountUnitsInGroup(overpack)
                        
                        if overCount > 5 then
                            set newpackunit = GroupPickRandomUnit(overpack)
                            call SetUnitAbilityLevel(newpackunit,'A00X',xlvl)
                            if  Pcount >= 5 then
                                set bj_forLoopAIndex = 10
                            endif
                        else
                            if overCount == (5 - Pcount) then
                                set newpackunit = GroupPickRandomUnit(overpack)
                                call SetUnitAbilityLevel(newpackunit,'A00X',xlvl)
                                if Pcount >= 5 then
                                    set bj_forLoopAIndex = 10
                                endif
                            endif
                        endif
                        set bj_forLoopAIndex = bj_forLoopAIndex + 1
                    endloop
                endif
                set bj_forLoopBIndex = bj_forLoopBIndex + 1
            endloop
        endif
        set LoopD = LoopD + 1
    endloop
    set newpackunit = null
    call DestroyGroup(packs)
    call DestroyGroup(overpack)
    set packs = null
    set overpack = null
endfunction

//===========================================================================
function InitTrig_SP_TogetherAdjustment takes nothing returns nothing
    local trigger t = CreateTrigger()
    call TriggerRegisterTimerEvent(t,.20,true)
    call TriggerAddAction(t,function SPTA_Act)
    set t = null
endfunction

I didn't inline the CountUnitsInGroup() and GroupPickRandomUnit() though since I was lazy. Overall, your code doesn't really have major leaks. DestroyGroup() leaks some RAM as far as I know, but for that you need the two groups you use to be global groups. In this case, using the global groups might make a difference since you are creating and destroying the groups every 0.2 seconds.
 
Level 12
Joined
Sep 4, 2007
Messages
407
Overall, your code doesn't really have major leaks. DestroyGroup() leaks some RAM as far as I know, but for that you need the two groups you use to be global groups. In this case, using the global groups might make a difference since you are creating and destroying the groups every 0.2 seconds.

any suggestion other than using global variables? they tend to make me confused and i got like severeal of this kind of trigger (this means huge global variable managing...).

do i need to create a local integer to store the unit number? i though that didnt leak. anyway, gonna do it because it helps organizing it. =)
 
Level 12
Joined
Sep 4, 2007
Messages
407
Ok remade it in your way (with some of mine) and it is like this. It is more organized. (i also made a couple changes in the triggering for the map but that doesnt really matter)

JASS:
function Trig_SP_TA_Func001A takes nothing returns boolean
    return ( GetUnitAbilityLevelSwapped('A00X', GetFilterUnit()) == GetForLoopIndexA())
endfunction

function Trig_SP_TA_Func001B takes nothing returns boolean
    return ( GetUnitAbilityLevelSwapped('A00X', GetFilterUnit()) == GetForLoopIndexB())
endfunction

function Trig_SP_TA_Actions takes nothing returns nothing
    local unit newpackunit
    local group pack
    local group overpack
    local integer LoopC
    local integer xlvl
    local integer packcount
    local integer overcount

    set LoopC = 1
    set bj_forLoopAIndex = 1
    set bj_forLoopBIndex = 1
    loop
        exitwhen LoopC > 12
        if (udg_CC_SocialBehavior[LoopC] == 3) then

                  loop
                      exitwhen bj_forLoopAIndex > 10
                      set pack = GetUnitsOfPlayerMatching(ConvertedPlayer(LoopC), Condition(function Trig_SP_TA_Func001A))
                      set packcount = CountUnitsInGroup(pack)
                      if packcount < 5 and packcount != 0 then
                         set xlvl = GetForLoopIndexA()

                         loop
                             exitwhen bj_forLoopBIndex > 10
                             set overpack = GetUnitsOfPlayerMatching(ConvertedPlayer(LoopC), Condition(function Trig_SP_TA_Func001B))
                             set overcount = CountUnitsInGroup(overpack)
                             if overcount > 5 then
                                 set newpackunit = GroupPickRandomUnit(overpack)
                                 call SetUnitAbilityLevelSwapped( 'A00X', newpackunit, xlvl )
                                 call GroupEnumUnitsOfPlayer(pack,Player(LoopC),Condition(function Trig_SP_TA_Func001A))
                                 set packcount = CountUnitsInGroup(pack)
                                 if ( CountUnitsInGroup(pack) >= 5 ) then
                                     set bj_forLoopBIndex = 11                                    
                                 else
                                 endif
                             else
                                 if overcount + packcount <= 5 then
                                 set newpackunit = GroupPickRandomUnit(overpack)
                                 call SetUnitAbilityLevelSwapped( 'A00X', newpackunit, xlvl )
                                    if packcount >= 5 then
                                       set bj_forLoopBIndex = 11                                   
                                    endif
                                 endif
                             endif
                             set bj_forLoopBIndex = bj_forLoopBIndex + 1
                         endloop

                      endif
                      set bj_forLoopAIndex = bj_forLoopAIndex + 1
                  endloop  

        endif
        set LoopC = LoopC + 1
    endloop
    set newpackunit = null
    set pack = null
    set overpack = null
    call DestroyGroup(pack)
    call DestroyGroup(overpack) 
endfunction

//===========================================================================
function InitTrig_SP_TogetherAdjustment takes nothing returns nothing
    local trigger SP_TogetherAdjustment = CreateTrigger(  )
    call TriggerRegisterTimerEventPeriodic( SP_TogetherAdjustment, 0.20 )
    call TriggerAddAction( SP_TogetherAdjustment, function Trig_SP_TA_Actions )
    set SP_TogetherAdjustment = null
endfunction

still, i gotta find a way to use those groups without using globals. There are other 16 triggers like this one, some with 5 groups in it. can't really use globals.
 
You should use a group array. It is instantaneous and pretty easy to implement in your case too. I'll try to modify your code a bit to see if I can replace it with a global group array.

EDIT: Basically this, it isn't the most optimal but I just quickly modified your code. Make a global group array named PackG:
JASS:
function Trig_SP_TA_Func001A takes nothing returns boolean
    return ( GetUnitAbilityLevelSwapped('A00X', GetFilterUnit()) == GetForLoopIndexA())
endfunction

function Trig_SP_TA_Func001B takes nothing returns boolean
    return ( GetUnitAbilityLevelSwapped('A00X', GetFilterUnit()) == GetForLoopIndexB())
endfunction

function Trig_SP_TA_Actions takes nothing returns nothing
    local unit newpackunit
    local group pack = udg_PackG[0]
    local group overpack = udg_PackG[1]
//used just for simple modification
    local integer LoopC
    local integer xlvl
    local integer packcount
    local integer overcount

    set LoopC = 1
    set bj_forLoopAIndex = 1
    set bj_forLoopBIndex = 1
    loop
        exitwhen LoopC > 12
        if (udg_CC_SocialBehavior[LoopC] == 3) then

                  loop
                      exitwhen bj_forLoopAIndex > 10
                      call GroupEnumUnitsOfPlayer(pack,ConvertedPlayer(LoopC),Condition(function Trig_SP_TA_Func001A))
                      set packcount = CountUnitsInGroup(pack)
                      if packcount < 5 and packcount != 0 then
                         set xlvl = GetForLoopIndexA()

                         loop
                             exitwhen bj_forLoopBIndex > 10
                             call GroupEnumUnitsOfPlayer(overpack,ConvertedPlayer(LoopC),Condition(function Trig_SP_TA_Func001B))
                             set overcount = CountUnitsInGroup(overpack)
                             if overcount > 5 then
                                 set newpackunit = GroupPickRandomUnit(overpack)
                                 call SetUnitAbilityLevelSwapped( 'A00X', newpackunit, xlvl )
                                 call GroupEnumUnitsOfPlayer(pack,ConvertedPlayer(LoopC),Condition(function Trig_SP_TA_Func001A))
                                 set packcount = CountUnitsInGroup(pack)
                                 if ( CountUnitsInGroup(pack) >= 5 ) then
                                     set bj_forLoopBIndex = 11                                    
                                 else
                                 endif
                             else
                                 if overcount + packcount <= 5 then
                                 set newpackunit = GroupPickRandomUnit(overpack)
                                 call SetUnitAbilityLevelSwapped( 'A00X', newpackunit, xlvl )
                                    if packcount >= 5 then
                                       set bj_forLoopBIndex = 11                                   
                                    endif
                                 endif
                             endif
                             set bj_forLoopBIndex = bj_forLoopBIndex + 1
                         endloop

                      endif
                      set bj_forLoopAIndex = bj_forLoopAIndex + 1
                  endloop  

        endif
        set LoopC = LoopC + 1
    endloop
    set newpackunit = null
    set pack = null
    set overpack = null 
//no need to clear them, enumeration automatically clears (afaik)
endfunction

//===========================================================================
function InitTrig_SP_TogetherAdjustment takes nothing returns nothing
    local trigger SP_TogetherAdjustment = CreateTrigger(  )
    set udg_PackG[0] = CreateGroup()
    set udg_PackG[1] = CreateGroup()
//create them here, this runs at map init
    call TriggerRegisterTimerEventPeriodic( SP_TogetherAdjustment, 0.20 )
    call TriggerAddAction( SP_TogetherAdjustment, function Trig_SP_TA_Actions )
    set SP_TogetherAdjustment = null
endfunction

This way, you only need 2 groups used every 0.2 seconds rather than creating 2 groups every 0.20 seconds.
That's like 600 groups a minute. It won't really lag much at first since they are being destroyed (so it isn't the worst leak), but it might build up eventually and get annoying.
 
Last edited:
Level 12
Joined
Sep 4, 2007
Messages
407
This way, you only need 2 groups used every 0.2 seconds rather than creating 2 groups every 0.20 seconds.
That's like 600 groups a minute. It won't really lag much at first since they are being destroyed (so it isn't the worst leak), but it might build up eventually and get annoying.

so, with this simple modification i make it leakless?
 
Level 12
Joined
Sep 4, 2007
Messages
407
i though the locals would leak anyway cuz they are not used next time the trigger runs! so your way just makes new locals to be created and not removed. o_O

JASS:
function Trig_leak_Actions takes nothing returns nothing
   local group group1 = udg_Group[1]
   local group group2 = udg_Group[2]

 //Trigger stuff here

   set group1 = null
   set group2 = null
endfuction

function InitTrig_SP_PackCreation takes nothing returns nothing
    local trigger t = CreateTrigger(  )
    set udg_Group[1] = CreateGroup()
    set udg_Group[2] = CreateGroup()
    call TriggerRegisterTimerEventPeriodic( t, 10.00 )
    call TriggerAddAction( t, function Trig_leak_Actions )
    set t = null
endfunction

this makes the locals to be used again instead of being created and used and destroied?
 
Last edited:
Level 12
Joined
Sep 4, 2007
Messages
407
oh and this:

JASS:
call GroupEnumUnitsOfPlayer(pack,ConvertedPlayer(LoopC),Condition(function Trig_SP_TA_Func001A))

don't work. it has to be:

JASS:
set pack = GetUnitsOfPlayerMatching(ConvertedPlayer(LoopC), Condition(function Trig_SP_TA_Func001A))
 
oh and this:

JASS:
call GroupEnumUnitsOfPlayer(pack,ConvertedPlayer(LoopC),Condition(function Trig_SP_TA_Func001A))

don't work. it has to be:

JASS:
set pack = GetUnitsOfPlayerMatching(ConvertedPlayer(LoopC), Condition(function Trig_SP_TA_Func001A))

If you use the 2nd one, it will leak. And it destroys a boolexpr which is "potentially dangerous" to the map.

Are you sure the first method doesn't work?
 
Level 12
Joined
Sep 4, 2007
Messages
407
Are you sure the first method doesn't work?

pretty sure it doesn't. I dunno why aswell, it should work.

I think i can do it another way, tell me if doing this will leak aswell.

JASS:
    set bj_wantDestroyGroup = true
    call GroupAddGroup( GetUnitsOfPlayerMatching(Player(LoopC), Condition(function Trig_01)), pack )

actually i don even know if bj_wantDestroyGroup affecs call GroupAddGroup()
 
It will still leak with it because it will create a group. Even though it destroys it, it will cause a minor RAM leak due to the enumeration. Try the code again. If you're basing it on the code I posted 4th post, try it again because I think I might've made a mistake right then.

It should work both ways since the they both do the exact same thing. (except that the GetUnitsOfPlayer() destroys a boolexpr which is considered "dangerous")
 
Level 12
Joined
Sep 4, 2007
Messages
407
I've tried again, the native function works and the other (the healthier) doesn't! This is strange...

oh, and I didnt converted my whole trigger to natives because of that... i needed to know if somethig would go wrong so i changed a part and tested everytime. after solving this i'll change the other natives to the types you posted.

It will still leak with it because it will create a group. Even though it destroys it, it will cause a minor RAM leak due to the enumeration. Try the code again. If you're basing it on the code I posted 4th post, try it again because I think I might've made a mistake right then.

what mistake?

by the way the trigger right now looks like this. It doesn't work.

JASS:
function Trig_SP_TA_Func001A takes nothing returns boolean
    return GetUnitAbilityLevel(GetFilterUnit(),'A00X') == bj_forLoopAIndex
endfunction

function Trig_SP_TA_Func001B takes nothing returns boolean
    return GetUnitAbilityLevel(GetFilterUnit(),'A00X') == bj_forLoopBIndex
endfunction

function Trig_SP_TA_Actions takes nothing returns nothing
    local unit newpackunit
    local group pack
    local group overpack
    local integer LoopC
    local integer xlvl
    local integer packcount
    local integer overcount
    local player packowner

    set LoopC = 1
    set bj_forLoopAIndex = 1
    set bj_forLoopBIndex = 1
    loop
        exitwhen LoopC > 12
        if (udg_CC_SocialBehavior[LoopC] == 3) then

                  loop
                      exitwhen bj_forLoopAIndex > 10
                      set packowner = ConvertedPlayer(LoopC)
                      call GroupEnumUnitsOfPlayer(pack,packowner,Condition(function Trig_SP_TA_Func001A))
                      set packcount = CountUnitsInGroup(pack)
                      if packcount < 5 and packcount != 0 then
                         set xlvl = bj_forLoopAIndex

                         loop
                             exitwhen bj_forLoopBIndex > 10
                             call GroupEnumUnitsOfPlayer(overpack,packowner,Condition(function Trig_SP_TA_Func001B))
                             set overcount = CountUnitsInGroup(overpack)
                             if overcount > 5 then
                                 set newpackunit = GroupPickRandomUnit(overpack)
                                 call SetUnitAbilityLevel( newpackunit,'A00X', xlvl )
                                 call GroupEnumUnitsOfPlayer(pack,packowner,Condition(function Trig_SP_TA_Func001A))
                                 set packcount = CountUnitsInGroup(pack)
                                 if packcount >= 5 then
                                     set bj_forLoopBIndex = 11                                    
                                 endif
                             else
                                 if overcount + packcount <= 5 then
                                 set newpackunit = GroupPickRandomUnit(overpack)
                                 call SetUnitAbilityLevel( newpackunit,'A00X', xlvl )
                                    if packcount >= 5 then
                                       set bj_forLoopBIndex = 11                                   
                                    endif
                                 endif
                             endif
                             set bj_forLoopBIndex = bj_forLoopBIndex + 1
                         endloop

                      endif
                      set bj_forLoopAIndex = bj_forLoopAIndex + 1
                  endloop  

        endif
        set LoopC = LoopC + 1
    endloop
    set newpackunit = null
    set packowner = null
    set pack = null
    set overpack = null
endfunction

//===========================================================================
function InitTrig_SP_TogetherAdjustment takes nothing returns nothing
    local trigger SP_TogetherAdjustment = CreateTrigger(  )
    set udg_PackG[0] = CreateGroup()
    set udg_PackG[1] = CreateGroup()
    call TriggerRegisterTimerEvent( SP_TogetherAdjustment, 0.20, true )
    call TriggerAddAction( SP_TogetherAdjustment, function Trig_SP_TA_Actions )
    set SP_TogetherAdjustment = null
endfunction

maybe its the "player" in the "call GroupEnumUnitsOfPlayer(overpack,ConvertedPlayer(LoopC),Condition(function Trig_SP_TA_Func001B))" I'll make a local player and see if it works.

Edit: nope, it's not the player. i dunno maybe a non-native function cannot reconize a native variable (bj_forLoopBIndex) in the condition, dunno...

by the way do you have any non-native for GroupPickRandomUnit() or CountUnitsInGroup()??
 
Last edited:
Ok, add this debug message:
JASS:
                      call GroupEnumUnitsOfPlayer(pack,packowner,Condition(function Trig_SP_TA_Func001A))
                      //^have this
                      set packcount = CountUnitsInGroup(pack)
                      call BJDebugMsg(I2S(packcount))
                      //add this debug message^

First try it out like that, and then tell me what number it produces.

Then try this:
JASS:
                      set pack = GetUnitsOfPlayerMatching(ConvertedPlayer(LoopC), Condition(function Trig_SP_TA_Func001A))
                      //have this^
                      set packcount = CountUnitsInGroup(pack)
                      call BJDebugMsg(I2S(packcount))
                      //add this debug message^

And then see what it produces.
 
Level 12
Joined
Sep 4, 2007
Messages
407
Ok, add this debug message:
JASS:
                      call GroupEnumUnitsOfPlayer(pack,packowner,Condition(function Trig_SP_TA_Func001A))
                      //^have this
                      set packcount = CountUnitsInGroup(pack)
                      call BJDebugMsg(I2S(packcount))
                      //add this debug message^

First try it out like that, and then tell me what number it produces.

Then try this:
JASS:
                      set pack = GetUnitsOfPlayerMatching(ConvertedPlayer(LoopC), Condition(function Trig_SP_TA_Func001A))
                      //have this^
                      set packcount = CountUnitsInGroup(pack)
                      call BJDebugMsg(I2S(packcount))
                      //add this debug message^

And then see what it produces.

in the first, i get nothing from the debug message, it's like the command never existed.

in the second, it locates each group (10 in total) and say the number of units. first 5, second 5, the rest 0 (there are only 10 units affected by the trigger)
 
Level 12
Joined
Sep 4, 2007
Messages
407
I can make an artificial function to get that group, such function would use an preexistant group instead of creating one. that would solve the creation and destruction of new groups. I know, i'm sort of doing what blizzard does so well, making "BJ"s, but my priority is to not to leak. so what do you think?

JASS:
function GUOfPM takes player whichPlayer, boolexpr filter returns group
    call GroupEnumUnitsOfPlayer(udg_PackG[0], whichPlayer, filter)
    call DestroyBoolExpr(filter)
    return udg_PackG[0]
endfunction

function Trig_SP_TA_Func001A takes nothing returns boolean
   return GetUnitAbilityLevel(GetFilterUnit(),'A00X') == bj_forLoopAIndex
endfunction

function Trig_SP_TA_Actions takes nothing returns nothing
     local group xgroup = udg_PackG[1]
     local player jogador = Player(PLAYER_NEUTRAL_PASSIVE)
     set xgroup = GUOfPM(jogador, Condition(function Trig_SP_TA_Func001A))
     set udg_PackG[0] = null
     
     //actions using xgroup
  
     set xgroup = null
     set jogador = null
endfunction

function InitTrig_SPTogetherAdjustment1 takes nothing returns nothing
    local trigger SP_TogetherAdjustment = CreateTrigger(  )
    set udg_PackG[0] = CreateGroup()
    set udg_PackG[1] = CreateGroup()
    call TriggerRegisterTimerEvent( SP_TogetherAdjustment, 0.20, true )
    call TriggerAddAction( SP_TogetherAdjustment, function Trig_SP_TA_Actions )
    set SP_TogetherAdjustment = null
endfunction

EDIT: Doing this with my trigger works really nice. It doesn't create new groups and delete them. Gonna try without destroying the boolexpr now.

EDIT: I've try it and not destroying the boolexpr makes the trigger not to work. Discovered why "call GroupEnumUnitsOfPlayer(group, whichPlayer, filter)" does not work. For it to work, you have to destroy the boolexpr it takes. Thats why " GetUnitsOfPlayerMatching(packowner, Condition(function Trig_SP_TA_Func001A))" worked. it destroys the boolexpr inside it.


The trigger now looks like this: (it is fully functional)

JASS:
function GUOfPM takes player whichPlayer, boolexpr filter returns group
    call GroupEnumUnitsOfPlayer(udg_GAME_PackG[5], whichPlayer, filter)
    call DestroyBoolExpr(filter)
    return udg_GAME_PackG[5]
endfunction

function Trig_SP_TA_Func001A takes nothing returns boolean
   return GetUnitAbilityLevel(GetFilterUnit(),'A00X') == bj_forLoopAIndex
endfunction

function Trig_SP_TA_Func001B takes nothing returns boolean
   return GetUnitAbilityLevel(GetFilterUnit(),'A00X') == bj_forLoopBIndex
endfunction

function Trig_SP_TA_Actions takes nothing returns nothing
    local unit newpackunit
    local group pack = udg_GAME_PackG[0]
    local group overpack = udg_GAME_PackG[1]
    local integer LoopC
    local integer xlvl
    local integer packcount
    local integer overcount
    local player packowner

    set LoopC = 1
    set bj_forLoopAIndex = 1
    set bj_forLoopBIndex = 1
    loop
        exitwhen LoopC > 12
        if (udg_CC_SocialBehavior[LoopC] == 3) then

                  loop
                      exitwhen bj_forLoopAIndex > 10
                      set packowner = Player(LoopC - 1)
                      set pack = GUOfPM(packowner, Condition(function Trig_SP_TA_Func001A))
                      set packcount = CountUnitsInGroup(pack)
                      if packcount < 5 and packcount != 0 then
                         set xlvl = bj_forLoopAIndex

                         loop
                             exitwhen bj_forLoopBIndex > 10
                             set overpack = GUOfPM(packowner, Condition(function Trig_SP_TA_Func001B))
                             set overcount = CountUnitsInGroup(overpack)
                             if overcount > 5 then
                                 set newpackunit = GroupPickRandomUnit(overpack)
                                 call SetUnitAbilityLevel( newpackunit,'A00X', xlvl )
                                 set pack = GUOfPM(packowner, Condition(function Trig_SP_TA_Func001A))
                                 set packcount = CountUnitsInGroup(pack)
                                 if packcount >= 5 then
                                     set bj_forLoopBIndex = 11                                    
                                 endif
                             else
                                 if overcount + packcount <= 5 then
                                 set newpackunit = GroupPickRandomUnit(overpack)
                                 call SetUnitAbilityLevel( newpackunit,'A00X', xlvl )
                                    if packcount >= 5 then
                                       set bj_forLoopBIndex = 11                                   
                                    endif
                                 endif
                             endif
                             set bj_forLoopBIndex = bj_forLoopBIndex + 1
                         endloop

                      endif
                      set bj_forLoopAIndex = bj_forLoopAIndex + 1
                  endloop  

        endif
        set LoopC = LoopC + 1
    endloop
    set udg_GAME_PackG[5] = null
    set newpackunit = null
    set packowner = null
    set pack = null
    set overpack = null
endfunction

//===========================================================================
function InitTrig_SP_TogetherAdjustment takes nothing returns nothing
    local trigger SP_TogetherAdjustment = CreateTrigger(  )
    set udg_GAME_PackG[0] = CreateGroup()
    set udg_GAME_PackG[1] = CreateGroup()
    set udg_GAME_PackG[5] = CreateGroup()
    call TriggerRegisterTimerEvent( SP_TogetherAdjustment, 0.20, true )
    call TriggerAddAction( SP_TogetherAdjustment, function Trig_SP_TA_Actions )
    set SP_TogetherAdjustment = null
endfunction
 
Last edited:
Status
Not open for further replies.
Top