You are basically creating a new BitmapData
object each frame - REALLY BAD. You don't clean up older frames - DOUBLE REALLY BAD. Can't emphasize enough. You need one Bitmap
object, and one BitmapData
object (and one Rectangle
object too) to make a working sprite. Imagine you'd get 1000 balls, each making a bitmap per frame - your game will crash too soon. But, if each of them balls will have a local bitmap, everything should run smoothly enough.
There is another caveat I've hit when making me sprite sheets, copyPixels()
approach works if there aren't many objects on the screen, if you cross a certain threshold, you'd better make one BitmapData
object for each frame of your animation, and just change bitmapData
links of those bitmaps your sprites have each frame.
public class Ball extends MovieClip {
private static var spriteSheet:BitmapData; // first, why storing a Bitmap if you don't need it be moving?
private static var spriteArray:Vector.<BitmapData>; // This will store split spritesheet
private var bitmap:Bitmap; // this will be displaying proper frame
private var currentFrame:int; // what frame are you displaying
public static function initialize():void {
// loading static assets should better be made in a static function
if (!spriteSheet) {
var loader:Loader = new Loader();
loader.contentLoaderInfo.addEventListener(Event.COMPLETE, onLoadComplete);
loader.load(new URLRequest("Ball.png"));
}
}
public function Ball() {
bitmap=new Bitmap(); // null bitmap is displayed
addChild(bitmap);
currentFrame=0;
addEventListener(Event.ENTER_FRAME, onFrameLoop,null,0,true); // weak listener
// to not hog memory if you'd create and remove balls
}
private function onFrameLoop(e:Event)
{
switchFrame();
}
private function switchFrame()
{
if (!spriteArray) return; // oops, not initialized
currentFrame++;
if (currentFrame>=spriteArray.length) currentFrame=0;
bitmap.bitmapData=spriteArray[currentFrame]; // voila. Now this particular Ball
// will display the proper BitmapData out of sliced sprite sheet.
}
private static function onLoadComplete(e:Event)
{
var loaderInfo:LoaderInfo = e.target as LoaderInfo;
spriteSheet = (loaderInfo.content as Bitmap).bitmapData; // store the bitmapdata
// now cut the loaded sprite sheet apart
var i:int=Math.floor(spritesheet.width/50); // how many frames are in there
var r:Rectangle=new Rectangle(0,0,50,50);
var p:Point=new Point(); // why making N identical points? Just make one
spriteArray=new Vector.<BitmapData>();
for (var j:int=0;j<i;j++) {
var bd:BitmapData=new BitmapData(50,50);
r.x=50*j; // update rectangle to cut next frame
bd.copyPixels(spriteSheet,r,p); // cut the frame in a new BitmapData
spriteArray.push(bd); // store the frame
}
// once this is complete, your sprite sheet is ready
}
}
}