Veronicans, Soar High!!

This is the virtual hangout for Veronicans! CSA BiƱan AY 2008-2009, signing up is for veronicans... but Who's to say that teachers aren't allowed!! So teachers... feel free to join us as moderators in this forum.~Darkside1362, webmaster~
 
PortalPortal  HomeHome  GalleryGallery  RegisterRegister  Log inLog in  

Share | 
 

 EquippedChaos Presents: Phoenix Circle

Go down 
AuthorMessage
Malkuthe Highwind
Admin
Admin
avatar

Male
Number of posts : 197
Age : 23
Location : In a tiny blue speck, floating upon the vastness of space.
Reputation : 10
Registration date : 2008-10-30

PostSubject: EquippedChaos Presents: Phoenix Circle   Fri Oct 31, 2008 10:43 am

Hey! This is currently Darkwulfv. Goldendercon and I formed a spellmaking duo called "EquippedChaos". We completed our first spell today, and I decided to come here for some last minute feedback before we moved into our next spell.

So, our first spell is an "omgwtfbbqhax" spell, in that it's insane with SFX and damage and stuff (I weakened it a bit, but making it more insane is easy). We decided to come in with a "BANG!", and this was the result.

Any script optimizations, etc. are appreciated.

NOTE: I've got a bit of a dilemma. This spell has a cooldown greater than its channel time, which is fine and dandy. But if, for some reason, someone were to lower the cooldown and cast the spell again while the first instance were active, the SFX do not die. I'd like to know the best way to accomplish this without ruining any MUI this spell has. Thanks!

Now, first off: The code:

Code:
scope PhoenixCircle initializer Init

globals
//ID of the spell
  private constant integer ABILITY_ID = 'A000'
 
//ID of the dummy spell
  private constant integer DUMMY_ID = 'A003'
 
//ID of the unit that will move around the caster
  private constant integer DUMMY_UNIT = 'h000'
 
//ID of the dummy caster
  private constant integer DUMMY_CASTER = 'h001'
 
//Number of air dummies
  private constant integer AIR_DUMMIES = 6
 
//Number of ground dummies
  private constant integer GROUND_DUMMIES = 18 
 
//Number of Flame Strikes
  private constant integer FLAME_STRIKES = 6
 
//Distance from the caster air dummies will be 
  private constant real AIR_DISTANCE = 200.
 
//Distance from the caster ground dummies will be
  private constant real GROUND_DISTANCE = 300. 
 
//Interval of the movement timer
//Higher values = less chance of lag, choppier movement
//Lower values = more chance of lag, smoother movement
//.035 is usually very good.
  private constant real TIMER_INTERVAL = .035 
 
//The height the dummies will float to 
  private constant real DUMMY_HEIGHT = 450.
 
//The height the caster will float to
  private constant real CASTER_HEIGHT = 225. 
 
//How long the spell will last (maximum), in seconds
//Always make it about 1/2 second less, for accuracy with effects
  private constant real SPELL_DURATION = 15
 
//Order string for the casting spell
  private constant string CAST_STRING = "starfall" 
 
//Order string for the dummy spell
  private constant string ORDER_STRING = "flamestrike"
 
//Path the dummy uses for its model
//This is here for preloading purposes, to stop cast-time lag.
  private constant string DUMMY_MODEL = "Abilities\\Weapons\\PhoenixMissile\\Phoenix_Missile.mdl"
endglobals


//NO TOUCHY!!! (from here and below)
struct PhoenixCircleData
  unit caster = null
  unit array dummies[8191]
  unit array groundies[8191]
  real rotation = 0
  timer runtimer = null
endstruct 

globals
  private group PhoenixCasters = CreateGroup()
endglobals

private function Callback takes nothing returns nothing
  local timer t = GetExpiredTimer()
  local PhoenixCircleData dat = GetHandleInt(t, "PhoenixData")
  local unit F = dat.caster
  local unit dummy
  local integer i = 1
  local real x = GetUnitX(F)
  local real y = GetUnitY(F)
  local real x2 = 0
  local real y2 = 0
  local real angle = 0
  local real rotation = dat.rotation
 
  loop
  exitwhen i > AIR_DUMMIES
    set dummy = dat.dummies[i]
    set angle = (Atan2(GetUnitY(dummy) - y, GetUnitX(dummy) - x)) + (bj_DEGTORAD *5.)
    set x2 = x + AIR_DISTANCE * Cos(angle)
    set y2 = y + AIR_DISTANCE * Sin(angle)
    call SetUnitPosition(dummy, x2, y2)
    set i = i + 1
  endloop

  set i = 1
  set rotation = rotation + 5.
  set angle = 0
 
  loop
    exitwhen i > GROUND_DUMMIES
    set angle = rotation + ((360 / GROUND_DUMMIES) * i)
    set x2 = x + GROUND_DISTANCE * Cos(angle * bj_DEGTORAD)
    set y2 = y + GROUND_DISTANCE * Sin(angle * bj_DEGTORAD)
    call SetUnitPosition(dat.groundies[i], x2, y2)
    set i = i + 1
  endloop
  set dat.rotation = rotation   
   
  set F = null
  set dummy = null
  set t = null
endfunction 
 
private function EmergencyClean takes unit caster returns boolean
  local PhoenixCircleData C = GetHandleInt(caster, "EmergencyClean")
  local integer i = 1
 
  loop
    exitwhen i > AIR_DUMMIES
    call RemoveUnit(C.dummies[i])
    set i = i + 1
  endloop
 
  set i = 1
 
  loop
    exitwhen i > GROUND_DUMMIES
    call RemoveUnit(C.groundies[i])
    set i = i + 1
  endloop
 
  call PauseTimer(C.runtimer)
  call DestroyTimer(C.runtimer)
 
  call SetUnitFlyHeight(caster, 0, 99999.)
 
  return true
endfunction
 
private function Conditions takes nothing returns boolean
    return GetSpellAbilityId() == ABILITY_ID
endfunction

private function Actions takes nothing returns nothing
  local unit dummy
  local unit C = GetTriggerUnit()
  local integer lvl = GetUnitAbilityLevel(C, ABILITY_ID)
  local integer i = 1
  local real X = GetUnitX(C)
  local real Y = GetUnitY(C)
  local real R = 360. / AIR_DUMMIES
  local real x2 = 0
  local real y2 = 0
  local player p = GetOwningPlayer(C)
  local timer t = CreateTimer()
  local boolean DoubleCast = false
  local PhoenixCircleData Data = PhoenixCircleData.create()
  set Data.caster = C
  set Data.runtimer = t
 
  if IsUnitInGroup(C, PhoenixCasters) then
    set DoubleCast = EmergencyClean(C)
    call GroupRemoveUnit(PhoenixCasters, C)
  endif
  call GroupAddUnit(PhoenixCasters, C)
 
  call UnitAddAbility(C, 'Amrf')
  call UnitRemoveAbility(C, 'Amrf') 
   
  call SetUnitFlyHeight(C, CASTER_HEIGHT, 75.) 
  if AIR_DUMMIES > 0 then
  loop
    exitwhen i > AIR_DUMMIES
    set x2 = X + AIR_DISTANCE * Cos((R * i) * bj_DEGTORAD)
    set y2 = Y + AIR_DISTANCE * Sin((R * i) * bj_DEGTORAD)
    set Data.dummies[i] = CreateUnit(p, DUMMY_UNIT, x2, y2, GetRandomReal(0, 360.))
    call SetUnitFlyHeight(Data.dummies[i], DUMMY_HEIGHT, 75.00 )
    set i = i + 1
  endloop
  endif
 
  set i = 1
  set x2 = 0
  set y2 = 0
  set R = 360. / GROUND_DUMMIES
 
  if GROUND_DUMMIES > 0 then
  loop
    exitwhen i > GROUND_DUMMIES
    set x2 = X + GROUND_DISTANCE * Cos((R * i) * bj_DEGTORAD)
    set y2 = Y + GROUND_DISTANCE * Sin((R * i) * bj_DEGTORAD)
    set Data.groundies[i] = CreateUnit(p, DUMMY_UNIT, x2, y2, GetRandomReal(0, 360.))
    set i = i + 1
  endloop
  endif
 
  call SetHandleInt(C, "EmergencyClean", Data)
  call SetHandleInt(t, "PhoenixData", Data)
  call TimerStart(t, TIMER_INTERVAL, true, function Callback)
 
  loop
  exitwhen OrderId2String(GetUnitCurrentOrder(C)) != CAST_STRING
    call PolledWait(.2)
  endloop 
 
  call SetUnitFlyHeight(C, 0, 75.00 )
 
    set i = 1
    loop
      exitwhen i > AIR_DUMMIES
      call KillUnit(Data.dummies[i])
      set i = i + 1
    endloop
    set i = 1
    loop
    exitwhen i > GROUND_DUMMIES
      call KillUnit(Data.groundies[i])
      set i = i + 1
    endloop
 
  call PauseTimer(t)
  call DestroyTimer(t)
 
  call PolledWait(1.)
  set i = 1
  set x2 = 0
  set y2 = 0
  set R = 0
 
  if FLAME_STRIKES > 0 and DoubleCast == false then
  loop
    exitwhen i > FLAME_STRIKES
    set dummy = CreateDummyUnit(p, DUMMY_CASTER, X, Y, DUMMY_ID, lvl, true)
    set x2 = X + (GROUND_DISTANCE * Cos(R * bj_DEGTORAD))
    set y2 = Y + (GROUND_DISTANCE * Sin(R * bj_DEGTORAD))
    call IssuePointOrder(dummy, ORDER_STRING, x2, y2)
    set R = ( R + ( 360.00 / FLAME_STRIKES ) )
    set i = i + 1
  endloop
  endif
 
  call GroupRemoveUnit(PhoenixCasters, C)
  call FlushHandleLocals(C)
 
  set dummy = null       
  set C = null
  set p = null
  set t = null
endfunction

//===========================================================================
private function Init takes nothing returns nothing
  local trigger t = CreateTrigger(  )
    call TriggerRegisterAnyUnitEventBJ(t, EVENT_PLAYER_UNIT_SPELL_EFFECT )
    call TriggerAddCondition(t, Condition( function Conditions ) )
    call TriggerAddAction(t, function Actions )
    call Preload(DUMMY_MODEL)
  set t = null
endfunction
endscope

changelog
Spoiler:
 



Here's the sample map:

mediafire.com file/djmyitzogvz/Phoenix Circle.w3x

EDIT: oops... I think I uploaded the modified version... if it does not spin in a circle, tell me
Back to top Go down
http://veronicans.aforumfree.com
 
EquippedChaos Presents: Phoenix Circle
Back to top 
Page 1 of 1
 Similar topics
-
» Phoenix-Class PCG Reliant
» Marijuana and my mom
» Steve Holt's Workshop Presents......
» Pirate ship and crop circles
» Fire 2.2 xTreme

Permissions in this forum:You cannot reply to topics in this forum
Veronicans, Soar High!! :: Un-Academically Related Stuff... :: EquippedChaos Productions-
Jump to: