Files
tubestation/gfx/layers/opengl/TextureClientOGL.h
Jamie Nicol 8f0b9e407f Bug 1784109 - Override SurfaceTexture transform for videos on Mediatek 6735. r=gfx-reviewers,media-playback-reviewers,lsalzman,alwu
On Android, SurfaceTextures provide a transform matrix that should be
applied to texture coordinates when sampling from the texture. Prior
to bug 1731980 we ignored this value, and simply y-flipped the video
instead. On most devices the transform is just a y-flip, so this
produced the correct results. However, on some devices the transform
included a scale as well as the y-flip, meaning that we rendered
videos at an incorrect size.

The fix for bug 1731980 was to correctly apply the transformation.
However, it now appears that on Mediatek 6735 devices the transform
provided by the system is incorrect. On these devices, videos were
rendered correctly when we ignored the transform and just did a
y-flip, and now that we apply the transform videos are rendered at the
wrong size.

This patch makes it so that we override the system-provided transform
on these devices with a simple y-flip. The existing mIgnoreTransform
flag has been changed to an optional "transform override" value to
achieve this. We ensure that we only override the transform for
SurfaceTextures that are output from a MediaCodec, to ensure that we
don't accidentally apply the wrong transform to SurfaceTextures
attached to other sources.

Differential Revision: https://phabricator.services.mozilla.com/D155706
2022-09-09 14:43:21 +00:00

165 lines
4.8 KiB
C++

/* -*- 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_TEXTURECLIENTOGL_H
#define MOZILLA_GFX_TEXTURECLIENTOGL_H
#include "GLContextTypes.h" // for SharedTextureHandle, etc
#include "GLImages.h"
#include "gfxTypes.h"
#include "mozilla/Attributes.h" // for override
#include "mozilla/gfx/Point.h" // for IntSize
#include "mozilla/gfx/Types.h" // for SurfaceFormat
#include "mozilla/layers/CompositorTypes.h"
#include "mozilla/layers/LayersSurfaces.h" // for SurfaceDescriptor
#include "mozilla/layers/TextureClient.h" // for TextureClient, etc
#ifdef MOZ_WIDGET_ANDROID
# include "AndroidSurfaceTexture.h"
# include "AndroidNativeWindow.h"
# include "mozilla/java/GeckoSurfaceWrappers.h"
# include "mozilla/layers/AndroidHardwareBuffer.h"
#endif
namespace mozilla {
namespace gfx {
class DrawTarget;
} // namespace gfx
namespace layers {
#ifdef MOZ_WIDGET_ANDROID
class AndroidHardwareBuffer;
class AndroidSurfaceTextureData : public TextureData {
public:
static already_AddRefed<TextureClient> CreateTextureClient(
AndroidSurfaceTextureHandle aHandle, gfx::IntSize aSize, bool aContinuous,
gl::OriginPos aOriginPos, bool aHasAlpha,
Maybe<gfx::Matrix4x4> aTransformOverride, LayersIPCChannel* aAllocator,
TextureFlags aFlags);
virtual ~AndroidSurfaceTextureData();
void FillInfo(TextureData::Info& aInfo) const override;
bool Serialize(SurfaceDescriptor& aOutDescriptor) override;
// Useless functions.
bool Lock(OpenMode) override { return true; }
void Unlock() override {}
// Our data is always owned externally.
void Deallocate(LayersIPCChannel*) override {}
protected:
AndroidSurfaceTextureData(AndroidSurfaceTextureHandle aHandle,
gfx::IntSize aSize, bool aContinuous,
bool aHasAlpha,
Maybe<gfx::Matrix4x4> aTransformOverride);
const AndroidSurfaceTextureHandle mHandle;
const gfx::IntSize mSize;
const bool mContinuous;
const bool mHasAlpha;
const Maybe<gfx::Matrix4x4> mTransformOverride;
};
class AndroidNativeWindowTextureData : public TextureData {
public:
static AndroidNativeWindowTextureData* Create(gfx::IntSize aSize,
gfx::SurfaceFormat aFormat);
void FillInfo(TextureData::Info& aInfo) const override;
bool Serialize(SurfaceDescriptor& aOutDescriptor) override;
bool Lock(OpenMode) override;
void Unlock() override;
void Forget(LayersIPCChannel*) override;
void Deallocate(LayersIPCChannel*) override {}
already_AddRefed<gfx::DrawTarget> BorrowDrawTarget() override;
void OnForwardedToHost() override;
protected:
AndroidNativeWindowTextureData(java::GeckoSurface::Param aSurface,
gfx::IntSize aSize,
gfx::SurfaceFormat aFormat);
private:
java::GeckoSurface::GlobalRef mSurface;
ANativeWindow* mNativeWindow;
ANativeWindow_Buffer mBuffer;
// Keeps track of whether the underlying NativeWindow is actually locked.
bool mIsLocked;
const gfx::IntSize mSize;
const gfx::SurfaceFormat mFormat;
};
class AndroidHardwareBufferTextureData : public TextureData {
public:
static AndroidHardwareBufferTextureData* Create(gfx::IntSize aSize,
gfx::SurfaceFormat aFormat);
virtual ~AndroidHardwareBufferTextureData();
void FillInfo(TextureData::Info& aInfo) const override;
bool Serialize(SurfaceDescriptor& aOutDescriptor) override;
bool Lock(OpenMode aMode) override;
void Unlock() override;
void Forget(LayersIPCChannel*) override;
void Deallocate(LayersIPCChannel*) override {}
already_AddRefed<gfx::DrawTarget> BorrowDrawTarget() override;
void OnForwardedToHost() override;
TextureFlags GetTextureFlags() const override;
Maybe<uint64_t> GetBufferId() const override;
mozilla::ipc::FileDescriptor GetAcquireFence() override;
AndroidHardwareBufferTextureData* AsAndroidHardwareBufferTextureData()
override {
return this;
}
AndroidHardwareBuffer* GetBuffer() { return mAndroidHardwareBuffer; }
protected:
AndroidHardwareBufferTextureData(
AndroidHardwareBuffer* aAndroidHardwareBuffer, gfx::IntSize aSize,
gfx::SurfaceFormat aFormat);
RefPtr<AndroidHardwareBuffer> mAndroidHardwareBuffer;
const gfx::IntSize mSize;
const gfx::SurfaceFormat mFormat;
void* mAddress;
// Keeps track of whether the underlying NativeWindow is actually locked.
bool mIsLocked;
};
#endif // MOZ_WIDGET_ANDROID
} // namespace layers
} // namespace mozilla
#endif