A BlitMask is basically a rectangular Sprite that acts as a high-performance mask for a DisplayObject by caching a bitmap version of it and blitting only the pixels that should be visible at any given time, although its bitmapMode can be turned off to restore interactivity in the DisplayObject whenever you want. When scrolling very large images or text blocks, BlitMask can greatly improve performance, especially on mobile devices that have weaker processors. (UPDATE: a Flex-friendly version of BlitMask called FlexBlitMask was added in version 0.44)

Think of it like a window through which you see the object.

Interactive example

Get Adobe Flash player

Over 1000% performance improvement?

When a simple tween of a large TextField was tested on an iPhone 3GS, the frame rate jumped from 3fps using a regular mask to 55fps using BlitMask. On the iPad, we signifcantly increased the scrolling area so that more pixels needed to be rendered on each frame, but there was still a massive increase in the frame rate from 3fps to almost 29fps. See the video below (special thanks to Jonah Simon for the video).

Watch the BlitMask Demo on an iPad and iPhone

On an Android-based phone (Droid 2) the fps jumped from 6.5 to 46.5. The improvements are less dramatic on regular computers because they have much beefier processors, but I ran a slightly different test with a heavier load on an Intel Core i3 computer and had the fps jump from 5fps with a regular mask to 59fps with BlitMask, so the 1000% improvement can still happen on regular computers in certain scenarios.

Of course your mileage will vary - the bigger, more complex your object (especially if it has text and vectors), the bigger the improvement you'll see with BlitMask. And keep in mind that you'll only see a speed improvement when bitmapMode is on. When it's off, BlitMask just acts like a standard mask in Flash. The benefit of turning bitmapMode off is that your object (the target DisplayObject that's being masked) will have its interactivity restored, meaning MouseEvents can be triggered inside that target like rollovers, clicks, etc. A common technique would be to turn bitmapMode on while you're scrolling/animating the object (to maximize performance), and then turn it back off afterwards. There's even convenient enableBitmapMode() and disableBitmapMode() methods that you can connect to your tweens like

var myBlitMask:BlitMask = new BlitMask(mc, 50, 50, 200, 200);, 2, {x:100, y:200, onStart:myBlitMask.enableBitmapMode, onUpdate:myBlitMask.update, onComplete:myBlitMask.disableBitmapMode});


  • Excellent scrolling performance
  • You don't need to do anything special with your target DisplayObject - move/scale/rotate it however you please and then update() the BlitMask and it syncs the pixels. The BlitMask basically sits on top of the DisplayObject in the display list and you can move it independently too if you want.
  • Use the BlitMask's scrollX and scrollY properties to move the target DisplayObject inside the masked area. For example, to scroll from top to bottom over the course of 2 seconds, simply do:
    myBlitMask.scrollY = 0;, 2, {scrollY:1});
  • BlitMask accommodates rotated and scaled content whereas scrollRect doesn't (well, it does, but as you can see in the example above, the rectangular masked area rotates with the target and scaling affects it too).
  • Use the wrap property to make the bitmap wrap around to the opposite side when it scrolls off one of the edges (only in bitmapMode of course), as though the BlitMask is filled with a grid of bitmap copies of the target.
  • Turn smoothing on to enable sub-pixel rendering (better quality in most situations) or turn it off for maximum performance.
  • You can toggle the bitmapMode to get either maximum performance or interactivity in the target DisplayObject anytime. (some other solutions out there are only viable for non-interactive content)
  • MouseEvents are dispatched by the BlitMask, so you can listen for clicks, rollovers, rollouts, etc.

How exactly does it work?

One of the most processor-intensive tasks for the Flash Player is calculating which pixels need to change on the screen and then rendering them. So let's say you've got a TextField that's 2,500 pixels wide and 2,500 pixels tall (that's a lotta text). Whenever you move it even one pixel, Flash must process all 6,250,000 pixels and figure out where they'd be on the new frame (even the ones that are off screen) and then display them appropriately. That requires tons of work, most of which is totally unnecessary when you're only wanting to display a small fraction of those pixels inside a masked area. BlitMask allows Flash to just worry about the pixels inside the masked area.

