Creating Timers in Flash, Part 1
Simple and straightforward to start
If you do any sort of ActionScripting in Flash at all, eventually you're going to come across a situation where you'll need some kind of timer. Whatever the need—a countdown clock, a simple pause before directing some sort of action, or even a timeout feature for a kiosk application—there are a bunch of ways to do it, so let's start with the two simplest.
Method 1: ol' (not-so) reliable frame-based timers
I'm guessing there are some of you out there who may be a tad shy about ActionScript. As one of those who formerly had the bejeezus scared out of them at the mere thought of writing a script, I do sympathize. However, the simplest (read: not so much ActionScript) way to make a timer is also the least reliable one to accurately measure time from within Flash. Nonetheless, it's still good in a pinch if you don't want to get your hands messy.
Now, in all of these methods, we're going to create a timer that counts to five seconds and then calls a trace event confirming that five seconds have indeed elapsed. Not super-exciting, but enough to illustrate the core concept without a lot of extraneous garbage getting in the way. To start, fire up Flash, create a new movie, head to the Properties panel, and make sure the frame rate is set to 30 fps (fig. 1).

Figure 1
With that out of the way, let's set up our frames in the Timeline:
- Create a new layer (Insert:Timeline:Layer)
- Change the name of Layer 1 (the bottom one) to "labels" and Layer 2 (the top one) to "actions"
- In the "labels" layer, create a new keyframe at frame 2 by clicking once on frame 2 and hitting the F6 key
- With frame 2 in the "labels" layer still selected, go to the Properties panel and enter "loop" in the Frame Label field
- (optional) Click once on frame 31 in the "labels" layer and hit the F5 key to stretch out the visible portion of the Timeline (this will make the entire "loop" label visible in the Timeline)
- In the "actions" layer, click once on frame 31 to select it, and then hit the F6 key to create a new keyframe
Once all that is done, your timeline should look something like Figure 2:

Figure 2
What we've done is nothing more than create one second's worth of frames and a loop point to jump back to. Now, let's add the minimal ActionScript needed to make this work. Click once on frame 1 of the "actions" layer, head to the Actions panel (Window:Actions), and enter the following script:
var interval:Number = 5; var currentTime:Number = 0;
Not much going on there; I'm just defining a couple of variables. The first, interval, will be used to define what number (in seconds) I'm counting to (in this case, 5). Now, I've entered in a whole number here, but you can easily use fractional values (in decimal points, e.g., 2.5) if you like. The second variable, currentTime, exists to set the clock to zero right off the bat. Otherwise, there would be no basis for comparison later. Now, let's add the other script. Click on the keyframe you made at frame 31 of the "actions" layer and enter the following into the Actions panel:
1 2 3 4 5 6 7 | currentTime++; if (currentTime<interval ) { gotoAndPlay("loop"); } else { stop(); trace(interval+" seconds have elapsed"); } |
I've added line numbers this time to make the forthcoming explanation easier, so make sure to get rid of those if you're doing a simple copy and paste into the Actions panel. Now go ahead and test your movie (Control:Test Movie). A blank screen will appear, and then approximately five seconds later, your Output window should display the following:

