HomeUser Control Panel (unavailable in archive)ForumsTutorialsArt GalleryResourcesMaps

help with waits

09-10-2004, 02:42 AM#1
curi
hi

I'm writing code to do repeated special effects (below). all of it is working ... except the waits. if i comment them out it works (but the repeated version does them all at once, and there isn't cleanup).

I guess the problem is waits only work in triggers, not in functions, or something like that? Could someone explain it to me? Is there a workaround?

PS does anyone know where i could find some code to copy that will take path strings and double all the backslashes, so they don't have to be typed in funny?

Thanks,

Code:
// functions to create and cleanup special effects in patterns, with the option of having them repeated

// 3 examples: (set udg_loc to something to use)

//call sfxr("random", 300, 60, .05, udg_loc, "Objects\\Spawnmodels\\Human\\FragmentationShards\\FragBoomSpawn.mdl")

//call sfxr("random", 400, 15, .2, udg_loc, "Abilities\\Spells\\Demon\\ReviveDemon\\ReviveDemon.mdx")

//call sfx("one", 400, udg_loc, "Abilities\\Spells\\Demon\\ReviveDemon\\ReviveDemon.mdx")


function sfx takes string pattern, real distance, location mytarget, string sfxpath returns nothing
   
local real ndistance = distance * -1
local effect e = null
local effect e2 = null
local effect e3 = null
local effect e4 = null
local real lx = GetLocationX(mytarget)
local real ly = GetLocationY(mytarget)
local integer p = GetRandomInt(1,5)
local real angle = GetRandomReal(0, 360)

if( pattern == "random" ) then
// pick a random pattern to do

	if( p == 1 ) then
		set pattern = "one"
	elseif( p == 2 ) then
		set pattern = "diamond"
	elseif( p == 3 ) then
		set pattern = "square"
	elseif( p == 4 ) then
		set pattern = "randomsquare"
	elseif( p == 5 ) then
		set pattern = "randomcircle"
	endif

endif

if( pattern == "one" ) then
// make sfx on mytarget
	set e = AddSpecialEffectLoc(sfxpath, mytarget)

    	
elseif( pattern =="diamond" ) then
// make sfx north, south, east, west of mytarget
	set e = AddSpecialEffectLoc(sfxpath, Location(lx + 0, ly + distance))
	set e2 = AddSpecialEffectLoc(sfxpath, Location(lx + 0, ly + ndistance))
	set e3 = AddSpecialEffectLoc(sfxpath, Location(lx + distance, ly + 0))
	set e4 = AddSpecialEffectLoc(sfxpath, Location(lx + ndistance, ly + 0))


elseif( pattern == "square" ) then
// make sfx ne, se, nw, sw of mytarget

	set e = AddSpecialEffectLoc(sfxpath, Location(lx + distance, ly + distance))
	set e2 = AddSpecialEffectLoc(sfxpath, Location(lx + ndistance, ly + ndistance))
	set e3 = AddSpecialEffectLoc(sfxpath, Location(lx + distance, ly + ndistance))
	set e4 = AddSpecialEffectLoc(sfxpath, Location(lx + ndistance, ly + distance))


elseif( pattern == "randomsquare" ) then
// make sfx randomly in square

	set e = AddSpecialEffectLoc(sfxpath, Location(lx + GetRandomReal(ndistance, distance), ly + GetRandomReal(ndistance, distance)))
	
elseif( pattern == "randomcircle" ) then
// make sfx randomly in circle

	set e = AddSpecialEffectLoc(sfxpath, Location(lx + distance * Cos(angle * bj_DEGTORAD), ly + distance * Sin(angle * bj_DEGTORAD)))
	
endif

call TriggerSleepAction( 120 )
// Wait two minutes, so the effects aren't needed anymore.  Don't use this with an effect you want to be permanent or longterm.  Make number bigger if you want.

call DestroyEffect(e)
set e = null
call DestroyEffect(e2)
set e2 = null
call DestroyEffect(e3)
set e3 = null
call DestroyEffect(e4)
set e4 = null
endfunction

function sfxr takes string pattern, real distance, integer times, real delay, location mytarget, string sfxpath returns nothing
if( times > 0 ) then
	call sfx ( pattern, distance, mytarget, sfxpath )
	call TriggerSleepAction( delay )
	call sfxr ( pattern, distance, times -1, delay, mytarget, sfxpath )
endif
endfunction
09-10-2004, 04:51 AM#2
Alfryd
call sfxr("random", 400, 15, .2, udg_loc, "Abilities\\Spells\\Demon\\ReviveDemon\\ReviveDemon .mdx")

Well, there's a potential problem there. TriggerSleepActions have minimum duration of 0.25 seconds. But there's probably something deeper.

Quote:
...and there isn't cleanup).
Strange. I don't know why the effects aren't being removed if you just commented out the wait. However,
call TriggerSleepAction( 120 )
Is probably interfering with the delays between calls to
call sfx (... ...)
Because they all belong to the same trigger. Different functions, same trigger. Have you tried creating a new trigger for each call to sfx, and removing those afterwards? You'd need a couple of globals and maybe relay functions to pass data, but it worked for me.

call DestroyEffect(e2)
Is it possible that calling DestroyEffect on a null variable could cause the function to hang? That might account for the lack of cleanup, though I can't understand why further calls to sfxr are unaffected.
09-10-2004, 10:11 AM#3
Cubasis
The function's code is in the same thread as the calling function/trigger, thus, when it comes to a wait, the whole thread waits the duration before continuing. I reccomend using the TimedSFX functions in the jass vault for easy fix. (http://www.wc3sear.ch/index.php?p=JASS&ID=100&sid= and http://www.wc3sear.ch/index.php?p=JASS&ID=99&sid= )

There is no problem with passing null to native functions. They know how to handle it. However, if you ever even tauch a uninitiated variable, the thread will crash. But obviously you allready initiate them all too null/value.

There is no problem calling Wait with less than 0.25, however, it will wait for 0.25 even if you use 0.0001.

However, I'm not really seeing why there is no cleanup in it, as it all looks fine to me. However, you might wanna fix some of those location memory leaks. Since you're allready working with X and Y. You might just want to use this function instead:
native AddSpecialEffect takes string modelName, real x, real y returns effect

~Cubasis
09-10-2004, 03:52 PM#4
Alfryd
Why don't you add a text message at the end of the function's cleanup, just to see if it gets that far?
09-10-2004, 05:25 PM#5
curi
oh, the reason there was no cleanup *with no waits* is that it would have been run immediately, so you'd never see anything, so I commented it out. sorry to confuse you.

The timed sfx thing was really helpful; I've copied the workaround of making a new trigger. Also thanks for mentioning the .25 wait minimum -- when I tested something with a .02 wait it was taking longer to finish than expected and I wasn't sure what was going on.