| 07-23-2006, 04:57 AM | #1 |
Alright, I tried to expand my limited understanding of JASS by changing a trigger straight from GUI to a more compact, clean JASS trigger... For those who know me, congradulations should be in order *The)TideHunter( cough cough* Unfortunatly, I know very little about JASS, so I could only do so much without threatening to turn my computer into a pile of sludge... So I need somebody to please check it over. It's still probably very crappy, but it gives me feeling of satisfaction that I now know a little more about JASS. So, in all it's limited glory, here's a before and after. +REP to anyone who helps out (unless I need to spread it :p) Also, I'll credit you in my WC3C sections of my credits. BEFORE! JASS:function Trig_Turn_on_Damage_Copy_Copy_Conditions takes nothing returns boolean if ( not ( GetSpellAbilityId() == 'A00E' ) ) then return false endif return true endfunction function Trig_Turn_on_Damage_Copy_Copy_Func008001002 takes nothing returns boolean return ( UnitHasBuffBJ(GetFilterUnit(), 'B002') == true ) endfunction function Trig_Turn_on_Damage_Copy_Copy_Func008Func003001001 takes nothing returns boolean return ( TimerGetRemaining(udg_TempTimer) == 0.00 ) endfunction function Trig_Turn_on_Damage_Copy_Copy_Func008A takes nothing returns nothing call StartTimerBJ( udg_TempTimer, false, udg_Real ) loop exitwhen(Trig_Turn_on_Damage_Copy_Copy_Func008Func003001001()) call UnitDamageTargetBJ( udg_TempUnit, GetEnumUnit(), udg_Real, ATTACK_TYPE_CHAOS, DAMAGE_TYPE_FIRE ) endloop endfunction function Trig_Turn_on_Damage_Copy_Copy_Actions takes nothing returns nothing local integer udg_TempInteger local unit udg_TempUnit local timer udg_TempTimer set udg_FlameStompUnit[GetConvertedPlayerId(GetOwningPlayer(GetTriggerUnit()))] = GetTriggerUnit() set udg_TempInteger = GetUnitAbilityLevelSwapped('A00E', udg_FlameStompUnit[GetConvertedPlayerId(GetOwningPlayer(GetTriggerUnit()))]) call CreateNUnitsAtLoc( 1, 'e001', GetOwningPlayer(GetTriggerUnit()), GetUnitLoc(GetTriggerUnit()), bj_UNIT_FACING ) set udg_TempUnit = GetLastCreatedUnit() call ForGroupBJ( GetUnitsInRectMatching(GetPlayableMapRect(), Condition(function Trig_Turn_on_Damage_Copy_Copy_Func008001002)), function Trig_Turn_on_Damage_Copy_Copy_Func008A ) endfunction AFTER! JASS:function Trig_Turn_on_Damage_Conditions takes nothing returns boolean if ( not ( GetSpellAbilityId() == 'A00E' ) ) then return false endif return true endfunction function Trig_Turn_on_Damage_Func008A takes nothing returns nothing call StartTimerBJ( TempTimer, false, TempReal ) loop exitwhen( TimerGetRemaining(TempTimer) == 0.00 ) call UnitDamageTargetBJ( TempUnit, GetEnumUnit(), TempReal, ATTACK_TYPE_CHAOS, DAMAGE_TYPE_FIRE ) endloop endfunction function Trig_Turn_on_Damage_Actions takes nothing returns nothing local integer TempInteger local unit TempUnit local timer TempTimer local unit u = GetTriggerUnit local real TempReal = TempInteger * 2 set udg_FlameStompUnit[GetConvertedPlayerId(GetOwningPlayer(u))] = u set TempInteger = GetUnitAbilityLevelSwapped('A00E', udg_FlameStompUnit[GetConvertedPlayerId(GetOwningPlayer(u))]) call CreateNUnitsAtLoc( 1, 'e001', GetOwningPlayer(u), GetUnitLoc(u), bj_UNIT_FACING ) set TempUnit = GetLastCreatedUnit() call ForGroupBJ( GetUnitsInRectMatching(GetPlayableMapRect(), Condition( UnitHasBuffBJ(GetFilterUnit(), 'B002') == true ), function Trig_Turn_on_Damage_Func008A ) endfunction Sorry for the very crappy codes, I'm sure half of this could be packed into 3 natives :p. Please, don't lecture me on the shittyness of BJ's and stuff, I just want this to work. |
| 07-23-2006, 06:35 AM | #2 |
JASS:Condition( UnitHasBuffBJ(GetFilterUnit(), 'B002') == true ) |
| 07-23-2006, 06:51 AM | #3 |
soooo... How exactly would I put it in? The way it was before? |
| 07-23-2006, 07:01 AM | #4 |
Mm yes, but remember that the whole func leaks as hell and is infected with holy BJ shit. |
| 07-23-2006, 07:07 AM | #5 |
greaaat, just when I thought I'd fixed leakage... Well, any way to fix that? Or is the leak major? becuase if not I think I can let it slide... |
| 07-23-2006, 10:09 AM | #6 |
Here: JASS:function Trig_Turn_on_Damage_Conditions takes nothing returns boolean return GetSpellAbilityId() == 'A00E' endfunction function HasB002Buff takes nothing returns boolean return GetUnitAbilityLevel(GetFilterUnit(), 'B002') > 0 endfunction function Trig_Turn_on_Damage_Actions takes nothing returns nothing local unit ut local unit uloop local unit u = GetTriggerUnit() local integer i = GetUnitAbilityLevel(udg_FlameStompUnit[GetPlayerId(GetOwningPlayer(u))], 'A00E') local real r = i * 2 local group g = CreateGroup() local boolexpr b = Condition(function HasB002Buff) set ut = CreateUnit(GetOwningPlayer(u), 'e001', GetUnitX(u), GetUnitY(u), 270) call GroupEnumUnitsInRect(g, GetPlayableMapRect(), b) call DestroyBoolExpr(b) set b = null call PolledWait(r) loop set uloop = FirstOfGroup(g) exitwhen uloop == null call UnitDamageTarget(ut, uloop, r, false, false, ATTACK_TYPE_CHAOS, DAMAGE_TYPE_FIRE, WEAPON_TYPE_WHOKNOWS) loop set ut = null set uloop = null set u = null call DestroyGroup(g) set g = null endfunction Could have used a timer, but then you'd need to use local handle variables. Also, this may not be exactly what you want, because your origional code made absolutely no sense in places, mainly that loop with no wait in it, with a function that called non-existant variables. |
| 07-23-2006, 12:43 PM | #7 |
erm... My trigger is supposed to do this: Unit casts spell == Flame Stomp (A00E) create a dummy unit (e001) unit group, units being those with flame stomp buff (B002) -loop start timer (TempTimer) damage target (dummy unit damages picked unit) for r damage (which would be integer * 2, which is spell level * 2 of the triggering unit, u) everything is then set to null. Is that what yours does? Pardon that it didnt make sense, I had an updated code that may have made the slightest bit more sense but it was late last night and Inever got around to it... |
| 07-23-2006, 01:05 PM | #8 |
Why start TempTimer? I see no point. |
| 07-23-2006, 01:46 PM | #9 |
The unit takes damage every second for r (the real = integer 2) seconds, guess I forgot to mention that, sorry :/. The loop is supposed to keep looping until the remaining time of the timer = zero. I've been changing and fixing the code almost non-stop for the past hour, so here's an updated version. I did use some of your code, so don't feel like I blew your effort off. NOTE: I know nothing is nulled, thats after this code works. But 1 question. Do local variables have to be nulled in the function they were declared in, or can they be nulled elsewhere? JASS:function Trig_Turn_on_Damage_Conditions takes nothing returns boolean return ( GetSpellAbilityId() == 'A00E' ) endfunction function HasB002Buff takes nothing returns boolean return GetUnitAbilityLevel(GetFilterUnit(), 'B002') > 0 endfunction function StartTimer takes nothing returns nothing local unit u = GetTriggerUnit() local integer i = GetUnitAbilityLevelSwapped('A00E', u ) local real r = i * 2 local timer t = CreateTimerBJ(false, r) local unit tu = CreateNUnitsAtLoc( 1, 'e001', GetOwningPlayer(u), GetUnitLoc(u), bj_UNIT_FACING ) loop call StartTimerBJ( t, false, r ) exitwhen( TimerGetRemaining(t) == 0.00 ) call UnitDamageTargetBJ( tu, GetEnumUnit(), r, ATTACK_TYPE_CHAOS, DAMAGE_TYPE_FIRE, WEAPON_TYPE_WHOKNOWS) call PolledWait( 1 ) endloop endfunction function Trig_Turn_on_Damage_Actions takes nothing returns nothing call ForGroupBJ( GetUnitsInRectMatching(GetPlayableMapRect(), Condition(function HasB002Buff)), function StartTimer ) endfunction -Darkwulfv |
| 07-23-2006, 06:51 PM | #10 |
I changed a few BJ's and stuff, yes local handles need to be nulled, but not in the function they was created in. Heres your code from your last post updated: JASS:function Trig_Turn_on_Damage_Conditions takes nothing returns boolean return (GetSpellAbilityId() == 'A00E') endfunction function HasB002Buff takes nothing returns boolean return GetUnitAbilityLevel(GetFilterUnit(), 'B002') > 0 endfunction function StartTimer takes nothing returns nothing local unit TriggerUnit = GetTriggerUnit() local integer AbilLevel = GetUnitAbilityLevelSwapped('A00E', TriggerUnit) local real r = AbilLevel * 2 local timer t = CreateTimer() local unit Dummy = CreateUnit(GetOwningPlayer(TriggerUnit), 'e001', GetUnitX(TriggerUnit), GetUnitY(TriggerUnit), bj_UNIT_FACING ) loop call TimerStart(t, r, false, null) exitwhen(TimerGetRemaining(t) == 0.00) call UnitDamageTarget(Dummy, GetEnumUnit(), r, true, false, ATTACK_TYPE_CHAOS, DAMAGE_TYPE_FIRE, WEAPON_TYPE_WHOKNOWS) call PolledWait(1) endloop set TriggerUnit = null call DestroyTimer(t) set t = null set Dummy = null endfunction Sorry for renaming the locals, i couldent understand what they meant at first. EDIT: I realised you used poll wait, in a loop, in a looped loop, Forgroup is a loop too. Thats bad because it will only damage 1 unit a time until its finished then go on to the next 1, polling will poll the intire trigger and not just that function. TriggerSleepAction would have the same effect. |
| 07-23-2006, 07:50 PM | #11 |
I knew that my locals needed to be nulled, I hadn't gotten around to it yet... So does this work? Oh, and np for changing local var. names, I was just trying to get it done... However, I must ask. Is that the whole trigger, or is it missing the Trig_Turn_on_ actions function? Also, will this work for what I'd like it to? (damaging multiple units multiple times? If this won't, is there a buff or something that does damage over time that I can give to those units, thus making the timer loop uneeded?) So what you were saying is that this won't work for what I want it to due to the polled waits? |
| 07-23-2006, 09:43 PM | #12 |
Well, that was everything but the Init_Trig function. And, unfortunatly, this wont work =(. The polled waits will make it damage 1 unit at a time instead of damaging multiple units at multiple times. To be perfectly honest, i would use a DoT method and the return bug for a good method. Heres what i just wrote up: JASS:function GC takes nothing returns gamecache if(udg_GC == null) then call FlushGameCache(InitGameCache("GC")) set udg_GC = InitGameCache("GC") endif return udg_GC endfunction function H2I takes handle H returns integer return H return 0 endfunction function I2Unit takes integer I returns unit return I return null endfunction function DamageOverTime_Update takes nothing returns nothing local timer t = GetExpiredTimer() local string tS = I2S(H2I(t)) local unit Target = I2Unit(GetStoredInteger(GC(), "DamageOverTime_Target", tS)) local unit Credit = I2Unit(GetStoredInteger(GC(), "DamageOverTime_Credit", tS)) local real Damage = GetStoredReal(GC(), "DamageOverTime_DPI", tS) local integer Intervals = GetStoredInteger(GC(), "DamageOverTime_Intervals", tS) - 1 local real Dur = GetStoredReal(GC(), "DamageOverTime_Duration", tS) if(Intervals != 0) then call UnitDamageTarget(Credit, Target, Damage, true, false, ATTACK_TYPE_CHAOS, DAMAGE_TYPE_FIRE, WEAPON_TYPE_WHOKNOWS) call StoreInteger(GC(), "DamageOverTime_Intervals", tS, Intervals) call TimerStart(t, Dur, false, function DamageOverTime_Update) else call FlushStoredMission(GC(), tS) call DestroyTimer(t) set t = null set Target = null set Credit = null endif endfunction function DamageOverTime takes unit whichUnit, unit Credit, real DamagePerInterval, integer Intervals, real IntervalDuration returns nothing local timer t = CreateTimer() local string tS = I2S(H2I(t)) call StoreInteger(GC(), "DamageOverTime_Target", tS, H2I(whichUnit)) call StoreInteger(GC(), "DamageOverTime_Credit", tS, H2I(Credit)) call StoreReal(GC(), "DamageOverTime_DPI", tS, DamagePerInterval) call StoreInteger(GC(), "DamageOverTime_Intervals", tS, Intervals) call StoreReal(GC(), "DamageOverTime_Duration", tS, IntervalDuration) call TimerStart(t, IntervalDuration, false, function DamageOverTime_Update) endfunction Put it in your main map script section, BTW, this requires a gamecache called GC (udg_GC). Then to use, type: JASS:call DamageOverTime(Target, Credit, DamagePerInterval, integer DamageIntervalCount, IntervalDuration) So lets say you wanted to do 50 damage per second every 1 second for 10 seconds, type: JASS:call DamageOverTime(Target, Credit, 50., 10, 1.) Anyway, to put this into your trigger, just do: JASS:function Trig_Turn_on_Damage_Conditions takes nothing returns boolean return (GetSpellAbilityId() == 'A00E') endfunction function HasB002Buff takes nothing returns boolean return GetUnitAbilityLevel(GetFilterUnit(), 'B002') > 0 endfunction function Trig_Turn_on_Damage_Actions takes nothing returns nothing local unit TriggerUnit = GetTriggerUnit() local integer AbilLevel = GetUnitAbilityLevel(TriggerUnit, 'A00E') local real Fixer = AbilLevel * 2 local group Enum = GetUnitsInRectMatching(GetPlayableMapRect(), Condition(function HasB002Buff)) local unit CurrentUnit loop set CurrentUnit = FirstOfGroup(Enum) exitwhen CurrentUnit == null call DamageOverTime(CurrentUnit, TriggerUnit, Fixer, R2I(Fixer), 1.) call GroupRemoveUnit(Enum, CurrentUnit) endloop set TriggerUnit = null call DestroyGroup(Enum) set Enum = null endfunction |
| 07-23-2006, 11:12 PM | #13 |
Wow... Thanks Tide... I'll insert this when I can and give it a try. The spell itself kicks ass (imagine the firelord with flames all around him and then war stomp...) I just hope the damage over time works. If it doesn't, then I don't think the world will end, but you know. |
