• Listen to a special audio message from Bill Roper to the Hive Workshop community (Bill is a former Vice President of Blizzard Entertainment, Producer, Designer, Musician, Voice Actor) 🔗Click here to hear his message!
  • Read Evilhog's interview with Gregory Alper, the original composer of the music for WarCraft: Orcs & Humans 🔗Click here to read the full interview.

[Trigger] Effect destroy problem

Status
Not open for further replies.
Level 9
Joined
Dec 6, 2007
Messages
233
Hello again everyone

For an ability i'm using, I am using a lighting bolt as a laser that comes from the sky. I knew that special effects leak, so i wrote into the trigger to destroy it right after it's made. Typically this works, but for the lightning bolt, the effect doesn't seem to be alive long enough to show itself. Unfortunately, to keep MUI, the trigger must be instantaneous, so waits are out of the picture. I tried it without removing the leaks, but the flash of the bolt made weird boxes appear in the terrain that i don't want. Is there a way to delay the destruction of the effect, so it doesn't leak and the boxes don't show up, but the effect remains alive long enough to show?
 
Level 9
Joined
Sep 28, 2004
Messages
365
Hi there.
This is what i have learnt from kingz's simple system. It let's the user to set the duration of the lightning. I also implemented a simple one in my chain system.

Basically you will need to create a Real variable. Depending on how you do the MUI. For me i used indexing.

