Bug 1673342 - Add Support of software WebRender with CompositorOGL on Android and Linux r=mattwoodrow
Differential Revision: https://phabricator.services.mozilla.com/D106234
This commit is contained in:
@@ -188,6 +188,7 @@ enum class WebRenderCompositor : int8_t {
|
||||
CORE_ANIMATION,
|
||||
SOFTWARE,
|
||||
D3D11,
|
||||
OPENGL,
|
||||
LAST
|
||||
};
|
||||
|
||||
|
||||
@@ -164,6 +164,16 @@ class KnowsCompositor {
|
||||
layers::WebRenderCompositor::D3D11;
|
||||
}
|
||||
|
||||
bool UsingSoftwareWebRenderOpenGL() const {
|
||||
auto lock = mData.Lock();
|
||||
return lock.ref().mTextureFactoryIdentifier.mParentBackend ==
|
||||
layers::LayersBackend::LAYERS_WR &&
|
||||
lock.ref().mTextureFactoryIdentifier.mWebRenderBackend ==
|
||||
WebRenderBackend::SOFTWARE &&
|
||||
lock.ref().mTextureFactoryIdentifier.mWebRenderCompositor ==
|
||||
layers::WebRenderCompositor::OPENGL;
|
||||
}
|
||||
|
||||
TextureFactoryIdentifier GetTextureFactoryIdentifier() const {
|
||||
auto lock = mData.Lock();
|
||||
return lock.ref().mTextureFactoryIdentifier;
|
||||
|
||||
@@ -358,23 +358,40 @@ void CompositorOGL::CleanupResources() {
|
||||
|
||||
mBlitTextureImageHelper = nullptr;
|
||||
|
||||
// On the main thread the Widget will be destroyed soon and calling
|
||||
// MakeCurrent after that could cause a crash (at least with GLX, see bug
|
||||
// 1059793), unless context is marked as destroyed. There may be some textures
|
||||
// still alive that will try to call MakeCurrent on the context so let's make
|
||||
// sure it is marked destroyed now.
|
||||
mGLContext->MarkDestroyed();
|
||||
if (mOwnsGLContext) {
|
||||
// On the main thread the Widget will be destroyed soon and calling
|
||||
// MakeCurrent after that could cause a crash (at least with GLX, see bug
|
||||
// 1059793), unless context is marked as destroyed. There may be some
|
||||
// textures still alive that will try to call MakeCurrent on the context so
|
||||
// let's make sure it is marked destroyed now.
|
||||
mGLContext->MarkDestroyed();
|
||||
}
|
||||
|
||||
mGLContext = nullptr;
|
||||
}
|
||||
|
||||
bool CompositorOGL::Initialize(GLContext* aGLContext,
|
||||
nsCString* const out_failureReason) {
|
||||
MOZ_ASSERT(!mDestroyed);
|
||||
MOZ_ASSERT(!mGLContext);
|
||||
|
||||
mGLContext = aGLContext;
|
||||
mOwnsGLContext = false;
|
||||
|
||||
return Initialize(out_failureReason);
|
||||
}
|
||||
|
||||
bool CompositorOGL::Initialize(nsCString* const out_failureReason) {
|
||||
ScopedGfxFeatureReporter reporter("GL Layers");
|
||||
|
||||
// Do not allow double initialization
|
||||
MOZ_ASSERT(mGLContext == nullptr, "Don't reinitialize CompositorOGL");
|
||||
MOZ_ASSERT(mGLContext == nullptr || !mOwnsGLContext,
|
||||
"Don't reinitialize CompositorOGL");
|
||||
|
||||
mGLContext = CreateContext();
|
||||
if (!mGLContext) {
|
||||
MOZ_ASSERT(mOwnsGLContext);
|
||||
mGLContext = CreateContext();
|
||||
}
|
||||
|
||||
#ifdef MOZ_WIDGET_ANDROID
|
||||
if (!mGLContext) {
|
||||
|
||||
@@ -130,6 +130,8 @@ class CompositorOGL final : public Compositor {
|
||||
already_AddRefed<DataTextureSource> CreateDataTextureSourceAround(
|
||||
gfx::DataSourceSurface* aSurface) override;
|
||||
|
||||
bool Initialize(GLContext* aGLContext, nsCString* const out_failureReason);
|
||||
|
||||
bool Initialize(nsCString* const out_failureReason) override;
|
||||
|
||||
void Destroy() override;
|
||||
@@ -285,6 +287,7 @@ class CompositorOGL final : public Compositor {
|
||||
/** Widget associated with this compositor */
|
||||
LayoutDeviceIntSize mWidgetSize;
|
||||
RefPtr<GLContext> mGLContext;
|
||||
bool mOwnsGLContext = true;
|
||||
RefPtr<SurfacePoolHandle> mSurfacePoolHandle;
|
||||
UniquePtr<GLBlitTextureImageHelper> mBlitTextureImageHelper;
|
||||
gfx::Matrix4x4 mProjMatrix;
|
||||
|
||||
@@ -168,6 +168,8 @@ CompositorBridgeChild* WebRenderLayerManager::GetCompositorBridgeChild() {
|
||||
void WebRenderLayerManager::GetBackendName(nsAString& name) {
|
||||
if (WrBridge()->UsingSoftwareWebRenderD3D11()) {
|
||||
name.AssignLiteral("WebRender (Software D3D11)");
|
||||
} else if (WrBridge()->UsingSoftwareWebRenderOpenGL()) {
|
||||
name.AssignLiteral("WebRender (Software OpenGL)");
|
||||
} else if (WrBridge()->UsingSoftwareWebRender()) {
|
||||
name.AssignLiteral("WebRender (Software)");
|
||||
} else {
|
||||
|
||||
@@ -50,6 +50,18 @@ class RenderAndroidSurfaceTextureHost final : public RenderTextureHostSWGL {
|
||||
return gfx::YUVColorSpace::UNKNOWN;
|
||||
}
|
||||
|
||||
RenderAndroidSurfaceTextureHost* AsRenderAndroidSurfaceTextureHost()
|
||||
override {
|
||||
return this;
|
||||
}
|
||||
|
||||
mozilla::java::GeckoSurfaceTexture::GlobalRef mSurfTex;
|
||||
const gfx::IntSize mSize;
|
||||
const gfx::SurfaceFormat mFormat;
|
||||
// mContinuousUpdate was used for rendering video in the past.
|
||||
// It is not used on current gecko.
|
||||
const bool mContinuousUpdate;
|
||||
|
||||
private:
|
||||
virtual ~RenderAndroidSurfaceTextureHost();
|
||||
bool EnsureAttachedToGLContext();
|
||||
@@ -63,12 +75,6 @@ class RenderAndroidSurfaceTextureHost final : public RenderTextureHostSWGL {
|
||||
STATUS_PREPARED
|
||||
};
|
||||
|
||||
const mozilla::java::GeckoSurfaceTexture::GlobalRef mSurfTex;
|
||||
const gfx::IntSize mSize;
|
||||
const gfx::SurfaceFormat mFormat;
|
||||
// mContinuousUpdate was used for rendering video in the past.
|
||||
// It is not used on current gecko.
|
||||
const bool mContinuousUpdate;
|
||||
// XXX const bool mIgnoreTransform;
|
||||
PrepareStatus mPrepareStatus;
|
||||
bool mAttachedToGLContext;
|
||||
|
||||
@@ -32,6 +32,7 @@ class CompositorWidget;
|
||||
|
||||
namespace wr {
|
||||
|
||||
class RenderCompositorLayersSWGL;
|
||||
class RenderCompositorD3D11SWGL;
|
||||
|
||||
class RenderCompositor {
|
||||
@@ -93,6 +94,10 @@ class RenderCompositor {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
virtual RenderCompositorLayersSWGL* AsRenderCompositorLayersSWGL() {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
// True if AttachExternalImage supports being used with an external
|
||||
// image that maps to a RenderBufferTextureHost
|
||||
virtual bool SupportsExternalBufferTextures() const { return false; }
|
||||
|
||||
@@ -19,6 +19,8 @@
|
||||
|
||||
#if defined(XP_WIN)
|
||||
# include "mozilla/webrender/RenderCompositorD3D11SWGL.h"
|
||||
#else
|
||||
# include "mozilla/webrender/RenderCompositorOGLSWGL.h"
|
||||
#endif
|
||||
|
||||
namespace mozilla {
|
||||
@@ -31,7 +33,7 @@ UniquePtr<RenderCompositor> RenderCompositorLayersSWGL::Create(
|
||||
#ifdef XP_WIN
|
||||
return RenderCompositorD3D11SWGL::Create(std::move(aWidget), aError);
|
||||
#else
|
||||
return nullptr;
|
||||
return RenderCompositorOGLSWGL::Create(std::move(aWidget), aError);
|
||||
#endif
|
||||
}
|
||||
|
||||
@@ -237,6 +239,8 @@ void RenderCompositorLayersSWGL::AttachExternalImage(
|
||||
#if defined(XP_WIN)
|
||||
MOZ_RELEASE_ASSERT(image->AsRenderDXGITextureHost() ||
|
||||
image->AsRenderDXGIYCbCrTextureHost());
|
||||
#elif defined(ANDROID)
|
||||
MOZ_RELEASE_ASSERT(image->AsRenderAndroidSurfaceTextureHost());
|
||||
#endif
|
||||
|
||||
auto surfaceCursor = mSurfaces.find(aId);
|
||||
|
||||
305
gfx/webrender_bindings/RenderCompositorOGLSWGL.cpp
Normal file
305
gfx/webrender_bindings/RenderCompositorOGLSWGL.cpp
Normal file
@@ -0,0 +1,305 @@
|
||||
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
*
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file,
|
||||
* You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "RenderCompositorOGLSWGL.h"
|
||||
|
||||
#include "GLContext.h"
|
||||
#include "GLContextEGL.h"
|
||||
#include "mozilla/layers/BuildConstants.h"
|
||||
#include "mozilla/layers/CompositorOGL.h"
|
||||
#include "mozilla/layers/Effects.h"
|
||||
#include "mozilla/layers/TextureHostOGL.h"
|
||||
#include "mozilla/widget/CompositorWidget.h"
|
||||
|
||||
#ifdef MOZ_WIDGET_ANDROID
|
||||
# include "mozilla/java/GeckoSurfaceTextureWrappers.h"
|
||||
# include "mozilla/widget/AndroidCompositorWidget.h"
|
||||
# include <android/native_window.h>
|
||||
# include <android/native_window_jni.h>
|
||||
#endif
|
||||
|
||||
#ifdef MOZ_WIDGET_GTK
|
||||
# include "mozilla/widget/GtkCompositorWidget.h"
|
||||
# include <gdk/gdk.h>
|
||||
# include <gdk/gdkx.h>
|
||||
#endif
|
||||
|
||||
namespace mozilla {
|
||||
using namespace layers;
|
||||
|
||||
namespace wr {
|
||||
|
||||
UniquePtr<RenderCompositor> RenderCompositorOGLSWGL::Create(
|
||||
RefPtr<widget::CompositorWidget>&& aWidget, nsACString& aError) {
|
||||
RefPtr<Compositor> compositor;
|
||||
#ifdef MOZ_WIDGET_ANDROID
|
||||
if (StaticPrefs::gfx_webrender_software_opengl_AtStartup()) {
|
||||
RefPtr<gl::GLContext> context = RenderThread::Get()->SharedGL();
|
||||
if (!context) {
|
||||
gfxCriticalNote << "SharedGL does not exist for SWGL";
|
||||
return nullptr;
|
||||
}
|
||||
nsCString log;
|
||||
RefPtr<CompositorOGL> compositorOGL;
|
||||
compositorOGL = new CompositorOGL(nullptr, aWidget, /* aSurfaceWidth */ -1,
|
||||
/* aSurfaceHeight */ -1,
|
||||
/* aUseExternalSurfaceSize */ true);
|
||||
if (!compositorOGL->Initialize(context, &log)) {
|
||||
gfxCriticalNote << "Failed to initialize CompositorOGL for SWGL: "
|
||||
<< log.get();
|
||||
return nullptr;
|
||||
}
|
||||
compositor = compositorOGL;
|
||||
}
|
||||
#elif defined(MOZ_WIDGET_GTK)
|
||||
if (StaticPrefs::gfx_webrender_software_opengl_AtStartup()) {
|
||||
nsCString log;
|
||||
RefPtr<CompositorOGL> compositorOGL;
|
||||
compositorOGL = new CompositorOGL(nullptr, aWidget);
|
||||
if (!compositorOGL->Initialize(&log)) {
|
||||
gfxCriticalNote << "Failed to initialize CompositorOGL for SWGL: "
|
||||
<< log.get();
|
||||
return nullptr;
|
||||
}
|
||||
compositor = compositorOGL;
|
||||
}
|
||||
#endif
|
||||
|
||||
if (!compositor) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
void* ctx = wr_swgl_create_context();
|
||||
if (!ctx) {
|
||||
gfxCriticalNote << "Failed SWGL context creation for WebRender";
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
return MakeUnique<RenderCompositorOGLSWGL>(compositor, std::move(aWidget),
|
||||
ctx);
|
||||
}
|
||||
|
||||
RenderCompositorOGLSWGL::RenderCompositorOGLSWGL(
|
||||
Compositor* aCompositor, RefPtr<widget::CompositorWidget>&& aWidget,
|
||||
void* aContext)
|
||||
: RenderCompositorLayersSWGL(aCompositor, std::move(aWidget), aContext) {}
|
||||
|
||||
RenderCompositorOGLSWGL::~RenderCompositorOGLSWGL() {
|
||||
#ifdef OZ_WIDGET_ANDROID
|
||||
java::GeckoSurfaceTexture::DestroyUnused((int64_t)GetGLContext());
|
||||
DestroyEGLSurface();
|
||||
#endif
|
||||
}
|
||||
|
||||
gl::GLContext* RenderCompositorOGLSWGL::GetGLContext() {
|
||||
return mCompositor->AsCompositorOGL()->gl();
|
||||
}
|
||||
|
||||
bool RenderCompositorOGLSWGL::MakeCurrent() {
|
||||
GetGLContext()->MakeCurrent();
|
||||
#ifdef MOZ_WIDGET_ANDROID
|
||||
if (GetGLContext()->GetContextType() == gl::GLContextType::EGL) {
|
||||
gl::GLContextEGL::Cast(GetGLContext())->SetEGLSurfaceOverride(mEGLSurface);
|
||||
}
|
||||
#endif
|
||||
RenderCompositorLayersSWGL::MakeCurrent();
|
||||
return true;
|
||||
}
|
||||
|
||||
EGLSurface RenderCompositorOGLSWGL::CreateEGLSurface() {
|
||||
MOZ_ASSERT(GetGLContext()->GetContextType() == gl::GLContextType::EGL);
|
||||
|
||||
EGLSurface surface = EGL_NO_SURFACE;
|
||||
surface = gl::GLContextEGL::CreateEGLSurfaceForCompositorWidget(
|
||||
mWidget, gl::GLContextEGL::Cast(GetGLContext())->mConfig);
|
||||
if (surface == EGL_NO_SURFACE) {
|
||||
gfxCriticalNote << "Failed to create EGLSurface";
|
||||
}
|
||||
return surface;
|
||||
}
|
||||
|
||||
void RenderCompositorOGLSWGL::DestroyEGLSurface() {
|
||||
MOZ_ASSERT(GetGLContext()->GetContextType() == gl::GLContextType::EGL);
|
||||
|
||||
const auto& gle = gl::GLContextEGL::Cast(GetGLContext());
|
||||
const auto& egl = gle->mEgl;
|
||||
|
||||
// Release EGLSurface of back buffer before calling ResizeBuffers().
|
||||
if (mEGLSurface) {
|
||||
gle->SetEGLSurfaceOverride(EGL_NO_SURFACE);
|
||||
egl->fDestroySurface(mEGLSurface);
|
||||
mEGLSurface = EGL_NO_SURFACE;
|
||||
}
|
||||
}
|
||||
|
||||
bool RenderCompositorOGLSWGL::BeginFrame() {
|
||||
MOZ_ASSERT(!mInFrame);
|
||||
RenderCompositorLayersSWGL::BeginFrame();
|
||||
|
||||
#ifdef MOZ_WIDGET_ANDROID
|
||||
java::GeckoSurfaceTexture::DestroyUnused((int64_t)GetGLContext());
|
||||
GetGLContext()
|
||||
->MakeCurrent(); // DestroyUnused can change the current context!
|
||||
#endif
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void RenderCompositorOGLSWGL::HandleExternalImage(
|
||||
RenderTextureHost* aExternalImage, FrameSurface& aFrameSurface) {
|
||||
MOZ_ASSERT(aExternalImage);
|
||||
|
||||
#ifdef MOZ_WIDGET_ANDROID
|
||||
GLenum target =
|
||||
LOCAL_GL_TEXTURE_EXTERNAL; // This is required by SurfaceTexture
|
||||
GLenum wrapMode = LOCAL_GL_CLAMP_TO_EDGE;
|
||||
|
||||
auto* host = aExternalImage->AsRenderAndroidSurfaceTextureHost();
|
||||
// We need to hold the texture source separately from the effect,
|
||||
// since the effect doesn't hold a strong reference.
|
||||
RefPtr<SurfaceTextureSource> layer = new SurfaceTextureSource(
|
||||
(TextureSourceProvider*)mCompositor, host->mSurfTex, host->mFormat,
|
||||
target, wrapMode, host->mSize, /* aIgnoreTransform */ true);
|
||||
RefPtr<TexturedEffect> texturedEffect =
|
||||
CreateTexturedEffect(host->mFormat, layer, aFrameSurface.mFilter,
|
||||
/* isAlphaPremultiplied */ true);
|
||||
|
||||
gfx::Rect drawRect(0, 0, host->mSize.width, host->mSize.height);
|
||||
|
||||
EffectChain effect;
|
||||
effect.mPrimaryEffect = texturedEffect;
|
||||
mCompositor->DrawQuad(drawRect, aFrameSurface.mClipRect, effect, 1.0,
|
||||
aFrameSurface.mTransform, drawRect);
|
||||
#endif
|
||||
}
|
||||
|
||||
void RenderCompositorOGLSWGL::Pause() {
|
||||
#ifdef MOZ_WIDGET_ANDROID
|
||||
DestroyEGLSurface();
|
||||
#elif defined(MOZ_WIDGET_GTK)
|
||||
mCompositor->Pause();
|
||||
#endif
|
||||
}
|
||||
|
||||
bool RenderCompositorOGLSWGL::Resume() {
|
||||
#ifdef MOZ_WIDGET_ANDROID
|
||||
// Destroy EGLSurface if it exists.
|
||||
DestroyEGLSurface();
|
||||
|
||||
// Query the new surface size as this may have changed. We cannot use
|
||||
// mWidget->GetClientSize() due to a race condition between
|
||||
// nsWindow::Resize() being called and the frame being rendered after the
|
||||
// surface is resized.
|
||||
EGLNativeWindowType window = mWidget->AsAndroid()->GetEGLNativeWindow();
|
||||
JNIEnv* const env = jni::GetEnvForThread();
|
||||
ANativeWindow* const nativeWindow =
|
||||
ANativeWindow_fromSurface(env, reinterpret_cast<jobject>(window));
|
||||
const int32_t width = ANativeWindow_getWidth(nativeWindow);
|
||||
const int32_t height = ANativeWindow_getHeight(nativeWindow);
|
||||
|
||||
GLint maxTextureSize = 0;
|
||||
GetGLContext()->fGetIntegerv(LOCAL_GL_MAX_TEXTURE_SIZE,
|
||||
(GLint*)&maxTextureSize);
|
||||
|
||||
// When window size is too big, hardware buffer allocation could fail.
|
||||
if (maxTextureSize < width || maxTextureSize < height) {
|
||||
gfxCriticalNote << "Too big ANativeWindow size(" << width << ", " << height
|
||||
<< ") MaxTextureSize " << maxTextureSize;
|
||||
return false;
|
||||
}
|
||||
|
||||
mEGLSurface = CreateEGLSurface();
|
||||
if (mEGLSurface == EGL_NO_SURFACE) {
|
||||
RenderThread::Get()->HandleWebRenderError(WebRenderError::NEW_SURFACE);
|
||||
return false;
|
||||
}
|
||||
|
||||
gl::GLContextEGL::Cast(GetGLContext())->SetEGLSurfaceOverride(mEGLSurface);
|
||||
mEGLSurfaceSize = Some(LayoutDeviceIntSize(width, height));
|
||||
ANativeWindow_release(nativeWindow);
|
||||
mCompositor->SetDestinationSurfaceSize(gfx::IntSize(width, height));
|
||||
#elif defined(MOZ_WIDGET_GTK)
|
||||
bool resumed = mCompositor->Resume();
|
||||
if (!resumed) {
|
||||
RenderThread::Get()->HandleWebRenderError(WebRenderError::NEW_SURFACE);
|
||||
return false;
|
||||
}
|
||||
#endif
|
||||
return true;
|
||||
}
|
||||
|
||||
bool RenderCompositorOGLSWGL::IsPaused() {
|
||||
#ifdef MOZ_WIDGET_ANDROID
|
||||
return mEGLSurface == EGL_NO_SURFACE;
|
||||
#endif
|
||||
return false;
|
||||
}
|
||||
|
||||
LayoutDeviceIntSize RenderCompositorOGLSWGL::GetBufferSize() {
|
||||
if (mEGLSurfaceSize) {
|
||||
return *mEGLSurfaceSize;
|
||||
}
|
||||
return mWidget->GetClientSize();
|
||||
}
|
||||
|
||||
UniquePtr<RenderCompositorLayersSWGL::Tile>
|
||||
RenderCompositorOGLSWGL::DoCreateTile(Surface* aSurface) {
|
||||
const auto tileSize = aSurface->TileSize();
|
||||
|
||||
RefPtr<DataTextureSource> source = new TextureImageTextureSourceOGL(
|
||||
mCompositor->AsCompositorOGL(), layers::TextureFlags::NO_FLAGS);
|
||||
|
||||
RefPtr<gfx::DataSourceSurface> surf = gfx::Factory::CreateDataSourceSurface(
|
||||
gfx::IntSize(tileSize.width, tileSize.height),
|
||||
gfx::SurfaceFormat::B8G8R8A8);
|
||||
|
||||
return MakeUnique<TileOGL>(source, surf);
|
||||
}
|
||||
|
||||
bool RenderCompositorOGLSWGL::MaybeReadback(
|
||||
const gfx::IntSize& aReadbackSize, const wr::ImageFormat& aReadbackFormat,
|
||||
const Range<uint8_t>& aReadbackBuffer, bool* aNeedsYFlip) {
|
||||
#ifdef MOZ_WIDGET_ANDROID
|
||||
MOZ_ASSERT(aReadbackFormat == wr::ImageFormat::RGBA8);
|
||||
const GLenum format = LOCAL_GL_RGBA;
|
||||
#else
|
||||
MOZ_ASSERT(aReadbackFormat == wr::ImageFormat::BGRA8);
|
||||
const GLenum format = LOCAL_GL_BGRA;
|
||||
#endif
|
||||
|
||||
GetGLContext()->fReadPixels(0, 0, aReadbackSize.width, aReadbackSize.height,
|
||||
format, LOCAL_GL_UNSIGNED_BYTE,
|
||||
&aReadbackBuffer[0]);
|
||||
return true;
|
||||
}
|
||||
|
||||
RenderCompositorOGLSWGL::TileOGL::TileOGL(layers::DataTextureSource* aTexture,
|
||||
gfx::DataSourceSurface* aSurface)
|
||||
: Tile(), mTexture(aTexture), mSurface(aSurface) {}
|
||||
|
||||
bool RenderCompositorOGLSWGL::TileOGL::Map(wr::DeviceIntRect aDirtyRect,
|
||||
wr::DeviceIntRect aValidRect,
|
||||
void** aData, int32_t* aStride) {
|
||||
gfx::DataSourceSurface::MappedSurface map;
|
||||
if (!mSurface->Map(gfx::DataSourceSurface::READ_WRITE, &map)) {
|
||||
return false;
|
||||
}
|
||||
*aData =
|
||||
map.mData + aValidRect.origin.y * map.mStride + aValidRect.origin.x * 4;
|
||||
*aStride = map.mStride;
|
||||
return true;
|
||||
}
|
||||
|
||||
void RenderCompositorOGLSWGL::TileOGL::Unmap(const gfx::IntRect& aDirtyRect) {
|
||||
mSurface->Unmap();
|
||||
nsIntRegion dirty(aDirtyRect);
|
||||
mTexture->Update(mSurface, &dirty);
|
||||
}
|
||||
|
||||
} // namespace wr
|
||||
} // namespace mozilla
|
||||
82
gfx/webrender_bindings/RenderCompositorOGLSWGL.h
Normal file
82
gfx/webrender_bindings/RenderCompositorOGLSWGL.h
Normal file
@@ -0,0 +1,82 @@
|
||||
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#ifndef MOZILLA_GFX_RENDERCOMPOSITOR_OGL_SWGL_H
|
||||
#define MOZILLA_GFX_RENDERCOMPOSITOR_OGL_SWGL_H
|
||||
|
||||
#include "mozilla/layers/Compositor.h"
|
||||
#include "mozilla/webrender/RenderCompositorLayersSWGL.h"
|
||||
|
||||
namespace mozilla {
|
||||
|
||||
namespace wr {
|
||||
|
||||
class RenderCompositorOGLSWGL : public RenderCompositorLayersSWGL {
|
||||
public:
|
||||
static UniquePtr<RenderCompositor> Create(
|
||||
RefPtr<widget::CompositorWidget>&& aWidget, nsACString& aError);
|
||||
|
||||
RenderCompositorOGLSWGL(layers::Compositor* aCompositor,
|
||||
RefPtr<widget::CompositorWidget>&& aWidget,
|
||||
void* aContext);
|
||||
virtual ~RenderCompositorOGLSWGL();
|
||||
|
||||
gl::GLContext* GetGLContext();
|
||||
|
||||
bool MakeCurrent() override;
|
||||
|
||||
bool BeginFrame() override;
|
||||
|
||||
void Pause() override;
|
||||
bool Resume() override;
|
||||
bool IsPaused() override;
|
||||
|
||||
LayoutDeviceIntSize GetBufferSize() override;
|
||||
|
||||
layers::WebRenderCompositor CompositorType() const override {
|
||||
return layers::WebRenderCompositor::OPENGL;
|
||||
}
|
||||
|
||||
bool MaybeReadback(const gfx::IntSize& aReadbackSize,
|
||||
const wr::ImageFormat& aReadbackFormat,
|
||||
const Range<uint8_t>& aReadbackBuffer,
|
||||
bool* aNeedsYFlip) override;
|
||||
|
||||
private:
|
||||
void HandleExternalImage(RenderTextureHost* aExternalImage,
|
||||
FrameSurface& aFrameSurface) override;
|
||||
UniquePtr<RenderCompositorLayersSWGL::Tile> DoCreateTile(
|
||||
Surface* aSurface) override;
|
||||
|
||||
EGLSurface CreateEGLSurface();
|
||||
void DestroyEGLSurface();
|
||||
|
||||
EGLSurface mEGLSurface = EGL_NO_SURFACE;
|
||||
// On android, we must track our own surface size.
|
||||
Maybe<LayoutDeviceIntSize> mEGLSurfaceSize;
|
||||
|
||||
class TileOGL : public RenderCompositorLayersSWGL::Tile {
|
||||
public:
|
||||
TileOGL(layers::DataTextureSource* aTexture,
|
||||
gfx::DataSourceSurface* aSurface);
|
||||
virtual ~TileOGL() = default;
|
||||
|
||||
bool Map(wr::DeviceIntRect aDirtyRect, wr::DeviceIntRect aValidRect,
|
||||
void** aData, int32_t* aStride) override;
|
||||
void Unmap(const gfx::IntRect& aDirtyRect) override;
|
||||
layers::DataTextureSource* GetTextureSource() override { return mTexture; }
|
||||
bool IsValid() override { return true; }
|
||||
|
||||
private:
|
||||
RefPtr<layers::DataTextureSource> mTexture;
|
||||
RefPtr<gfx::DataSourceSurface> mSurface;
|
||||
};
|
||||
};
|
||||
|
||||
} // namespace wr
|
||||
} // namespace mozilla
|
||||
|
||||
#endif
|
||||
@@ -24,6 +24,7 @@ class GLContext;
|
||||
|
||||
namespace wr {
|
||||
|
||||
class RenderAndroidSurfaceTextureHost;
|
||||
class RenderCompositor;
|
||||
class RenderDXGITextureHost;
|
||||
class RenderDXGIYCbCrTextureHost;
|
||||
@@ -81,6 +82,10 @@ class RenderTextureHost {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
virtual RenderAndroidSurfaceTextureHost* AsRenderAndroidSurfaceTextureHost() {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
virtual RenderTextureHostSWGL* AsRenderTextureHostSWGL() { return nullptr; }
|
||||
|
||||
protected:
|
||||
|
||||
@@ -13,6 +13,7 @@ EXPORTS.mozilla.webrender += [
|
||||
"RenderCompositorEGL.h",
|
||||
"RenderCompositorLayersSWGL.h",
|
||||
"RenderCompositorOGL.h",
|
||||
"RenderCompositorOGLSWGL.h",
|
||||
"RenderCompositorSWGL.h",
|
||||
"RenderEGLImageTextureHost.h",
|
||||
"RendererOGL.h",
|
||||
@@ -35,6 +36,7 @@ UNIFIED_SOURCES += [
|
||||
"RenderCompositorEGL.cpp",
|
||||
"RenderCompositorLayersSWGL.cpp",
|
||||
"RenderCompositorOGL.cpp",
|
||||
"RenderCompositorOGLSWGL.cpp",
|
||||
"RenderCompositorSWGL.cpp",
|
||||
"RenderEGLImageTextureHost.cpp",
|
||||
"RendererOGL.cpp",
|
||||
|
||||
@@ -4874,6 +4874,11 @@
|
||||
value: true
|
||||
mirror: once
|
||||
|
||||
- name: gfx.webrender.software.opengl
|
||||
type: bool
|
||||
value: false
|
||||
mirror: once
|
||||
|
||||
- name: gfx.webrender.software.d3d11.upload-mode
|
||||
type: RelaxedAtomicInt32
|
||||
value: 4
|
||||
|
||||
Reference in New Issue
Block a user