September 2003 Archives

Strange getURL() behavior

| 1 Comment

Has anyone using Flash MX 2004 experienced strange behavior with the getURL() function? I use Mozilla Firebird for web browsing, and I've been getting some strange results.

If you can, please follow along:

* Create a blank Flash document
* Type this action on frame 1: getURL("akjlhsd");
* Test the movie

Tell me what happens. On my system, a new instance of Firebird will open with 2 tabs. The first tab will be untitled, and the second tab opens up to some website that I've never seen until today.

It's rather funny, I think. I've also had it randomly open to this article in the Microsoft knowledge base. It looks like the second tab that opens is automatically submitting a google search and opening up the first link in the search results page.

Additionally, doing a getURL("some.zip") and testing it locally produces the same strange result.

Now, the question is, what is the root of this problem? Is this specific to only my system, is this a bug in Flash somehow with Firebird as the default web browser, or is this a bug in Firebird with how new documents are opened? If you have any ideas, I'd be interested in hearing them.

Dynamic MovieClip Registration with AS2

| 17 Comments

This handy little class (download here) will allow you to change the registration point of a MovieClip on the fly (instead of having to modify the symbol in the library and repostion all of the contents).

Usage: For every MovieClip you want to apply this to, navigate to it's Linkage properties in the Library, make sure it is exported for ActionScript, change the AS 2.0 Class to "com.darronschall.DynamicRegistration" and then use it in script like this... (also make sure that the DynamicRegistration class is in your movie's classpath)

UPDATE 7/28/05 - I goofed when I originally made this code. It's a bad idea to have to extend this class, rather it works much better with a mixin approach. So, I've updated the zip file, but usage is a lot easier. Rather than dealing with the linkage and stuff, simply call: com.darronschall.DynamicRegistration.initialize(my_clip); and my_clip will be decorated with setRegistration, _x2, _y2, _xscale2, _yscale2, _xmouse2, _ymouse2, and _rotation2. This is much easier to use... sorry about not fixing this for 2 years.. :-P

import com.darronschall.DynamicRegistration;

// Assume there is an instance named square_mc on the stage
var square_mc:MovieClip;

// updated 7/28/05 - add the dynamic registration stuff at runtime to our square movieclip
DynamicRegistration.initialize(square_mc);

// The square_mc has an original registration at 0,0 so
// let's change that to 10, 60 at runtime.
square_mc.setRegistration(10, 60); 

// Now whenever we access a property of the square_mc that deals
// with the registration point, use a "2" after the property name...  
// These are the available properties:
square_mc._x2 = 4;
square_mc._y2 = 7;
square_mc._rotation2 = 40;
square_mc._xscale2 = 140;
square_mc._yscale2 = 80;
// square_mc._xmouse2 is readonly
// square_mc._ymouse2 is readonly

Use the properties with a "2" to manipulate the MovieClip in regards to it's "new" registration point that you set with "setRegistration". Note that you must call setRegistration on a MovieClip before trying to manipulate it with the above properties.

Special thanks go out to Robert Penner for originally creating the AS 1 code. I simply ported it over to AS 2 and made the test bed you see below.. credit where credit is due.

The List ADT

| No Comments

Continuing with my ADT discussion (part 1, part 2), the next topic in the list is, ironically, the List ADT.

The List ADT is one of the most basic data structures in computer science. It is the basic foundation for more complex data types (such as Trees, Stacks, Queues, etc). Even an entire programming language, Lisp, has been built around the list as the only data structure. Lisp stands for "list processing" and is a commonly used language in Artificial Intelligence.

The List ADT is known as a recursive ADT. An ADT is recursive if it has access methods that return the same class as the ADT itself. In this case, the List ADT will return a List with it's access function "rest," as you will see shortly.

An interesting fact about the List ADT is that is has no manipulator (mutator) methods available. Remember that there are 4 types of operations on an ADT - constructors, interrogators (accessors), manipulators (mutators), and destructors. We can take advantage of the recursive definition and simply create access methods to make the List ADT surprisingly simple.

