Hack 8 Video Color Effects 
Simulate a video transition using Flash color
effects.
This hack alters video using the
Color class to create a unique type of color
transition. This is not an obvious technique and not one ordinarily
applied to video transitions, but that's the whole
point of a hack—to explore the nonobvious.
The Boy Can't Dance
You can always tell when videographers have to create a pop music
video with a singer who can't move to the beat in a
hip sort of way. In such a case, the videographer moves the camera or
adds lots of video transitions and effects that are in sync with the
music. That way, you get onscreen movement in time with the beat even
if the band is standing hopelessly still and nodding their heads in a
70s prog-rock kinda way.
Flash video poses a similar challenge: video is bandwidth-heavy, and
to keep compression ratios as high as possible, we have to create
sequences in which not much changes between frames. Most codecs,
including the Sorenson codec that Flash uses, perform both spatial
and temporal compression. Spatial compression is performed by
looking for similarities within the frame (for example, a solid
colored background compresses very easily). Temporal compression is
achieved by looking at consecutive frames and including only
deltas
(differences) between the frames. It therefore makes sense to reduce
large-scale movement in our videos, allowing the difference
frames, which contain only the deltas between
frames, to be as bandwidth-light as possible. (For want of a better
analogy, difference frames are akin to the tween frames used in
animation within Flash's timeline. Video, like
animation, has keyframes as well.) Video keyframes are used to maintain
image quality and to handle situations in which the differences
between frames are so large as to make difference frames inefficient.
Therefore, more changes per frame requires either larger difference
frames or more keyframes.
This leaves us stuck in the same situation as the pop music video; we
can't have too much big movement in our visuals
without a massive increase in the download size of the video.
The trick, as in pop music videos, is to add movement or effects
somewhere else. We apply the effects programmatically at runtime (on
the client side) so you don't affect the video
compression (i.e., the bandwidth required) by adding big interframe
discontinuities.
 |
The key to saving bandwidth without boring the viewer is to
programmatically introduce variations that don't
exist in the source video.
|
|
For example, you can also use runtime video effects to hide the fact
that your video is looping, another popular way
of conserving bandwidth. You can also make the video effects
user-controllable, thus adding variation by making it an interactive
element instead of a linear video.
Color Coding
You have probably applied colors to
movie clips using the Advanced Effect dialog box shown in Figure 2-1. If you've never used color
effects before, you can set up a color tween as follows:
Draw a black circle on stage in frame 1 and convert it to a movie
clip symbol (F8). Insert a keyframe in frame 10 by selecting frame 10 in the main
timeline and choosing Insert Timeline Keyframe. Click on the keyframe in frame 1, and apply a motion tween to the
movie clip instance by setting the Tween option in the Properties
panel to Motion. Click on the keyframe in frame 10. Then use the Selection tool to
click on the Stage to deselect the frame. Finally, click on the movie
clip instance on stage to select it. Set the Color option in the Properties panel to Advanced. Click the Settings button in the
Properties panel to open the Advanced Effect dialog box, and set the
rb value, as indicated in Figure 2-1, to 200. Click OK to close the dialog box.