So for example (Don't bother about the naming, i just copied it out from my chain system):

  • Set QJCS_LightningDur[QJCS_LightningIndex[2]] = 1.00
  • Chain Effect
    • Events
      • Time - Every 0.03 seconds of game time
    • Conditions
    • Actions
      • For each (Integer QJCS_LightningIndex[3]) from 1 to QJCS_LightningIndex[2], do (Actions)
        • Loop - Actions
          • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
            • If - Conditions
              • QJCS_LightningDur[QJCS_LightningIndex[3]] Greater than 0.00
            • Then - Actions
              • -------- Lightning Duration --------
              • Set QJCS_LightningDur[QJCS_LightningIndex[3]] = (QJCS_LightningDur[QJCS_LightningIndex[3]] - 0.03)
              • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                • If - Conditions
                  • QJCS_LightningDur[QJCS_LightningIndex[3]] Less than or equal to 0.00
                • Then - Actions
                  • Lightning - Destroy QJCS_LightningSFX[QJCS_LightningIndex[3]]
                  • Set QJCS_LightningIndex[1] = (QJCS_LightningIndex[1] - 1)
                  • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                    • If - Conditions
                      • QJCS_LightningIndex[1] Equal to 0
                    • Then - Actions
                      • Set QJCS_LightningIndex[2] = 0
                      • Trigger - Turn off Chain Effect <gen>
                    • Else - Actions
                • Else - Actions
            • Else - Actions


This is a really good way to delete lightning after a certain amount of time. Credits goes to Kingz [:
 
Level 9
Joined
Dec 6, 2007
Messages
233
@JeffreyQ mind if you make a list of all of the variables in that trigger (array size, variable type)? Otherwise, thanks a bunch for that. (+rep when i get list and i make sure it works)

@Dr. Super Good, won't work, too many lightning effects are called. Take a look :)

  • phase 1 effect spin
    • Events
      • Time - Every 0.10 seconds of game time
    • Conditions
    • Actions
      • Unit Group - Pick every unit in Ion_Group and do (Actions)
        • Loop - Actions
          • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
            • If - Conditions
              • (Load Ion_Timer of (Key (Picked unit)) from Ion_Hash) Less than 50
            • Then - Actions
              • For each (Integer A) from 1 to 6, do (Actions)
                • Loop - Actions
                  • Set Temp_Loc = ((Position of (Picked unit)) offset by 500.00 towards (((Real((Integer A))) x 60.00) + ((Real((Load Ion_Timer of (Key (Picked unit)) from Ion_Hash))) x 2.00)) degrees)
                  • Special Effect - Create a special effect at Temp_Loc using Doodads\Cinematic\Lightningbolt\Lightningbolt.mdl
                  • Set Ion_Phase1_Damage_Group = (Units within 100.00 of Temp_Loc)
                  • Unit Group - Pick every unit in Ion_Phase1_Damage_Group and do (Actions)
                    • Loop - Actions
                      • Unit - Set life of (Picked unit) to ((Life of (Picked unit)) - 10.00)
            • Else - Actions
              • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                • If - Conditions
                  • (Load Ion_Timer of (Key (Picked unit)) from Ion_Hash) Less than 100
                  • (Load Ion_Timer of (Key (Picked unit)) from Ion_Hash) Greater than 50
                • Then - Actions
                  • For each (Integer A) from 1 to 6, do (Actions)
                    • Loop - Actions
                      • Set Temp_Loc = ((Position of (Picked unit)) offset by (1000.00 - ((Real((Load Ion_Timer of (Key (Picked unit)) from Ion_Hash))) x 10.00)) towards (((Real((Integer A))) x 60.00) + ((Real((Load Ion_Timer of (Key (Picked unit)) from Ion_Hash))) x 2.00)) degrees)
                      • Special Effect - Create a special effect at Temp_Loc using Doodads\Cinematic\Lightningbolt\Lightningbolt.mdl
                      • Set Ion_Phase1_Damage_Group = (Units within 100.00 of Temp_Loc)
                      • Unit Group - Pick every unit in Ion_Phase1_Damage_Group and do (Actions)
                        • Loop - Actions
                          • Unit - Set life of (Picked unit) to ((Life of (Picked unit)) - 10.00)
                • Else - Actions
                  • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                    • If - Conditions
                      • (Load Ion_Timer of (Key (Picked unit)) from Ion_Hash) Greater than 100
                      • (Load Ion_Timer of (Key (Picked unit)) from Ion_Hash) Less than 120
                    • Then - Actions
                      • Set Temp_Loc = (Position of (Picked unit))
                      • Special Effect - Create a special effect at Temp_Loc using Abilities\Spells\Undead\ReplenishMana\ReplenishManaCasterOverhead.mdl
                      • Special Effect - Destroy (Last created special effect)
                      • Special Effect - Create a special effect at Temp_Loc using Abilities\Spells\Other\Drain\ManaDrainCaster.mdl
                      • Special Effect - Destroy (Last created special effect)
                      • Special Effect - Create a special effect at Temp_Loc using Abilities\Spells\Items\AIma\AImaTarget.mdl
                      • Special Effect - Destroy (Last created special effect)
                      • Special Effect - Create a special effect at Temp_Loc using Doodads\Cinematic\Lightningbolt\Lightningbolt.mdl
                      • Set Ion_Phase1_Damge_Group = (Units within 100.00 of Temp_Loc)
                      • Unit Group - Pick every unit in Ion_Phase1_Damge_Group and do (Actions)
                        • Loop - Actions
                          • Unit - Set life of (Picked unit) to ((Life of (Picked unit)) - 10.00)
                    • Else - Actions
                      • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                        • If - Conditions
                          • (Load Ion_Timer of (Key (Picked unit)) from Ion_Hash) Greater than 120
                          • (Load Ion_Timer of (Key (Picked unit)) from Ion_Hash) Less than 150
                        • Then - Actions
                          • Set Temp_Loc = (Position of (Picked unit))
                          • Special Effect - Create a special effect at Temp_Loc using Abilities\Spells\Undead\ReplenishMana\ReplenishManaCasterOverhead.mdl
                          • Special Effect - Destroy (Last created special effect)
                          • Special Effect - Create a special effect at Temp_Loc using Abilities\Spells\Other\Drain\ManaDrainCaster.mdl
                          • Special Effect - Destroy (Last created special effect)
                          • Special Effect - Create a special effect at Temp_Loc using Abilities\Spells\Items\AIma\AImaTarget.mdl
                          • Special Effect - Destroy (Last created special effect)
                        • Else - Actions
          • Hashtable - Save ((Load Ion_Timer of (Key (Picked unit)) from Ion_Hash) + 1) as Ion_Timer of (Key (Picked unit)) in Ion_Hash
          • Custom script: call RemoveLocation(udg_Temp_Loc)
          • Custom script: call DestroyGroup(udg_Ion_Phase1_Damage_Group)
 
Level 9
Joined
Sep 28, 2004
Messages
365
For indexing the array size is just 1 for everything. And you play around with the numbers.

Whenever you change the value of the array. It will automatically increase the array size for you. This is what i quoted from my question thread regarding indexing.

That what you call "size" in GUI is merely a number up to what index the array gets initialized to.

When you're having an integer variable with size 49, the Editor automatically does this:

JASS:
function InitGlobals takes nothing returns nothing
    local integer i= 0
    set i=0
    loop
        exitwhen ( i > 49 )
        set udg_i[i]=0
        set i=i + 1
    endloop

endfunction

Array type i used are: Lightning, Real of size 1 in the variable editor. Thats all.
It is also doable with hashtable. Since i see you loading stuff. Let me know if you want the way of doing it in hashtable.
 
Level 9
Joined
Dec 6, 2007
Messages
233
er, i'm not using a "lightning effect," i'm using a "special effect" that happens to be a lightning bolt. shoulda cleared that up earlier. Will your trigger still work? if so, how do i set the part where it destroys the effect?
 
Level 14
Joined
Jul 26, 2008
Messages
1,009
The trigger probably won't work as special effects and lightning effects are different.

I would suggest the use of hash tables and timers. You save your special effect from one trigger into hash tables then carry them over to another trigger that is part of a timer. The timer then run it's course and finally removes the special effect at the end, giving your effect a long enough duration with whatever tweaking you decide to do.

This is a valuable method to learn as it will allow you to make duration spells and perhaps even channeling spells.

Good luck!
 
Level 9
Joined
Dec 6, 2007
Messages
233
I do know how to use hashtables. The whole backbone of my trigger above is a hastable timer. In fact, a hashtable based system was the first approach i tried. The issue i have with solving this with a hashtimer is, i can't assign a value to a special effect, so what do i assign it to? If i can't call the special effect in a hashtimer, i can't destroy it with a hashtimer.

I beleive the only way to do this is with an indexing system, which i know nothing of.
 
Level 9
Joined
Dec 6, 2007
Messages
233
This whole thing just keeps getting more complicated. I suppose i'll have to learn it sometime, but it's 11:30, and i just don't feel like it right now. I'll shop around for an effect that can be deleted instantaneously tomorrow. You'll both still get rep, i appreciate the help.


On the other had, that trigger i posted up above, plus this one:

  • Begin effect
    • Events
      • Unit - A unit Begins casting an ability
    • Conditions
      • (Ability being cast) Equal to Serpent Ward
    • Actions
      • Set Temp_Loc = (Target point of ability being cast)
      • Unit - Create 1 Ion Target for Neutral Passive at Temp_Loc facing Default building facing degrees
      • Unit Group - Add (Last created unit) to Ion_Group
      • Hashtable - Save 0 as Ion_Timer of (Key (Last created unit)) in Ion_Hash
      • Unit - Add a 15.00 second Generic expiration timer to (Last created unit)
      • Custom script: call RemoveLocation(udg_Temp_Loc)
Only work once.

The dummy unit will spawn, but nothing else will happen. any ideas?
 
Level 9
Joined
Dec 6, 2007
Messages
233
@Jeffrey: Typically when i make a hashtimer, i add a value to a unit, add the unit to a unit group, then periodically call the unit group and decrease the value for the units inside by 1. I might be able to store data on a special effect, but how do i call it later?
 
Level 9
Joined
Sep 28, 2004
Messages
365
Here you go, a simple example:

Type of StringSFX is String
  • String SFX
    • Events
    • Conditions
    • Actions
      • Set StringSFX = Abilities\Spells\Human\Thunderclap\ThunderClapCaster.mdl
      • Hashtable - Save StringSFX as (Key stringsfx) of (Key (Triggering unit)) in sfxTable
      • Unit Group - Add (Triggering unit) to casterGroup
  • Real SFX
    • Events
    • Conditions
    • Actions
      • Unit Group - Pick every unit in casterGroup and do (Actions)
        • Loop - Actions
          • Set StringSFX = (Load (Key stringsfx) of (Key (Picked unit)) from sfxTable)
          • Special Effect - Create a special effect at (Center of (Playable map area)) using StringSFX
          • Special Effect - Destroy (Last created special effect)
 
Level 9
Joined
Dec 6, 2007
Messages
233
no, jeffrey, you've just created the same issue. I can't destroy the effect instantly after creating it, it has to have a slight delay or else the effect doesn't show.
 
Level 9
Joined
Sep 28, 2004
Messages
365
I was just giving an example how to store it in hashtable using strings.
To destroy it after a duration. I just combine it with the code i posted earlier from my system and modify it to hashtables.


  • String SFX
    • Events
    • Conditions
    • Actions
      • Set StringSFX = Abilities\Spells\Human\Thunderclap\ThunderClapCaster.mdl
      • Hashtable - Save StringSFX as (Key stringsfx) of (Key (Triggering unit)) in sfxTable
      • Unit Group - Add (Triggering unit) to casterGroup
  • Real SFX
    • Events
    • Conditions
    • Actions
      • Unit Group - Pick every unit in casterGroup and do (Actions)
        • Loop - Actions
          • Set StringSFX = (Load (Key stringsfx) of (Key (Picked unit)) from sfxTable)
          • Special Effect - Create a special effect at (Center of (Playable map area)) using StringSFX
          • Set MyCustomEffect = (Last created special effect)
          • Set EffectDuration = 1.00
          • -------- Create a dummy for every cast to make it MUI --------
          • Unit - Create 1 Dummy for (Owner of (Picked unit)) at (Center of (Playable map area)) facing Default building facing degrees
          • Unit Group - Add (Last created unit) to dummyGroup
          • Hashtable - Save Handle OfMyCustomEffect as (Key effect) of (Key (Last created unit)) in sfxTable
          • Hashtable - Save EffectDuration as (Key dur) of (Key (Last created unit)) in sfxTable
          • Unit Group - Remove (Picked unit) from casterGroup
  • Remove After Duration
    • Events
      • Time - Every 0.03 seconds of game time
    • Conditions
    • Actions
      • Unit Group - Pick every unit in dummyGroup and do (Actions)
    • Loop - Actions
      • Set MyCustomEffect = (Load (Key effect) of (Key (Picked unit)) in sfxTable
      • Set EffectDuration = (Load (Key dur) of (Key (Picked unit)) from sfxTable
      • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
      • If - Conditions
        • EffectDuration Greater than 0.00
      • Then - Actions
        • Set EffectDuration = (EffectDuration - 0.03)
        • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
          • If - Conditions
            • EffectDuration Less than or equal to 0.00
          • Then - Actions
            • Trigger - Turn off (This trigger)
            • Special Effect - Destroy MyCustomEffect
            • Unit - Remove (Picked unit) from the game
            • Unit Group - Remove (Picked unit) from dummyGroup
          • Else - Actions
      • Else - Actions


Please note that i did this with free hand, so i am not sure if those syntax are correct.
Also don't copy directly. It might not work as i am just giving a basic idea on how to remove it after a duration.
 
Status
Not open for further replies.
Top