As WebGL becomes more widely supported in browsers, we’re proud to announce that after working in collaboration with Mozilla, a shiny new WebGL renderer for EaselJS is now in early beta!
Following research, internal discussions, and optimizations, we’ve managed to pump out a renderer that draws a subset of 2D content anywhere from 6x to 50x faster than is currently possible on the Canvas 2D Context.
We thought about what we wanted to gain from a WebGL renderer, and narrowed it down to three key goals:
- Very fast performance for drawing sprites and bitmaps
- Consistency and integration with the existing EaselJS API
- The ability to fall back to Context2D rendering if WebGL is not available
Here’s what we came up with:
SpriteStage & SpriteContainer
Two new classes, SpriteStage and SpriteContainer, enforce restrictions on the display list to enable aggressively optimized rendering of bitmap content. This includes images, spritesheet animations, and bitmap text.
These new classes extend existing EaselJS classes (Stage and Container) and share the same API, so creating WebGL content is super simple if you’re familiar with EaselJS. Existing content using EaselJS can be WebGL-enabled with a few keystrokes.
This approach allows WebGL and Context2D content to be layered on screen, and mouse/touch interactions can pass seamlessly between the layers. For example, an incredibly fast game engine using WebGL rendering can be displayed under a UI layer that leverages the more robust capabilities of the Context2D renderer. You can even swap assets between a WebGL and Context2D layer.
Finally, WebGL content is fully compatible with the existing Context2D renderer. On devices or browsers that don’t support WebGL, your content will automatically be rendered via canvas 2D.
While it took some work to squeeze every last iota of performance out of the new renderer, we’re really happy with this new approach. It allows developers to build incredibly high performance content for a wide range of devices, and also leverage the extremely rich existing API and toolchain surrounding CreateJS. Below, you’ll find a few demos that show off its capabilities.
A very popular (though limited) benchmark for web graphics is Bunnymark. This benchmark simply measures the maximum number of bouncing bunny bitmap sprites (try saying that 5 times fast) a renderer can support at 60fps.
Example: Benchmark (updated for StageGL)
See the Pen CreateJS: StageGL Benchmark by CreateJS (@createjs) on CodePen.0
The following table compares Bunnymark scores using the classic Context2D renderer and the new WebGL renderer. Higher numbers are better.
|2012 Macbook Pro, Firefox 26||900||46,000||51x|
|2012 Macbook Pro, Chrome 31||2300||60,000||26x|
|2012 Win 7 laptop, IE11 (x64 NVIDIA GeForce GT 630M, 1 GB VRAM)||1900||9800||5x|
|FxOS 220.127.116.11-prerelease (early 1.2 device)||45||270||6x|
|Nexus 5, Firefox 26||225||4400||20x|
|Nexus 5, Chrome 31||230||4800||21x|
Since these numbers show maximum sprites at 60fps, the above numbers can increase significantly if a lower framerate is allowed. It’s worth noting that the only FxOS device we have in house is an early FxOS 1.2 device with a relatively low-powered GPU, yet we’re still seeing significant performance gains.
Example: Sparkles Benchmark
This very simple demo was made to test the limits of how many particles could be put on screen while pushing the browser to 24fps.
Sparkles Benchmark (update for StageGL)
See the Pen CreateJS: WebGL Sparkles by CreateJS (@createjs) on CodePen.0
Example: Planetary Gary
We often use the Planetary Gary game demo as a test bed for new capabilities in the CreateJS libraries. In this case, we retrofitted the existing game to use the new SpriteStage and SpriteContainer classes for rendering in WebGL.
This was surprisingly easy to do, requiring only three lines of changed or added code, and demonstrates the ease of use, and consistency of the new APIs. It’s a particularly good example because it shows how the robust feature set of the Context2D renderer can be used for user interface elements (ex. the start screen) in cooperation with the superior performance of the WebGL renderer (ex. the game).
Even better, the game art is packaged as vector graphics, which are drawn to sprite sheets via the Context2D renderer at run time (using EaselJS’s SpriteSheetBuilder), then passed to the WebGL renderer. This allows for completely scaleable graphics with tiny file size (~85kb over the wire) and incredible performance!
We’ve posted a public preview of the new WebGL renderer to allow the community to take it for a test drive and provide feedback. Soon it will be included it in the next major release.
Follow @createjs on twitter to stay up to date with the latest news and let us know what you think — thanks for reading!
73,500 particles on the Sparkle Benchmark on my iMac. Not bad at all.
22 000 bunnies at 60fps (better than pixijs) and 64 000 particles on the Sparkle Benchmark on my Mac Mini. I’m happy to see a WebGL renderer on easeljs.
Pingback: CreateJSがWebGLを公式にサポート！爆速になったCreateJSのパフォーマンスを検証してみた | ICS LAB
Really like what I’m seeing. Looks like a lot of thought went into this implementation, and is something that can be built upon. Good job!
Pingback: 【誰得】秒速40億円稼ぐことも夢ではない！与沢翼が秒速で稼ぐウェブサービス | gori.me（ゴリミー）
When you say “Existing content using EaselJS can be WebGL-enabled with a few keystrokes” is this strictly true? Won’t I need to go and update all of my Containers to use SpriteContainer? Is this a simple case of a find and replace?
That’s the philosophy, since SpriteContainer was built to match the API of Container. Heads up that SpriteStage cannot render Containers, but SpriteContainers instead (and a few other classes, like Bitmap, Sprite, BitmapText).
There are some restrictions enforced on SpriteContainer to ensure that the content is well suited for WebGL rendering (in fact, that’s the purpose of SpriteContainer: to enforce those restrictions), so as long as your content meets that criteria, you should be good to go.
Check out our Technical Intro for more info: http://blog.createjs.com/webgl-easeljs-a-technical-intro/
Currently Chrome support for WebGL is a bit shaky (https://support.google.com/chrome/answer/1220892?hl=en) compared to firefox. E.g. these may perfectly work on firefox but not work in chrome, depending on the OS and graphics card:
Can we expect falling back to canvas (context 2d) to work in Chrome? I mean saying that the fallback will work where WebGL is not available is very general – WebGL can partially work/fail varying by WebGL feature, it is not a monolithic available or not available situation. So how will easel.js determine whether WebGL is available or not?
new webGL in createjs… it will be super. Hope you will get it done soon !!!!
Pingback: Starling, PixiJS, and CreateJS
Pingback: Using CreateJs: PreloadJS, SoundJS, and TweenJS | WarWebDev
Pingback: Using CreateJs: PreloadJS, SoundJS, and TweenJS - InfoLogs
Pingback: Using CreateJs: PreloadJS, SoundJS, and TweenJS | base38.co.uk
Pingback: Using CreateJs: PreloadJS, SoundJS, TweenJS - Fire Bull Design Studio
Pingback: Using CreateJs: PreloadJS, SoundJS, and TweenJS - IWCN Official Blog | Indoreators Web Creations Network P. Ltd.
Hello! When can I use the new webGL???
@Jackson21, you can use the WebGL renderer today in the latest libs in the EaselJS git repo
@matan, EaselJS’s WebGL rendering is not meant to provide or support 3D WebGL.
What is does, is allow developers to render 2D EaselJS content via WebGL for a performance gain.
You may also be interested in Blend4Web which is designed for 3D webdesign tasks.
Pingback: Canvas 2Dライブラリを作ろうとして感じたこととDisplayObject « イナヅマTVログ
Pingback: WebGL Support in EaselJS + Mozilla Sponsors CreateJS - gskinner blog
Thanks for the article. I am really enjoying using easelJS, and the createJS suite. I just have some framerate issues sometimes, and not sure what is causing it..
Is there a reliable way to check at runtime if the GPU is being used or not? Like Pixijs has a log which tells you if software or hardware rendering is currently being used. I’m trying to debug an issue with spritesheet animations.
We are experiencing very variable framerates in our game on desktop… And although it has a large amount of assets in it: (3 spritesheets 2024×2024 pixels big).. animations which need to play at the same time are always on the same spritesheet.
Sometimes it runs at 60fps, sometimes at 10-14fps, but when that happens, switching tab away and tabbing back to the game puts the framerate back to 60fps.. Weird!
Pingback: 意地でもCreateJSでWebGLを使ってみよう―CreateJS勉強会/川勝発表資料 – ICS LAB
Hi there! It’s hard to come by anything interesting on this subject (that is not overly simplistic), because everything related to 3D seems rather difficult. You however sound like you know what you’re talking about :) Thank you for spending your time writing some good content for us!