views:

485

answers:

1

I'm trying to write some code to an animated images of squares on a Flex Canvas. There's something wrong with my code below because it becomes progressively slower. I assume I'm supposed to clear the old squares or something.

What am I doing wrong below?:

<?xml version="1.0" encoding="utf-8"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" creationComplete="init();">
<mx:Script>
<![CDATA[
public var ticker:Timer;

    public function init():void {

     ticker = new Timer(10);

     // This implements the timerEvent
     ticker.addEventListener(TimerEvent.TIMER, update);
     ticker.start();

     draw();
    }

    public function update(evt:TimerEvent):void {
     draw();
    }

    public function draw():void {
     var squareSize:uint = 10;
     var square:Shape = new Shape();

     square.graphics.beginFill(0xFFFFFF, 1.0);
     square.graphics.drawRect(0, 0, myCanvas.width, myCanvas.height);

     var i:int;
     for (i = 0; i < myCanvas.height / squareSize; i++) {
      var j:int;
      for (j = 0; j < myCanvas.width / squareSize; j++) {
       if (Math.random() < 0.5) {
        square.graphics.beginFill(0x000000, 1.0);
        square.graphics.drawRect(j * squareSize, i * squareSize, squareSize, squareSize);
       }
      }
     }

     square.graphics.endFill();
     myCanvas.rawChildren.addChild(square);
    }
]]>
</mx:Script>

    <mx:Panel title="Random Squares" height="95%" width="95%" 
        paddingTop="5" paddingLeft="5" paddingRight="5" paddingBottom="5">

        <mx:Canvas id="myCanvas" borderStyle="solid" height="100%" width="100%">
        </mx:Canvas>

    </mx:Panel>
</mx:Application>
+2  A: 

You're adding an indefinite number of children to your display list, so you're definitely in performance trouble.

You can remove the old shapes before adding the new one

myCanvas.rawChildren.removeChildAt(0);
myCanvas.rawChildren.addChild(square);

You could also do away with the square entirely--note the Graphics.clear() call before drawing, though. Otherwise, the graphics object will fill up with data just like the display list is now.

public function draw():void {
    var squareSize:uint = 10;

    myCanvas.graphics.clear();
    myCanvas.graphics.beginFill(0xFFFFFF, 1.0);
    myCanvas.graphics.drawRect(0, 0, myCanvas.width, myCanvas.height);
    ...
        myCanvas.graphics.beginFill(0x000000, 1.0);
        myCanvas.graphics.drawRect(...)
    ...
    myCanvas.graphics.endFill();
}
Michael Brewer-Davis
Thanks! That worked. There was just one small typo in your second solution. This line: square.graphics.drawRect(0, 0, myCanvas.width, myCanvas.height);should read: myCanvas.graphics.drawRect(0, 0, myCanvas.width, myCanvas.height);
Paul Reiners