Open weepy opened 10 years ago
In Ejecta, all images (JPG, PNG) and all Canvases are internally represented as RGBA with premultiplied alpha. If you hand over a 2D Canvas as a texture to WebGL, Ejecta may have to un-premultiply this Canvas. This is done on the CPU and probably quite slow for large textures (source).
Try to enable WebGL's UNPACK_PREMULTIPLY_ALPHA_WEBGL
mode and see if it makes a difference.
Ah that makes a lot of sense. I'll give that a go. Is that flag just unlocking a faster way of doing the same?
That flag instructs WebGL to load textures as RGBA with premultiplied alpha - which happens to be Ejecta's internal format for Images and Canvas2D, so there's no conversion needed when handing these over to WebGL.
Uploading a Canvas2D as a texture in WebGL still causes Ejecta to get the Canvas' pixel data (using glReadPixels()
) and creating a new texture with it, which is expensive.
We can't just share the Canvas2D FBO with WebGL, as the Canvas2D may be re-used for something else. Maybe there's a smarter way to handle this, but it's complicated enough as it is.
I would advise you to use Canvas2D for 2D stuff.
Hey thanks for the in depth explanation. I'll give the flag a go to see how it goes, but I think you're right that Canvas 2D is probably the best way to go. I was mostly seduced by the pixel shading filters that you can do with WebGL, but I can do without these for now.
Canvas2D also affords some nice optimisations by only updating stuff that changes which is useful for me.
On Sat, Mar 15, 2014 at 8:26 PM, Dominic Szablewski < notifications@github.com> wrote:
That flag instructs WebGL to load textures as RGBA with premultiplied alpha - which happens to be Ejecta's internal format for Images and Canvas2D, so there's no conversion needed when handing these over to WebGL.
Uploading a Canvas2D as a texture in WebGL still causes Ejecta to get the Canvas' pixel data (using glReadPixels()) and creating a new texture with it, which is expensive.
We can't just share the Canvas2D FBO with WebGL, as the Canvas2D may be re-used for something else. Maybe there's a smarter way to handle this, but it's complicated enough as it is.
I would advise you to use Canvas2D for 2D stuff.
Reply to this email directly or view it on GitHubhttps://github.com/phoboslab/Ejecta/issues/360#issuecomment-37737020 .
I just realized that we could use glCopyTexImage2D
to copy the canvas into a new texture for WebGL if there's no further processing needed. This should be faster than getting pixel data using glReadPixels
and re-uploading it. I'll try that sometime.
I had a look - it seems that PIXI is already using that mode :
PIXI.createWebGLTexture = function(texture, gl) {
...
gl.pixelStorei(gl.UNPACK_PREMULTIPLY_ALPHA_WEBGL, true);
....
}
We're finding that like for like WebGL is much faster than Canvas for our
purposed, except for the canvas => texture conversion. I wanted to try
out glCopyTexImage2D
- wondering if this is something I can try
easily (or not?)
Thanks
On Sun, Mar 16, 2014 at 3:45 PM, Dominic Szablewski < notifications@github.com> wrote:
I just realized that we could use glCopyTexImage2D to copy the canvas into a new texture for WebGL if there's no further processing needed. This should be faster than getting pixel data using glReadPixels and re-uploading it. I'll try that sometime.
Reply to this email directly or view it on GitHubhttps://github.com/phoboslab/Ejecta/issues/360#issuecomment-37760449 .
I'm finding that on the device, updating a [large] WebGL texture can cause the UI to block for about a second. It's about a millisecond on my Macbook/Chrome. Does it make sense for such a large discrepancy ?
FYI I'm calling PIXI.updateWebGLTexture.