| Index: Source/core/html/canvas/WebGLFramebuffer.cpp
|
| diff --git a/Source/core/html/canvas/WebGLFramebuffer.cpp b/Source/core/html/canvas/WebGLFramebuffer.cpp
|
| index 106af406ac1a1603bac6d3ceb599113b0eccbacb..8827fcf94a0d9457385a235951992053984b0183 100644
|
| --- a/Source/core/html/canvas/WebGLFramebuffer.cpp
|
| +++ b/Source/core/html/canvas/WebGLFramebuffer.cpp
|
| @@ -54,8 +54,8 @@ namespace {
|
| virtual bool isSharedObject(WebGLSharedObject*) const override;
|
| virtual bool valid() const override;
|
| virtual void onDetached(WebGraphicsContext3D*) override;
|
| - virtual void attach(WebGraphicsContext3D*, GLenum attachment) override;
|
| - virtual void unattach(WebGraphicsContext3D*, GLenum attachment) override;
|
| + virtual void attach(WebGraphicsContext3D*, GLenum target, GLenum attachment) override;
|
| + virtual void unattach(WebGraphicsContext3D*, GLenum target, GLenum attachment) override;
|
|
|
| RefPtrWillBeMember<WebGLRenderbuffer> m_renderbuffer;
|
| };
|
| @@ -117,24 +117,24 @@ namespace {
|
| m_renderbuffer->onDetached(context);
|
| }
|
|
|
| - void WebGLRenderbufferAttachment::attach(WebGraphicsContext3D* context, GLenum attachment)
|
| + void WebGLRenderbufferAttachment::attach(WebGraphicsContext3D* context, GLenum target, GLenum attachment)
|
| {
|
| Platform3DObject object = objectOrZero(m_renderbuffer.get());
|
| if (attachment == GC3D_DEPTH_STENCIL_ATTACHMENT_WEBGL && m_renderbuffer->emulatedStencilBuffer()) {
|
| - context->framebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, object);
|
| - context->framebufferRenderbuffer(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT, GL_RENDERBUFFER, objectOrZero(m_renderbuffer->emulatedStencilBuffer()));
|
| + context->framebufferRenderbuffer(target, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, object);
|
| + context->framebufferRenderbuffer(target, GL_STENCIL_ATTACHMENT, GL_RENDERBUFFER, objectOrZero(m_renderbuffer->emulatedStencilBuffer()));
|
| } else {
|
| - context->framebufferRenderbuffer(GL_FRAMEBUFFER, attachment, GL_RENDERBUFFER, object);
|
| + context->framebufferRenderbuffer(target, attachment, GL_RENDERBUFFER, object);
|
| }
|
| }
|
|
|
| - void WebGLRenderbufferAttachment::unattach(WebGraphicsContext3D* context, GLenum attachment)
|
| + void WebGLRenderbufferAttachment::unattach(WebGraphicsContext3D* context, GLenum target, GLenum attachment)
|
| {
|
| if (attachment == GC3D_DEPTH_STENCIL_ATTACHMENT_WEBGL) {
|
| - context->framebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, 0);
|
| - context->framebufferRenderbuffer(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT, GL_RENDERBUFFER, 0);
|
| + context->framebufferRenderbuffer(target, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, 0);
|
| + context->framebufferRenderbuffer(target, GL_STENCIL_ATTACHMENT, GL_RENDERBUFFER, 0);
|
| } else {
|
| - context->framebufferRenderbuffer(GL_FRAMEBUFFER, attachment, GL_RENDERBUFFER, 0);
|
| + context->framebufferRenderbuffer(target, attachment, GL_RENDERBUFFER, 0);
|
| }
|
| }
|
|
|
| @@ -162,8 +162,8 @@ namespace {
|
| virtual bool isSharedObject(WebGLSharedObject*) const override;
|
| virtual bool valid() const override;
|
| virtual void onDetached(WebGraphicsContext3D*) override;
|
| - virtual void attach(WebGraphicsContext3D*, GLenum attachment) override;
|
| - virtual void unattach(WebGraphicsContext3D*, GLenum attachment) override;
|
| + virtual void attach(WebGraphicsContext3D*, GLenum target, GLenum attachment) override;
|
| + virtual void unattach(WebGraphicsContext3D*, GLenum target, GLenum attachment) override;
|
|
|
| RefPtrWillBeMember<WebGLTexture> m_texture;
|
| GLenum m_target;
|
| @@ -223,19 +223,19 @@ namespace {
|
| m_texture->onDetached(context);
|
| }
|
|
|
| - void WebGLTextureAttachment::attach(WebGraphicsContext3D* context, GLenum attachment)
|
| + void WebGLTextureAttachment::attach(WebGraphicsContext3D* context, GLenum target, GLenum attachment)
|
| {
|
| Platform3DObject object = objectOrZero(m_texture.get());
|
| - context->framebufferTexture2D(GL_FRAMEBUFFER, attachment, m_target, object, m_level);
|
| + context->framebufferTexture2D(target, attachment, m_target, object, m_level);
|
| }
|
|
|
| - void WebGLTextureAttachment::unattach(WebGraphicsContext3D* context, GLenum attachment)
|
| + void WebGLTextureAttachment::unattach(WebGraphicsContext3D* context, GLenum target, GLenum attachment)
|
| {
|
| if (attachment == GC3D_DEPTH_STENCIL_ATTACHMENT_WEBGL) {
|
| - context->framebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, m_target, 0, m_level);
|
| - context->framebufferTexture2D(GL_FRAMEBUFFER, GL_STENCIL_ATTACHMENT, m_target, 0, m_level);
|
| + context->framebufferTexture2D(target, GL_DEPTH_ATTACHMENT, m_target, 0, m_level);
|
| + context->framebufferTexture2D(target, GL_STENCIL_ATTACHMENT, m_target, 0, m_level);
|
| } else {
|
| - context->framebufferTexture2D(GL_FRAMEBUFFER, attachment, m_target, 0, m_level);
|
| + context->framebufferTexture2D(target, attachment, m_target, 0, m_level);
|
| }
|
| }
|
|
|
| @@ -292,38 +292,44 @@ WebGLFramebuffer::~WebGLFramebuffer()
|
| detachAndDeleteObject();
|
| }
|
|
|
| -void WebGLFramebuffer::setAttachmentForBoundFramebuffer(GLenum attachment, GLenum texTarget, WebGLTexture* texture, GLint level)
|
| +void WebGLFramebuffer::setAttachmentForBoundFramebuffer(GLenum target, GLenum attachment, GLenum texTarget, WebGLTexture* texture, GLint level)
|
| {
|
| ASSERT(isBound());
|
| - removeAttachmentFromBoundFramebuffer(attachment);
|
| + removeAttachmentFromBoundFramebuffer(attachment, target);
|
| if (!m_object)
|
| return;
|
| if (texture && texture->object()) {
|
| - m_attachments.add(attachment, WebGLTextureAttachment::create(texture, texTarget, level));
|
| + if (target == GL_READ_FRAMEBUFFER)
|
| + m_readAttachments.add(attachment, WebGLTextureAttachment::create(texture, texTarget, level));
|
| + else
|
| + m_attachments.add(attachment, WebGLTextureAttachment::create(texture, texTarget, level));
|
| drawBuffersIfNecessary(false);
|
| texture->onAttached();
|
| }
|
| }
|
|
|
| -void WebGLFramebuffer::setAttachmentForBoundFramebuffer(GLenum attachment, WebGLRenderbuffer* renderbuffer)
|
| +void WebGLFramebuffer::setAttachmentForBoundFramebuffer(GLenum target, GLenum attachment, WebGLRenderbuffer* renderbuffer)
|
| {
|
| ASSERT(isBound());
|
| - removeAttachmentFromBoundFramebuffer(attachment);
|
| + removeAttachmentFromBoundFramebuffer(attachment, target);
|
| if (!m_object)
|
| return;
|
| if (renderbuffer && renderbuffer->object()) {
|
| - m_attachments.add(attachment, WebGLRenderbufferAttachment::create(renderbuffer));
|
| + if (target == GL_READ_FRAMEBUFFER)
|
| + m_readAttachments.add(attachment, WebGLRenderbufferAttachment::create(renderbuffer));
|
| + else
|
| + m_attachments.add(attachment, WebGLRenderbufferAttachment::create(renderbuffer));
|
| drawBuffersIfNecessary(false);
|
| renderbuffer->onAttached();
|
| }
|
| }
|
|
|
| -void WebGLFramebuffer::attach(GLenum attachment, GLenum attachmentPoint)
|
| +void WebGLFramebuffer::attach(GLenum target, GLenum attachment, GLenum attachmentPoint)
|
| {
|
| ASSERT(isBound());
|
| - WebGLAttachment* attachmentObject = getAttachment(attachment);
|
| + WebGLAttachment* attachmentObject = getAttachment(attachment, target);
|
| if (attachmentObject)
|
| - attachmentObject->attach(context()->webContext(), attachmentPoint);
|
| + attachmentObject->attach(context()->webContext(), target, attachmentPoint);
|
| }
|
|
|
| WebGLSharedObject* WebGLFramebuffer::getAttachmentObject(GLenum attachment) const
|
| @@ -421,39 +427,46 @@ bool WebGLFramebuffer::isAttachmentComplete(WebGLAttachment* attachedObject, GLe
|
| return true;
|
| }
|
|
|
| -WebGLFramebuffer::WebGLAttachment* WebGLFramebuffer::getAttachment(GLenum attachment) const
|
| +WebGLFramebuffer::WebGLAttachment* WebGLFramebuffer::getAttachment(GLenum attachment, GLenum target) const
|
| {
|
| + if (target == GL_READ_FRAMEBUFFER) {
|
| + const AttachmentMap::const_iterator it = m_readAttachments.find(attachment);
|
| + return (it != m_readAttachments.end()) ? it->value.get() : 0;
|
| + }
|
| const AttachmentMap::const_iterator it = m_attachments.find(attachment);
|
| return (it != m_attachments.end()) ? it->value.get() : 0;
|
| }
|
|
|
| -void WebGLFramebuffer::removeAttachmentFromBoundFramebuffer(GLenum attachment)
|
| +void WebGLFramebuffer::removeAttachmentFromBoundFramebuffer(GLenum attachment, GLenum target)
|
| {
|
| ASSERT(isBound());
|
| if (!m_object)
|
| return;
|
|
|
| - WebGLAttachment* attachmentObject = getAttachment(attachment);
|
| + WebGLAttachment* attachmentObject = getAttachment(attachment, target);
|
| if (attachmentObject) {
|
| attachmentObject->onDetached(context()->webContext());
|
| - m_attachments.remove(attachment);
|
| + if (target == GL_READ_FRAMEBUFFER)
|
| + m_readAttachments.remove(attachment);
|
| + else
|
| + m_attachments.remove(attachment);
|
| drawBuffersIfNecessary(false);
|
| switch (attachment) {
|
| case GC3D_DEPTH_STENCIL_ATTACHMENT_WEBGL:
|
| - attach(GL_DEPTH_ATTACHMENT, GL_DEPTH_ATTACHMENT);
|
| - attach(GL_STENCIL_ATTACHMENT, GL_STENCIL_ATTACHMENT);
|
| + attach(target, GL_DEPTH_ATTACHMENT, GL_DEPTH_ATTACHMENT);
|
| + attach(target, GL_STENCIL_ATTACHMENT, GL_STENCIL_ATTACHMENT);
|
| break;
|
| case GL_DEPTH_ATTACHMENT:
|
| - attach(GC3D_DEPTH_STENCIL_ATTACHMENT_WEBGL, GL_DEPTH_ATTACHMENT);
|
| + attach(target, GC3D_DEPTH_STENCIL_ATTACHMENT_WEBGL, GL_DEPTH_ATTACHMENT);
|
| break;
|
| case GL_STENCIL_ATTACHMENT:
|
| - attach(GC3D_DEPTH_STENCIL_ATTACHMENT_WEBGL, GL_STENCIL_ATTACHMENT);
|
| + attach(target, GC3D_DEPTH_STENCIL_ATTACHMENT_WEBGL, GL_STENCIL_ATTACHMENT);
|
| break;
|
| }
|
| }
|
| }
|
|
|
| -void WebGLFramebuffer::removeAttachmentFromBoundFramebuffer(WebGLSharedObject* attachment)
|
| +void WebGLFramebuffer::removeAttachmentFromBoundFramebuffer(WebGLSharedObject* attachment, GLenum target)
|
| {
|
| ASSERT(isBound());
|
| if (!m_object)
|
| @@ -464,12 +477,12 @@ void WebGLFramebuffer::removeAttachmentFromBoundFramebuffer(WebGLSharedObject* a
|
| bool checkMore = true;
|
| while (checkMore) {
|
| checkMore = false;
|
| - for (const auto& it : m_attachments) {
|
| + for (const auto& it : (target == GL_READ_FRAMEBUFFER ? m_readAttachments : m_attachments)) {
|
| WebGLAttachment* attachmentObject = it.value.get();
|
| if (attachmentObject->isSharedObject(attachment)) {
|
| GLenum attachmentType = it.key;
|
| - attachmentObject->unattach(context()->webContext(), attachmentType);
|
| - removeAttachmentFromBoundFramebuffer(attachmentType);
|
| + attachmentObject->unattach(context()->webContext(), target, attachmentType);
|
| + removeAttachmentFromBoundFramebuffer(attachmentType, target);
|
| checkMore = true;
|
| break;
|
| }
|
| @@ -487,14 +500,14 @@ GLenum WebGLFramebuffer::colorBufferFormat() const
|
| return attachment->format();
|
| }
|
|
|
| -GLenum WebGLFramebuffer::checkStatus(const char** reason) const
|
| +GLenum WebGLFramebuffer::checkStatus(const char** reason, GLenum target) const
|
| {
|
| unsigned count = 0;
|
| GLsizei width = 0, height = 0;
|
| bool haveDepth = false;
|
| bool haveStencil = false;
|
| bool haveDepthStencil = false;
|
| - for (const auto& it : m_attachments) {
|
| + for (const auto& it : (target == GL_READ_FRAMEBUFFER ? m_readAttachments : m_attachments)) {
|
| WebGLAttachment* attachment = it.value.get();
|
| if (!isAttachmentComplete(attachment, it.key, reason))
|
| return GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT;
|
| @@ -544,9 +557,9 @@ GLenum WebGLFramebuffer::checkStatus(const char** reason) const
|
| return GL_FRAMEBUFFER_COMPLETE;
|
| }
|
|
|
| -bool WebGLFramebuffer::onAccess(WebGraphicsContext3D* context3d, const char** reason)
|
| +bool WebGLFramebuffer::onAccess(WebGraphicsContext3D* context3d, const char** reason, GLenum target)
|
| {
|
| - if (checkStatus(reason) != GL_FRAMEBUFFER_COMPLETE)
|
| + if (checkStatus(reason, target) != GL_FRAMEBUFFER_COMPLETE)
|
| return false;
|
| return true;
|
| }
|
| @@ -571,6 +584,8 @@ void WebGLFramebuffer::deleteObjectImpl(WebGraphicsContext3D* context3d)
|
| // not needed.
|
| for (const auto& attachment : m_attachments)
|
| attachment.value->onDetached(context3d);
|
| + for (const auto& attachment : m_readAttachments)
|
| + attachment.value->onDetached(context3d);
|
| #endif
|
|
|
| context3d->deleteFramebuffer(m_object);
|
| @@ -631,6 +646,7 @@ DEFINE_TRACE(WebGLFramebuffer)
|
| {
|
| #if ENABLE(OILPAN)
|
| visitor->trace(m_attachments);
|
| + visitor->trace(m_readAttachments);
|
| #endif
|
| WebGLContextObject::trace(visitor);
|
| }
|
|
|