Article
The Flash Anthology: Cool Effects & Practical ActionScript - Chapter 3: Animation Effects
Raindrops Keep Falling on My Head
One of the quickest ways to create an animated effect is to take an animation and duplicate it multiple times on the stage. The success of this technique depends on the original animation being cool enough to warrant this kind of replication. In this example, we'll create a quick rainfall effect by duplicating a movie clip several times on the canvas. Sound simple? Let's look at how it's done.
To skip the details and jump straight into the effect, locate the Duplication.fla file in the code archive.
Figure 3.7. This simple raindrop effect is created using duplication.
Setting the Scene
First, we need to create the movie clip we'll reference in our control code.
- Create a new movie that's 350 pixels wide and 400 pixels high. Increase the frame rate to 18 fps. Create three layers and name them Actions, Raindrops and Background.
- Create a graphic symbol named Raindrop and use the drawing tools to draw a falling drop of water.
- Create a new movie clip symbol, also named
Raindrop. Make sure it's open for editing, then drag an instance of theRaindropgraphic from the Library Panel onto the stage. Name the instanceRaindrop. Position it at (0, 0) within the clip. - Create a new keyframe within the movie clip at frame 40. Select frame 1, right-click, and select Motion Tween. Shift back to frame 40 and move the raindrop graphic to the bottom of the stage—about (0, 390).
- In the Library Panel, duplicate the
Raindropmovie clip you created, and name this duplicateRaindropSlow. Edit theRaindropSlowmovie clip, grab the end keyframe in the timeline, and drag it out to frame 80. This will produce a slower animation. - Drag one instance each of the
RaindropandRaindropSlowmovie clips into the Raindrops layer. Name themraindropandraindropSlow, respectively. - Move the two clips so they sit near the top of the stage, but outside its left edge. I placed them at (-45, 10) and (-30, 10). If you can't see past the edge of the stage, you may have to choose View > Work Area first. The goal here is to have the drops as part of the scene, but not visible on stage.
- Select the Background layer and add some rolling hills and a storm cloud to it using the drawing tools. To finish, lock this layer.
- Navigate to the first frame of the Actions layer within the timeline and add the following code:
- Save your movie and preview it within Flash. You'll notice that, even though the raindrops appear to be randomly spaced along the x and y axes, they fall in a straight line. It certainly doesn't rain like this in my neighborhood! We can quickly remedy the situation by introducing more random elements to the code.
- Replace the code in the Actions Panel with the following:
- Save and preview your movie. You'll notice that the raindrops now fall much more naturally than they did before.
- Modify the code in the Actions layer as follows:
- Add the following code below the existing code in the first frame of the Actions layer:
- Our for loop counts to 100, instead of 50, so we'll create twice as many duplicates.
- We create duplicates of the raindropSlow clip this time.
- We use a new counter variable for this loop (
j), and add it to the count at the end of our previous loop (i) when setting the stacking order of the new duplicates. This ensures that all the drops get their own place in the stacking order. (Otherwise, the slow raindrops would replace the fast raindrops on the stage!) - We set alpha values between zero and 25% for our slow raindrops, to make them appear further away.
- Because
RaindropSlowis 80 frames in length instead of forty, we have adjusted the value we pass torandomon the last line.
We will use these two Raindrop clips to create a subtle effect a little later. Now let's assemble the main scene:
Adding the Control Code
All the graphics are created and in place on the stage; we just need to duplicate them a few times. If you were to preview the movie now, you'd see two single raindrops, one falling faster than the other, off the side of the stage. I think we'd better spice things up with a little ActionScript.
Example 3.14. Duplication.fla Actions : 1
for (i = 0; i < 50; i++)
{
var newDrop = raindrop.duplicateMovieClip ("raindrop" + i,
i);
newDrop._x = random (350);
newDrop._y = random (20);
}
Here, we use the duplicateMovieClip method to create 50 copies of the raindrop clip that resides on the root of the timeline. If you want more raindrops, you can change the number 50 in the for loop to whatever you like. However, beware of the increased CPU load that comes with large numbers of movie clips.
As with the attachMovie method we saw earlier in this chapter, duplicateMovieClip requires parameters that set the instance name for the new movie clip (in this case, raindrop with a number appended to it) and its position in the stacking order.
After we duplicate the movie clip, we assign each duplicate a random horizontal location between zero and the right-hand side of the stage (x=350). We also shift each instance of the clip vertically using a random value between zero and twenty, to make it look as if the raindrops are falling out of different parts of the cloud.
Example 3.15. Duplication.fla Actions : 1 (excerpt)
for (i = 0; i < 50; i++)
{
var newDrop = raindrop.duplicateMovieClip ("raindrop" + i,
i);
newDrop._x = random (350);
newDrop._y = random (20);
newDrop.gotoAndPlay(random(40) + 1);
}
Notice the extra line of code within this block, shown in bold. This little snippet may look insignificant, but it brings the animation to life. Using the gotoAndPlay method of each new clip, the animation is advanced to a random frame between 1 and 40 (remember, random(40) generates values from 0 to 39) and then played from that point.
Although this animation is simple to accomplish, it's effective in its execution. There are numerous ways to extend this example and make it more interesting. Let's take a little time to examine them now.
Add Some Randomness
To make this effect more engaging, we can modify the horizontal scale and alpha values of each drop of rain as it's created:
Example 3.16. Duplication.fla Actions : 1 (excerpt)
for (i = 0; i < 50; i++)
{
var newDrop = raindrop.duplicateMovieClip ("raindrop" + i,
i);
newDrop._x = random (350);
newDrop._y = random (20);
newDrop._xscale = random (100);
newDrop._alpha = random (50);
newDrop.gotoAndPlay (random (40) + 1);
}
Save and preview the movie. You'll see raindrops with differing widths—from little, skinny drops to big, fat ones. Each drop's opacity value is also picked at random between zero and 50%.
And the Heavens Opened…
Remember the movie clip we created earlier that was slower than the original raindrop? We have a use for it now! Not all raindrops fall at the same speed, and we can use that clip to make our animation more realistic. Let's add some code that will include the second raindrop movie clip in our animation.
To edit this effect for your own needs, locate Duplication_Modification.fla in the code archive.
Example 3.17. Duplication_Modification.fla Actions : 1 (excerpt)
for (j = i; j < i + 100; j++)
{
var newDrop = raindropSlow.duplicateMovieClip (
"raindropSlow" + j, j);
newDrop._x = random (350);
newDrop._y = random (20);
newDrop._xscale = random (100);
newDrop._alpha = random (25);
newDrop.gotoAndPlay (random (80) + 1);
}
This works just like the previous block of code: the for loop creates a number of duplicates of the movie clip, then uses the random function to set values for various properties of the duplicates. Here are the differences in this second block of code:
That's it for the raindrops! Now let's see if we can further enhance the scene with some more complicated effects.
Creating a Parallax Cloud Structure
Like raindrops, the movement of clouds is extremely random—each cloud moves at a different speed. With some clever math and a few simple cloud movie clips, you can create an interesting effect that adds depth to the scene (see Figure 3.8).
Figure 3.8. By choosing the right random values, you can create this smooth cloud movement.
We'll start where we left the example in the previous section. To jump straight to the finished product, locate in the code archive.
- Create two new movie clip symbols, named
LargeCloudandSmallCloud, and place an image that resembles a cloud in each. Make the cloud in theSmallCloudclip about half the size of its counterpart inLargeCloud. - Create above the RainDrops layer a new layer called Clouds, and drag instances of the two new movie clips into this layer. Name them according to their master movie clips (
largeCloudandsmallCloud, respectively). Again, place them off the side of the stage. - Add the following code to frame 1 of the Actions layer, beneath the existing code:
- Save the movie and preview it. To see how the effect looks without the objects running off the stage, export the movie to a SWF file and double-click it to view the movie in Flash Player.
We'll use these two clouds in a manner similar to our work with the two raindrops, duplicating them with ActionScript code to create a random scene. To add a feeling of depth to our cloud structure, we'll create a parallax effect. This involves making faraway objects (our small clouds) move more slowly than nearby objects (our large clouds), which creates a sense of perspective and depth.
Example 3.18. Duplication_Modification_Clouds.fla Actions : 1 (excerpt)
for (i = j; i < j + 60; i++)
{
var newCloud = smallCloud.duplicateMovieClip (
"smallCloud" + i, i);
newCloud._alpha = random (100);
newCloud._x = random (450) - 100;
newCloud._y = random (60) + 10;
newCloud.step = random(4);
newCloud.onEnterFrame = cloudStep;
}
for (j = i; j < i + 30; j++)
{
var newCloud = largeCloud.duplicateMovieClip (
"largeCloud" + j, j);
newCloud._alpha = random (100);
newCloud._x = random (450) - 100;
newCloud._y = random (40) - 20;
newCloud.step = random(4) + 2;
newCloud.onEnterFrame = cloudStep;
}
function cloudStep()
{
if (this._x >= 350) this._x = -100;
this._x += this.step;
}
As you can probably figure out by examining the code, we're creating 60 duplicates of the small cloud and thirty duplicates of the large cloud. Our loops continue to use the i and j variables so that the clouds are added to the top of the stacking order and the raindrops appear to come from behind or within them.
For each cloud we assign a random opacity between 0% and 99%, and a random horizontal position between -100 and 350. Remember that this is the position of the left edge of the cloud, so we need those negative values to allow for clouds partially obscured by the left edge of the stage.
To develop the sense of depth even further, and to ensure our small clouds aren't obscured by the large clouds, we make our small clouds sit lower on the stage (with random vertical positions from 10 to 69) than our large clouds (from -20 to 19). With the small clouds closer to the horizon, they will seem further away.
Now for the crux of our parallax effect: the motion of the clouds. All of our clouds will move across the stage from left to right. Each cloud will have its own randomly assigned step size, which indicates the number of pixels per frame it should move. For the small clouds, we generate step sizes from zero to three pixels, while the large clouds will get step sizes from two to five pixels. We store each cloud's step size into a variable called step within the cloud's movie clip (newCloud.step).
Finally, we add an onEnterFrame event handler for each of the clouds, all of which will use a common function called cloudStep. This uses the clip's step size to move it to the right until it reaches a horizontal position of 350 pixels, at which point it's sent back to -100.
That's a pretty cool effect! All the clouds move at different speeds, so the effect doesn't look "manufactured." But there is still more we can add to this scene…