Exit
  • Global community
    • Language:
      • Deutsch
      • English
      • Español
      • Français
      • Português
  • 日本語コミュニティ
  • 한국 커뮤니티
0

setInterval Question

Guest
Jul 20, 2007 Jul 20, 2007
I am not having the best of luck understanding the setInterval command and am a designer more than a developer so some of this ActionScript gets me confused so forgive me if the question seems kind of lame.

How would I or can I use the setInterval to make a movie play for a certain period of time? Generally I would just create a layer that extends out as long as I want it to play the movie for and place stop(); at the end. I was hoping there was an easier or more precise way of doing this. Mainly because the fla I am creating exists on 1 frame and is all driven by action script to make clips appear at set points for a set time. I was just looking for a way to simplify the length of the whole movie action.

I hope that made sense to someone
TOPICS
ActionScript
653
Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
LEGEND ,
Jul 20, 2007 Jul 20, 2007
Hi shurleynova,

setInterval runs on the system timer (loosely) and is unreliable, not
to mention overkill for controlling animation. A simpler solution is an
onEnterFrame loop that simply counts the number of elapsed frames and
does stuff based on that value.

First of all, what is the frame rate of your movie? At 30fps, for
example, the onEnterFrame function gets called 30 times every second so
use this in your calculations. Let's say you have a clip on the _root
layer with the instance name "controlMe" and you want to stop it after 3
seconds. Your onEnterFrame handler (on some other clip) would look like
this:

var counter=0;
function onEnterFrame() {
counter++;
//90 frames/30 frames per second=3 seconds
if (counter>=90) {
_root.controMe.stop();
this.onEnterFrame=undefined;
}
}

This runs just once and is very rudimentary but hopefully it'll give you
some ideas on how to proceed.

Regards,
Patrick


shurleynova wrote:
> I am not having the best of luck understanding the setInterval command and am a
> designer more than a developer so some of this ActionScript gets me confused so
> forgive me if the question seems kind of lame.
>
> How would I or can I use the setInterval to make a movie play for a certain
> period of time? Generally I would just create a layer that extends out as long
> as I want it to play the movie for and place stop(); at the end. I was hoping
> there was an easier or more precise way of doing this. Mainly because the fla
> I am creating exists on 1 frame and is all driven by action script to make
> clips appear at set points for a set time. I was just looking for a way to
> simplify the length of the whole movie action.
>
> I hope that made sense to someone
>

--
http://www.baynewmedia.com
Faster, easier, better...ActionScript development taken to new heights.
Download the BNMAPI today. You'll wonder how you ever did without it!
Available for ActionScript 2.0/3.0.
Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
LEGEND ,
Jul 21, 2007 Jul 21, 2007
I have to agree and disagree with what Patrick B has said here.

Yes setInterval is not an exact interval and will vary based on many things. But then again so is the frame rate. You cannot count on 90 frame taking exactly 3 seconds either.

The only thing that is spot on with the time is getTimer() it gives you the milliseconds since the flash file started running. But unfortunately you can only use it as an after-the-fact kind of test. So when you start you could set a startTime and then periodically test to see if enough time has passed since the startTime.

So then the question becomes how do you check from time to time to see if enough time has gone by? The main choices are setInterval and onEnterFrame. I would suggest that it is the other way around from Patrick B's suggestion: onEnterFrame is overkill whereas setInterval is just the right amount of kill. :)

onEnterFrame will check 30 times per second. But do you really need to stop it within 1/30 of a second? Sometimes the answer may be yes, in which case that is fine and onEnterFrame would be a good choice. However for most purposes 1/10 or even 1/4 of a second might be just fine. So in that case you can use setInterval to check at some interval that is small enough for accuracy, but big enough that the code won't have to run sooo many times. If this is something that is the only thing running then the drain on the processor really doesn't matter, but if you get lots of onEnterFrames going…

Anyway, here is probably how I would do it:

var myDuration:Number=3000
var startTime:Number=getTimer();

clearInterval(endCheckID)

endCheckID=setInterval(endCheck,100);

function endCheck(){
var elapsedTime:Number=getTimer()-startTime;
if(elapsedTime>=myDuration){
clearInterval(endCheckID);
myMovie.stop() \\ or whatever it is that you need
trace("Time expired at "+elapsedTime);
}
}

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Guru ,
Jul 21, 2007 Jul 21, 2007
Hi Rothrock, I would also be inclined to use a timer over onEnterFrame as a general approach, unless there was an existing onEnterFrame requirement that I could tag it on to.

You're using getTimer to get an accurate check, but because its using setInterval (which, along with onEnterFrame you point out as being inaccurate) it will still only get close (as you also pointed out).
If the point is to capture the amount of time taken then getTimer makes sense... e.g. your time expired trace ... but I would be inclined to use setTimeout over setInterval for a time-based (and admittedly non-accurate!) one-off timer like this. I'd set it for 3000 millisecs and just accept that whatever elapsed time had happened was as close as it could get. That would avoid the additional executions of endCheck for all the times we know its not necessary (even at 100ms intervals).