Read on ...

A script-only formatter in FMX2004 pro

| 1 Comment

After discovering how you can bind component values in Flash MX 2004 pro, I immediately wondered how to implement the "formatter" functionality via only script. As you may know, I've created a dateFormat function to format a Date object in ActionScript 1, and I was curious to see if this was implemented in FMX2004 or not.

For an overview of what I'm referring to, read this article on Data Binding over at Macromedia's website. I'm not opposed to the menu driven technique displayed in the article. This was a thought experiment to see if I could make use of the formatters via code only. This is what I came up with...

var dataFormatter:mx.utils.StringFormatter;
dataFormatter = new mx.utils.StringFormatter( "MM/DD/YYYY", "M,D,Y,H,N,S",
			mx.data.binding.DateBase.extractTokenDate, 
			mx.data.binding.DateBase.infuseTokenDate );

var today:Date = new Date();
trace(dataFormatter.formatValue(today)); // 09/18/2003

In order for this to work, you need access to the mx.data.binding classes and the mx.utils classes, all of which have been left out of the Classes folder in the "FirstRun\Classes" directory under your Flash MX 2004 installation directory. An easy way to compile the code above is to add these classes to your library. So... where do we get these classes?

If you look in the "C:\Program Files\Macromedia\Flash MX 2004\en\First Run\Data" directory (or something similar), you'll see a file "DataBindingClasses.swc". This compiled swf file contains the information we need to execute the script above.

An easy way to add this to your library is to copy the DataBindingClasses.swc file to "C:\Program Files\Macromedia\Flash MX 2004\en\First Run\Components\Data Components" and then re-start Flash to update the components panel. I've tried selecting "Reload" from the components panel, but the only way I've found to consistently update the panel is to restart Flash.

EDIT - Thanks to Chafic Kazoun of RewindLife.com there is an easier way to add the .swc to your library. In the IDE, select "Window" -> "Other Panels" -> "Common Libraries" -> "Classes". This will open up a library with the DataBindingClasses already inside.

Now, open up a blank .fla document, drag the DataBindingClasses (from the "Classes" library) onto the stage, and copy/paste that code onto frame 1 to see it in action.

Personally, I think I'll stick with my own dateFormat function if I want to format Date values. My version seems to be a little more flexible anyway (month name support, single-digit support, etc), but this process of discovery was enjoyable... Explore explore explore!!

Object.prototype.someMethod

| 2 Comments

If you've been trying to get accustomed to ActionScript 2, you've probably wondered how the ActionScript 1 style ClassName.prototype.someMethod = function() {} code fits into the "big picture." This has been a hot topic of discussion lately.

Consider the following example: I want to overwrite the MovieClip method "moveTo" to reposition the MovieClip and additionally return the coordinates in an Object. Currently the moveTo method will only reposition the MovieClip without returning any information.

To accomplish the above, what we need to do is create a custom class that extends MovieClip. The reason we "extend" MovieClip is because we're creating a class that "is a" MovieClip, but contains some additional functionality not present in the MovieClip class. The additional functionality, in this case, is a different implementation of the "moveTo" method. In Object Oriented Programming, the "is a" relationship is an example of inheritance and is implemented in ActionScript 2.0 through the "extends" keyword. The class looks like this:

// CustomMC.as
class CustomMC extends MovieClip {
	// hide the constructor from the outside world since
	// no one should be using it
	private function CustomMC() {}
	
	// override the MovieClip.moveTo method
	public function moveTo(x:Number, y:Number):Object {
		this._x = x;
		this._y = y;
				
		return {x:x, y:y};
	}
}

Now that we have our custom class created, we need to associate the class with a MovieClip symbol in the library so the symbol uses our over-ridden moveTo function and not the default MovieClip.moveTo one. Do this by right-clicking on a MovieClip in the library and selecting "Linkage...". A dialog box will appear. Check "Export for ActionScript." Then, where is says "AS 2.0 Class:", enter the name of the class to associate with the MovieClip instances on the stage. In our example, this is "CustomMC". Click ok.

