13 Replies Latest reply on Feb 24, 2012 9:31 AM by Flex harUI

    AS3 Preloader (without Flex SDK or Flash CS)

    eprevot123 Level 2

      I use FlashBuilder but not the Flex SDK, just pure Actionscript. I have a swf application that is too long to download, so I would like to display a progressbar while the swf is being downloaded from the host.

      My main class is a Sprite. I tried to add a progressEvent.PROGRESS listener on root.loaderInfo in the constructor of my main Sprite, but then a PROGRESS event is fired only when all the swf is downloaded. Useless.

       

      On a Flex project, you have a Preloader included in the main Application, that displays a progressBar while the application swf is being downloaded from the server and initializing.

      That's what I want.

       

      Does someone understand how the Flex Preloader works ?

      Do you know how to do that without Flex SDK ?

        • 1. Re: AS3 Preloader (without Flex SDK or Flash CS)
          Flex harUI Adobe Employee

          The main class needs metadata on it specifying the class to use as the preloader class.  See the source code of Application.as for an example.

           

          Keep in mind that when testing from file:// (instead of http://) the file is loaded in one huge chunk so you will get fewer progress events.  That’s when the Flex preloader says “downloading...”.  When it says “initializing” the SWF is already downloaded, and we have broken the initialization of the first screen of components into a minimum of 3 stages and spread it across multiple frames in order to allow the progress bar to be updated.  If initialization is a problem for you, you will have to break it up across multiple frames somehow.

          1 person found this helpful
          • 2. Re: AS3 Preloader (without Flex SDK or Flash CS)
            eprevot123 Level 2

            Thank you, I don't know why there is a link to this post in the middle of your sentence but I understood you say to look to some metadata in Application.as and I found the Frame/factoryClass.

            What I understand : with this tag the Application is on frame 2, and SystemManager is on frame 1. The SystemManager class displays the preloader and instanciates the Application when it downloaded.

             

            SystemManager is complicated but in combination with this blog post, I managed to create my own factoryClass to display the preloader when the swf starts downloading.

            • 3. Re: AS3 Preloader (without Flex SDK or Flash CS)
              eprevot123 Level 2

              When I use the profiler to inspect my application, I can see my Preloader class stays instanciated when the application is completely downloaded and the currentFrame is no longer on the Preloader class.

              I removed all listeners and cleared the properties, but it seems my Preloader class is still referenced by the Stage.

              I don't need the Preloader after initialization, how can I free it to the GC ?

              • 4. Re: AS3 Preloader (without Flex SDK or Flash CS)
                Flex harUI Adobe Employee

                Did you call removeChild?  What is the reference from the Stage?

                • 5. Re: AS3 Preloader (without Flex SDK or Flash CS)
                  eprevot123 Level 2

                  1) In my Preloader class, I don't call the stage anywhere, I don't add the Preloader instance to anything, I think it is automatically done when I use the [Frame(factoryClass="Preloader")] metadata tag.

                  When the download is complete, I add the main application this way :

                   

                  var mainClass:Class = Class(getDefinitionByName("MainApplication"));

                  if(mainClass)

                  {

                    var app:Sprite = new mainClass();

                    stage.addChild(app);

                  }

                   

                  2) I don't know what is the reference from the Stage, I just see there is one in the profiler (if I understand what the profiler shows, that's not sure !)

                  Here is the way I use the profiler :

                  - click on "take memory snapshot" button

                  - double-click on Preloader line in the Memory Snapshot list

                  - see the only object property (progress bar) is null

                  - expand the preloader instance and see 1 path to the stage as "child0" (child1 is MainApplication)

                  • 6. Re: AS3 Preloader (without Flex SDK or Flash CS)
                    eprevot123 Level 2

                    I didnt understand we have to manually remove the preloader from the stage, since it is automatically added. I thought going to nextFrame would remove the preloader from the stage.

                     

                    So when loading is complete, I display the MainApplication on the next frame, and remove the preloader from the stage.

                    But in the profiler I still have an instance of the Preloader... when I expand it, there is nothing more, I just see "Preloader (1path)" and "GC Root=Yes" (don't know what it means)

                    • 7. Re: AS3 Preloader (without Flex SDK or Flash CS)
                      eprevot123 Level 2

                      I still don't know why the Preloader is not gargbage collected. I don't see where it could be referenced and the FlashBuilder Profiler won't tell me.

                       

                      Does someone know if it's related to the Frame[classFactory] metadata tag ?

                      Can the classFactory be deleted ?

                      • 8. Re: AS3 Preloader (without Flex SDK or Flash CS)
                        Flex harUI Adobe Employee

                        Make sure the preloader isn’t listening to events from somewhere.  If you can reproduce in a simple test case, post it.

                        • 9. Re: AS3 Preloader (without Flex SDK or Flash CS)
                          eprevot123 Level 2

                          Here is the Preloader class :

                           

                          public class Preloader extends MovieClip

                          {

                            public function Preloader()

                            {

                              super();

                              stop();

                           

                              if (root && root.loaderInfo)

                              root.loaderInfo.addEventListener(Event.INIT, initHandler, false, 0, true);

                            }

                           

                            private function initHandler(e:Event):void

                            {

                              root.loaderInfo.removeEventListener(Event.INIT, initHandler);

                           

                              displayProgressBar();

                           

                              root.loaderInfo.addEventListener(ProgressEvent.PROGRESS, progressHandler, false, 0, true);

                              root.loaderInfo.addEventListener(Event.COMPLETE, completeHandler, false, 0, true);

                            }

                           

                            private function progressHandler(e:ProgressEvent):void

                            {

                              displayProgressBar(e.bytesLoaded, e.bytesTotal);

                            }

                           

                            private function completeHandler(e:Event):void

                            {

                              root.loaderInfo.removeEventListener(ProgressEvent.PROGRESS, progressHandler);

                              root.loaderInfo.removeEventListener(Event.COMPLETE, completeHandler);

                              removeProgressBar();

                           

                              nextFrame();

                           

                              var mainClass:Class = Class(getDefinitionByName("MainApplication"));

                              if(mainClass)

                             {

                                var app:Sprite = new mainClass();

                                stage.addChild(app);

                              }

                           

                              stage.removeChild(this);

                            }

                           

                            private function displayProgressBar(bytesLoaded:int = -1, bytesTotal:int = -1):void

                            {

                             // add a progressBar and display the progress

                            }

                           

                            private function removeProgressBar(bytesLoaded:int = -1, bytesTotal:int = -1):void

                            {

                             // remove the progressBar

                            }

                           

                          }

                          • 10. Re: AS3 Preloader (without Flex SDK or Flash CS)
                            eprevot123 Level 2

                            I still don't know how I could do to not have the Preloader class stucked in memory when the MainApplication is loaded and displayed.

                            The code is still the one I posted above.

                             

                            The FlashBuilder Profiler shows :

                            Preloader (1 Path), not expandable, no property, GC Root=YES, and it holds 4% of the memory.

                            • 11. Re: AS3 Preloader (without Flex SDK or Flash CS)
                              Flex harUI Adobe Employee

                              It looks like this Preloader class is the root class for the SWF, so no, it will not get GC’d.

                              • 12. Re: AS3 Preloader (without Flex SDK or Flash CS)
                                eprevot123 Level 2

                                MainApplication is the main Sprite of the project, what I thought to be the root class.

                                Preloader is the factoryClass (Frame tag on MainApplication class).

                                So you are saying the classFactory of the main Sprite can't be GC'd ?

                                • 13. Re: AS3 Preloader (without Flex SDK or Flash CS)
                                  Flex harUI Adobe Employee

                                  Yes.  With metadata, the factoryClass is the root, not the class it annotates.