ActionScript.org Flash, Flex and ActionScript Resources - http://www.actionscript.org/resources
Building a Web Site completely with ActionScript
http://www.actionscript.org/resources/articles/1068/1/Building-a-Web-Site-completely-with-ActionScript/Page1.html
HariBabu Suraneni
While I am working in www.onemg.in as a Flash Developer, I have really entered into Flash Script writing even though I started my career with AS2 in 2007. From that humble begening, now I have grown up to a successfull AS3 programmer. In my process of learning, actionscript org has a major role as I Learnt so much from the published tutorials and forums. Now, I think I have learnt some new techniques that are rarely finding their place in these articles, I want to share my knowledge through some of the educative tutorials. 
By HariBabu Suraneni
Published on December 29, 2010
 
This is a tutorial about how to build a web site completely with Flash AS3. it will introduce you basic scriping techniques ike creating new elements on the fly, adding graphics to the Visual Interface and finally activating them to animate. More importantly It deals with Object level communication.

Building basic Interface

Building entire Flash Website with only ActionScript

While I am learning flash, my faculty planted me a seed. He is an ardent fan of flash actionscript. He has a goal: to build an entire website with only script, that means without creating any content on stage by authoring time interface. I liked that iIdea - to be frank, I too am bitten by that idea. Can we do it really? Yes, we can! In fact, Flash actionscript started with very litle syntax in it's begining stages. Mostly, gotoAndPlay, gotoAndStop play and stop. But It has evolved into a full functional control system in AS2. We can create most of the objects at runtime and we can do every thing with script - all type of transformations and transitions - what we are doing at authoring time.

And, with the advent of AS3 - with all it's robust packages - we can do it very easily. Now, I am an experienced programmer to do it with an ease. So, I am waiting for a situation to show it to others in a simple way, and now, I got it. One of my fellow flash designers created a beautiful authoring time animation, and I am impressed by it. I want to work on this model to show all of you. First I want to show his original work. He called it as a printing press animation(old time art, now we are in the age of desktop publishing, you may not see it regularly). Click any one of the two buttons to see the action.

Yes, it is very nice. But it is very hard to create, and It needs your time and patience. You can download the flash file  from here -> to see how tedious to design it. But It has very simple structure. That's why I took this as an example. First I studied all the object features and their Tween Time charecterestics. Once I understood perfectly, I am ready to do it right from the begining with ActionScript.

step1:Document Class

I have created a new blank file mainTimeLineTestApp.fla in authoring time window. It is fully clean.  I think you know where we put all our code in TimeLine mode. We are doing it from the ages by pressing F9 on the First frame of the top most layer. But I am fascinated by the other recent Document Class Model. In this way We will leave the flash file there. We need to create a new script file. We are doing it now also to use it as include file in main time line code, right? But, I am going in a different way. I have created a class here and attached it to the flash file as Document class. To do so, You need to take two carefull things. First You need to know backbone structure of a simple ActionScript class.

[as] /*mainTimeLine.as*/ package{     import flash.display.MovieClip;     public class mainTimeLine extends MovieClip{         public function mainTimeLine(){             trace("Dcument class Constructor");         }     } } [/as]

