Table of Contents

Chapter 14. Movie Clip Subclasses and Components

In Chapter 12 we created a custom Ball class and used it to instantiate individual Ball objects. When it came time to display the ball objects, we were faced with several options. A separate Room class might contain balls and be responsible for drawing them on screen with the Drawing API. Or, a Ball object might have a property, mc, that contains a movie clip used to represent the ball. In some cases, it's redundant to have one object that represents a thing (such as a ball) and a separate movie clip object that displays it on screen. Movie clips, themselves, are already objects, so it often makes sense to use a movie clip to both describe an object and display that object on screen. In Flash MX, we can do so by creating a subclass based on the MovieClip class, thus creating a specialized type of object that provides built-in screen display.

In Flash 5, creating a MovieClip subclass involved an arduous series of workarounds that proved impractical for most developers. Flash MX introduces a formal MovieClip subclassing architecture that involves the following new features: #initclip, new MovieClip( ), Object.registerClass( ), and attachMovie( )'s initObj parameter.

To see how MovieClip subclasses are created, we'll implement our Ball class from Chapter 12 as a MovieClip subclass. In our example, each ball instance will be a movie clip responsible for moving itself around the screen. Read through the code in Example 14-1. We'll discuss it in the sections that follow. Generally, the code uses the OOP techniques we studied in Chapter 12, but with a few twists required by the MovieClip subclassing architecture. All of the example code in this chapter can be downloaded from the online Code Depot.

Example 14-1. The Ball class, a sample MovieClip subclass
// =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =
// Create namespace in which to store classes
// =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =
if (_global.org =  = undefined) {
  _global.org = new Object( );
}
if (_global.org.moock =  = undefined) {
  _global.org.moock = new Object( );
}
// =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =
// Create the Ball class
// =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =
/*
 * Ball Class. Extends MovieClip.
 *   Version: 1.0.0
 *   Desc: A movie clip subclass for depicting balls.
 *         Requires a Library symbol named ballSymbol.
 *
 * Constructor Params:
 *   radius          -The ball's size (half its diameter)
 *   ballColor       -The ball's color
 *   x               -The ball's initial x position
 *   y               -The ball's initial y position
 *   velocity        -The ball's movement vector: {x:0, y:0}
 * 
 * Methods:
 *   setSize( )       -Make the ball clip's size match the supplied radius
 *   setPosition( )   -Place the ball clip at an (x,y) coordinate
 *   setColor( )      -Apply an RGB color value to the ball clip
 *   move( )          -Apply the ball's velocity vector to its current position
 *
 * Event Handlers:
 *   onEnterFrame( )  -Invokes move( ) every frame.
 */
/*
 * Ball Class Constructor (parameters are passed by attachMovie( )'s initObj)
 */
org.moock.Ball = function ( ) {
  // Create instance properties
  this.velocity = this.params.velocity;
  // Initialize instance
  this.setPosition(this.params.x, this.params.y);
  this.setColor(this.params.ballColor);
  this.setSize(this.params.radius);
  this.onEnterFrame = this.move;
  // Remove constructor params object from the instance
  delete this.params;
}
/*
 * Set MovieClip as Ball's superclass
 */
org.moock.Ball.prototype = new MovieClip( );
/*
 * Associate the Library's ballSymbol with the Ball class
 */
Object.registerClass("ballSymbol", org.moock.Ball);
/*
 * Instance Methods
 */
/*
 * Method: Ball.setSize( )
 *   Desc: Sets the ball clip's size
 *
 * Params: 
 *   newRadius     -The ball's new radius
 */
org.moock.Ball.prototype.setSize = function (newRadius) {
  this._width = this._height = (newRadius * 2);
};
/*
 *  Method: Ball.setPosition( )
 *   Desc: Sets the ball clip's position to the point (x, y)
 *
 * Params:
 *   x             -The new horizontal position
 *   y             -The new vertical position
 */
org.moock.Ball.prototype.setPosition = function (x, y) {
  this._x = x;
  this._y = y;
};
/*
 * Method: Ball.setColor( )
 *   Desc: Changes the ball clip's color
 *
 * Params: 
 *   newColor      -The numeric RGB color to apply to the ball clip
 *
 */
org.moock.Ball.prototype.setColor = function (newColor) {
  var col = new Color(this);
  col.setRGB(newColor);
};
/*
 * Method: Ball.move( )
 *   Desc: Moves the ball according to its velocity vector
 *
 * Params: None
 *
 */
org.moock.Ball.prototype.move = function ( ) {
  this._x += this.velocity.x;
  this._y += this.velocity.y;
}
// =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =
// START APPLICATION
// =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =  =
main( );
// Function: main( )
//     Desc: Application entry point
function main ( ) {
  // Create an object whose properties will be used
  // as the Ball constructor's parameters
  var ballParams = new Object( );
  ballParams.radius = 10;
  ballParams.ballColor = 0xFF0000;
  ballParams.x = 250;
  ballParams.y = 250;
  ballParams.velocity = {x:12, y:4};

  // Assign the ballParams object to a single property
  // of initObj, which we'll pass to attachMovie( ). 
  // Properties of initObj are copied to each ball instance at attach-time.
  var initObj = new Object( );
  initObj.params = ballParams;

  // Create a ball
  this.attachMovie("ballSymbol", "redBall", 1, initObj);
} 

Table of Contents