If you scrub the playhead across the first 10 frames of the timeline,
you should see the movie clip change slowly from black to red,
effectively creating a color transition. (If you
didn't apply the motion tween properly, the clip
remains black until frame 9 and then suddenly turns red in frame 10.)
So far, so good. But how do you apply the color transition to a video
at runtime? You can use the Color class to apply
a similar transform to any movie clip, including a movie clip
containing a video. The Color.setTransform(
) method accepts one argument, a
transform object with properties ra,
ga, ba, aa,
rb, gb, bb,
and ab. So now you're thinking,
"Whuh?"
A transform object (a.k.a. transObject) is just
an instance of the Object class that contains
properties used to perform the color transformation. The eight
properties simply correspond to the values of the eight fields in the
Advance Effect dialog box, as shown in Figure 2-1.
To get a feel for what the properties do, play around with the
Advanced Effect values manually.
Manually applying advanced color effects to a bitmap photograph image
embedded inside a movie clip will give you the best indication of
what can be done with color and a video instance. Experiment with one
or more still images captured from the video for best results.
Color Video Transforms
This hack creates one typical
transform type: an instantaneous effect, such as going quickly from
normal color film to the photographic negative for a few frames,
before returning back to normal. This looks really cool if you also
sync sound to the same effect [Hack #59] . This technique can be
extended to create another typical effect: fades and other gradual
transitions [Hack #9].
Let's look at instantaneous effects first. Figure 2-2 shows the original image and Figure 2-3 and Figure 2-4 show two
possible effects.
Figure 2-2 shows the original image, with a neutral
transform of:

{ra:100, rb:0, ga:100, gb:0, ba:100, bb:0, aa:100, ab:0}
Figure 2-3 shows the inverted image, with a
transform of:
{ra:-100, rb:255, ga:-100, gb:255, ba:-100, bb:255, aa:100, ab:0}

You are not limited to the negative effect, though.
Scripted transforms allow you to
overdrive further than the UI will take you via the Advanced Effect
dialog box. Figure 2-4 shows a high-contrast
transform:
{ra:500, rb:-500, ga:500, gb:-500, ba:500, bb:-500, aa:100, ab:0}

You can create lots of other effects, such as the
"washout effect" in
which the image appears overexposed, using the following transform to
lighten the image:
{ra:100, rb:150, ga:100, gb:150, ba:100, bb:150, aa:100, ab:0}
You can boost the red tones with a transform of:
{ra:500, rb:-500, ga:100, gb:0, ba:100, bb:0, aa:100, ab:0}
You can darken an image with a transform of:
{ra:100, rb:-150, ga:100, gb:-150, ba:100, bb:-150, aa:100, ab:0}
For full appreciation of the effects, see the sample images or
colortransforms.fla file downloadable from this
book's web site.
The following code applies an instantaneous color spot transform to
any content inside a movie clip:
function negativeFlick(targetClip, duration) {
this.neutralizer = function( ) {
negColor.setTransform(neutral);
// Refresh the screen
updateAfterEvent( );
// Clear the interval
clearInterval(negInterval);
};
// Define a transform that reverses the current colors
var negTrans = {ra:-100, rb:255, ga:-100, gb:255,
ba:-100, bb:255, aa:100, ab:0};
// Define and apply a neutral transform to cancel the effect
var neutral = {ra:100, rb:0, ga:100, gb:0, ba:100, bb:0, aa:100, ab:0};
// Target the specified clip and apply the transform
var negColor = new Color(targetClip);
negColor.setTransform(negTrans);
// Set up a callback to reverse the effect some time later
var negInterval = setInterval(this.neutralizer, duration);
}
Here we invoke the effect for one second on a clip named
bitmapClip, which presumably is a clip
we've created that contains a bitmap
(make sure you give the clip an instance name of
bitmapClip using the Properties panel):
negativeFlick(bitmapClip, 1000);
To apply the effect to a video, call negativeFlick(
) with the name of the clip containing
the video. Here is an example in which the effect is applied to a
clip named myVideo_mc for two seconds (2000
milliseconds). Again, you should set the instance name of the clip,
which presumably contains a video, using the Properties panel:
negativeFlick(myVideo_mc, 2000);
Typically, the script that defines the negativeFlick(
) function and the call that invokes it are attached to a
separate actions layer.
To invoke negativeFlick( ) from the timeline of
the myVideo_mc video clip, you would use:
negativeFlick(this, 2000);
The negativeFlick( ) function creates a
Color instance and uses it to apply our
transformation to the target clip. The last line of
negativeFlick( ) also sets up an interval (i.e.,
a timer using setInterval( )) that invokes
neutralizer( ). The neutralizer(
) function negates our transformation by
applying a neutral transform. The code clears the interval to prevent
it from repeating, as it would periodically if we failed to clear it.
Note that setInterval(
) is not tied directly to the frame rate,
so the callback function, in this case neutralizer(
), will typically execute before
other frame-based events (such as
onEnterFrame). When using setInterval(
) to produce graphic effects, the usefulness of having a
non-frame-based event is lost if you have to wait for the next frame
before you see the animated effect it creates. Therefore, the call to
updateAfterEvent( ) addresses the issue by
forcing a screen refresh at the end of the callback
function.
So, in this hack, we've seen several keys to
applying color transforms to video:
Use a color transform object to transform the
video's color. Use an interval and a callback function to make the change temporary. Use a neutral color transform to restore the original colors.
These techniques aren't limited to videos. You can
target any movie clip or even the main timeline. Furthermore, you
need not reset the color scheme using a neutral transform. You could
apply a random color transform periodically, for example. In that
case, you would want to randomize the values of the color transform
object's properties (instead of using a neutral
transform in the callback function), and you
wouldn't want to clear the interval in the callback
function. See the ActionScript Cookbook by Joey
Lott (O'Reilly) for more examples of using color
transformations and generating random numbers.
|