diff --git a/components/script/dom/webglframebuffer.rs b/components/script/dom/webglframebuffer.rs index 4dddfb047a08..0211a0bc31fc 100644 --- a/components/script/dom/webglframebuffer.rs +++ b/components/script/dom/webglframebuffer.rs @@ -231,6 +231,7 @@ impl WebGLFramebuffer { _ => { *binding.borrow_mut() = None; + self.update_status(); None } }; @@ -245,6 +246,49 @@ impl WebGLFramebuffer { Ok(()) } + pub fn detach_renderbuffer(&self, rb: &WebGLRenderbuffer) { + let attachments = [&self.color, + &self.depth, + &self.stencil, + &self.depthstencil]; + + for attachment in &attachments { + let matched = { + match *attachment.borrow() { + Some(WebGLFramebufferAttachment::Renderbuffer(ref att_rb)) + if rb.id() == att_rb.id() => true, + _ => false, + } + }; + + if matched { + *attachment.borrow_mut() = None; + self.update_status(); + } + } + } + + pub fn detach_texture(&self, texture: &WebGLTexture) { + let attachments = [&self.color, + &self.depth, + &self.stencil, + &self.depthstencil]; + + for attachment in &attachments { + let matched = { + match *attachment.borrow() { + Some(WebGLFramebufferAttachment::Texture(ref att_texture)) + if texture.id() == att_texture.id() => true, + _ => false, + } + }; + + if matched { + *attachment.borrow_mut() = None; + } + } + } + pub fn target(&self) -> Option { self.target.get() } diff --git a/components/script/dom/webglrenderingcontext.rs b/components/script/dom/webglrenderingcontext.rs index 59f27aa31399..b67f524825f1 100644 --- a/components/script/dom/webglrenderingcontext.rs +++ b/components/script/dom/webglrenderingcontext.rs @@ -1280,6 +1280,20 @@ impl WebGLRenderingContextMethods for WebGLRenderingContext { if let Some(renderbuffer) = renderbuffer { handle_object_deletion!(self, self.bound_renderbuffer, renderbuffer, Some(WebGLCommand::BindRenderbuffer(constants::RENDERBUFFER, None))); + // From the GLES 2.0.25 spec, page 113: + // + // "If a renderbuffer object is deleted while its + // image is attached to the currently bound + // framebuffer, then it is as if + // FramebufferRenderbuffer had been called, with a + // renderbuffer of 0, for each attachment point to + // which this image was attached in the currently + // bound framebuffer." + // + if let Some(fb) = self.bound_framebuffer.get() { + fb.detach_renderbuffer(renderbuffer); + } + renderbuffer.delete() } } @@ -1291,6 +1305,18 @@ impl WebGLRenderingContextMethods for WebGLRenderingContext { Some(WebGLCommand::BindTexture(constants::TEXTURE_2D, None))); handle_object_deletion!(self, self.bound_texture_cube_map, texture, Some(WebGLCommand::BindTexture(constants::TEXTURE_CUBE_MAP, None))); + + // From the GLES 2.0.25 spec, page 113: + // + // "If a texture object is deleted while its image is + // attached to the currently bound framebuffer, then + // it is as if FramebufferTexture2D had been called, + // with a texture of 0, for each attachment point to + // which this image was attached in the currently + // bound framebuffer." + if let Some(fb) = self.bound_framebuffer.get() { + fb.detach_texture(texture); + } texture.delete() } } diff --git a/tests/wpt/metadata/webgl/conformance-1.0.3/conformance/misc/object-deletion-behaviour.html.ini b/tests/wpt/metadata/webgl/conformance-1.0.3/conformance/misc/object-deletion-behaviour.html.ini index 70c044382d17..8e2be3e1863d 100644 --- a/tests/wpt/metadata/webgl/conformance-1.0.3/conformance/misc/object-deletion-behaviour.html.ini +++ b/tests/wpt/metadata/webgl/conformance-1.0.3/conformance/misc/object-deletion-behaviour.html.ini @@ -165,3 +165,81 @@ [WebGL test #227: at (0, 0) expected: 0,255,0,255 was 255,0,0,255] expected: FAIL + [WebGL test #168: gl.getFramebufferAttachmentParameter(gl.FRAMEBUFFER, gl.COLOR_ATTACHMENT0, gl.FRAMEBUFFER_ATTACHMENT_OBJECT_NAME) should be [object WebGLRenderbuffer\]. Threw exception TypeError: gl.getFramebufferAttachmentParameter is not a function] + expected: FAIL + + [WebGL test #170: gl.getFramebufferAttachmentParameter(gl.FRAMEBUFFER, gl.COLOR_ATTACHMENT0, gl.FRAMEBUFFER_ATTACHMENT_OBJECT_NAME) threw exception TypeError: gl.getFramebufferAttachmentParameter is not a function] + expected: FAIL + + [WebGL test #171: gl.getFramebufferAttachmentParameter(gl.FRAMEBUFFER, gl.COLOR_ATTACHMENT0, gl.FRAMEBUFFER_ATTACHMENT_OBJECT_TYPE) threw exception TypeError: gl.getFramebufferAttachmentParameter is not a function] + expected: FAIL + + [WebGL test #187: gl.checkFramebufferStatus(gl.FRAMEBUFFER) should not be 36053.] + expected: FAIL + + [WebGL test #196: gl.getFramebufferAttachmentParameter(gl.FRAMEBUFFER, gl.COLOR_ATTACHMENT0, gl.FRAMEBUFFER_ATTACHMENT_OBJECT_NAME) should be [object WebGLTexture\]. Threw exception TypeError: gl.getFramebufferAttachmentParameter is not a function] + expected: FAIL + + [WebGL test #198: gl.getFramebufferAttachmentParameter(gl.FRAMEBUFFER, gl.COLOR_ATTACHMENT0, gl.FRAMEBUFFER_ATTACHMENT_OBJECT_NAME) threw exception TypeError: gl.getFramebufferAttachmentParameter is not a function] + expected: FAIL + + [WebGL test #199: gl.checkFramebufferStatus(gl.FRAMEBUFFER) should not be 36053.] + expected: FAIL + + [WebGL test #210: gl.getParameter(gl.ARRAY_BUFFER_BINDING) should be null. Was [object WebGLBuffer\].] + expected: FAIL + + [WebGL test #219: gl.getParameter(gl.ARRAY_BUFFER_BINDING) should be null. Was [object WebGLBuffer\].] + expected: FAIL + + [WebGL test #227: gl.getParameter(gl.ELEMENT_ARRAY_BUFFER_BINDING) should be null. Was [object WebGLBuffer\].] + expected: FAIL + + [WebGL test #230: gl.bufferData(gl.ARRAY_BUFFER, 1, gl.STATIC_DRAW) threw exception TypeError: Value is not an object.] + expected: FAIL + + [WebGL test #233: gl.bufferData(gl.ARRAY_BUFFER, 1, gl.STATIC_DRAW) threw exception TypeError: Value is not an object.] + expected: FAIL + + [WebGL test #244: gl.getVertexAttrib(1, gl.VERTEX_ATTRIB_ARRAY_BUFFER_BINDING) should be [object WebGLBuffer\]. Was null.] + expected: FAIL + + [WebGL test #245: gl.getVertexAttrib(2, gl.VERTEX_ATTRIB_ARRAY_BUFFER_BINDING) should be [object WebGLBuffer\]. Was null.] + expected: FAIL + + [WebGL test #246: gl.getVertexAttrib(3, gl.VERTEX_ATTRIB_ARRAY_BUFFER_BINDING) should be [object WebGLBuffer\]. Was null.] + expected: FAIL + + [WebGL test #247: getError expected: NO_ERROR. Was INVALID_ENUM : after evaluating: gl.deleteBuffer(b2);] + expected: FAIL + + [WebGL test #248: gl.getVertexAttrib(1, gl.VERTEX_ATTRIB_ARRAY_BUFFER_BINDING) should be [object WebGLBuffer\]. Was null.] + expected: FAIL + + [WebGL test #251: getError expected: NO_ERROR. Was INVALID_ENUM : after evaluating: gl.deleteBuffer(b1);] + expected: FAIL + + [WebGL test #253: getError expected: NO_ERROR. Was INVALID_ENUM : after evaluating: gl.bindFramebuffer(gl.FRAMEBUFFER, fbo)] + expected: FAIL + + [WebGL test #281: at (0, 0) expected: 255,0,0,255 was 0,0,0,0] + expected: FAIL + + [WebGL test #289: at (16, 0) expected: 0,255,0,255 was 0,0,0,0] + expected: FAIL + + [WebGL test #292: at (0, 0) expected: 0,255,0,255 was 255,0,0,255] + expected: FAIL + + [WebGL test #258: getError expected: NO_ERROR. Was INVALID_OPERATION : after evaluating: gl.bindFramebuffer(gl.FRAMEBUFFER, fbo)] + expected: FAIL + + [WebGL test #278: at (16, 16) expected: 0,0,0,0 was 9,0,0,0] + expected: FAIL + + [WebGL test #281: at (0, 0) expected: 255,0,0,255 was 0,0,0,255] + expected: FAIL + + [WebGL test #289: at (16, 0) expected: 0,255,0,255 was 0,0,0,14] + expected: FAIL +