Removing and Adding Ability Problem.

Nherwyziant

Be better than you were yesterday :D
Reaction score
96
I have this trigger part on my spell. This spell is a passive spell, when a unit is damaged, this will happen. .u is the damage source and rawcode is the spell and .u us the cooldown spell.

[lJASS]call UnitRemoveAbility(.u,RAWCODE)[/lJASS]
[lJASS]call UnitAddAbility(.u,COOLDOWN)[/lJASS]
after a few sec, it is followed by
[lJASS]call UnitRemoveAbility(.u,COOLDOWN)[/lJASS]
[lJASS]call UnitAddAbility(.u,RAWCODE)[/lJASS]

but sometimes, the second trig doesn't remove and add, but it do runs. Why?

EDIT: I think the hero has something to do with this, cuz this spell is being learned(RAWCODE).
EDIT: Cuz i tried removing the part with adding and removing the cooldown, and the rawcode does not returned after removing but it do runs cuz i use messages.
 

Romek

Super Moderator
Reaction score
963
Showing us two working native functions and saying "it do nots works" isn't going to get you much help at all.

Post the rest of your code.
 

Nherwyziant

Be better than you were yesterday :D
Reaction score
96
Did you make sure you retrieved the struct data in the second trigger correctly?

Yeah

Showing us two working native functions and saying "it do nots works" isn't going to get you much help at all.

Post the rest of your code.

I was making a test spell, similar to DotA's Geminate Attack, which doubles your attack. But DotA's Geminate Attack is not triggered, and I decided to make a triggered one and ask IceFrog to use this trigger cuz non-triggered Geminate Attack is buggy.
JASS:
scope GeminateAttack initializer I
    private constant function Cooldown takes integer lvl returns integer
        return 5-lvl
    endfunction

    private struct s
        private static constant real    SPEED    = 750.   //The speed of the missile.
        private static constant integer RAWCODE  = 'A000' //The rawcode of the spell.
        private static constant integer COOLDOWN = 'A001' //The alternate spell which is the cooldown.
        private static constant integer DUMMY    = 'h000' //The code of the flying missile.

        unit u
        unit c
        unit r
        real x
        real y
        real d
        real a
        timer t
        timer t2
        method onDestroy takes nothing returns nothing
            call ReleaseTimer(.t)
            call UnitDamageTarget(.c,.r,.d,true,false,ATTACK_TYPE_NORMAL,DAMAGE_TYPE_NORMAL,null)
            call KillUnit(.c)
            set .u = null
            set .c = null
            set .r = null
            set .t = null
        endmethod

        static method create takes unit u,unit r,real x,real y,real d returns s
            local s this = s.allocate()
            set .t = NewTimer()
            set .t2 = NewTimer()
            set .r = r
            set .u = u
            set .x = x
            set .y = y
            set .d = d
            return this
        endmethod

        static method Mover takes nothing returns nothing
            local s this = GetTimerData(GetExpiredTimer())
            local real dx
            local real dy

            if GetWidgetLife(.r) < .405 then
                call RemoveUnit(.c)
            endif
            set .a = Atan2(GetUnitY(.r)-GetUnitY(.c),GetUnitX(.r)-GetUnitX(.c))
            set .x = GetUnitX(.c)+(SPEED/100)*Cos(.a)
            set .y = GetUnitY(.c)+(SPEED/100)*Sin(.a)
            call SetUnitPositionLoc(.c,Location(.x,.y))
            call SetUnitX(.c,.x)
            call SetUnitY(.c,.y)
            call SetUnitFacing(.c,.a)
            set dx = GetUnitX(.r)-GetUnitX(.c)
            set dy = GetUnitY(.r)-GetUnitY(.c)
            if SquareRoot(dx*dx+dy*dy) <= 25. then
                call .onDestroy()
            endif
        endmethod
        
        static method Refresh takes nothing returns nothing
            local s this = GetTimerData(GetExpiredTimer())

            call UnitRemoveAbility(.u,COOLDOWN)
            call UnitAddAbility(.u,RAWCODE)
            call ReleaseTimer(.t2)
        endmethod

        static method Act takes nothing returns nothing
            local s this = s.create(GetEventDamageSource(),GetTriggerUnit(),GetUnitX(GetEventDamageSource()),GetUnitY(GetEventDamageSource()),GetEventDamage())

            call UnitRemoveAbility(.u,RAWCODE)
            call UnitAddAbility(.u,COOLDOWN)
            set .a = Atan2(GetUnitY(.r)-GetUnitY(.u),GetUnitX(.r)-GetUnitX(.u))
            set .c = CreateUnit(GetOwningPlayer(u),DUMMY,.x,.y,.a)
            call SetTimerData(.t,this)
            call SetTimerData(.t2,this)
            call TimerStart(.t,.01,true,function s.Mover)
            call TimerStart(.t2,Cooldown(GetUnitAbilityLevel(.u,RAWCODE)),true,function s.Refresh)
        endmethod

        static method Conditions takes nothing returns boolean
            if GetUnitAbilityLevel(GetEventDamageSource(),RAWCODE) >= 1 then
                if GetWidgetLife(GetEventDamageSource()) > .405 then
                    if Damage_IsAttack() == true then
                        call s.Act()
                    endif
                endif
            endif
            return false
        endmethod
    endstruct

    private function I takes nothing returns nothing
        local trigger t=CreateTrigger()
        call TriggerAddCondition(t,Condition(function s.Conditions))
        call Damage_RegisterEvent(t)
    endfunction
endscope

Requires:
Damage(J4L)
TimerUtils(RedFlavor)
 

Viikuna

No Marlo no game.
Reaction score
265
If I remember correctly, adding and removing ability is not always instant. You should maybe add some debug msgs and checks here and there.

edit. Also rename your onDestroy to destroy.
 

saw792

Is known to say things. That is all.
Reaction score
280
>for what?

He doesn't mean renaming your onDestroy function, he means changing your call from [ljass]call .onDestroy[/ljass] to [ljass]call .destroy[/ljass]. Calling .onDestroy won't deallocate the struct instance it will just run your cleanup, whereas calling .destroy will both deallocate the instance properly (created struct instances have to be destroyed...) and then run your cleanup (your .onDestroy method).
 
General chit-chat
Help Users
  • No one is chatting at the moment.

      The Helper Discord

      Staff online

      Members online

      Affiliates

      Hive Workshop NUON Dome World Editor Tutorials

      Network Sponsors

      Apex Steel Pipe - Buys and sells Steel Pipe.
      Top