| 10-15-2007, 10:53 AM | #2 |
JASS:function Fireball_Callback takes nothing returns nothing local timer T = GetExpiredTimer() local integer ArrayIndex = GetCSData(T) local real X local real Y local real Offset local unit Dummy = GetArrayUnit(ArrayIndex, 3) local boolean OutOfBounds = false local group G local unit U3 local unit CastDummy local integer DummyAbilityId local integer Level local real cos local real sin call BJDebugMsg("Callback Index: "+I2S(ArrayIndex)) if GetWidgetLife(Dummy) > 0.405 then call BJDebugMsg("Then; Life: "+R2S(GetWidgetLife(Dummy))) set Level = GetArrayInt(ArrayIndex, 5) set Offset = Fireball_DistancePerInterval(Level) set X = GetUnitX(Dummy) set Y = GetUnitY(Dummy) set cos = GetArrayReal(ArrayIndex, 1) set sin = GetArrayReal(ArrayIndex, 2) call BJDebugMsg("Old X: "+R2S(X)) call BJDebugMsg("Old Y: "+R2S(Y)) call BJDebugMsg("Offset: "+R2S(Offset)) call BJDebugMsg("MoveCos: "+R2S(cos)) call BJDebugMsg("MoveSin: "+R2S(sin)) set X = X+Offset*cos set Y = Y+Offset*sin call BJDebugMsg("New X: "+R2S(X)) call BJDebugMsg("New Y: "+R2S(Y)) // if X < GetRectMinX(bj_mapInitialPlayableArea) then // call BJDebugMsg("Set OutOfBounds 1") // set OutOfBounds = true // elseif X > GetRectMaxX(bj_mapInitialPlayableArea) then // call BJDebugMsg("Set OutOfBounds 2") // set OutOfBounds = true // elseif Y < GetRectMinY(bj_mapInitialPlayableArea) then // call BJDebugMsg("Set OutOfBounds 3") // set OutOfBounds = true // elseif Y > GetRectMaxY(bj_mapInitialPlayableArea) then // call BJDebugMsg("Set OutOfBounds 4") // set OutOfBounds = true // endif if not(OutOfBounds) then call BJDebugMsg("Not Out of Bounds") call SetUnitX(Dummy, X) call SetUnitY(Dummy, Y) set G = GetArrayGroup(ArrayIndex, 4) set bj_stockPickedItemLevel = Level set bj_forceRandomCurrentPick = GetOwningPlayer(Dummy) call GroupEnumUnitsInRange(G, X, Y, Fireball_CollisionRadius(Level), Condition(function Fireball_Filter)) set U3 = FirstOfGroup(G) if U3 != null then call BJDebugMsg("Collision") set DummyAbilityId = Fireball_DummyStunSpellId(Level) set CastDummy = CreateUnit(bj_forceRandomCurrentPick, Fireball_DummyUnitId(), X, Y, 0.00) call UnitAddAbility(CastDummy, DummyAbilityId) call SetUnitAbilityLevel(CastDummy, DummyAbilityId, Level) call IssueTargetOrder(CastDummy, Fireball_DummyStunSpellOrderString(Level), U3) call UnitApplyTimedLife(CastDummy, 'BTLF', 2.00) call DestroyEffect(AddSpecialEffect(Fireball_CollideEffectPath(Level), X, Y)) call KillUnit(Dummy) set CastDummy = null set U3 = null endif else call BJDebugMsg("Out of Bounds") call KillUnit(Dummy) endif else call BJDebugMsg("Else; Life: "+R2S(GetWidgetLife(Dummy))) call DestroyGroup(GetArrayGroup(ArrayIndex, 4)) call DestroyArray(ArrayIndex) call PauseTimer(T) call DestroyTimer(T) endif set T = null set Dummy = null endfunction |
| 10-15-2007, 12:20 PM | #3 |
That would have to do with the 'having to set reals to a variable before return bugging them' thing. Edit: Just by the way, your thread title is incredibly misleading as this has nothing to do with integers or the max size of them. |
| 10-15-2007, 01:47 PM | #4 |
Looks like integer 2 real got the same bugs as real 2 intger. JASS:
//===================================================================================================
// Indexes of real types
//
function SetArrayReal takes integer id, integer index, real val returns nothing
set index=id+index
if (index<8191) then
set cs_array1[index]=CS_r2i(val)
elseif (index<16382) then
set cs_array2[index-8191]=CS_r2i(val)
else
call StoreReal(cs_cache,I2S(-id),I2S(index),val)
endif
endfunction
function GetArrayReal takes integer id, integer index returns real
local real r
set index=id+index
if (index<8191) then
set r= CS_i2r(cs_array1[index])
elseif (index<16382) then
set r= CS_i2r( cs_array2[index-8191] )
else
set r=GetStoredReal(cs_cache,I2S(-id),I2S(index))
endif
return r
endfunction
If you ask me, people shouldn't really be using cscache's dynamic arrays... At least not on things that are not integers. |
| 10-15-2007, 05:29 PM | #5 |
Question: if you're using new gen, why don't you use constant globals instead of all those constant functions? It would save you some space (and will also spare you of that annoying "()" typing) |
| 10-15-2007, 05:59 PM | #6 | |
Quote:
|
| 10-15-2007, 07:14 PM | #7 |
Well, I said that I broke the integer limit because I thought the max integer was something like 2235901257012 and I was getting numbers bigger than that which weren't causing the game to crash. Is it really a bad idea to use Dynamic Arrays for spells, Vexorian? I thought it would be smarter because it avoids gamecache lookup and they aren't permanently taking up space for available indexes. |
| 10-15-2007, 11:58 PM | #8 |
Whoo. Double post. I've fixed the random fuckups with the dynamic arrays' reals and encountered another problem: the spell itself works fine, no errors or anything and all the effects happen as they should. The problem arises when the same unit casts the spell once and then once more again whilst the first fireball is still in existence. If this happens, the game immediately crashes. I thought I would try it with two different units casting the spell at the same time to see if it caused a crash, and it turns out that it does not; instead, something far weirder happens. The first timer simply stops running. After both instances have finished, both units can once again cast as normal (though still not at the same time)... but the value of ArrayIndex increases each time. Normally, the text "Callback ArrayIndex: 2" shows up during the spells, but after doing the above, the message "Callback ArrayIndex: 7" is displayed instead. My guess is that this is because the first array (of which 5 slots are used) is not being destroyed when the timer stops running. Of his, however, I am not sure. Here's the spell code: JASS://*****************************************************************************************\\ // Spell Name: Fireball \\ // Spell Author: Pyrogasm \\ // \\ // Follows the JESP Standard \\ //*****************************************************************************************\\ //*****************************************************************************************\\ // Start Configuration Functions \\ //*****************************************************************************************\\ constant function Fireball_AbilityId takes nothing returns integer return 'A000' //Rawcode of the actual spell endfunction constant function Fireball_FireballDummyId takes integer Level returns integer return 'h002' //Rawcode of the unit that will be moved as the fireball endfunction constant function Fireball_DummyUnitId takes nothing returns integer return 'h000' //Rawcode of the dummy caster endfunction constant function Fireball_DummyStunSpellId takes integer Level returns integer return 'A001' //Rawcode of the dummy stun/damage spell endfunction constant function Fireball_DummyStunSpellOrderString takes integer Level returns string return "thunderbolt" //The orderstring for the dummy stun/damage spell endfunction constant function Fireball_FireballDuration takes integer Level returns real return 1.50 //The duration of the spell (how long the dummy unit lasts for) endfunction constant function Fireball_CollisionRadius takes integer Level returns real return 100.00 //How close to the fireball a unit has to be in order for the fireball to "collide" endfunction function Fireball_CollisionFilter takes unit FilterUnit, integer Level, player OwnerOfCaster returns boolean return GetWidgetLife(FilterUnit) > 0.405 and IsUnitEnemy(FilterUnit, OwnerOfCaster) //Make your own filter for checking for units in range for a collision here endfunction constant function Fireball_TimerInterval takes integer Level returns real return 0.04 //How often the move timer runs (in seconds) endfunction constant function Fireball_DistancePerInterval takes integer Level returns real return 25.00 //How far the fireball moves each iteration endfunction constant function Fireball_CastSpawnOffset takes integer Level returns real return 100.00 //When the spell is cast, the fireball will be created this far away from the caster //In the direction towards where the spell was cast endfunction constant function Fireball_CollideEffectPath takes integer Level returns string return "" //Optional special effect to be played on the position of the fireball when it collides endfunction //*****************************************************************************************\\ // End Configuration Functions \\ //*****************************************************************************************\\ function Fireball_CastConditions takes nothing returns boolean return GetSpellAbilityId() == Fireball_AbilityId() endfunction function Fireball_Filter takes nothing returns boolean local unit U3 = GetFilterUnit() local boolean B = Fireball_CollisionFilter(U3, bj_stockPickedItemLevel, bj_forceRandomCurrentPick) set U3 = null return B endfunction function Fireball_Callback takes nothing returns nothing local timer T = GetExpiredTimer() local integer ArrayIndex = GetCSData(T) local real X local real Y local real Offset local unit Dummy = GetArrayUnit(ArrayIndex, 3) local boolean OutOfBounds = false local group G local unit U3 local unit CastDummy local integer DummyAbilityId local integer Level local real MoveCos = GetArrayReal(ArrayIndex, 1) local real MoveSin = GetArrayReal(ArrayIndex, 2) call BJDebugMsg("Callback ArrayIndex: "+I2S(ArrayIndex)) if GetWidgetLife(Dummy) > 0.405 then set Level = GetArrayInt(ArrayIndex, 5) set Offset = Fireball_DistancePerInterval(Level) set X = GetUnitX(Dummy)+Offset*MoveCos set Y = GetUnitY(Dummy)+Offset*MoveSin if X < GetRectMinX(bj_mapInitialPlayableArea) then set OutOfBounds = true elseif X > GetRectMaxX(bj_mapInitialPlayableArea) then set OutOfBounds = true elseif Y < GetRectMinY(bj_mapInitialPlayableArea) then set OutOfBounds = true elseif Y > GetRectMaxY(bj_mapInitialPlayableArea) then set OutOfBounds = true endif if not(OutOfBounds) then call SetUnitX(Dummy, X) call SetUnitY(Dummy, Y) set G = GetArrayGroup(ArrayIndex, 4) set bj_stockPickedItemLevel = Level set bj_forceRandomCurrentPick = GetOwningPlayer(Dummy) call GroupEnumUnitsInRange(G, X, Y, Fireball_CollisionRadius(Level), Condition(function Fireball_Filter)) set U3 = FirstOfGroup(G) if U3 != null then set DummyAbilityId = Fireball_DummyStunSpellId(Level) set CastDummy = CreateUnit(bj_forceRandomCurrentPick, Fireball_DummyUnitId(), X, Y, 0.00) call UnitAddAbility(CastDummy, DummyAbilityId) call SetUnitAbilityLevel(CastDummy, DummyAbilityId, Level) call IssueTargetOrder(CastDummy, Fireball_DummyStunSpellOrderString(Level), U3) call UnitApplyTimedLife(CastDummy, 'BTLF', 2.00) call DestroyEffect(AddSpecialEffect(Fireball_CollideEffectPath(Level), X, Y)) call KillUnit(Dummy) set CastDummy = null set U3 = null endif else call KillUnit(Dummy) endif else set G = GetArrayGroup(ArrayIndex, 4) call DestroyGroup(G) set G = null call DestroyArray(ArrayIndex) call PauseTimer(T) call DestroyTimer(T) endif set T = null set Dummy = null endfunction function Fireball_Cast takes nothing returns nothing local unit U = GetTriggerUnit() local location L = GetSpellTargetLoc() local real X = GetUnitX(U) local real Y = GetUnitY(U) local real X2 = GetLocationX(L) local real Y2 = GetLocationY(L) local real Angle = Atan2((Y2-Y),(X2-X)) local real MoveCos = Cos(Angle) local real MoveSin = Sin(Angle) local integer Level = GetUnitAbilityLevel(U, Fireball_AbilityId()) local integer ArrayIndex = NewArray(7, true) local real Offset = Fireball_CastSpawnOffset(Level) local timer T = CreateTimer() local unit Dummy = CreateUnit(GetOwningPlayer(U), Fireball_FireballDummyId(Level), X+Offset*MoveCos, Y+Offset*MoveSin, Angle*57.2958) call BJDebugMsg("Cast ArrayIndex: "+I2S(ArrayIndex)) call UnitApplyTimedLife(Dummy, 'BTLF', Fireball_FireballDuration(Level)) call SetArrayReal(ArrayIndex, 1, MoveCos) call SetArrayReal(ArrayIndex, 2, MoveSin) call SetArrayObject(ArrayIndex, 3, Dummy) call SetArrayObject(ArrayIndex, 4, CreateGroup()) call SetArrayInt(ArrayIndex, 5, Level) call SetCSData(T, ArrayIndex) call TimerStart(T, Fireball_TimerInterval(Level), true, function Fireball_Callback) call RemoveLocation(L) set L = null set Dummy = null set U = null set T = null endfunction //=========================================================================== function InitTrig_Fireball takes nothing returns nothing //Preloading local unit U = CreateUnit(Player(15), Fireball_FireballDummyId(1), 0.00, 0.00, 0.00) call UnitAddAbility(U, Fireball_DummyStunSpellId(1)) call RemoveUnit(U) set U = null set gg_trg_Fireball = CreateTrigger() call TriggerRegisterAnyUnitEventBJ(gg_trg_Fireball, EVENT_PLAYER_UNIT_SPELL_EFFECT) call TriggerAddCondition(gg_trg_Fireball, Condition(function Fireball_CastConditions)) call TriggerAddAction(gg_trg_Fireball, function Fireball_Cast) endfunction |
| 10-16-2007, 02:52 AM | #9 | |
Quote:
I think though that it might be possible to fix it, I dunno. |
| 10-16-2007, 03:29 AM | #10 |
So how is it worse than gamecache? Storing/getting things using AttachObject(...) and GetAttachedUnit(...) still uses I2U. No ideas on the current issue? One thing I forgot to mention is that I commented out the SetUnitX/Y lines to try to eliminate the crash there but to no avail... so it definitely isn't that. |
| 10-16-2007, 09:58 AM | #11 |
seems that local unit Dummy = GetArrayUnit(ArrayIndex, 3) is failing when cast 2 times at the same time. JASS:function Fireball_Callback takes nothing returns nothing local timer T = GetExpiredTimer() local integer ArrayIndex = GetCSData(T) //local real X //local real Y //local real Offset local unit Dummy = GetArrayUnit(ArrayIndex, 3) // ... only comments here JASS:function Fireball_Callback takes nothing returns nothing local timer T = GetExpiredTimer() local integer ArrayIndex = GetCSData(T) //local real X //local real Y //local real Offset //local unit Dummy = GetArrayUnit(ArrayIndex, 3) // ... only comments here |
| 10-17-2007, 01:51 AM | #12 |
Dumb. It turns out I accidentally deleted the trigger that initialized CSCache at some point or another. Stupidest mistake I've made in a long time. |
| 10-17-2007, 01:23 PM | #13 | |
Quote:
|
