Bug 709490 - Part 1: Let ImageBridge transfer CanvasClient async. r=nical
Thanks Jon Morton [:jmorton] (jonanin@gmail.com) for polishing patches.
This commit is contained in:
@@ -13,6 +13,7 @@
|
||||
#include "gfxPlatform.h" // for gfxPlatform
|
||||
#include "GLReadTexImageHelper.h"
|
||||
#include "mozilla/gfx/BaseSize.h" // for BaseSize
|
||||
#include "mozilla/layers/AsyncCanvasRenderer.h"
|
||||
#include "mozilla/layers/CompositableForwarder.h"
|
||||
#include "mozilla/layers/CompositorChild.h" // for CompositorChild
|
||||
#include "mozilla/layers/GrallocTextureClient.h"
|
||||
@@ -38,14 +39,32 @@ CanvasClient::CreateCanvasClient(CanvasClientType aType,
|
||||
switch (aType) {
|
||||
case CanvasClientTypeShSurf:
|
||||
return MakeAndAddRef<CanvasClientSharedSurface>(aForwarder, aFlags);
|
||||
break;
|
||||
|
||||
case CanvasClientAsync:
|
||||
return MakeAndAddRef<CanvasClientBridge>(aForwarder, aFlags);
|
||||
default:
|
||||
return MakeAndAddRef<CanvasClient2D>(aForwarder, aFlags);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
CanvasClientBridge::UpdateAsync(AsyncCanvasRenderer* aRenderer)
|
||||
{
|
||||
if (!GetForwarder() || !mLayer || !aRenderer ||
|
||||
!aRenderer->GetCanvasClient()) {
|
||||
return;
|
||||
}
|
||||
|
||||
uint64_t asyncID = aRenderer->GetCanvasClientAsyncID();
|
||||
if (asyncID == 0 || mAsyncID == asyncID) {
|
||||
return;
|
||||
}
|
||||
|
||||
static_cast<ShadowLayerForwarder*>(GetForwarder())
|
||||
->AttachAsyncCompositable(asyncID, mLayer);
|
||||
mAsyncID = asyncID;
|
||||
}
|
||||
|
||||
void
|
||||
CanvasClient2D::Update(gfx::IntSize aSize, ClientCanvasLayer* aLayer)
|
||||
{
|
||||
@@ -321,13 +340,38 @@ CloneSurface(gl::SharedSurface* src, gl::SurfaceFactory* factory)
|
||||
void
|
||||
CanvasClientSharedSurface::Update(gfx::IntSize aSize, ClientCanvasLayer* aLayer)
|
||||
{
|
||||
auto gl = aLayer->mGLContext;
|
||||
Renderer renderer;
|
||||
renderer.construct<ClientCanvasLayer*>(aLayer);
|
||||
UpdateRenderer(aSize, renderer);
|
||||
}
|
||||
|
||||
void
|
||||
CanvasClientSharedSurface::UpdateAsync(AsyncCanvasRenderer* aRenderer)
|
||||
{
|
||||
Renderer renderer;
|
||||
renderer.construct<AsyncCanvasRenderer*>(aRenderer);
|
||||
UpdateRenderer(aRenderer->GetSize(), renderer);
|
||||
}
|
||||
|
||||
void
|
||||
CanvasClientSharedSurface::UpdateRenderer(gfx::IntSize aSize, Renderer& aRenderer)
|
||||
{
|
||||
GLContext* gl = nullptr;
|
||||
ClientCanvasLayer* layer = nullptr;
|
||||
AsyncCanvasRenderer* asyncRenderer = nullptr;
|
||||
if (aRenderer.constructed<ClientCanvasLayer*>()) {
|
||||
layer = aRenderer.ref<ClientCanvasLayer*>();
|
||||
gl = layer->mGLContext;
|
||||
} else {
|
||||
asyncRenderer = aRenderer.ref<AsyncCanvasRenderer*>();
|
||||
gl = asyncRenderer->mGLContext;
|
||||
}
|
||||
gl->MakeCurrent();
|
||||
|
||||
RefPtr<TextureClient> newFront;
|
||||
|
||||
if (aLayer->mGLFrontbuffer) {
|
||||
mShSurfClient = CloneSurface(aLayer->mGLFrontbuffer.get(), aLayer->mFactory.get());
|
||||
if (layer && layer->mGLFrontbuffer) {
|
||||
mShSurfClient = CloneSurface(layer->mGLFrontbuffer.get(), layer->mFactory.get());
|
||||
if (!mShSurfClient) {
|
||||
gfxCriticalError() << "Invalid canvas front buffer";
|
||||
return;
|
||||
@@ -351,11 +395,18 @@ CanvasClientSharedSurface::Update(gfx::IntSize aSize, ClientCanvasLayer* aLayer)
|
||||
|
||||
bool needsReadback = (surf->mType == SharedSurfaceType::Basic);
|
||||
if (needsReadback) {
|
||||
TextureFlags flags = aLayer->Flags() |
|
||||
TextureFlags::IMMUTABLE;
|
||||
TextureFlags flags = TextureFlags::IMMUTABLE;
|
||||
|
||||
CompositableForwarder* shadowForwarder = nullptr;
|
||||
if (layer) {
|
||||
flags |= layer->Flags();
|
||||
shadowForwarder = layer->ClientManager()->AsShadowForwarder();
|
||||
} else {
|
||||
MOZ_ASSERT(asyncRenderer);
|
||||
flags |= mTextureFlags;
|
||||
shadowForwarder = GetForwarder();
|
||||
}
|
||||
|
||||
auto manager = aLayer->ClientManager();
|
||||
auto shadowForwarder = manager->AsShadowForwarder();
|
||||
auto layersBackend = shadowForwarder->GetCompositorBackendType();
|
||||
mReadbackClient = TexClientFromReadback(surf, forwarder, flags, layersBackend);
|
||||
|
||||
@@ -371,6 +422,14 @@ CanvasClientSharedSurface::Update(gfx::IntSize aSize, ClientCanvasLayer* aLayer)
|
||||
return;
|
||||
}
|
||||
|
||||
mNewFront = newFront;
|
||||
}
|
||||
|
||||
void
|
||||
CanvasClientSharedSurface::Updated()
|
||||
{
|
||||
auto forwarder = GetForwarder();
|
||||
|
||||
#ifndef MOZ_WIDGET_GONK
|
||||
if (mFront) {
|
||||
if (mFront->GetFlags() & TextureFlags::RECYCLE) {
|
||||
@@ -385,12 +444,13 @@ CanvasClientSharedSurface::Update(gfx::IntSize aSize, ClientCanvasLayer* aLayer)
|
||||
// - Call RemoveTexture() after newFront's UseTextures() call.
|
||||
// It could improve performance of Host side's EGL handling on gonk
|
||||
AutoRemoveTexture autoRemove(this);
|
||||
if (mFront && mFront != newFront) {
|
||||
if (mFront && mFront != mNewFront) {
|
||||
autoRemove.mTexture = mFront;
|
||||
}
|
||||
#endif
|
||||
|
||||
mFront = newFront;
|
||||
mFront = mNewFront;
|
||||
mNewFront = nullptr;
|
||||
|
||||
// Add the new TexClient.
|
||||
MOZ_ALWAYS_TRUE( AddTextureClient(mFront) );
|
||||
@@ -406,6 +466,7 @@ void
|
||||
CanvasClientSharedSurface::ClearSurfaces()
|
||||
{
|
||||
mFront = nullptr;
|
||||
mNewFront = nullptr;
|
||||
mShSurfClient = nullptr;
|
||||
mReadbackClient = nullptr;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user