This is the Simple structure of a Flash ActionScript class.I will explain you all the bits you are seeing above one by one. First thing you need to remember is saving the .as file with same name of the class.And that package refers to the folder that contains the script. Here, I left it without any name, because I saved it into the same folder, normally refered as root/home of the website when you hosted the project into server. If I saved it in a com or flash or any other named folder, I need to write here package com{ there. Next line is import statement. If you are working in TimeLine mode all the general packages will be opened to the Global RunTime Memory automatically. But, in this class mode you need to import the relevant package for each and every type of the Object, which you are manipulating through your code. I have imported MovieClip class because, I have defined my class by extending MovieClip. You can extend Sprite also for a Document Class. Every Document Class must contain a constructor function, that also must be with the class name.

Now, we need to attach it to our flash file. It is very simple. First lock the one and only layer and press <ctrl>F3. It will open properties panel to the Flash Document. There expand the publish tab, if it is in collapsed state.Here you type in the class name. That's it. Publish it and you will get the trace which I wrote in the constructor function. So, we are successful in our first step, creating a Document Class for our Flash Document.

step2:Adding Buttons

Now, we need to create Interface. They are simple Rounded rectangles with a TextField having the Label. Drawing two rounded Rectangles and Putting some TextField inside them is not a complicated thing. We can simply add two Sprites, and - inside their graphics Object - We can draw Rectangles and Text, and can activate them to open relevant pages. But, I wanted to do it in a separate Object. This is a type of granular coding. In the class structure of coding, It is a better practice to make each major object, a code granule - a self sufficient container to behave on it's own taking responsibilities for it's role - to reuse it again and again in the project. So, I have created ButtonsObj class.

[as] /*ButtonsObj.as*/ package{     import flash.display.Sprite;     import flash.events.Event;        public class ButtonsObj extends Sprite{         private var sprHOMEbtn:Sprite=new Sprite();         private var sprABOUTUSbtn:Sprite=new Sprite();         public function ButtonsObj(){ trace("ButtonsObj constructor");            addEventListener(Event.ADDED_TO_STAGE,handleAddedToStageEvent);         }         private function handleAddedToStageEvent(arg_Event:Event):void{ trace("ButtonsObj Added to Stage")                drawButtons();         activateButtons();         }         private function drawButtons():void{         }          public function activateButtons():void{         }                  } } [/as]

I have already explained you about class structure. Here, our tasks are only two. First drawing buttons and activate them. But for positioning the buttons, we need some stage related values. Before adding it to stage, we cannot refer the stage object. So, I have shifted that functionality to a function, which captures the Event.ADDED_TO_STAGE for this ButtonsObj object. Then, I have modified mainTimeLine code.Before the constructor function defenition I have created a reference variable.

[as]         private var myButtons:ButtonsObj=new ButtonsObj(); [/as]

And, I have wrote a function INITAPP to add this object into mainTimeLine.We can add the object in the constructor itself. But, it is a newly practicing style, to make the function reusable.

[as]         private function InitApp(){             addChild(myButtons);         } [/as]

And, in the constructor, I added one command InitApp(); next to the trace command. If you publish the mainTimeLineTestApp.fla now, three lines of text will appear in it's output panel.

[as] ButtonsObj constructor Dcument class Constructor ButtonsObj Added to Stage [/as]

Can you imagine why "ButtonsObj constructor" is coming before "Document class Constructor"? Because, we are creating it's instance while declaring itself, and that is taking place before the Instance creation of mainTimeLine class object. So, the Logical Chaining of the code I wrote is successful, even for that Event.ADDED_TO_STAGE capturing. Now, we need to place the actual objects on Stage. I have wrote code for creating that Rounded rectangles and Caption TextFields inside drawButtons function.

[as]             sprHOMEbtn.graphics.clear();             sprHOMEbtn.graphics.lineStyle(0,0x000000,0);             sprHOMEbtn.graphics.beginFill(0xFFFFFF,1);             sprHOMEbtn.graphics.drawRoundRect(-(num_BUTTONWIDTH_obj/2),-(num_BUTTONHEIGHT_obj/2),num_BUTTONWIDTH_obj,num_BUTTONHEIGHT_obj,num_ellipseWidth_obj,num_ellipseHeight_obj);             sprHOMEbtn.graphics.endFill();             addChild(sprHOMEbtn);             sprHOMEbtn.x=(stage.stageWidth/2)-(((sprHOMEbtn.width/2)+(num_BUTTONMARGIN_obj/2))*1);             sprHOMEbtn.y=50;             var txthomeCaptionobj:TextField=new TextField();             txthomeCaptionobj.autoSize=TextFieldAutoSize.LEFT;             txthomeCaptionobj.type=TextFieldType.DYNAMIC;             txthomeCaptionobj.text="Home";             txthomeCaptionobj.mouseEnabled=false;             var fmtHomeObj:TextFormat=new TextFormat();             fmtHomeObj.font="Times New Roman";             fmtHomeObj.size=20;             txthomeCaptionobj.setTextFormat(fmtHomeObj);             sprHOMEbtn.addChild(txthomeCaptionobj);             txthomeCaptionobj.x=-txthomeCaptionobj.width/2;             txthomeCaptionobj.y=-txthomeCaptionobj.height/2;             txthomeCaptionobj.selectable=false;             sprHOMEbtn.mouseChildren=false;                                    //Home button added             sprABOUTUSbtn.graphics.clear();             sprABOUTUSbtn.graphics.lineStyle(0,0x000000,0);             sprABOUTUSbtn.graphics.beginFill(0xFFFFFF,1);             sprABOUTUSbtn.graphics.drawRoundRect(-(num_BUTTONWIDTH_obj/2),-(num_BUTTONHEIGHT_obj/2),num_BUTTONWIDTH_obj,num_BUTTONHEIGHT_obj,num_ellipseWidth_obj,num_ellipseHeight_obj);             sprABOUTUSbtn.graphics.endFill();             addChild(sprABOUTUSbtn);             sprABOUTUSbtn.x=(stage.stageWidth/2)+(((sprHOMEbtn.width/2)+(num_BUTTONMARGIN_obj/2))*1);             sprABOUTUSbtn.y=50;             var txtaboutCaptionobj:TextField=new TextField();             txtaboutCaptionobj.autoSize=TextFieldAutoSize.LEFT;             txtaboutCaptionobj.type=TextFieldType.DYNAMIC;             txtaboutCaptionobj.text="About";             txtaboutCaptionobj.setTextFormat(fmtHomeObj);             sprABOUTUSbtn.addChild(txtaboutCaptionobj);             txtaboutCaptionobj.x=-txtaboutCaptionobj.width/2;             txtaboutCaptionobj.y=-txtaboutCaptionobj.height/2;             txtaboutCaptionobj.selectable=false; [/as]

All I have done here is creating two Sprites with Rounded Rectangle graphics and placing text for each of them.I have positioned one on right to stage Half and the other one on left Stage Half with equal margin. I made all the building and positioning with variables, not with fixed values. It will be easy to change just a common variable rather than editing each of the button creating statements. To enable this i have defined variables before constructor.

[as]         private var num_BUTTONWIDTH_obj:Number=200;         private var num_BUTTONHEIGHT_obj:Number=30;         private var num_ellipseWidth_obj:Number=num_BUTTONHEIGHT_obj;         private var num_ellipseHeight_obj:Number=num_BUTTONHEIGHT_obj;            private var num_BUTTONMARGIN_obj:Number=30; [/as]

Please note that we are Using TextField object newly and adding some TextField specific properties to it. So, we need the packages into Document Memory Space. So, I am importing them also.

[as]     import flash.text.TextField;     import flash.text.TextFormat;     import flash.text.TextFieldType;     import flash.text.TextFieldAutoSize; [/as]

Now that, construction of Basic Interface is Over. If you publish the flash file, It will look like the screen shot below. If you compare this with old model, buttons look smaller here. First I have created them as  replicas to old buttons, but I thought of smaller size willl be nice. I just did it with changing only two lines of coding!


Activating the Interface

I will proceed to activate those buttons to receive click events. We can do it while adding itself. But there is a problem. We need to deactivate them before First tween starts, otherwise, new objects will be piled up continuously and we cannot control all the Event Chains properly. To overcome that burden, we need toggle functions activate/deactivate. So that, I have added one more function suppressButtons to ButtonsObj.  Their code will be like this:

[as]         public function activateButtons():void{             sprHOMEbtn.buttonMode=true;             sprHOMEbtn.addEventListener(MouseEvent.CLICK,handleHomeButtonClickEvent);             }         public function suppressButtons():void{             sprHOMEbtn.buttonMode=false;             sprHOMEbtn.removeEventListener(MouseEvent.CLICK,handleHomeButtonClickEvent);         }         private function handleHomeButtonClickEvent(arg_Event:MouseEvent):void{             suppressButtons();             myHomePage=new homePageObj();         mainTimeLine(this.parent).addChild(myHomePage);         }         [/as]

They are self-explanatory, right? AS we are using MouseEvent, we need to import it in the imports section. And we need a reference variable to Home Page.

[as]     import flash.events.MouseEvent; //in imports section         private var myHomePage:homePageObj; //in variable declaration section [/as]

I am activating only Home Button in this demo. After completing this tutorial and understanding the concepts fully, you can do that for About button yourself. That will be a home work to you. [ me |:-) , you |:( ].

step3:Showing Home Page

Now, our final guest is coming - homePageObj. Upto now, I am displaying only slices of coding, not only to save the HTML space but also to finish the tutorial as fast as I can. But, I won't leave you half-learned. I think now you got some confidence that we can build an entire flash site with only scripting, and you have learnt basic concepts of creating graphics and text inside DisplayObjects and adding them to the DisplayObjectContainers. Now, the most important things are happening inside the homePageObj - Creating two blocks, Placing them Off stage, Tweening them two times in a chain. Please follow the code carefully, I am explaining it very little at this time.

[as] /*homePageObj.as*/ package{     import flash.display.Sprite;     import flash.events.Event;     import flash.display.Sprite;     import flash.text.TextField;     import flash.text.TextFormat;     import flash.text.TextFieldType;     import flash.text.TextFieldAutoSize;      import fl.transitions.Tween;      import fl.transitions.easing.*;      import  fl.transitions.TweenEvent;      import flash.display.DisplayObject;      import flash.display.DisplayObjectContainer;      import flash.events.Event;      import com.pageevents.PageEvent;     public class homePageObj extends Sprite{         private var sprLeftPage:Sprite=new Sprite();         private var sprRigtPage:Sprite=new Sprite();         private var num_LeftPageWidth_obj:Number=300;         private var num_LeftPageHeight_Obj:Number=400;         private var num_RESIZE_SCALE_RATIO_START_obj:Number=1.2;         private var num_RESIZE_SCALE_RATIO_LIMIT_obj:Number=1;         public function homePageObj(){             InitPages();         addEventListener(Event.ADDED_TO_STAGE,handleAddedToStageEvent);         }         private function InitPages():void{             sprLeftPage.graphics.clear();             sprLeftPage.graphics.lineStyle(0,0x000000,0);             sprLeftPage.graphics.beginFill(0xFFFFFF,1);             sprLeftPage.graphics.drawRect(0,0,num_LeftPageWidth_obj,num_LeftPageHeight_Obj);             sprLeftPage.graphics.endFill();             var txthomeCaptionobj:TextField=new TextField();             txthomeCaptionobj.autoSize=TextFieldAutoSize.LEFT;             txthomeCaptionobj.type=TextFieldType.DYNAMIC;             txthomeCaptionobj.text="Home Page Title";             txthomeCaptionobj.mouseEnabled=false;             var fmtHomeObj:TextFormat=new TextFormat();             fmtHomeObj.font="Times New Roman";             fmtHomeObj.size=20;             txthomeCaptionobj.setTextFormat(fmtHomeObj);                    sprLeftPage.addChild(txthomeCaptionobj);             addChild(sprLeftPage);             //Left Page added             sprRigtPage.graphics.clear();             sprRigtPage.graphics.lineStyle(0,0x000000,0);             sprRigtPage.graphics.beginFill(0xFFFFFF,1);             sprRigtPage.graphics.drawRect(0,0,num_LeftPageWidth_obj,num_LeftPageHeight_Obj);             sprRigtPage.graphics.endFill();             var txthomeContentobj:TextField=new TextField();             txthomeContentobj.autoSize=TextFieldAutoSize.LEFT;             txthomeContentobj.type=TextFieldType.DYNAMIC;             txthomeContentobj.text="Home Page Content";             txthomeContentobj.mouseEnabled=false;             txthomeContentobj.setTextFormat(fmtHomeObj);                    sprRigtPage.addChild(txthomeContentobj);             addChild(sprRigtPage);                    }         private function handleAddedToStageEvent(arg_Event:Event):void{             removeEventListener(Event.ADDED_TO_STAGE,handleAddedToStageEvent);             sprLeftPage.scaleX=sprLeftPage.scaleY=num_RESIZE_SCALE_RATIO_START_obj;             sprRigtPage.scaleX=sprRigtPage.scaleY=num_RESIZE_SCALE_RATIO_START_obj;             sprLeftPage.x=-sprLeftPage.width;             sprLeftPage.y=(stage.stageHeight/2)-(sprLeftPage.height/2);             sprRigtPage.x=stage.stageWidth;             sprRigtPage.y=(stage.stageHeight/2)-(sprRigtPage.height/2);         START_TWEENS();            }         private function START_TWEENS():void{             var leftXTween:Tween = new Tween(sprLeftPage, "x", Regular.easeOut, -sprLeftPage.width, (stage.stageWidth/2)-(num_LeftPageWidth_obj), 0.5, true);             var rigtTween:Tween = new Tween(sprRigtPage, "x", Regular.easeOut, stage.stageWidth, (stage.stageWidth/2), 0.5, true);         rigtTween.addEventListener(TweenEvent.MOTION_FINISH,handleMoveToCenterTweenFinishEvent);         }         private function handleMoveToCenterTweenFinishEvent(arg_Event:TweenEvent):void{             var leftscaleXTween:Tween = new Tween(sprLeftPage, "scaleX", Regular.easeOut, num_RESIZE_SCALE_RATIO_START_obj, num_RESIZE_SCALE_RATIO_LIMIT_obj, 0.5, true);             var leftscaleYTween:Tween = new Tween(sprLeftPage, "scaleY", Regular.easeOut, num_RESIZE_SCALE_RATIO_START_obj, num_RESIZE_SCALE_RATIO_LIMIT_obj, 0.5, true);             var leftYTween:Tween = new Tween(sprLeftPage, "y", Regular.easeOut, sprLeftPage.y, (stage.stageHeight/2)-(num_LeftPageHeight_Obj/2), 0.5, true);             var rigtscaleXTween:Tween = new Tween(sprRigtPage, "scaleX", Regular.easeOut, num_RESIZE_SCALE_RATIO_START_obj, num_RESIZE_SCALE_RATIO_LIMIT_obj, 0.5, true);             var rigtscaleYTween:Tween = new Tween(sprRigtPage, "scaleY", Regular.easeOut, num_RESIZE_SCALE_RATIO_START_obj, num_RESIZE_SCALE_RATIO_LIMIT_obj, 0.5, true);             var rigtYTween:Tween = new Tween(sprRigtPage, "y", Regular.easeOut, sprRigtPage.y, (stage.stageHeight/2)-(num_LeftPageHeight_Obj/2), 0.5, true);         }     } } [/as]

It is just like ButtonsObj in all the features. Only difference is executing InitPages in the constructor itself. Because the internal content of this object must be added to it before it is added to stage. I Simply added there without any specific positioning commands. Positioning them off-stage will start in the handleAddedToStageEvent. You already knew the reason. Then I am starting the First Tween. from each side, they will tween to the corresponding positions in a way that they will form a continuous rectangle.

Now, wait a moment. I have added the code to Open Home Page in the Button Click Event of ButtonsObj. OK, it will open home page beautifully. But what about default appearence? We need to show it on site load event itself as the old model file.It is very simple - add homePageObj there also in the InitApp function. I will show you the fully developed mainTimeLine.as.   Now fully blown up mainTimeLine looks like this:

[as] /*mainTimeLine.as*/ package{     import flash.display.MovieClip;     import flash.display.Sprite;     public class mainTimeLine extends MovieClip{         private var myButtons:ButtonsObj=new ButtonsObj();         private var myHomePage:homePageObj;         public function mainTimeLine(){             trace("Dcument class Constructor");         InitApp();         }         private function InitApp(){             addChild(myButtons);             myHomePage=new homePageObj();         addChild(myHomePage);         }     } } [/as]

That's why I have created InitApp function separately instead of doing that simple task in the constructor itself. we are simply clubbing similar code in a condensed form. So, we have successfully finished our goal. This is a very simple example, but we can extend it to higher level complexity also.

   

Above sample is my creation with full ActionScript. This way, We can recreate most of the authoring time animations in run time with Script. If we want authoring time frame level animation, we can do it on a seperate file, and we can load it as an external asset. And, what real performance issue in Object Level programming is we can dispose off all the Removed Objects including their internal assets. Here I didn't use that function to be simpler. In each removal of homePageObj object, we can execute it's public function like this : homePageObj.disposeOff(), which removes all the graphics and texts of its owncontent.


making objects to talk

step4:Object Communication

Inside that homePageObj.as again I have suppressed a piece of code. Before showing it, I will tell you the situation. What I am doing to create the old sample effect is creating new homePageObj object on every click event and adding that page to the mainTimeLine object. What happens after a thousand clicks? A pile of thousand homePageObjs on the stage! We need to remove the old content from the stage before or after the Tweeen Sequence. if we did it before starting new Sequence, It would be easy for us, But it will leave a blank screen at the begining of the animation. We can do it after the second Tween Finished by assgning a handle for Tween_finish Event. We can calculate Root Document childs. In the standard scene only two members should be there inside the mainTimeLine(Stage). One is ButtonsObj, a mandatory existence. And then only one of the two pages , either the Home page or the About page. Inside that handler function we can check the condition and If it is the Third element, We will remove the second element, like this:

[as]         private function handleMoveToCenterTweenFinishEvent(arg_Event:TweenEvent):void{             var leftscaleXTween:Tween = new Tween(sprLeftPage, "scaleX", Regular.easeOut, num_RESIZE_SCALE_RATIO_START_obj, num_RESIZE_SCALE_RATIO_LIMIT_obj, 0.5, true);             var leftscaleYTween:Tween = new Tween(sprLeftPage, "scaleY", Regular.easeOut, num_RESIZE_SCALE_RATIO_START_obj, num_RESIZE_SCALE_RATIO_LIMIT_obj, 0.5, true);             var leftYTween:Tween = new Tween(sprLeftPage, "y", Regular.easeOut, sprLeftPage.y, (stage.stageHeight/2)-(num_LeftPageHeight_Obj/2), 0.5, true);             var rigtscaleXTween:Tween = new Tween(sprRigtPage, "scaleX", Regular.easeOut, num_RESIZE_SCALE_RATIO_START_obj, num_RESIZE_SCALE_RATIO_LIMIT_obj, 0.5, true);             var rigtscaleYTween:Tween = new Tween(sprRigtPage, "scaleY", Regular.easeOut, num_RESIZE_SCALE_RATIO_START_obj, num_RESIZE_SCALE_RATIO_LIMIT_obj, 0.5, true);             var rigtYTween:Tween = new Tween(sprRigtPage, "y", Regular.easeOut, sprRigtPage.y, (stage.stageHeight/2)-(num_LeftPageHeight_Obj/2), 0.5, true);         rigtYTween.addEventListener(TweenEvent.MOTION_FINISH,handleScaleToCenterTweenFinishEvent);         }         private function handleScaleToCenterTweenFinishEvent(arg_Event:TweenEvent):void{             if(mainTimeLine(this.parent).numChildren>2){                 mainTimeLine(this.parent).removeChildAt(1);             }         } [/as]

Removing of Second Child is ok, but how to activate buttons? we cannot execute the private function of ButtonsObj from here. We are inside the homePageObj! I can easily change that function as public with single stroke. But, I took an intuitive way in this little demo to tell you about object level communication, which is very usefull while building larger projects, where you cannot simply make such functions public. How it will be if the homePageObj give a hint to ButtonsObj that , "I have finished my Tween Event Chain. Now You can activate your Button Childs", and the ButtonsObj felt the tickle in it's ribs and responds in a way like, "It's OK! I am doing it right now, and next time don't tickle me that much.", and simply does it's duty of activating it's Button Childs. That can be achieved with dispatching and handling our own CustomEvents. AS3 made Event Dispaching very very easy. First of all we need to write a CustomEvent class by extending flash.events.Event. It is very simple in it's comstructon. Except the First Argument 'type', all the other properties are optional. We need not to worry about them. Constructor function deals with initialization of Event with that argument, that'as all!

[as] /*PageEvent.as*/ package com.pageevents{     import flash.events.*;     // A class representing the custom "PageEvent" event     public class PageEvent extends Event {         // A constant for the "PageEvent" event type         public static const HOMEPAGE_COMPLETE:String = "homePageReady";                // a message to pass om as  an instruction or state maintenance string         public var msgStr:String = "none";                // Constructor         public function PageEvent (type:String,bubbles:Boolean = false,cancelable:Boolean = false,msgStr:String = "none") {             // Pass constructor parameters to the superclass constructor             super(type, bubbles, cancelable);             // Remember the PageEvent's state so it can be accessed within             // PageEvent.HOMEPAGE_COMPLETE listeners             this.msgStr = msgStr;         }         // Every custom event class must override clone( )         public override function clone( ):Event {             return new PageEvent(type, bubbles, cancelable, msgStr);         }         // Every custom event class must override toString( ). Note that         // "eventPhase" is an instance variable relating to the event flow.         public override function toString( ):String {             return formatToString("PageEvent", "type", "bubbles","cancelable", "eventPhase", "msgStr");         }     } } [/as]

This is enough. You can use it in your work also by changing name and optional msgStr parameter. You can add any number of type constants, which you will give as type argument while dispatching the Event.Now, In tthat handleMoveToCenterTweenFinishEvent function in homePageObj class I have added one more command after the last Tween command. It is it's TweenComplete Event handler.In that function, I am simply dispatching our CustomEvent.

[as]      import com.pageevents.PageEvent; //in the imports section             rigtYTween.addEventListener(TweenEvent.MOTION_FINISH,handleScaleToCenterTweenFinishEvent);         //in the handleMoveToCenterTweenFinishEvent function                }         private function handleScaleToCenterTweenFinishEvent(arg_Event:TweenEvent):void{             trace("STEP 006: Second Scaling Tween Finished");             //mainTimeLine(this.parent)             dispatchEvent(new PageEvent(PageEvent.HOMEPAGE_COMPLETE,true,false,String("ok")));         } //as the last private function inside the class range                [/as]

As I told you that If we are using any object with new type we need to import it's calss. I did the same thing here in imports section to make it to work.Now, I am going to ButtonsObj. Even though We added the dispatchEvent( command, It won't fire automatically in run time. You need to prompt homePageObj to dispatch that CustomEvent, when that event happened in run time. We need to add that EventListener before or after adding homePageObj to stage DisplayList. Naturally, like all the other EventListeners, you need to write a EventHandler function. Now the modified code will look like this:

[as]     import com.pageevents.PageEvent; //in imports section            private function handleHomeButtonClickEvent(arg_Event:MouseEvent):void{             suppressButtons();             myHomePage=new homePageObj();             myHomePage.addEventListener(PageEvent.HOMEPAGE_COMPLETE, HANDLE_HOMEPAGE_PAGEEVENT_COMPLETE_EVENT);             mainTimeLine(this.parent).addChild(myHomePage);         } //modified the old function                private function HANDLE_HOMEPAGE_PAGEEVENT_COMPLETE_EVENT(arg_Event:PageEvent){             if(mainTimeLine(this.parent).numChildren>2){                 mainTimeLine(this.parent).removeChildAt(1);             trace("STEP 007: Old homePahgeObject Removed");                            }         activateButtons();         } //added the Handler function        [/as]

The journey is finished. Let us relax, and retrospect what we learnt. We have successfully created a Document class, that will pe paralel to the stage instance. We also created a default interface containing two buttons and activated them to do their tasks. We made it so independent that it can take care all the responsibillties in run time looking for guidelines from within it's own infrastructure. And, we successfully started the First Tween in Tween Event Chain. We have provided all the regulations to that object to go on it's mission as we defined it to do. More important, we made our objects to commnicate themselves to do their Team Work in a seamless way. As most of our Development Projects are repeatedly using these basic things, we learnt 99.9%, Right? To assimilate all the knowledge at one place, I have provided a zip of all the files. You can get all of them from here -> I have provided only code files. You cann create a blank flash file and just paste "mainTimeLine" in it's class property field. That will do the remaining task.

General Discussion

Building a Flash Website  fully with ActionScript is only a playfull challenge. Don't take it as a serious thing. I know some things can't do with ActionScript. Filters are one such thing. Scripted filters are not looking so stunning when compared to the filters which are created at authoring time, though I have passed all the arguments very precisely. And, some times you must need TimeLine frame Tweens, to show cartoon like animating display. But, they are minor things when you can handle 80% or 90% of the site maintenance with ActionScript. You can see yourself that Performance was surely improved with Impressive ActionScript knowledge.

THIS MAY COME AND THAT MAY GO, BUT FLASH GOES ON FOREVER