Figure 3
Score! Now, just in case that mishmash of code I just told you to write means little, if anything, here's the line-by-line analysis of what I did:
Line 1: currentTime++;
The ++ is the quickest way of adding one to any variable. Since I set currentTime to 0 in the first frame, the first time Flash runs through this frame currentTime will be set to 1, the second time to 2, and so on. And since the frame rate is 30 fps, and since I created 30 blank frames between the loop point and this script, adding one to the currentTime variable is the equivalent of counting off seconds.
Line 2: if (currentTime<interval) {
I've got to check how currentTime compares to the interval I originally set, so an if...then statement is needed to run the comparison. On this first line, I'm simply asking if currentTime is less than interval.
Line 3: gotoAndPlay("loop");
This is the code that runs if currentTime is, in fact, less than interval. I need to have the loop run, so I'm sending the play head back to the loop point at frame 2. As an aside, why is the loop point located at frame 2 anyway? Well, if it's at frame 1, interval would reset to zero (because that's where we put that code), and the counter would never get past 1. Hence, the label is at frame 2.
Line 4: } else {
This line is a continuation of line 2, as the else statement will run the code once currentTime is no longer less than interval. To close out the if...then statement we started back in line 2, we also need a closing curly brace on line 7.
Line 5: stop;
Remember, lines 5 and 6 are the code that runs once currentTime is no longer less than interval, so the first order of business is to stop the play head from advancing or looping bak to the loop point. A simple stop() will suffice here.
Line 6: trace(interval+" seconds have elapsed");
The payoff. Sorry it's not more exciting, but a simple trace will have to do. (In my defense, I did dress it up a bit by placing the interval variable into the trace call.) It's been five seconds, the loop has been broken, and here's the code that executes once all is said and done.
Now, I mentioned that this method is rather unreliable. How, you might ask? Simple. Frame-based timers are defined by the frame rate you specify in your overall Flash movie, but in reality, not every machine will play back movies at the rate you want. And since a frame-based timer goes through every frame regardless of the speed of hte host machine, a five second timer may play back in five seconds on one computer but may take eight seconds on another (or even longer, depending on the complexity of the movie and what is being rendered in each frame). There's also the somewhat messy issue of having to adjust the number of blank frames in the middle if you ever have to change the overall frame rate of your movie. So while the frame-based method is one of the more hassle-free ways of creating a timer, if you want any semblance of accuracy you'll be better off using one of the other methods I'll be getting to right about now.
Method 2: getTimer()
Did you know that Flash already times every movie you've ever made? OK, that may be a bit of a stretch, since I'm not entirely sure which version of Flash the getTimer() function originally showed up in, but my point remains the same: the clock is already running, so why not make use of it?
In a nutshell, here's what's going on: at the start of any Flash movie, the getTimer() counter starts anew at zero. As long as your movie remains playing (or running, or active, or whatever), Flash dutifully ticks off milliseconds. So, if you use the getTimer() function at any point in your movie, Flash will return a number (which will fall somewhere between large and ludicrously large) that represents how many milliseconds have elapsed since the start of the movie. Therefore, by asking Flash what the getTimer() number is at various intervals, you can set up comparisons and determine how much time has passed. And since getTimer() works independently of both the desired and actual frame rate your movie is playing at (for the most part, as I'll explain below), it's a much more accurate way to measure time. Anyway, enough background; let's see getTimer() in action.
The easiest thing to do is to set up a loop that checks how many milliseconds have elapsed, and then run an if...then statement to see if your predefined interval has been passed or not. So fire up Flash, create a new movie, click once in Layer 1, open the Actions panel (Window:Actions), and enter in the following code (again, ignoring the line numbers I've put in there):
1 2 3 4 5 6 7 8 9 | var interval:Number = 5; var startTime:Number = getTimer(); this.onEnterFrame = function() { var currentTime:Number = getTimer(); if (currentTime>=startTime+(interval*1000)) { delete this.onEnterFrame; trace(interval+" seconds have elapsed"); } }; |
Let's test the movie (Control:Test Movie). Once again, a blank screen will appear, and once again, five seconds later, your output window should look like this:

Figure 3, again
Woo-freaking-hoo. Let's go through the code line-by-line:
Line 1: var interval:Number = 5;
This should look familiar, as it's the same variable I used in the frame-based method, so I'm guessing no further explanation is needed here.
Line 2: var startTime:Number = getTimer();
Yet another variable, this time named startTime, which establishes the baseline time by asking Flash, in effect, "what time is it right now?"
Line 3: this.onEnterFrame = function() {
As an aside, calling an onEnterFrame function is one of the more useful things you can learn in Flash. Basically, it's a no-fuss, no-muss, and (most importantly) frameless way of setting up a simple loop. This loop will call the code contained within it x amount of times per second, with x representing the overall frame rate of your movie. So, if you have a movie that's running at 15 fps, the code will run 15 times every second as well (again, in theory—specified and actual framerates, as we've discussed, can often differ wildly). This particular loop is checking to see if a particular condition has been met (the code for which shows up in line 5), but for now, just know that this line simply establishes the loop. Of course, you have to close any function you call with another curly brace, so I've done that in line 9.
Line 4: var currentTime:Number = getTimer();
Now that I'm within the loop I just defined, I'm dealing with code that gets called once per frame. Seems like a perfect place to continually ask what time it is now, and store that number in a variable. So allow me to introduce the variable known as currentTime.
Line 5: if (currentTime>=startTime+(interval*1000)) {
This is where the rubber meets the road, so to speak. In this line, I'm checking (again, via way of an if...then statement) whether the currentTime variable is larger or equal than the startTime variable plus my interval variable times 1000. In case that last sentence presented you with a decisive "eh?" moment, let me put it another way—basically, I'm asking Flash if currentTime is larger than startTime plus five seconds (or five thousand milliseconds, to be more precise). If the answer is no, the loop keeps running, but if the answer is yes, we get dumped down to...
Line 6: delete this.onEnterFrame;
Since the condition has been met, the first thing we have to do before any more code gets called is to stop the loop from repeating any further. Now, if you're familiar with ActionScript already, then you know that to "bust out" of a for or while loop you would use the break command. In the case of an onEnterFrame loop, you actually have to delete the function containing it, hence line 6.
Line 7: trace(interval+" seconds have elapsed");
This line may also look familiar, so I'll not get into how exciting it is any more than I already have.
That's it. Much cleaner than the frame-based method, if you're willing to put up with a tad more code. But now, the caveat to the getTimer() method. I mentioned earlier that this method is more accurate than the frame-based method, but only up to a point. You see, slower systems are hellbent on spoiling the party again, but not nearly as much as the havoc they wreak using the frame-based method. Since the onEnterFrame loop repeats itself at the frame rate you've specified in the Properties panel, there's the potential for at least a slight lag over the desired interval, as you're still at the mercy of how fast the host system is actually playing back the movie. Now, unless you've got your frame rate set to 1 or 2 fps, this lag isn't likely to cause a huge issue, as a single frame probably isn't going to present any appreciable delay on most systems. However, the potential is there, however small, for inaccuracy, so be warned.
With me so far? Good. We've gone over two methods of adding a timer to your Flash movies, but we're just getting warmed up. Next time we'll go over two more, both a bit more precise than these, including one method that gets a little sneaky with a class that wasn't really designed to keep time. So stay tuned, amigos!
Got Feedback? to send an email. I'll do my best to answer. Really.