When in bitmapMode, the BlitMask sets the target's visible property to false so that Flash doesn't need to worry about rendering its pixels. It takes a bitmap capture of the target and copies only the necessary pixels onto the rectangular area of its (the BlitMask's) graphics layer. You can move the target wherever you want and then simply call the BlitMask's update() method to have it look at where the target is and copy the necessary pixels into itself (refreshing the display to synchronize with the target's position). When the target changes its rotation or scale, the internal bitmap must be recaptured (try to avoid this if possible because it degrades performance). BlitMask will automatically check to see if the scale or rotation changed since the last update() and if so, it'll recapture the bitmap. You can force a recapture using the 2nd parameter of the update() method, like update(null, true).

When bitmapMode is set to false, BlitMask automatically turns on the target's visible property and sets its mask property to the BlitMask. Consequently, performance degrades but interactivity is restored to the target. Visually things should be relatively seamless.


View the full ASDocs here.

Sample AS3 code

import com.greensock.*;

//create a 200x200 BlitMask positioned at x:20, y:50 to mask our "mc" object and turn smoothing on:
var blitMask:BlitMask = new BlitMask(mc, 20, 50, 200, 200, true);

//animate mc and make sure the BlitMask updates, 5, {x:-300, y:50, onUpdate:blitMask.update});

//or position mc at the top left of the BlitMask using the scrollX and scrollY properties
blitMask.scrollX = 0;
blitMask.scrollY = 0;

//tween the scrollY to make mc scroll to the bottom over the course of 3 seconds and then turn off bitmapMode so that mc becomes interactive:, 3, {scrollY:1, onComplete:blitMask.disableBitmapMode});

//or simply position mc manually and then call update() to sync the display:
mc.x = 350;

Video tutorial

Check out Carl Schooff's video tutorial covering BlitMask. It's a great starting point.

Hidden benefit: objects with filters tween smoother

Smooth animation isn't just about reducing the load on the CPU. Without BlitMask, if you apply a filter (i.e. GlowFilter, DropShadowFilter, etc.) to an object and then tween its coordinates slowly, you'll notice jerky movement because Flash only allows the object to render on whole pixel coordinates. However, with BlitMask and its smoothing feature, sub-pixel rendering is possible, making these types of animations significantly smoother visually. See the example below:

Get Adobe Flash player


  1. When should I NOT use BlitMask?
    It doesn't make much sense to use BlitMask when the target is smaller than the BlitMask or if you must maintain interactivity in child DisplayObjects even during scrolling/animation. While animating the scale or rotation of the target, there isn't benefit in using bitmapMode either because the internal bitmap would need to keep getting recaptured on each frame/render.
  2. Can I use BlitMask with ThrowPropsPlugin for better flick-scrolling performance?
    Absolutely. See the ThrowPropsPlugin page for more information about flick-scrolling. The interactive example there has been updated to use BlitMask.
  3. Can I use BlitMask in Flex?
    Sure, a Flex-friendly version of BlitMask is now available called FlexBlitMask that extends UIComponent instead of Sprite in order to be...well...Flex-friendly. See the ASDocs here.
  4. Can I animate the BlitMask itself?
    Definitely, but you shouldn't alter its rotation. Feel free to tween its x, y, width, and height properties. Doing so will automatically update() the BlitMask too.
  5. Wait, I thought Flash didn't work on iPads or iPhones - how did you do that?
    You can publish apps for iOS devices with Flash (which is what we did here for the tests) but you still can't view .swf files on web pages.
  6. I'm animating my target but it doesn't seem to be working. What's wrong?
    I bet you forgot to call update() each time you moved the target. For a tween, use the onUpdate like

    //don't forget the onUpdate, 3, {x:100, y:200, onUpdate:myBlitMask.update});
  7. Can't I just set the target DisplayObject's cacheAsBitmap property to true and get the same result? Why use BlitMask?
    If you set a DisplayObject's cacheAsBitmap property to true, Flash takes a bitmap capture of that object so that when you move it (only altering the x and/or y properties), the text and vectors don't need to be re-rasterized again before being rendered to the screen. However, Flash would still need to concern itself with extra pixels on every frame if you're masking them to only show a small portion of the area. BlitMask, however, only cares about that smaller masked area (after the initial capture of course) which alleviates Flash from having to even think about the extra pixels.
  8. Is the API locked-down or might it change?
    No changes are planned to the API right now, but this is a brand new tool and I'd consider it somewhat experimental at this point. I'm committed to making improvements and enhancements if the need arises as it gets out into the wild and folks provide feedback. So yes, there could definitely be some changes down the road. Please feel free to submit your feedback and suggestions.
  9. Do I have to purchase a license to use this code? Can I use it in commercial projects?
    You may use the code at no charge in commercial or non-commercial web sites, games, components, applications, and other software as long as end users are not charged a fee of any kind to use your product or gain access to it. If your client pays you a one-time fee to create the site/product, that's perfectly fine and qualifies under the "no charge" license. If multiple end users are charged a usage/access/license fee of any kind, please simply sign up for a corporate Club GreenSock membership which comes with a special commercial license granting you permission to do so. Click here for details. Club GreenSock members get several useful bonus plugins, classes, update notifications, SVN access, and more. Please see the licensing page for details on licensing.

Need help?

Feel free to post your question on the forums. You'll increase your chances of getting a prompt answer if you provide a brief explanation and include a simplified FLA file (and any class files) that clearly demonstrates the problem.


Version: 2.1.3 updated 2019-05-18




        By using GreenSock code, you agree to the terms of use.

        For an all-access pass to premium content

        Join Club GreenSock