And I guess I say that from a theory point of view because in practice - if I'm totally honest with myself - while I do think generally ponder the most efficient way to do things... often unless I'm forced to optimise everything because what I'm doing is overheating my CPU I could very well end up just picking an approach at random.

var startTime:Number=getTimer();
clearTimeout(endCheckID)

endCheckID=setTimeout(endCheck,3000);

function endCheck(){
var elapsedTime:Number=getTimer()-startTime;
clearTimeout(endCheckID);
myMovie.stop() \\ or whatever it is that you need
trace("Time expired at "+elapsedTime);

}
Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
LEGEND ,
Jul 22, 2007 Jul 22, 2007
Oh, I would probably use setTimeout myself, I haven't done much to test the accuracy of it so if that is important then I still don't know. My initial test seems to indicate that setTimeout is more accurate than setInterval.

BTW, you don't need to clear the setTimeout in the function that it calls, I suppose if there is a risk that the function would get called by some other mechanism and you didn't want to have it called by the setTimeout. But that is the beauty of the setTimeout, it cancels itself when it executes.
Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Guru ,
Jul 22, 2007 Jul 22, 2007
@Rothrock: I didn't understand why, but after a quick search it seems like the reason why repeating timers are less accurate is explained well here (as2 & as3). They are also frame rate dependent based on my tests (setInterval is anyway).

Have a quick read through this.

http://www.bit-101.com/blog/?p=910

@ shurleynova - aplogies for hijacking your thread somewhat - although its still relevant its gone a bit theoretical, sorry. Please let us know if you need more help with what you're doing or if you have more questions.

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
LEGEND ,
Jul 22, 2007 Jul 22, 2007
Yes setInterval is frame rate dependent and onEnterFrame, setTimeout and, setInterval are all inaccurate, but as far as I know, getTimer() is always accurate.

That is why I often use a combination of setInterval and getTimer(). If the interval is small compared to the desired elapsed time, then it doesn't matter if the setInterval is off by some percentage and adds up the repeated error.

The final paragraph there is advocating the idea of using whatever repeating mechanism, but then using the getTimer() to know exactly how long has elapsed and to animated to the points of time.
Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
LEGEND ,
Jul 23, 2007 Jul 23, 2007
LATEST
I have to agree and disagree with this. True, onEnterFrame isn't
completely reliable but it does tend to get hit closer to the real
framerate. An internal running at 100ms is going to be pretty imprecise
unless you have nothing running. Like you said, it depends on the
complexity of the app. But I've had timers that have fired off every 3
seconds and were set to 10ms. The onEnterFrame handlers were much more
exact in comparison. I had run these comparisons many times: when
writing a music sequencer (which is very touchy when it comes to
timing), casino games (which needed to be greatly optimized), and my
encryption engine which had to loop through megabytes of data to get the
job done. Intervals were great when the only code running was the
interval....that thing flew. But once more stuff was added to the stage,
onEnterFrame reliability stayed about the same and intervals chugged.

But that being said, checking for elapsed time *is* much better than
counting frames, that is absolutely true. I would take Rothrock's advice
on this one and forget my previous post. Regarding onEnterFrame/timer,
run the tests yourself. I can't say with 100% certainty that interval
won't work, just that it's not very scalable.

Patrick

Rothrock wrote:
> I have to agree and disagree with what Patrick B has said here.
>
> Yes setInterval is not an exact interval and will vary based on many things.
> But then again so is the frame rate. You cannot count on 90 frame taking
> exactly 3 seconds either.
>
> The only thing that is spot on with the time is getTimer() it gives you the
> milliseconds since the flash file started running. But unfortunately you can
> only use it as an after-the-fact kind of test. So when you start you could set
> a startTime and then periodically test to see if enough time has passed since
> the startTime.
>
> So then the question becomes how do you check from time to time to see if
> enough time has gone by? The main choices are setInterval and onEnterFrame. I
> would suggest that it is the other way around from Patrick B's suggestion:
> onEnterFrame is overkill whereas setInterval is just the right amount of kill.
> :)
>
> onEnterFrame will check 30 times per second. But do you really need to stop it
> within 1/30 of a second? Sometimes the answer may be yes, in which case that is
> fine and onEnterFrame would be a good choice. However for most purposes 1/10 or
> even 1/4 of a second might be just fine. So in that case you can use
> setInterval to check at some interval that is small enough for accuracy, but
> big enough that the code won't have to run sooo many times. If this is
> something that is the only thing running then the drain on the processor really
> doesn't matter, but if you get lots of onEnterFrames going?
>
> Anyway, here is probably how I would do it:
>
> var myDuration:Number=3000
> var startTime:Number=getTimer();
>
> clearInterval(endCheckID)
>
> endCheckID=setInterval(endCheck,100);
>
> function endCheck(){
> var elapsedTime:Number=getTimer()-startTime;
> if(elapsedTime>=myDuration){
> clearInterval(endCheckID);
> myMovie.stop() \\ or whatever it is that you need
> trace("Time expired at "+elapsedTime);
> }
> }
>
>
>

--
http://www.baynewmedia.com
Faster, easier, better...ActionScript development taken to new heights.
Download the BNMAPI today. You'll wonder how you ever did without it!
Available for ActionScript 2.0/3.0.
Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines