I recommend that you open another copy of this document in a separate browser window and use the following links to easily find and view the figures and listings while you are reading about them.
Figures
Listings
- Listing 1 . Beginning of the class named Bitmap03.
- Listing 2 . Draw a yellow cross on the background.
- Listing 3 . Encapsulate the BitmapData object in a Bitmap object and add it to the display.
- Listing 4 . MXML code for the program named Bitmap04.
- Listing 5 . Beginning of the Driver class for the program named Bitmap04.
- Listing 6 . Draw a yellow cross on the background.
- Listing 7 . Encapsulate the bitmap data in a Bitmap object and add it to the display.
- Listing 8 . Source code for the program named Bitmap03.
- Listing 9 . MXML code for the program named Bitmap04.
- Listing 10 . Source code for the Driver class in the program named Bitmap04.
Supplemental material
I recommend that you also study the other lessons in my extensive collection of online programming tutorials. You will find a consolidated index at www.DickBaldwin.com .
General background information
The ActionScript documentation provides sample programs on the following web pages that cannot be run without modification in a Flex application, even when the entire application is programmed in ActionScript .
The problem is that these two sample programs were written to be compiled and run as pure ActionScript programs. There are some additional requirements that you must adhere to when writing bitmap programs to run as Flex applications.
Preview
I will explain two sample programs in this lesson. Both programs are scaled down versions of the sample program provided in the first link listed above .
The first program that I will explain can be compiled and run as a pure ActionScript program. The second program can be compiled and run as a Flex application with the majority of the code being written in ActionScript.
Run the online version of the programs
I encourage you to run the online versions of the two programs before continuing with this discussion.
Screen output from the program named Bitmap03
Both programs are designed to display a red square, 100 pixels on a side, with a yellow cross in the square. The screen output for the pure ActionScript program named Bitmap03 is shown in Figure 1. (Note that the yellow cross is much more visible in the original than in this screen shot.)
Screen output from the program named Bitmap03. |
---|
The size and position of the square varies
If you run the online version of this program, you will note that the size and position of the square varies depending on the width and height of the browser window.
Screen output from the program named Bitmap04
The program named Bitmap04 places the red square in a VBox container with a cyan background. The screen output is shown in Figure 2.
Screen output from the program named Bitmap04. |
---|
Although the VBox moves horizontally to remain centered in the browser window, neither the VBox nor the red square change size as the width and height of the browser window is changed.
Discussion and sample code
I will explain two programs in the remainder of this lesson.
The program named Bitmap03
Will discuss in fragments
I will explain the code for these two programs in fragments. Complete listings of all the code for both of the programs are provided beginning with Listing 8 near the end of the lesson.
Beginning of the class named Bitmap03
This program consists of a single class definition file named Bitmap03 , which begins in Listing 1.
LISTING 1: Beginning of the class named Bitmap03.
package {
import flash.display.Sprite
import flash.display.Bitmap;
import flash.display.BitmapData;
public class Bitmap03 extends Sprite {
public function Bitmap03(){
var bitmapData:BitmapData =
new BitmapData(100, 100, false, 0xFF0000);
The two main bitmap classes
The two main ActionScript classes that are used with bitmaps are:
What is the difference between the two classes?
Briefly, an object of the BitmapData class encapsulates the actual pixel color and transparency values that represent an image. An object of the Bitmap class is a subclass of theDisplayObject class, meaning that it can be placed on the display list. A Bitmap object encapsulates a BitmapData object.
NOTE:
A 32-bit ARGB color value: I will have a lot more to say about pixels, color values, etc. in future lessons. My objective for this lesson is simply to get you to the point that you can create and display bitmap data.A new object of the BitmapData class
The constructor for the Bitmap03 class begins in Listing 1. The constructor instantiates a new object of the BitmapData class with a red opaque background. The constructor parameters for a BitmapData object are:
- width :int -- The width of the bitmap image in pixels. The width is specified as 100 pixels in Listing 1.
- height :int -- The height of the bitmap image in pixels. The height is specified as 100 pixels in Listing 1.
- transparent -- Boolean (default = true) -- Specifies whether the bitmap image supports per-pixel transparency. The default value is true (transparent). A value of false (opaque) is specified in Listing 1.
- fillColor :uint (default = 0xFFFFFFFF -- A 32-bit ARGB color value that you use to fill the bitmap image area. The color red is specified in Listing 1.
Draw a yellow cross on the background
A BitmapData object encapsulates a rectangular array of pixel data. The class provides several methods that make it possible for you to get and set individual pixel values in terms of color and transparency.
One of those methods is the method named setPixel that lets you replace (or merge with transparency) an existing pixel with a new pixel on the basis of the horizontal and vertical coordinates of the pixel.
Listing 2 uses a for loop to replace some of the red pixels in the BitmapData object with yellow pixels to form a yellow cross as shown in Figure 1.
LISTING 2: Draw a yellow cross on the background.
var yellow:uint = 0xFFFF00;
for(var cnt:uint = 0; cnt < 100; cnt++){
bitmapData.setPixel(cnt, cnt, yellow);
bitmapData.setPixel(100 - cnt, cnt, yellow);
} //end for loop
The setPixel method
The setPixel method requires three parameters. The first two are the horizontal and vertical coordinates of the pixel whose color values are to be set. The third is an unsigned integer value that specifies the color that will be assigned to the pixel at that location.
Without getting into the details at this point, suffice it to say that the value assigned to the yellow variable in Listing 2 specifies the visible color of yellow.
Encapsulate the BitmapData object in a Bitmap object
The constructor for the Bitmap class has three parameters, but they all have default values. The first parameter, if provided, must be a reference to an object of type BitmapData .
Continuing with the constructor for the Bitmap03 class, Listing 3 instantiates a new Bitmap object passing the BitmapData object prepared in Listing 2 as a parameter.
LISTING 3: Encapsulate the BitmapData object in a Bitmap object and add it to the display.
var bitmapObj:Bitmap = new Bitmap(bitmapData);
addChild(bitmapObj);
} //end constructor
} //end class
} //end package
Add the new Bitmap object to the display
Then Listing 3 calls the addChild method on the Sprite object to add the new Bitmap object to the display. This produces the screen output shown in Figure 1.
Simple enough?
This seems simple enough - right? However, there is a potential problem. In particular, an ActionScript project does not have access to any of those great Flex components. Therefore, if you are going to create ActionScript projects, you will need to have access to similar resources from some other source.
Not compatible with Flex
This is the form of the sample programs provided in the ActionScript documentation on the two web pages listed above . Unfortunately, I didn't see a warning on either of those pages to the effect that the programs are not compatible with Flex. I finally found a comment at the bottom of a different documentation page that gave me the first clue about the compatibility problem.
The program named Bitmap04
In this program, I will show you how to update the program named Bitmap03 to make it compatible with Flex.
MXML code for the program named Bitmap04
We will begin with the MXML code shown in Listing 4 and repeated in Listing 9 for your convenience.
LISTING 4: MXML code for the program named Bitmap04.
<?xml version="1.0" encoding="utf-8"?>
<mx:Application
xmlns:mx="http://www.adobe.com/2006/mxml"
xmlns:cc="CustomClasses.*">
<cc:Driver/>
</mx:Application>
Two files
This program consists of two files. One file, named Bitmap04.mxml contains the code shown in Listing 4. The other file named Driver.as contains the definition of a class named Driver. It is located in a package folder named CustomClasses , leading to the namespace declaration in Listing 4.
Instantiate an object of the Driver class
As you can see, the MXML code in Listing 4 simply instantiates an object of the Driver class. Beyond that point, the behavior of the program is completely controlled by ActionScript code.
Beginning of the Driver class for the program named Bitmap04
The Driver class begins in Listing 5. The code in Listing 5 is very similar to the code in Listing 1 with a few exceptions.
LISTING 5: Beginning of the Driver class for the program named Bitmap04.
package CustomClasses{
import mx.containers.VBox;
import flash.display.Bitmap;
import flash.display.BitmapData;
import mx.core.UIComponent;
public class Driver extends VBox{
//Note that this class extends Sprite, nothing shows
// on the display. Therefore it extends VBox instead.
public function Driver(){
//Prepare the display area. This is window dressing.
setStyle("backgroundAlpha",1.0);
setStyle("backgroundColor",0x00FFFF);
width = 150;
height = 150;
//Create a BitmapData object with a red opaque
// background.
var bitmapData:BitmapData =
new BitmapData(100, 100, false, 0xFF0000);
Extend the VBox class
This class extends VBox instead of extending Sprite as is the case in the previous program. Although this program will compile and run by extending Sprite , nothing appears on the output screen.
Apparently the reason is that Flex requires user interface display objects to be subclasses of the class named UIComponent , and the Sprite class is not a subclass of that class. This is the first major difference between this program and the previous one.
Some window dressing
The code at the beginning of the constructor in Listing 5 sets the height, width, background color, and transparency of the VBox container so that it can be seen in the display. As indicated in the comments, this is window dressing and is not a requirement for the program to execute properly. The cyan rectangle in Figure 2 is the VBox container.
A new BitmapData object
The last statement in Listing 5 instantiates a new BitmapData object identical to the one instantiated in the previous program.
Draw a yellow cross on the background
The code is listing 6 is identical to the code in Listing 2. This code draws the yellow cross on the red background that you see in Figure 2.
LISTING 6: Draw a yellow cross on the background.
var yellow:uint = 0xFFFF00;
for(var cnt:uint = 0; cnt < 100; cnt++){
bitmapData.setPixel(cnt, cnt, yellow);
bitmapData.setPixel(100 - cnt, cnt, yellow);
} //end for loop
Encapsulate the bitmap data in a Bitmap object and add it to the display
This is where the second major difference between the two programs arises. Although both programs encapsulate the bitmap data in the Bitmap object using the same code, the code required to add the Bitmap object to the output display is very different.
LISTING 7: Encapsulate the bitmap data in a Bitmap object and add it to the display.
var bitmapObj:Bitmap = new Bitmap(bitmapData);
var uiComponent:UIComponent = new UIComponent();
uiComponent.addChild(bitmapObj);
addChild(uiComponent);
} //end constructor
} //end class
} //end package
Call the addChild method
In the previous ActionScript program, it was possible to simply call the addChild method to add the Bitmap object to the output display. However, that is not possible in a Flex application. If you try to do so, your program will throw a runtime error indicating an incompatible type.
Two requirements
In order to add a child to a VBox object, that child:
- Must be a subclass of the DisplayObject class and
- Must implement the IUIComponent interface.
While a Bitmap object is a subclass of DisplayObject , it does not implement the IUIComponent interface. Therefore, it is not compatible with being added directly to the VBoxobject.
Use a UIComponent object as an intermediary
One way to handle this is to add the Bitmap object to a new UIComponent object and then add the UIComponent object to the VBox object.
That is what I did in Listing 7. The result is shown in Figure 2 with the red Bitmap object contained in the cyan VBox object.
This is the second major difference between the two programs.
The end of the program
Listing 7 also signals the end of the class and the end of the program.
Run the program
I encourage you to run this program from the web. Then copy the code from Listing 8 through Listing 10. Use that code to create an ActionScript project and a Flex project. Compile and run the projects. Experiment with the code, making changes, and observing the results of your changes. Make certain that you can explain why your changes behave as they do.
Resources
I will publish a list containing links to ActionScript resources as a separate document. Search for ActionScript Resources in the Connexions search box.
Complete program listings
Complete listings of the source code for the two programs discussed in this lesson are provided below.
LISTING 8: Source code for the program named Bitmap03.
/*********************************************************
* Bitmap03 11/29/09
* Can be run as an ActionScript project. However, some
* changes are required to convert it to a Flex project.
*
* For some reason, the size and position of the 100x100
* pixel red square depends on the size and the height to
* width ration of the browser window.
*********************************************************/
package {
import flash.display.Sprite
import flash.display.Bitmap;
import flash.display.BitmapData;
public class Bitmap03 extends Sprite {
public function Bitmap03(){
//Create a BitmapData object with a red opaque
// background.
var bitmapData:BitmapData =
new BitmapData(100, 100, false, 0xFF0000);
//Draw a yellow cross on the background
var yellow:uint = 0xFFFF00;
for(var cnt:uint = 0; cnt < 100; cnt++){
bitmapData.setPixel(cnt, cnt, yellow);
bitmapData.setPixel(100 - cnt, cnt, yellow);
} //end for loop
//Encapsulate the bitmap data into a new Bitmap
// object and add it to the display. For some
// reason, the red square displays as 50x50 instead
// of 100x100.
var bitmapObj:Bitmap = new Bitmap(bitmapData);
addChild(bitmapObj);
} //end constructor
} //end class
} //end package
LISTING 9: MXML code for the program named Bitmap04.
<?xml version="1.0" encoding="utf-8"?>
<!--Bitmap04
-->
<mx:Application
xmlns:mx="http://www.adobe.com/2006/mxml"
xmlns:cc="CustomClasses.*">
<cc:Driver/>
</mx:Application>
LISTING 10: Source code for the Driver class in the program named Bitmap04.
/*********************************************************
* Bitmap04 11/29/09
* This is an update to Bitmap03 to make it possible to
* compile and run it as a Flex project. Unlike Bitmap03
* the red square produced by this program displays at the
* correct size of 100x100 pixels.
*********************************************************/
package CustomClasses{
import mx.containers.VBox;
import flash.display.Bitmap;
import flash.display.BitmapData;
import mx.core.UIComponent;
public class Driver extends VBox{
//Note that this class extends Sprite, nothing shows
// on the display. Therefore it extends VBox instead.
public function Driver(){
//Prepare the display area. This is window dressing.
setStyle("backgroundAlpha",1.0);
setStyle("backgroundColor",0x00FFFF);
width = 150;
height = 150;
//Create a BitmapData object with a red opaque
// background.
var bitmapData:BitmapData =
new BitmapData(100, 100, false, 0xFF0000);
//Draw a yellow cross on the background
var yellow:uint = 0xFFFF00;
for(var cnt:uint = 0; cnt < 100; cnt++){
bitmapData.setPixel(cnt, cnt, yellow);
bitmapData.setPixel(100 - cnt, cnt, yellow);
} //end for loop
//Encapsulate the bitmap data into a new Bitmap
// object and add it to the display.
var bitmapObj:Bitmap = new Bitmap(bitmapData);
//The following is necessary because the Bitmap
// class is not a subclass of UIComponent.
var uiComponent:UIComponent = new UIComponent();
uiComponent.addChild(bitmapObj);
addChild(uiComponent);
} //end constructor
} //end class
} //end package
No comments:
Post a Comment