That's it! Now, whenever you drag a MovieClip from the stage that is associated with the "CustomMC" class and invoke the moveTo method, the overridden moveTo method will be called instead of the "base" moveTo. The "base" class (also known as "super" class) is the class which is extended (in this case, "MovieClip"). A "subclass" "is a" "superclass". The "child" class "inherits from" the "parent" or "base" class.

A quick example:

// test_mc is the instance name of symbol associated with the "CustomMC" class
// .. this call executes CustomMC.moveTo
coords = test_mc.moveTo(5, 10);
trace(coords.x); // 5
trace(coords.y); // 10

// test2_mc is a regular movieclip, NOT associated with the "CustomMC" class
// .. this call executes MovieClip.moveTo
coords2 = test2_mc.moveTo(6, 6);
trace(coords2.x); // undefined, since the built in MovieClip.moveTo does not return anything

For additional information and a discussion around this topic, please see this FlashCoders thread.

Password Generation in AS2

| 1 Comment

You knew this was coming... I've updated the Password Generator to ActionScript 2. The .fla for this is really sweet - it contains only these 3 lines of code and the UI components in the library so we can attach them at runtime:

import com.darronschall.PasswordGeneratorUI;

// change the color of all of the UI elements to dark blue
_global.style.setStyle("themeColor", 0x000066);

/* the magic of creating the ui happens here, when the class constructor
is executed */
var UI:PasswordGeneratorUI = new PasswordGeneratorUI(this);

The interface is created 100% dynamically by the PasswordGeneratorUI class. For the Java programmers out there, here is a "real-world" example of how you can apply your knowledge to Flash. The only thing I did in the Flash IDE was set the document size and populate the library with the components the class needs. Everything else is done in the 2 class files. Once you learn some of the syntax quirks of AS2 and how the UI components work, it shouldn't take too long to start being productive if you're comfortable with Java.

This just goes to show how developer friendly the new version of Flash is... You can download the new Password Generator here.









Engaged!

| 1 Comment

Wooooohooooo!!! I just asked Jen, my girlfriend of two and a half years, to marry me this weekend.. and she said yes!!

Anyone out there know anything about planning weddings? We're aiming to get married in the summer of 2005, probably early to mid June.

I'm so happy... my nerdy programmer vibes didn't have a negative effect at all! :-)

class Engagement extends Relationship {
   private var commitment:Boolean;

   public function Engagement() {
     commitment = true;
   }
   
   public function getCommitment():Boolean {
	return commitment;   
   }
}

Method Overloading in ActionScript 2

| 1 Comment

You say it's impossible to overload a method in ActionScript 2? I say you're wrong! Well.. okay, you're not entirely wrong. The compiler will not let you overload a method the same way you would in, say, Java... but if you're sneaky about it you can achieve method overloading with ActionScript 2.

First of all, we need to establish what an overloaded method is so more people can follow along. An overloaded method is a method that has one name but multiple argument lists. An argument list is the number of parameters passed into the function along with each parameter's type. For example, function x(y:Number, s:String) has an argument list with length 2. The first argument is of type Number and the second of type String. This is different from function x(s:String, d:Date) because even though the argument list is still lenth 2, the first parameter is a String and the second is a Date. Why is overloading like this useful? Consider the following scenario...

I have a car object that allows me to paint the parts of it. The variable "car" is an instance of the Car class (defined in Car.as) with a public method available called paintPart. Because paintPart is public, I'm allowed to invoke that method on the instance. The paintPart method will take in a part of the car and output the part with a fresh coat of paint. All of the parts of the car are different.. a door is not a trunk, a trunk is not a hood, a hood is not a fender, etc. Because they are all different, they need to painted differently. A door cannot be painted the same as a hood - more care would be needed around the handle, for instance. However, I don't want to have more than one paint method on my car. To make things simple from the point of view of the car, I want to use the same method for all painting, like this:

car.paintPart(door);
car.paintPart(hood);
car.paintPart(trunk);

Rather than this:

car.paintDoor(door);
car.paintHood(hood);
car.paintTrunk(trunk);

Notice how the first segment has one function to paint parts, where the last segment has 3 different functions. It's easier to remember that if you want to paint part of a car you call paintPart since remembering one method to invoke is easier than remembering 3.

Even though the paintPart name is the same for all calls to it in segment 1, the method itself needs to do different things because each part passed in is a different type of car part. This is where method overloading comes to the rescue. We can re-use the method name and have it do different things based on its argument list.

In other languages, overloading is done automatically by the compiler. It "knows" which function to call based on the type and number of parameters. We would define paintPart 3 times with different argument lists. One would take in a Door object, one a Hood object, and another a Trunk object. The compiler would know the difference and call the correct function at run time.

In ActionScript 2, even though the language is strongly typed, the compiler will not do method overloading for you. You will get a syntax error if you try to define a function more than once with different argument lists. Instead, if you want to overload a method, you have to fake the compiler out and handle things yourself.

The Stack ADT

| 2 Comments

Continuing on yesterday's topic of Abstract Data Types, this evening I will be explaining what is probably the most common ADT – the Stack. ActionScript 2.0 source code is included in the examples.

