• 🏆 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!

Spells & Systems Mini-Contest #20

Status
Not open for further replies.
Level 16
Joined
Jun 24, 2009
Messages
1,409
Here should be my final result ill post map when im done with tooltips
  • Elemental Festival 1
    • Events
      • Unit - A unit Starts the effect of an ability
    • Conditions
      • (Ability being cast) Equal to Channel
    • Actions
      • Set ElementalFestivalCaster = (Triggering unit)
      • Set ElementalFestivalSEString[0] = Abilities\Spells\Human\ThunderClap\ThunderClapCaster.mdl
      • Set ElementalFestivalSEString[1] = Abilities\Spells\Orc\WarStomp\WarStompCaster.mdl
      • Set ElementalFestivalDamage[1] = 10.00
      • Set ElementalFestivalDamage[2] = 20.00
      • Set ElementalFestivalDamage[3] = 30.00
      • Set ElementalFestivalDamage[4] = 40.00
      • Set ElementalFestivalDamage[5] = 50.00
      • Set ElementalFestivalPoint[0] = (Target point of ability being cast)
      • Set ElementalFestivalPoint[1] = (Position of ElementalFestivalCaster)
      • Wait 0.10 seconds
      • Unit - Create 1 Dummy for (Owner of ElementalFestivalCaster) at ElementalFestivalPoint[0] facing Default building facing degrees
      • Unit - Add Slow to (Last created unit)
      • Unit - Order (Last created unit) to Human Mountain King - Thunder Clap
      • Unit - Add a 1.00 second Generic expiration timer to (Last created unit)
      • Unit - Add Crow Form to ElementalFestivalCaster
      • Animation - Change ElementalFestivalCaster flying height to 300.00 at 800.00
      • Unit - Remove Crow Form from ElementalFestivalCaster
      • Unit - Pause ElementalFestivalCaster
      • Unit - Make ElementalFestivalCaster Invulnerable
      • Animation - Change ElementalFestivalCaster's animation speed to 300.00% of its original speed
      • Trigger - Turn on Elemental Festival 2 <gen>
      • Wait 1.84 seconds
      • Animation - Change ElementalFestivalCaster's animation speed to 150.00% of its original speed
      • Set ElementalFestivalDistance = (Distance between ElementalFestivalPoint[0] and ElementalFestivalPoint[1])
      • Unit - Create 1 Dummy FireballEffect for (Owner of ElementalFestivalCaster) at ElementalFestivalPoint[1] facing Default building facing degrees
      • Set ElementalFestivalDummy[0] = (Last created unit)
      • Animation - Play ElementalFestivalCaster's spell animation
      • Trigger - Turn on Elemental Festival 3 <gen>
      • Wait 0.40 seconds
      • Trigger - Turn off Elemental Festival 3 <gen>
      • Unit - Remove ElementalFestivalDummy[0] from the game
      • Special Effect - Create a special effect at ElementalFestivalPoint[0] using Objects\Spawnmodels\Other\NeutralBuildingExplosion\NeutralBuildingExplosion.mdl
      • Special Effect - Destroy (Last created special effect)
      • Special Effect - Create a special effect at ElementalFestivalPoint[0] using Objects\Spawnmodels\Other\NeutralBuildingExplosion\NeutralBuildingExplosion.mdl
      • Special Effect - Destroy (Last created special effect)
      • Special Effect - Create a special effect at ElementalFestivalPoint[0] using Objects\Spawnmodels\Other\NeutralBuildingExplosion\NeutralBuildingExplosion.mdl
      • Special Effect - Destroy (Last created special effect)
      • Set ElementalFestivalUnitGroup[0] = (Units within 400.00 of ElementalFestivalPoint[0] matching ((((Matching unit) belongs to an enemy of (Owner of ElementalFestivalCaster)) Equal to True) and ((((Matching unit) is Magic Immune) Equal to False) and (((Matching unit) is A structure) Equal to Fals
      • Unit Group - Pick every unit in ElementalFestivalUnitGroup[0] and do (Actions)
        • Loop - Actions
          • Unit - Create 1 Dummy for (Owner of ElementalFestivalCaster) at ElementalFestivalPoint[0] facing Default building facing degrees
          • Unit - Add a 1.00 second Generic expiration timer to (Last created unit)
          • Unit - Cause (Last created unit) to damage (Picked unit), dealing (ElementalFestivalDamage[(Level of Channel for ElementalFestivalCaster)] x 2.00) damage of attack type Spells and damage type Normal
      • Animation - Change ElementalFestivalCaster flying height to 0.00 at 1600.00
      • Unit - Unpause ElementalFestivalCaster
      • Unit - Make ElementalFestivalCaster Vulnerable
      • Animation - Change ElementalFestivalCaster's animation speed to 100.00% of its original speed
      • For each (Integer A) from 0 to 6, do (Actions)
        • Loop - Actions
          • Unit - Remove ElementalFestivalSpecialEffect[(Integer A)] from the game
      • Custom script: call RemoveLocation(udg_ElementalFestivalPoint[0])
      • Custom script: call RemoveLocation(udg_ElementalFestivalPoint[1])
      • Custom script: call DestroyGroup(udg_ElementalFestivalUnitGroup[0])
  • Elemental Festival 2
    • Events
      • Time - Every 0.23 seconds of game time
    • Conditions
    • Actions
      • Set ElementalFestivalCount = (ElementalFestivalCount + 1)
      • Set ElementalFestivalPoint[2] = (Random point in (Region centered at ElementalFestivalPoint[0] with size (300.00, 300.00)))
      • Set ElementalFestivalRandomInt = (Random integer number between 0 and 1)
      • Special Effect - Create a special effect at ElementalFestivalPoint[2] using ElementalFestivalSEString[ElementalFestivalRandomInt]
      • Special Effect - Destroy (Last created special effect)
      • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
        • If - Conditions
          • ElementalFestivalRandomInt Equal to 0
        • Then - Actions
          • Special Effect - Create a special effect at ElementalFestivalPoint[2] using Abilities\Spells\Other\Monsoon\MonsoonBoltTarget.mdl
          • Special Effect - Destroy (Last created special effect)
        • Else - Actions
      • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
        • If - Conditions
          • ElementalFestivalRandomInt Equal to 1
        • Then - Actions
          • Special Effect - Create a special effect at ElementalFestivalPoint[2] using ElementalFestivalSEString[1]
          • Special Effect - Destroy (Last created special effect)
          • Special Effect - Create a special effect at ElementalFestivalPoint[2] using ElementalFestivalSEString[1]
          • Special Effect - Destroy (Last created special effect)
        • Else - Actions
      • Special Effect - Create a special effect at ElementalFestivalPoint[2] using Units\NightElf\Wisp\WispExplode.mdl
      • Special Effect - Destroy (Last created special effect)
      • Set ElementalFestivalUnitGroup[0] = (Units within 150.00 of ElementalFestivalPoint[2] matching ((((Matching unit) belongs to an enemy of (Owner of ElementalFestivalCaster)) Equal to True) and ((((Matching unit) is Magic Immune) Equal to False) and (((Matching unit) is A structure) Equal to Fals
      • Unit Group - Pick every unit in ElementalFestivalUnitGroup[0] and do (Actions)
        • Loop - Actions
          • Unit - Create 1 Dummy for (Owner of ElementalFestivalCaster) at ElementalFestivalPoint[2] facing Default building facing degrees
          • Unit - Add a 1.00 second Generic expiration timer to (Last created unit)
          • Unit - Cause (Last created unit) to damage (Picked unit), dealing ElementalFestivalDamage[(Level of Channel for ElementalFestivalCaster)] damage of attack type Spells and damage type Normal
      • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
        • If - Conditions
          • ElementalFestivalCount Equal to 1
        • Then - Actions
          • Animation - Play ElementalFestivalCaster's attack,1 animation
        • Else - Actions
          • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
            • If - Conditions
              • (ElementalFestivalCount mod 2) Equal to 0
            • Then - Actions
              • Animation - Play ElementalFestivalCaster's attack animation
            • Else - Actions
              • Animation - Play ElementalFestivalCaster's attack,3 animation
      • Custom script: call RemoveLocation(udg_ElementalFestivalPoint[2])
      • Custom script: call DestroyGroup(udg_ElementalFestivalUnitGroup[0])
      • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
        • If - Conditions
          • ElementalFestivalCount Equal to 8
        • Then - Actions
          • Trigger - Turn off (This trigger)
          • Set ElementalFestivalCount = 0
        • Else - Actions
  • Elemental Festival 3
    • Events
      • Time - Every 0.02 seconds of game time
    • Conditions
    • Actions
      • Set ElementalFestivalPoint[2] = (Position of ElementalFestivalDummy[0])
      • Set ElementalFestivalPoint[3] = (ElementalFestivalPoint[2] offset by (ElementalFestivalDistance / 20.00) towards (Angle from ElementalFestivalPoint[1] to ElementalFestivalPoint[0]) degrees)
      • Unit - Move ElementalFestivalDummy[0] instantly to ElementalFestivalPoint[3]
      • For each (Integer A) from 1 to 20, do (Actions)
        • Loop - Actions
          • Animation - Change ElementalFestivalDummy[0] flying height to (400.00 - (30.00 x (Real((Integer A))))) at 800.00
      • Custom script: call RemoveLocation(udg_ElementalFestivalPoint[2])
      • Custom script: call RemoveLocation(udg_ElementalFestivalPoint[3])
  • Elemental Festival 4
    • Events
      • Unit - A unit Starts the effect of an ability
    • Conditions
      • (Ability being cast) Equal to Channel
    • Actions
      • For each (Integer A) from 0 to 6, do (Actions)
        • Loop - Actions
          • Unit - Create 1 Dummy SpecialEffect for (Owner of (Triggering unit)) at ElementalFestivalPoint[1] facing Default building facing degrees
          • Set ElementalFestivalSpecialEffect[(Integer A)] = (Last created unit)
      • Special Effect - Create a special effect at ElementalFestivalPoint[1] using Abilities\Spells\Human\ReviveHuman\ReviveHuman.mdl
      • Special Effect - Destroy (Last created special effect)
attachment.php
attachment.php
attachment.php


Ah then i should fix some stuff to make it MUI..

EDIT: Its impossible to make it MUI in GUI and leakless.. GUI dont have have local variables nor accept variables in custom script array index. if anyone have any idea how to make it leakless and MUI i would love to hear..

Why don't you use effects with more light? For example a big Faerie Dragon missile? Also you could change the color of the others, and combinate more aura model's to get nearly the same effect. And if you modify the resurrect model's visibility a bit (around 70%) it would look better.
 
Level 33
Joined
Mar 27, 2008
Messages
8,035

Maybe I'll be doing this spell (0:58 ~ 1:02)
I said maybe :)

EDIT:
Can it be an additional effect ?
Like, we add the effect of X eye-candy but the actual spell doesn't even have that eye-candy (but still sticks to the original base spell)
 
Level 7
Joined
Nov 19, 2007
Messages
253
Why don't you use effects with more light? For example a big Faerie Dragon missile? Also you could change the color of the others, and combinate more aura model's to get nearly the same effect. And if you modify the resurrect model's visibility a bit (around 70%) it would look better.

I dont like the effect of Faerie dragon missle (not for this kind a spell), i agree with auras ill do something to make them look better, and about resurrect ill just change it or make it bigger..

@D3athM3at - GUI can use locals... but even if you do it, I think the waits are still unacceptable...

If i could make local units im sure i would find a way to remove those waits...
 
Level 7
Joined
Nov 19, 2007
Messages
253
Does declaring a local with udg_ prefix still transform globals into locals with patch 1.26?

can you give me example ?

  • Custom script: local unit Caster = GetTriggerUnit()
This doesnt work or im doing it wrong..
 
Last edited:
Level 7
Joined
Nov 19, 2007
Messages
253
Cos I don't have time to play other games :>

A game of lol takes 15-45 minutes in average, depends on game type. And because they are cool and also useful/wc3 like.

you can try something like this:
this looks simple enought and you can make it look good
 
If you could pull off any of the "Quickenings" from Final Fantasy 12 that would produce a great spell.

What's that?
I'll see if I can make it, but I'm not too good in triggering.

[EDIT]
Okay, I'm having a really hard time right now.
The spell works the first time, but only with one unit in the area.
I don't know what to do. Could you guys see what's wrong?
  • Start
    • Events
      • Unit - A unit Starts the effect of an ability
    • Conditions
      • (Ability being cast) Equal to Bad Breath
    • Actions
      • Set BadBreathCastingUnit = (Casting unit)
      • Set BadBreathCastingUnitPoint = (Position of BadBreathCastingUnit)
      • Set BadBreathCastPoint = (Target point of ability being cast)
      • Unit - Create 1 Dummy Bad Breath for (Triggering player) at BadBreathCastingUnitPoint facing Default building facing degrees
      • Custom script: call RemoveLocation(udg_BadBreathCastingUnitPoint)
      • Unit - Order (Last created unit) to Move To BadBreathCastPoint
      • Unit - Set (Last created unit) movement speed to 1000000000.00
      • Unit - Add a 5.00 second Generic expiration timer to (Last created unit)
      • For each (Integer BadBreathBuffInteger) from 1 to 5, do (Actions)
        • Loop - Actions
          • Unit Group - Pick every unit in (Units within 200.00 of BadBreathCastPoint matching ((((Matching unit) is A structure) Equal to False) and ((((Matching unit) is Mechanical) Equal to False) and (((Matching unit) is dead) Equal to False)))) and do (Actions)
            • Loop - Actions
              • Set BadBreathBuffRandomInteger = (Random integer number between 1 and 100)
              • Set BadBreath_UnitHasSlow = False
              • Set BadBreath_UnitHasBanish = False
              • Set BadBreath_UnitHasCurse = False
              • Set BadBreath_UnitHasDisease = False
              • Set BadBreath_UnitHasFaerieFire = False
              • Set BadBreath_UnitHasHex = False
              • Set BadBreath_UnitHasManaLeak = False
              • Set BadBreath_UnitHasSilence = False
              • Set BadBreath_UnitHasSleep = False
              • Set BadBreath_UnitHasStun = False
              • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                • If - Conditions
                  • BadBreathBuffRandomInteger Less than or equal to 10
                  • BadBreath_UnitHasSlow Equal to False
                  • BadBreathNumberofBuffs Not equal to 5
                • Then - Actions
                  • Set BadBreathUnitPoint = (Position of (Picked unit))
                  • Unit - Create 1 Dummy Caster for (Owner of BadBreathCastingUnit) at BadBreathUnitPoint facing Default building facing degrees
                  • Unit - Add a 2.00 second Generic expiration timer to (Last created unit)
                  • Unit - Order (Last created unit) to Human Sorceress - Slow (Picked unit)
                  • Set BadBreath_UnitHasSlow = True
                  • Set BadBreathNumberofBuffs = (BadBreathNumberofBuffs + 1)
                  • Custom script: call RemoveLocation(udg_BadBreathUnitPoint)
                  • Set BadBreathBuffRandomInteger = (Random integer number between 1 and 100)
                • Else - Actions
              • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                • If - Conditions
                  • BadBreathBuffRandomInteger Less than or equal to 20
                  • BadBreathBuffRandomInteger Greater than or equal to 11
                  • BadBreath_UnitHasHex Equal to False
                  • BadBreathNumberofBuffs Not equal to 5
                • Then - Actions
                  • Set BadBreathUnitPoint = (Position of (Picked unit))
                  • Unit - Create 1 Dummy Caster for (Owner of BadBreathCastingUnit) at BadBreathUnitPoint facing Default building facing degrees
                  • Unit - Add a 2.00 second Generic expiration timer to (Last created unit)
                  • Unit - Order (Last created unit) to Orc Shadow Hunter - Hex (Picked unit)
                  • Set BadBreath_UnitHasHex = True
                  • Set BadBreathNumberofBuffs = (BadBreathNumberofBuffs + 1)
                  • Custom script: call RemoveLocation(udg_BadBreathUnitPoint)
                  • Set BadBreathBuffRandomInteger = (Random integer number between 1 and 100)
                • Else - Actions
              • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                • If - Conditions
                  • BadBreathBuffRandomInteger Less than or equal to 30
                  • BadBreathBuffRandomInteger Greater than or equal to 21
                  • BadBreath_UnitHasStun Equal to False
                  • BadBreathNumberofBuffs Not equal to 5
                • Then - Actions
                  • Set BadBreathUnitPoint = (Position of (Picked unit))
                  • Unit - Create 1 Dummy Caster for (Owner of BadBreathCastingUnit) at BadBreathUnitPoint facing Default building facing degrees
                  • Unit - Add a 2.00 second Generic expiration timer to (Last created unit)
                  • Unit - Order (Last created unit) to Neutral - Firebolt (Picked unit)
                  • Set BadBreath_UnitHasStun = True
                  • Set BadBreathNumberofBuffs = (BadBreathNumberofBuffs + 1)
                  • Custom script: call RemoveLocation(udg_BadBreathUnitPoint)
                  • Set BadBreathBuffRandomInteger = (Random integer number between 1 and 100)
                • Else - Actions
              • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                • If - Conditions
                  • BadBreathBuffRandomInteger Less than or equal to 40
                  • BadBreathBuffRandomInteger Greater than or equal to 31
                  • BadBreath_UnitHasSilence Equal to False
                  • BadBreathNumberofBuffs Not equal to 5
                • Then - Actions
                  • Set BadBreathUnitPoint = (Position of (Picked unit))
                  • Unit - Create 1 Dummy Caster for (Owner of BadBreathCastingUnit) at BadBreathUnitPoint facing Default building facing degrees
                  • Unit - Add a 2.00 second Generic expiration timer to (Last created unit)
                  • Unit - Order (Last created unit) to Neutral Dark Ranger - Silence BadBreathUnitPoint
                  • Set BadBreath_UnitHasSilence = True
                  • Set BadBreathNumberofBuffs = (BadBreathNumberofBuffs + 1)
                  • Custom script: call RemoveLocation(udg_BadBreathUnitPoint)
                  • Set BadBreathBuffRandomInteger = (Random integer number between 1 and 100)
                • Else - Actions
              • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                • If - Conditions
                  • BadBreathBuffRandomInteger Less than or equal to 50
                  • BadBreathBuffRandomInteger Greater than or equal to 41
                  • BadBreath_UnitHasDisease Equal to False
                  • BadBreathNumberofBuffs Not equal to 5
                • Then - Actions
                  • Set BadBreathUnitPoint = (Position of (Picked unit))
                  • Unit - Create 1 Dummy Caster for (Owner of BadBreathCastingUnit) at BadBreathUnitPoint facing Default building facing degrees
                  • Unit - Add a 2.00 second Generic expiration timer to (Last created unit)
                  • Unit - Order (Last created unit) to Neutral Alchemist - Acid Bomb (Picked unit)
                  • Set BadBreath_UnitHasDisease = True
                  • Set BadBreathNumberofBuffs = (BadBreathNumberofBuffs + 1)
                  • Custom script: call RemoveLocation(udg_BadBreathUnitPoint)
                  • Set BadBreathBuffRandomInteger = (Random integer number between 1 and 100)
                • Else - Actions
              • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                • If - Conditions
                  • BadBreathBuffRandomInteger Less than or equal to 60
                  • BadBreathBuffRandomInteger Greater than or equal to 51
                  • BadBreath_UnitHasFaerieFire Equal to False
                  • BadBreathNumberofBuffs Not equal to 5
                • Then - Actions
                  • Set BadBreathUnitPoint = (Position of (Picked unit))
                  • Unit - Create 1 Dummy Caster for (Owner of BadBreathCastingUnit) at BadBreathUnitPoint facing Default building facing degrees
                  • Unit - Add a 2.00 second Generic expiration timer to (Last created unit)
                  • Unit - Order (Last created unit) to Night Elf Druid Of The Talon - Faerie Fire (Picked unit)
                  • Set BadBreath_UnitHasFaerieFire = True
                  • Set BadBreathNumberofBuffs = (BadBreathNumberofBuffs + 1)
                  • Custom script: call RemoveLocation(udg_BadBreathUnitPoint)
                  • Set BadBreathBuffRandomInteger = (Random integer number between 1 and 100)
                • Else - Actions
              • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                • If - Conditions
                  • BadBreathBuffRandomInteger Less than or equal to 70
                  • BadBreathBuffRandomInteger Greater than or equal to 61
                  • BadBreath_UnitHasCurse Equal to False
                  • BadBreathNumberofBuffs Not equal to 5
                • Then - Actions
                  • Set BadBreathUnitPoint = (Position of (Picked unit))
                  • Unit - Create 1 Dummy Caster for (Owner of BadBreathCastingUnit) at BadBreathUnitPoint facing Default building facing degrees
                  • Unit - Add a 2.00 second Generic expiration timer to (Last created unit)
                  • Unit - Order (Last created unit) to Undead Banshee - Curse (Picked unit)
                  • Set BadBreath_UnitHasCurse = True
                  • Set BadBreathNumberofBuffs = (BadBreathNumberofBuffs + 1)
                  • Custom script: call RemoveLocation(udg_BadBreathUnitPoint)
                  • Set BadBreathBuffRandomInteger = (Random integer number between 1 and 100)
                • Else - Actions
              • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                • If - Conditions
                  • BadBreathBuffRandomInteger Less than or equal to 80
                  • BadBreathBuffRandomInteger Greater than or equal to 71
                  • BadBreath_UnitHasManaLeak Equal to False
                  • BadBreathNumberofBuffs Not equal to 5
                • Then - Actions
                  • Set BadBreathUnitPoint = (Position of (Picked unit))
                  • Unit - Set mana of (Picked unit) to ((Mana of (Picked unit)) - 100.00)
                  • Special Effect - Create a special effect attached to the origin of (Picked unit) using Abilities\Spells\Undead\DarkRitual\DarkRitualTarget.mdl
                  • Set BadBreath_UnitHasManaLeak = True
                  • Set BadBreathNumberofBuffs = (BadBreathNumberofBuffs + 1)
                  • Custom script: call RemoveLocation(udg_BadBreathUnitPoint)
                  • Set BadBreathBuffRandomInteger = (Random integer number between 1 and 100)
                • Else - Actions
              • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                • If - Conditions
                  • BadBreathBuffRandomInteger Less than or equal to 90
                  • BadBreathBuffRandomInteger Greater than or equal to 81
                  • BadBreath_UnitHasSleep Equal to False
                  • BadBreathNumberofBuffs Not equal to 5
                • Then - Actions
                  • Set BadBreathUnitPoint = (Position of (Picked unit))
                  • Unit - Create 1 Dummy Caster for (Owner of BadBreathCastingUnit) at BadBreathUnitPoint facing Default building facing degrees
                  • Unit - Add a 2.00 second Generic expiration timer to (Last created unit)
                  • Unit - Order (Last created unit) to Undead Dreadlord - Sleep (Picked unit)
                  • Set BadBreath_UnitHasSleep = True
                  • Set BadBreathNumberofBuffs = (BadBreathNumberofBuffs + 1)
                  • Custom script: call RemoveLocation(udg_BadBreathUnitPoint)
                  • Set BadBreathBuffRandomInteger = (Random integer number between 1 and 100)
                • Else - Actions
              • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                • If - Conditions
                  • BadBreathBuffRandomInteger Greater than or equal to 91
                  • BadBreath_UnitHasBanish Equal to False
                  • BadBreathNumberofBuffs Not equal to 5
                • Then - Actions
                  • Set BadBreathUnitPoint = (Position of (Picked unit))
                  • Unit - Create 1 Dummy Caster for (Owner of BadBreathCastingUnit) at BadBreathUnitPoint facing Default building facing degrees
                  • Unit - Add a 2.00 second Generic expiration timer to (Last created unit)
                  • Unit - Order (Last created unit) to Human Blood Mage - Banish (Picked unit)
                  • Set BadBreath_UnitHasBanish = True
                  • Set BadBreathNumberofBuffs = (BadBreathNumberofBuffs + 1)
                  • Custom script: call RemoveLocation(udg_BadBreathUnitPoint)
                  • Set BadBreathBuffRandomInteger = (Random integer number between 1 and 100)
                • Else - Actions
 
Last edited:
WIP... all's working fine...

JASS:
library SpaceCollapse requires Nova, T32

    globals
        private constant integer SC_ID = 'A000' //rawcode of spell
        private constant integer DUMMY_ID = 'h000' //rawcode of dummy caster
        private constant integer CASTER_ID = 'h001' //rawcode of the caster images
        private constant integer IMAGES = 5 //number of images created + the caster itself, don't set it to too high
        private constant string CIRCLE_A = "Abilities\\Spells\\Undead\\RegenerationAura\\ObsidianRegenAura.mdl" //the path to the effect that will be shown below the caster and its images
        private constant string CIRCLE_B = "Abilities\\Spells\\Undead\\UnholyAura\\UnholyAura.mdl" //the path to the effect that will be shown on the AoE
        private constant string CIRCLE_C = "Abilities\\Spells\\Undead\\RegenerationAura\\ObsidianRegenAura.mdl" //the path to the effect that will be shown above CIRCLE_B
        private constant string COLLAPSE = "Abilities\\Spells\\Items\\TomeOfRetraining\\TomeOfRetrainingCaster.mdl" //the path to the effect of the collapse
        private constant string ANIMATION = "spell" //the animation that will be played by the caster and its images
        private constant real DELAY = 1.50 //the delay before the spell explodes, better scale this to be the same as the duration of the spell animation or whatever animation you will be using 
        private constant real SCALE = 1.0 //the scale of CIRCLE_A
        private constant real OFFSET = 100.0 //the offset of the caster images from the radius of the AOE
        private constant real HEIGHT = 200.0 //the height of CIRCLE_C
        private constant boolean SCALE_Z = false //determines if the Z value of the dummy will also be scaled
        private constant attacktype AT = ATTACK_TYPE_MAGIC //the attack type of the spell
        private constant damagetype DT = DAMAGE_TYPE_NORMAL //the damage type of the spell
        private constant integer FLY = 'Amrf' //rawcode of Medivh's raven form
        private constant integer CIRCLES = IMAGES + 1//do not edit
    endglobals
    
    //I suggest making the cast range to be equal to the radius + (50 to 100)
    private function GetRadius takes integer level returns real
        return 200.0*level
    endfunction
    
    //the function for setting the damage dealt by the spell
    private function GetDamage takes integer level returns real
        return 100.0*level
    endfunction
    
    //the function for setting the scale of CIRCLE_B and CIRCLE_C
    //I've set CIRCLE_C to be half the scale of CIRCLE_B
    private function GetScaleAB takes integer level returns real
        return GetRadius(level)/100.0
    endfunction
    
    //the function for setting the scale of the collapse effect
    private function GetScaleCollapse takes integer level returns real
        return GetRadius(level)/100.0
    endfunction

    
    //the initializer Module
    module init
        private static method onInit takes nothing returns nothing
            local trigger t = CreateTrigger()
            local integer i = 0
            loop
                exitwhen i > 15
                call TriggerRegisterPlayerUnitEvent(t, Player(i), EVENT_PLAYER_UNIT_SPELL_EFFECT, null)
                set i = i + 1
            endloop
            call TriggerAddCondition(t, Condition(function thistype.SpaceCollapseAction))
            set t = null
        endmethod
    endmodule
    
    //the struct for the main part of the spell
    struct SpaceCollapse
    
        implement init
        
        static unit caster
        static integer level
        static real x
        static real y
        static real x2
        static real y2
        static location TempLoc = Location(0,0)
        real time
        real xc
        real yc
        unit casterr
        unit array images [IMAGES]
        unit array circles [CIRCLES]
        effect array effects [CIRCLES]
        
        private method onDestroy takes nothing returns nothing
            local integer i = 0
            call SetUnitX(this.casterr, this.xc)
            call SetUnitY(this.casterr, this.yc)
            loop
                exitwhen i > CIRCLES
                set this.images[i] = null
                set this.circles[i] = null
                call DestroyEffect(this.effects[i])
                set this.effects[i] = null
                set i = i + 1
            endloop
        endmethod
        
        private method periodic takes nothing returns nothing
            local integer i = 0
            loop
                exitwhen i > CIRCLES
                if i != CIRCLES - 1 then
                    call SetUnitFacing(this.circles[i], this.time*2.0)
                else
                    call SetUnitFacing(this.circles[i], this.time*-2.0)
                endif
                set i = i + 1
            endloop
            set this.time = this.time + T32_PERIOD 
            if this.time >= DELAY then
                call this.stopPeriodic()
                call this.destroy()
            endif
        endmethod
        
        implement T32x
        
        static method create takes player owner, real angle, real x2, real y2, integer level  returns thistype
            local thistype this = .allocate()
            local real angle2 = (360.0/I2R(IMAGES))*.017453292
            local integer i = 1
            local real x = x2 + (GetRadius(level) + OFFSET )*Cos(angle)
            local real y = y2 + (GetRadius(level) + OFFSET )*Sin(angle)
            local real x3
            local real y3
            local real z
            local real fz
            local real scales = GetScaleAB(level)
            set this.circles[0] = CreateUnit(owner, DUMMY_ID, x, y, 0.0)
            set this.effects[0] = AddSpecialEffectTarget(CIRCLE_A, this.circles[0], "origin")
            call UnitApplyTimedLife(this.circles[0], 'BTLF', DELAY + .2)
            call SetUnitScale(this.circles[0], SCALE, SCALE, SCALE)
            call SetUnitExploded(this.circles[0], true)
            call MoveLocation(thistype.TempLoc, x2, y2)
            set this.xc = thistype.x
            set this.yc = thistype.y
            call SetUnitX(thistype.caster, x )
            call SetUnitY(thistype.caster, y )
            set z = GetLocationZ(thistype.TempLoc)
            call UnitAddAbility(this.circles[0], FLY)
            call UnitRemoveAbility(this.circles[0], FLY)
            call MoveLocation(thistype.TempLoc, x, y)
            set fz = z - GetLocationZ(thistype.TempLoc)
            call SetUnitFlyHeight(this.circles[0], fz, 0.0)
            call SetUnitFlyHeight(thistype.caster, fz, 0.0)
            set this.time = 0.0
            loop
                exitwhen i == IMAGES
                set x3 = x2 + (GetRadius(level) + OFFSET )*Cos(angle + angle2*i)
                set y3 = y2 + (GetRadius(level) + OFFSET )*Sin(angle + angle2*i)
                set this.circles[i] = CreateUnit(owner, DUMMY_ID, x3, y3, 0.0)
                call UnitAddAbility(this.circles[i], FLY)
                call UnitRemoveAbility(this.circles[i], FLY)
                set this.images[i] = CreateUnit(owner, CASTER_ID, x3, y3, (angle + angle2*i + 3.141592654)/.017453292)
                call UnitAddAbility(this.images[i], FLY)
                call UnitRemoveAbility(this.images[i], FLY)
                call MoveLocation(thistype.TempLoc, x3, y3)
                if SCALE_Z then
                    call SetUnitScale(this.circles[i], SCALE, SCALE, SCALE)
                else
                    call SetUnitScale(this.circles[i], SCALE, SCALE, 1.0)
                endif
                set fz = z - GetLocationZ(thistype.TempLoc)
                call SetUnitFlyHeight(this.circles[i], fz, 0.0)
                call SetUnitFlyHeight(this.images[i], fz, 0.0)
                call SetUnitExploded(this.circles[i], true)
                call SetUnitExploded(this.images[i], true)
                call SetUnitAnimation(this.images[i], ANIMATION)
                call UnitApplyTimedLife(this.circles[i], 'BTLF', DELAY + .2)
                call UnitApplyTimedLife(this.images[i], 'BTLF', DELAY + .2)
                set this.effects[i] = AddSpecialEffectTarget(CIRCLE_A, this.circles[i], "origin")
                set i = i + 1
            endloop
            set this.circles[CIRCLES - 1] = CreateUnit(owner, DUMMY_ID, x2, y2, 0.0)
            set this.effects[CIRCLES - 1] = AddSpecialEffectTarget(CIRCLE_B, this.circles[CIRCLES - 1], "origin")
            set this.circles[CIRCLES] = CreateUnit(owner, DUMMY_ID, x2, y2, 0.0)
            set this.effects[CIRCLES] = AddSpecialEffectTarget(CIRCLE_C, this.circles[CIRCLES], "origin")
            if SCALE_Z then
                call SetUnitScale(this.circles[CIRCLES - 1], scales, scales, scales)
                call SetUnitScale(this.circles[CIRCLES], scales/2.0, scales/2.0, scales/2.0)
            else
                call SetUnitScale(this.circles[CIRCLES - 1], scales, scales, 1.0)
                call SetUnitScale(this.circles[CIRCLES], scales/2.0, scales/2.0, 1.0)
            endif
            call SetUnitExploded(this.circles[CIRCLES - 1], true)
            call SetUnitExploded(this.circles[CIRCLES], true)
            call UnitAddAbility(this.circles[CIRCLES], FLY)
            call UnitRemoveAbility(this.circles[CIRCLES], FLY)
            call SetUnitFlyHeight(this.circles[CIRCLES], HEIGHT, 0.0)
            call UnitApplyTimedLife(this.circles[CIRCLES - 1], 'BTLF', DELAY + .2)
            call UnitApplyTimedLife(this.circles[CIRCLES], 'BTLF', DELAY + .2)
            call this.startPeriodic()
            set casterr = thistype.caster
            return this
        endmethod
        
        static method SpaceCollapseAction takes nothing returns boolean
            if GetSpellAbilityId() == SC_ID then
                set thistype.caster = GetTriggerUnit()
                set thistype.level = GetUnitAbilityLevel(thistype.caster, SC_ID)
                call SetUnitAnimation(thistype.caster, ANIMATION)
                set thistype.x = GetUnitX(thistype.caster)
                set thistype.y = GetUnitY(thistype.caster)
                set thistype.x2 = GetSpellTargetX()
                set thistype.y2 = GetSpellTargetY()
                call thistype.create(GetOwningPlayer(thistype.caster), Atan2(thistype.y-thistype.y2, thistype.x-thistype.x2), thistype.x2, thistype.y2, thistype.level)
                call NovaSystem.create(thistype.caster, thistype.x2, thistype.y2, 0.0, GetRadius(thistype.level), 0.0, 1, 1, DELAY - .1 , DELAY - .1, GetDamage(thistype.level), GetScaleCollapse(thistype.level), false, false, false, COLLAPSE, AT, DT)
            endif
            return false
        endmethod
        
    endstruct
    

endlibrary

I would upload it as a spell resource together with LoV, once the contest finishes... ^_^
 
Level 37
Joined
Mar 6, 2006
Messages
9,240
Does declaring a local with udg_ prefix still transform globals into locals with patch 1.26?

Yes it does, for example this kills all entering units:
  • Untitled Trigger 077
    • Events
      • Unit - A unit enters Region 000 <gen>
    • Conditions
    • Actions
      • Custom script: local unit udg_u = GetTriggerUnit()
      • Wait 2.00 seconds
      • Unit - Kill u
@indomitable1319
Post the spell in a map and I'll take a look at it.
 
Level 16
Joined
Jun 24, 2009
Messages
1,409
I've attached a test map for my spell for those who wanna test it... I might still do adjustments and optimizations depending on feedback...

and the code is here:

Waow, nice one but I have some suggestions ~.~.
Create an extra dummy with a -180 pitch angle for the Unholy Aura effect and you will get an effect more likely the original one.
Also some spin effect could be good for the casters.
And last but not least, an idea for the blast effect. In the original version these are spikes. With an XYZ 5% 5% 100% Levelup effect with a little pitch angle you can make the same effects.
 
Level 11
Joined
May 31, 2008
Messages
698
Here's my latest wip. I'm anxious to see what people think :)

http://upload.willhost.it/1/plxpn.w3x

You should make it so you cant hurt yourself with it. Cause if you launch it right before it gets to you, it continues to come towards you and passes thru you and goes behind you. And when it goes thru you it damages.

But other than that it looks pretty cool :)
 
I can't use the revive effect with .05/.05/1.0 scaling... because effects don't scale xyz with the unit that they're attached to... they seem to scale with the lowest scaling value that unit has... on that sample, the effect scaled as .05/.05/.05

I don't think the effect would justify the extra dummy and the extra code...

but I would apply the multiple effects, and now the damage will be dealt by each effect...
 
Level 16
Joined
Jun 24, 2009
Messages
1,409
Aw, since I've changed the base spell type to a channeling one everything is messed up... I've made very n00b and obvious mistakes because I'm too tired, but I fixed every of these(I think). But there is still something I can't find. Could someone help me a little?

  • Init
    • Events
      • Map initialization
    • Conditions
    • Actions
      • Visibility - Disable fog of war
      • Visibility - Disable black mask
      • Set SBMax = 2
      • -------- Configurables on each level --------
      • -------- Level 1 --------
      • Set Distance[1] = 1250.00
      • -------- Level 2 --------
      • Set Distance[2] = 1500.00
      • -------- Level 3 --------
      • Set Distance[3] = 1750.00
  • Soul Blast
    • Events
      • Unit - A unit Begins channeling an ability
    • Conditions
      • (Ability being cast) Equal to Soul Blast
    • Actions
      • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
        • If - Conditions
          • SBHas[SBLastRecycled] Equal to True
        • Then - Actions
          • Set SBMax = (SBMax + 1)
          • Set SBLastRecycled = SBMax
          • Set SBIndex = SBLastRecycled
          • Set SBLastRecycled = SBRecycledList[SBLastRecycled]
        • Else - Actions
          • Set SBIndex = SBLastRecycled
          • Set SBLastRecycled = SBRecycledList[SBLastRecycled]
      • Set SBCaster[SBIndex] = (Triggering unit)
      • Set SBCasterPoint[SBIndex] = (Position of SBCaster[SBIndex])
      • Set SBTargetPoint[SBIndex] = (Target point of ability being cast)
      • Set SBDistance[SBIndex] = 50.00
      • Set SBLevel[SBIndex] = (Level of Soul Blast for SBCaster[SBIndex])
      • Set SBMaxDistance[SBIndex] = Distance[SBLevel[SBIndex]]
      • Set SBAngle[SBIndex] = (Angle from SBCasterPoint[SBIndex] to SBTargetPoint[SBIndex])
      • Set SBTempPoint = (SBCasterPoint[SBIndex] offset by 50.00 towards SBAngle[SBIndex] degrees)
      • Unit - Create 1 Missile Body 1 for (Triggering player) at SBCasterPoint[SBIndex] facing SBAngle[SBIndex] degrees
      • Unit Group - Add (Last created unit) to SBDummyGroup[SBIndex]
      • Animation - Change (Last created unit)'s animation speed to 5.00% of its original speed
      • Unit - Create 1 Missile Body 2 for (Triggering player) at SBCasterPoint[SBIndex] facing SBAngle[SBIndex] degrees
      • Unit Group - Add (Last created unit) to SBDummyGroup[SBIndex]
      • Unit - Create 1 Missile Head for (Triggering player) at SBTempPoint facing SBAngle[SBIndex] degrees
      • Unit Group - Add (Last created unit) to SBDummyGroup[SBIndex]
      • Set SBHas[SBIndex] = True
      • Set SBCount = (SBCount + 1)
      • Set SBTimer[SBIndex] = 3.00
      • Set SBEffect[SBIndex] = False
      • Custom script: call RemoveLocation (udg_SBTempPoint)
      • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
        • If - Conditions
          • (Soul Blast Loop <gen> is on) Equal to False
        • Then - Actions
          • Trigger - Turn on Soul Blast Loop <gen>
          • Trigger - Turn on Wave Effect <gen>
        • Else - Actions
  • Soul Blast Halt
    • Events
      • Unit - A unit Stops casting an ability
      • Unit - A unit Finishes casting an ability
    • Conditions
      • (Ability being cast) Equal to Soul Blast
    • Actions
      • For each (Integer A) from 0 to SBMax, do (Actions)
        • Loop - Actions
          • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
            • If - Conditions
              • SBCaster[(Integer A)] Equal to (Triggering unit)
            • Then - Actions
              • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                • If - Conditions
                  • SBTimer[(Integer A)] Greater than 0.00
                • Then - Actions
                  • Unit Group - Pick every unit in SBDummyGroup[(Integer A)] and do (Unit - Kill (Picked unit))
                  • Unit Group - Remove all units from SBDummyGroup[(Integer A)]
                  • Set SBTimer[(Integer A)] = 0.00
                  • Custom script: call RemoveLocation (udg_SBTargetPoint[GetForLoopIndexA()])
                  • Custom script: call RemoveLocation (udg_SBCasterPoint[GetForLoopIndexA()])
                  • Set SBHas[(Integer A)] = False
                  • Set SBRecycledList[(Integer A)] = SBLastRecycled
                  • Set SBLastRecycled = (Integer A)
                  • Set SBEffect[(Integer A)] = False
                  • Set SBCount = (SBCount - 1)
                  • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                    • If - Conditions
                      • SBCount Equal to 0
                    • Then - Actions
                      • Trigger - Turn off Wave Effect <gen>
                      • Trigger - Turn off Soul Blast Loop <gen>
                    • Else - Actions
                • Else - Actions
            • Else - Actions
  • Soul Blast Loop
    • Events
      • Time - Every 0.03 seconds of game time
    • Conditions
    • Actions
      • For each (Integer SBInteger) from 0 to SBMax, do (Actions)
        • Loop - Actions
          • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
            • If - Conditions
              • SBHas[SBInteger] Equal to True
            • Then - Actions
              • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                • If - Conditions
                  • SBTimer[SBInteger] Greater than 0.00
                • Then - Actions
                  • Set SBTimer[SBInteger] = (SBTimer[SBInteger] - 0.03)
                • Else - Actions
                  • Set SBEffect[SBInteger] = True
                  • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                    • If - Conditions
                      • SBDistance[SBInteger] Less than SBMaxDistance[SBInteger]
                    • Then - Actions
                      • Set SBDistance[SBInteger] = (SBDistance[SBInteger] + 40.00)
                      • Set SBTempPoint = (SBCasterPoint[SBInteger] offset by SBDistance[SBInteger] towards SBAngle[SBInteger] degrees)
                      • Unit Group - Pick every unit in SBDummyGroup[SBInteger] and do (Actions)
                        • Loop - Actions
                          • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                            • If - Conditions
                              • (Unit-type of (Picked unit)) Equal to Missile Head
                            • Then - Actions
                              • Set SBTempPoint2 = (SBCasterPoint[SBInteger] offset by (SBDistance[SBInteger] + 40.00) towards SBAngle[SBInteger] degrees)
                              • Unit - Move (Picked unit) instantly to SBTempPoint2
                              • Custom script: call RemoveLocation (udg_SBTempPoint2)
                            • Else - Actions
                              • Unit - Move (Picked unit) instantly to SBTempPoint
                      • Set SBTempGroup = (Units within 100.00 of SBTempPoint matching ((((Matching unit) is A structure) Equal to False) and ((((Matching unit) is Magic Immune) Equal to False) and ((((Matching unit) is alive) Equal to True) and (((Matching unit) belongs to an enemy of (Owner of SBCa
                      • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                        • If - Conditions
                          • (SBTempGroup is empty) Equal to True
                        • Then - Actions
                        • Else - Actions
                          • Custom script: call RemoveLocation (udg_SBTargetPoint[udg_SBInteger])
                          • Custom script: call RemoveLocation (udg_SBCasterPoint[udg_SBInteger])
                          • Custom script: set bj_wantDestroyGroup = true
                          • Set SBEffect[SBIndex] = False
                          • Unit Group - Pick every unit in (Units within 250.00 of SBTempPoint matching ((((Matching unit) is A structure) Equal to False) and ((((Matching unit) is Magic Immune) Equal to False) and ((((Matching unit) is alive) Equal to True) and (((Matching unit) belongs to an enemy of (Owner of SBCa and do (Actions)
                            • Loop - Actions
                              • Unit - Cause SBCaster[SBInteger] to damage (Picked unit), dealing (100.00 x (Real(SBLevel[SBInteger]))) damage of attack type Spells and damage type Magic
                          • Unit Group - Pick every unit in SBDummyGroup[SBInteger] and do (Unit - Kill (Picked unit))
                          • Unit Group - Remove all units from SBDummyGroup[SBInteger]
                          • Unit - Create 1 Blast Effect for (Owner of SBCaster[SBInteger]) at SBTempPoint facing Default building facing degrees
                          • Unit - Add a 0.10 second Generic expiration timer to (Last created unit)
                          • Set SBHas[SBInteger] = False
                          • Set SBCount = (SBCount - 1)
                          • Set SBRecycledList[SBInteger] = SBLastRecycled
                          • Set SBLastRecycled = SBInteger
                          • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                            • If - Conditions
                              • SBCount Equal to 0
                            • Then - Actions
                              • Trigger - Turn off (This trigger)
                              • Trigger - Turn off Wave Effect <gen>
                            • Else - Actions
                      • Custom script: call DestroyGroup (udg_SBTempGroup)
                      • Custom script: call RemoveLocation (udg_SBTempPoint)
                    • Else - Actions
                      • Set SBHas[SBInteger] = False
                      • Custom script: set bj_wantDestroyGroup = true
                      • Set SBEffect[SBIndex] = False
                      • Unit Group - Pick every unit in SBDummyGroup[SBInteger] and do (Unit - Kill (Picked unit))
                      • Unit Group - Remove all units from SBDummyGroup[SBInteger]
                      • Custom script: call RemoveLocation (udg_SBTargetPoint[udg_SBInteger])
                      • Custom script: call RemoveLocation (udg_SBCasterPoint[udg_SBInteger])
                      • Set SBCount = (SBCount - 1)
                      • Set SBRecycledList[SBInteger] = SBLastRecycled
                      • Set SBLastRecycled = SBInteger
                      • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                        • If - Conditions
                          • SBCount Equal to 0
                        • Then - Actions
                          • Trigger - Turn off (This trigger)
                          • Trigger - Turn off Wave Effect <gen>
                        • Else - Actions
            • Else - Actions
  • Wave Effect
    • Events
      • Time - Every 0.05 seconds of game time
    • Conditions
    • Actions
      • For each (Integer B) from 0 to SBMax, do (Actions)
        • Loop - Actions
          • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
            • If - Conditions
              • SBHas[(Integer B)] Equal to True
              • SBEffect[(Integer B)] Equal to True
            • Then - Actions
              • Unit Group - Pick every unit in SBDummyGroup[(Integer B)] and do (Actions)
                • Loop - Actions
                  • If (All Conditions are True) then do (Then Actions) else do (Else Actions)
                    • If - Conditions
                      • ((Picked unit) is alive) Equal to True
                      • (Unit-type of (Picked unit)) Equal to Missile Head
                    • Then - Actions
                      • Set SBTempPoint = (Position of (Picked unit))
                      • Unit - Create 1 Wave Effect for (Owner of (Picked unit)) at SBTempPoint facing (Facing of (Picked unit)) degrees
                      • Animation - Change (Last created unit)'s animation speed to 150.00% of its original speed
                      • Unit - Add a 1.00 second Generic expiration timer to (Last created unit)
                      • Custom script: call RemoveLocation (udg_SBTempPoint)
                    • Else - Actions
            • Else - Actions
View attachment Soul Blast.w3x
 
Level 37
Joined
Mar 6, 2006
Messages
9,240

IceShards.jpg


A video I recorded, the game is Titan Quest:

Needs some refinement:
JASS:
scope IceShards initializer InitTrig_Ice_Shards

    globals
    
        private constant integer    ABILID          = 'A000'
        private constant integer    SHARDID         = 'h000'
        private constant integer    CASTERID         = 'h001'
    
        private constant integer    BASESHARDS      = 2
        private constant integer    BONUSSHARDS     = 2
        
        private constant real       SHARDTIMEOUT         = 0.03
        private constant real       BURNTIMEOUT          = 0.10
        
        private constant real       AOE             = 50.
        private constant real       BASEDAMAGE      = 15.
        private constant real       BONUSDAMAGE     = 10.
        private constant real       BASEBURNDAMAGE  = 10. * BURNTIMEOUT
        private constant real       BONUSBURNDAMAGE = 5. * BURNTIMEOUT
        private constant real       BURNTIME        = 3.
        private constant real       MAXDELAYTIME    = 0.5
        private constant real       BASESPEED       = 15.
        private constant real       BONUSSPEED      = 3.
        private constant real       BASEPASS        = 40.
        private constant real       BONUSPASS       = 10.
        private constant real       PROJHEIGHT      = 65.
        private constant real       SPAWNOFFSET     = 40.
        private constant real       OFFSETANGLE     = 15 * bj_PI / 180
        private constant real       NEXTANGLE       = 8 * bj_PI / 180
        private constant real       NEXTANGLEREDUCT = 2 * bj_PI / 180
        private constant real       NEXTANGLEMIN    = 3 * bj_PI / 180
        
        private constant attacktype ATK_T = ATTACK_TYPE_NORMAL
        private constant damagetype DMG_T = DAMAGE_TYPE_COLD
        
        //private constant string HITEFFECT = "Abilities\\Weapons\\SpiritOfVengeanceMissile\\SpiritOfVengeanceMissile.mdl"
        private constant string HITEFFECT = "Abilities\\Weapons\\DragonHawkMissile\\DragonHawkMissile.mdl"
        
        private player plr
        private unit un
        private real dam
        private real bdam
        private real pierce
        private boolean bln
        private integer HID
        private integer projs = 0
        private integer burns = 0
        
        private group grp = CreateGroup()
        private group tgrp = CreateGroup()
        private group burnGrp = CreateGroup()
        private group shardGrp = CreateGroup()
        private timer burnTmr = CreateTimer()
        private timer shardTmr = CreateTimer()
        private hashtable ht = InitHashtable()
        
    endglobals
    
    
    private constant function HashCaster takes nothing returns integer
        return 0
    endfunction
    
    
    private constant function HashDamage takes nothing returns integer
        return 1
    endfunction
    
    
    private constant function HashAngle takes nothing returns integer
        return 2
    endfunction
    
    
    private constant function HashPass takes nothing returns integer
        return 3
    endfunction
    
    
    private constant function HashSpeed takes nothing returns integer
        return 4
    endfunction
    
    
    private constant function HashGroup takes nothing returns integer
        return 5
    endfunction
    
    
    private constant function HashBurnDmg takes nothing returns integer
        return 6
    endfunction
    
    
    private constant function HashBurnTime takes nothing returns integer
        return 7
    endfunction
    
    
    private constant function HashDelayTime takes nothing returns integer
        return 8
    endfunction
    
    
    private constant function HashBoolean takes nothing returns integer
        return 9
    endfunction
    
    
    private function BurnLoop takes nothing returns nothing
        local unit u = GetEnumUnit()
        local integer id = GetHandleId(u)
        local real time = LoadReal(ht, id, HashBurnDmg())
        if GetWidgetLife(u) > 0.405 and time > 0 then
            set dam = LoadReal(ht, id, HashBurnDmg())
            set un = LoadUnitHandle(ht, id, HashCaster())
            call UnitDamageTarget(un, u, dam, false, true, ATK_T, DMG_T, null)
            call SaveReal(ht, id, HashBurnDmg(), time - BURNTIMEOUT)
        else
            call GroupRemoveUnit(burnGrp, u)
            call FlushChildHashtable(ht, id)
            set burns = burns - 1
            if burns == 0 then
                call PauseTimer(burnTmr)
            endif
        endif
        set u = null
    endfunction
    
    
    private function BurnTimerExp takes nothing returns nothing
        call ForGroup(burnGrp, function BurnLoop)
    endfunction
    
    
    private function DamageFilt takes nothing returns boolean
        local unit u = GetFilterUnit()
        local integer id = GetHandleId(u)
        if not(IsUnitInGroup(u, tgrp))                                      and /*
        */ IsUnitEnemy(u, plr)                                              and /*
        */ GetWidgetLife(u) > 0.405                                         and /*
        */ bln != TRUE                                                      and /*
        */ GetUnitFlyHeight(u) < PROJHEIGHT                                 then
            call GroupAddUnit(tgrp, u)
            call DestroyEffect(AddSpecialEffectTarget(HITEFFECT, u, "chest"))
            call UnitDamageTarget(un, u, dam, false, true, ATK_T, DMG_T, null)
            set bj_lastCreatedUnit = CreateUnit(Player(15), CASTERID, GetUnitX(u), GetUnitY(u), 0)
            call IssueTargetOrder(bj_lastCreatedUnit, "slow", u)
            call SetUnitExploded(bj_lastCreatedUnit, true)
            call UnitApplyTimedLife(bj_lastCreatedUnit, 1, 1)
            
            if GetRandomReal(0, 100) > pierce then
                set bln = true
                call SaveBoolean(ht, HID, HashBoolean(), bln)
            endif
            
            if not(IsUnitInGroup(u, burnGrp)) then
                call GroupAddUnit(burnGrp, u)
                if burns == 0 then
                    call TimerStart(burnTmr, BURNTIMEOUT, true, function BurnTimerExp)
                endif
                set burns = burns + 1
            endif
            call SaveReal(ht, id, HashBurnDmg(), bdam)
            call SaveReal(ht, id, HashBurnTime(), BURNTIME)
            call SaveUnitHandle(ht, id, HashCaster(), un)
        endif
        set u = null
        return false
    endfunction
    
    
    private function ShardLoop takes nothing returns nothing
        local unit u = GetEnumUnit()
        local integer id = GetHandleId(u)
        local real spd = LoadReal(ht, id, HashSpeed())
        local real ang = LoadReal(ht, id, HashAngle())
        local real time = LoadReal(ht, id, HashDelayTime())
        local real x
        local real y
        if GetWidgetLife(u) > 0.405 then
            if time < 0 then
                set x = GetUnitX(u) + spd * Cos(ang)
                set y = GetUnitY(u) + spd * Sin(ang)
                call SetUnitX(u, x)
                call SetUnitY(u, y)
                set dam = LoadReal(ht, id, HashDamage())
                set bdam = LoadReal(ht, id, HashBurnDmg())
                set pierce = LoadReal(ht, id, HashPass())
                set un = LoadUnitHandle(ht, id, HashCaster())
                set plr = GetOwningPlayer(un)
                set HID = id
                set bln = LoadBoolean(ht, id, HashBoolean())
                set tgrp = LoadGroupHandle(ht, id, HashGroup())
                call GroupEnumUnitsInRange(grp, x, y, AOE, function DamageFilt)
                if bln then
                    call KillUnit(u)
                endif
            else
                if time - SHARDTIMEOUT < 0 then
                    call ShowUnit(u, true)
                    call UnitApplyTimedLife(u, 1, 1)
                endif
                call SaveReal(ht, id, HashDelayTime(), time - SHARDTIMEOUT)
            endif
        else
            call DestroyGroup(LoadGroupHandle(ht, id, HashGroup()))
            call GroupRemoveUnit(shardGrp, u)
            call FlushChildHashtable(ht, id)
            set projs = projs - 1
            if projs == 0 then
                call PauseTimer(shardTmr)
            endif
        endif
        set u = null
    endfunction
    
    
    private function ShardTimerExp takes nothing returns nothing
        call ForGroup(shardGrp, function ShardLoop)
    endfunction

    
    private function onCast takes nothing returns boolean
        local unit u = GetTriggerUnit()
        local integer id = 0
        local integer side = 0
        local integer shards = 0
        local integer loops = 0
        local integer level = GetUnitAbilityLevel(u, ABILID)
        //local real f = GetUnitFacing(u) * bj_DEGTORAD
        local real f = Atan2(GetSpellTargetY()-GetUnitY(u), GetSpellTargetX()-GetUnitX(u))
        local real x = GetUnitX(u) + SPAWNOFFSET * Cos(f)
        local real y = GetUnitY(u) + SPAWNOFFSET * Sin(f)
        local real dmg = 0
        local real ang = 0
        local real pass = 0
        local real speed = 0
        local real nxtang = 0
        local real burndmg = 0
        
        if GetSpellAbilityId() == ABILID then
        
            if projs == 0 then
                call TimerStart(shardTmr, SHARDTIMEOUT, true, function ShardTimerExp)
            endif
            
            set dmg = BASEDAMAGE + BONUSDAMAGE * level
            set burndmg = BASEBURNDAMAGE + BONUSBURNDAMAGE * level
            set shards = BASESHARDS + BONUSSHARDS * level
            set pass = BASEPASS + BONUSPASS * level
            set speed = BASESPEED + BONUSSPEED * level
            set nxtang = NEXTANGLE - (level-1)*NEXTANGLEREDUCT
            if nxtang < NEXTANGLEMIN then
                set nxtang = NEXTANGLEMIN
            endif
            
            if GetRandomInt(1,2) == 1 then
                set side = 1
            else
                set side = -1
            endif
            loop
                set ang = side * ang + f + GetRandomReal(0, OFFSETANGLE)
                
                set bj_lastCreatedUnit = CreateUnit(Player(15), SHARDID, x, y, ang * bj_RADTODEG)
                call ShowUnit(bj_lastCreatedUnit, true)
                call SetUnitExploded(bj_lastCreatedUnit, true)
                call SetUnitFlyHeight(bj_lastCreatedUnit, PROJHEIGHT, 0)
                call GroupAddUnit(shardGrp, bj_lastCreatedUnit)
                set id = GetHandleId(bj_lastCreatedUnit)
                
                call SaveBoolean(ht, id, HashBoolean(), false)
                call SaveReal(ht, id, HashAngle(), ang)
                call SaveReal(ht, id, HashPass(), pass)
                call SaveReal(ht, id, HashDamage(), dmg)
                call SaveReal(ht, id, HashSpeed(), speed)
                call SaveReal(ht, id, HashBurnDmg(), burndmg)
                call SaveReal(ht, id, HashDelayTime(), GetRandomReal(0, MAXDELAYTIME))
                call SaveUnitHandle(ht, id, HashCaster(), u)
                call SaveGroupHandle(ht, id, HashGroup(), CreateGroup())
                
                set projs = projs + 1
                set side = side * -1
                set loops = loops + 1
                exitwhen loops == shards
                if ModuloInteger(loops, 2) == 1 then
                    set ang = nxtang * (1 + loops/2)
                else
                    set ang = nxtang * (loops/2)
                endif
            endloop
        endif
        
        set u = null
        return false
    endfunction
    

    private function InitTrig_Ice_Shards takes nothing returns nothing
        local trigger t = CreateTrigger()
        call TriggerAddCondition(t, function onCast )
        call TriggerRegisterAnyUnitEventBJ(t, EVENT_PLAYER_UNIT_SPELL_EFFECT)
        set t = null
    endfunction

endscope
 

Attachments

  • IceShards.w3x
    32.9 KB · Views: 62
Status
Not open for further replies.
Top