[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: [Public WebGL] Addition to WebGLContextLostEvent wrt extensions




The WebGL app needs to be able to control when the context is usable again once it's lost. Not the browser.  Consider the following code.


for (var ii = 0; ii < 1000; ++ii) {
  var tex = ctx.createTexture();
  ctx.bindTexture(ctx.TEXURE_2D, ctx);
  ctx.texImage2D(ctx.TEXTURE_2D, 0, someArrayOf16x16Imgs[ii]);
};

Assume that at ii = 120 the context is lost.

Assume that at ii = 140 the context is restored.

If the context magically restores itself on WebGLContextRegainedEvent or WebGLContextRestoredEvent then how do I know that textures 120 through 139 are bad and how do I now get rid of 140 to 999 so I can restart my app by calling my init function?

It seems like instead once the context is lost it's an unusable context and should stay unusable until the WebGL app decides it's in a state where it ready to recover.

Suggestion:

*) WebGLContextLostEvent  : Good, useful

*) ctx.isContextLost() : Good, also useful. Let's me distinguish between gl.getError() == gl.INVALID_OPERATION as a true error and as a response to a lost context. Personally I'd prefer gl.getError() return gl.CONTEXT_LOST but that would require getting the OpenGL ES people to add an enum where as ctx.isContextLost() let's us avoid asking for the new enum value to be added.

*) WebGLContextRegainedEvent or WebGLContextRestoredEvent : Bad (by name).  The context should not auto-restore

*) WebGLContextResetableEvent: Good. Means you can now call context.reset() or some other function

*) context.reset() : Good, lets the WebGL app have control over recovery.  It's only valid to call when both the context has been lost AND the WebGLContextResetableEvent has been received.

Does this make sense?

To confuse the matter further there is this following issue.

In the OpenGL C API, most programs may handle lost context but they don't stop running. OpenGL just starts generating lots of errors which generally get ignored by C programs.

In WebGL though we've boxed somethings. The code need to keep running and just generate errors during a lost context. The issue that comes up is the boxing of getActiveAttrib and getActiveUniform.

If I have code like this

// Get my uniforms
var uniformsByName = {}
var numUniforms = ctx.getProgramParameter(program, ctx.ACTIVE_UNIFORMS);
for (var ii = 0; ii < numUniforms; ++ii) {
  var uniformInfo = ctx.getActiveUniform(program, ii);
 
// the following line will throw if lost context comes in after
  // getProgramParameter because uniformInfo will
  // be null and therefore uniformInfo.name will
  // cause a _javascript_ exception.
  uniformsByName[uniforimInfo.name] = uniformInfo; 
}


The suggested solution is that ctx.getActiveUniform has to return some kind of dummy WebGLActiveInfo if the context is lost.

This same issue is true in other places.  ctx.readPixels must always turn a WebGLArray even if the context is lost.

ctx.getParameter, ctx.getBufferParameter, ctx.getFramebufferAttachmentParameter, ctx.getShaderParameter, ctx.getUniform, get.getVertexAttrib all have this issue as well.

The C API works because no objects are returned. The C passes in some memory pointer an either a value gets filled in or it doesn't so the C will continue on.  But most WebGL code that expects an object to be returned must always get an object. The only exceptions off the top of my head might be the create functions like createTexture, createBuffer etc though even those are problematic. If the user can use them as property names or array indices then returning null during lost context could be an issue as well.