As stated yesterday, an ADT is the declaration and the specifications (interface). Because of this, the ADT itself is actually language independent. A Stack is a Stack regardless of the language it is implemented in (Java, C#, or even ActionScript).

The specifications of any ADT should only focus on "public" operations because the users of the ADT are unaware of any private variables. This includes documentation – do not include private variable information in an ADT specification. Instead, document ADTs with"“preconditions" and "postconditions." Preconditions are statements that are assumed to be true before an operation executes. Postconditions are statements that will be true after an operation has completed. It is the ADT user's responsibility to ensure that the preconditions are true before calling an operation, not the responsibility of the ADT programmer. If a precondition is not satisfied unexpected results will occur. Whenever possible, try to define the preconditions and postconditions in terms of the parameters of the operation.

Operations on an ADT, as stated yesterday, fall into four categories. These categories are:

  • Constructors - create an instance of the ADT
  • Interrogators - return information about an instance without modifying the instance
  • Manipulators - modify the properties of an instance without returning any information about it
  • Destructors - de-allocate storage space, close any open documents, and release system resources

IMPORTANT: After an instance is created it can be interrogated and manipulated, but not by the same operation.

Please note is that an ADT constructor is not the same as a class constructor. This is because ADTs are language independent and not every programming language has a "new" operator. Rather, the constructor is invoked just like any operation by a simpe method call.

Another thing to note: in our example, there is no destructor. This is because the Flash Player uses a garbage collector that automagically cleans up resources of an object that has been deleted or fallen out of scope.

Additionally, before I get into the Stack ADT specification, there are few points yet to be made. Because access and modifiers are separate, we normally do not need to give postconditions for access functions. Likewise, postconditions should describe how the object has changed in terms of the access functions. If this cannot be done, then the ADT needs to be re-designed until it has all the access functions required. All of this may seem a little confusing at first, but it should become clearer as we step through an example.

And finally, the part you've all been waiting for…

Abstract Data Types

| No Comments

Data abstraction, a part of Object Orientated Programming, is a technique used to simplify data structures by focusing only on the important aspects of the data. The implementation details are hidden while the details of the data are grouped together allowing the data to be manipulated as a unit. Abstract Data Types (type abstraction) and Objects (procedural abstraction) are the two primary forms of data abstraction.

An Abstract Data Type (ADT) is a data abstraction that consists of the data structure declaration and the interface describing the data operations. The interface contains operations to create, interrogate, manipulate, and destroy instances of the ADT. The interface should be stable and well defined, with infrequent modifications.

An important principle behind ADTs is data encapsulation. Data encapsulation, sometimes referred to as information hiding, prevents the implementation details of the ADT from being accessed directly. Users of an ADT must use the well defined interface to act on the type.

By forcing access through an interface, programmers can achieve independent development by working on large parts of a project in parallel because the interface that will connect the parts has been standardized. This leads to faster and easier debugging, as an ADT can be tested on its own before integrated into a project. ADTs are also built for re-use. Once the ADT is written, it can be used in any application. Even two ADTs that have different implementations can be interchanged dynamically if their interfaces are the same.

Another advantage of ADTs comes into play when designing algorithms. The interface of the ADT can be used to prove algorithm correctness. Once this is established, frequently used operations can then be identified and work can be done to optimize these common operations, yielding in possibly dramatic performance gains.

Perhaps the most common example of an ADT is a Stack. Tomorrow I will get into the Stack ADT specification and provide an example implementation in ActionScript 2.0, as well as some example usage scenarios.

My next few entries will be all about ADTs and ActionScript 2.0. Stay tuned… there's plenty more to come!

Scripting color transitions

| 1 Comment

Did you ever need to fade from 0xC47D31 to 0x67DEF9 and have no idea where to start? Typically the timeline is used to tween color transisiton at author-time, but what do you do if you want to fade colors at run-time? The answer is here... take a look at the code below.

/*
Darron Schall
Sept. 8, 2003

Takes in an integer in and splits it up into is red, green, and blue parts
*/
function int_to_rgb(i) {
	var r = (i & 0xFF0000) >> 16;
	var g = (i & 0x00FF00) >> 8;
	var b = i & 0x0000FF;
	return {r:r, g:g, b:b};
}

/* 
Darron Schall
Sept. 8, 2003

Smoothly transitions a movie clip from one color to another
over a certain duration.
SIDE EFFECT: onEnterFrame is used to perform the loop,
calling this function will overwrite any existing onEnterFrame 
function.  A better alternative may be to make use of 
setInterval instead. */
MovieClip.prototype.fadeFromTo = function(start_val, stop_val, duration) {
	/* We don't need to save the stop_color, so just 
declare it as a local variable */
	var stop_color = int_to_rgb(stop_val);

	this.start_color = int_to_rgb(start_val);
	this.duration = duration;
	/* Delta is an object with 3 fields - each field specifies
 the amount of color shift from the start value to the stop value */
	this.delta = {
		r:(this.start_color.r-stop_color.r)/this.duration,
		g:(this.start_color.g-stop_color.g)/this.duration,
		b:(this.start_color.b-stop_color.b)/this.duration};
	
	/* Create a color object that refers to ourself, so we can change 
our own color.  We create this object outside of the loop so it's 
not continually created and destroyed*/
	this.colorObj = new Color(this);
 
	/* Start the ball rolling by changing our color initially, 
before the loop. */
	this.colorObj.setRGB(start_val);
	
	this.count = 1;
	this.onEnterFrame = function() {
		/* Construct an integer value from the 3 color parts.  
We always add from the start color so that error in rounding
 doesn't get multiplied for each color change.  Doing things this 
way makes the transition smoother and ensures that we 
end up on the right color as well. */
		var colorVal = ((this.start_color.r-this.count*this.delta.r) << 16)
			+ ((this.start_color.g-this.count*this.delta.g) << 8)
			+ (this.start_color.b-this.count*this.delta.b);
		// Update our color value
		this.colorObj.setRGB(colorVal);
		if (this.count++ == this.duration) {
			// Clean up after ourselves
			delete this.start_color;
			delete this.duration;
			delete this.delta;
			delete this.colorObj;
			delete this.count;
			delete this.onEnterFrame;
		}
	}
};

// Example usage:
some_mc.fadeFromTo(0xFFCC33, 0x990099, 45);

Let me know if you find this one useful. The same concept can be applied to TextFields as well to fade their background colors. Enjoy!

Anticipation

| No Comments

With the upcoming release of Flash MX 2004 and ActionScript 2.0 just around the corner, I'm looking forward to a new era of Flash development. One of the most exciting aspects about the new release is the evolution of ActionScript. No longer are we attached to the prototype for Object-Orientated Programming in our applications, as ActionScript has evolved into a full featured "true" Object-Oriented languauge with it's 2.0 debut.

I believe this is a good thing on a number of levels.

First, developers accustomed to other languages will have an easier time migrating to Flash. To me this is a great thing, as it will allow Java developers, for example, to dive into Flash with much less of a learning curve. The community is in a fantastic position to grow, and that benefits everyone involved with more opportunities and better exposure.

Second, it should make learning Object-Oriented Programming that much easier. Trying to learn a concept in a language that doesn't fully a concept is difficult. Not that ActionScript didn't support the concept.. but it supported the concept differently than the other popular OOP languages. I think it will be easier for people to see parallels now, and I hope to see a lot of light bulbs of understanding light up the community.

Third, it gives me something to talk about. Having been exposed to OOP for quite some time and having been in the trenches, I'm looking forward to sharing my experiences with others to help them grow and overcome some of the stumbling blocks.

The new language elements are not something to fear, but rather something to embrace. I will be among the many offering tips, tricks, and techniques to help coders get accustomed to ActionScript 2.0 in the coming weeks and months.

MMUG Meeting thoughts

| No Comments

I attended Macromedia's worldwide user group meeting this afternoon (The 2:00pm Eastern Time one) in Philadelphia, with PACFUG. Of course, we showed up fashionably late. Not on purpose, but we missed an exit on the highway. Whoever made Route 320 exit 330 needs their head examined. Either that, or maybe we should just pay more attention to signs when driving.

Anyway, the meeting itself was pretty neat. They used Breeze live to connect everyone and give the presentation. We saw the Macromedia's computer screen as they were giving live demos of the new MX 2004 product line. With the chat capability we were able to ask questions in real time and have people give us the answers via the speakers hooked up to our local computer.

All in all, it was a good experience. There were a few technical difficulties (lost audio sometimes, sometimes we lost the screen feed as well), but I'd say it was a success at least for our local group.

I didn't win the copy of Studio MX 2004 that was raffled off, or the one year subscription to the Community MX website, but I did have fun meeting and interacting.

It would've been nice to be able to see the presenters with video, and allow them to see us with video, but we were already sucking up so much bandwidth with just audio, text and screen images that asking for video as well would've put too much pressure on the servers.

A link was also shared to a "beta" site that Macromedia has made with the MX 2004 line. I won't divuldge the link location - it will be available to the public in the near future... but it's nice to see that the company uses their tools just like the community would.

Thank you Macromedia for involving the community like this. It's great using products from a company that cares about it's end users and values their opinions and feedback.

SharpFlash documentation now available

| No Comments

I've finally had a chance to update the SharpFlash home page with some documentation and content. You can find it here. Most important in the update is the API reference is starting to take shape.

Try to get past the lack of design on the page. I just exported a word document as html and modified it a little. Eventually the page will look better, but my primary concern right now was giving Flash developers something they can reference to start using and experimenting with SharpFlash.

The plan this week is to work on expanding the API. I want to try and complete sfFile by the end of the week... but generally what I want to do and what actually happens are two different things.

I don't want this weblog to turn into a SharpFlash advertisement so I'm probably going to stop posting about these minor SharpFlash updates. If you're concerned about updates, keep checking the two pages I listed in my previous entry. There is also an rss feed available on the project page on SourceForge, if you feel like aggregating changes to the program. Additionally, you can subscribe to the release files and recieve an update when a new release is uploaded.

As always, I hope everyone finds what I've done so far useful. I'll keep developing as time allows, but I can't make any guarantees on anything. If you would like to help out and see things get done faster, let me know.

Flex.org - The Directory for Flex

Archives