mirror of
https://gitlab.winehq.org/wine/wine-gecko.git
synced 2024-09-13 09:24:08 -07:00
Bug 938591 - New D3D11 TextureClient/Host. r=nrc
This commit is contained in:
parent
9b69f08462
commit
8aba9aaa4a
@ -146,6 +146,11 @@ TemporaryRef<TextureHost> CreateTextureHostBasic(const SurfaceDescriptor& aDesc,
|
||||
ISurfaceAllocator* aDeallocator,
|
||||
TextureFlags aFlags);
|
||||
|
||||
// implemented in TextureD3D11.cpp
|
||||
TemporaryRef<TextureHost> CreateTextureHostD3D11(const SurfaceDescriptor& aDesc,
|
||||
ISurfaceAllocator* aDeallocator,
|
||||
TextureFlags aFlags);
|
||||
|
||||
// static
|
||||
TemporaryRef<TextureHost>
|
||||
TextureHost::Create(const SurfaceDescriptor& aDesc,
|
||||
@ -166,6 +171,7 @@ TextureHost::Create(const SurfaceDescriptor& aDesc,
|
||||
#endif
|
||||
#ifdef XP_WIN
|
||||
case LAYERS_D3D11:
|
||||
return CreateTextureHostD3D11(aDesc, aDeallocator, aFlags);
|
||||
case LAYERS_D3D9:
|
||||
// XXX - not implemented yet
|
||||
#endif
|
||||
|
@ -338,6 +338,14 @@ CompositorD3D11::Initialize()
|
||||
return true;
|
||||
}
|
||||
|
||||
TemporaryRef<DataTextureSource>
|
||||
CompositorD3D11::CreateDataTextureSource(TextureFlags aFlags)
|
||||
{
|
||||
RefPtr<DataTextureSource> result = new DataTextureSourceD3D11(gfx::FORMAT_UNKNOWN,
|
||||
this);
|
||||
return result.forget();
|
||||
}
|
||||
|
||||
TextureFactoryIdentifier
|
||||
CompositorD3D11::GetTextureFactoryIdentifier()
|
||||
{
|
||||
@ -576,13 +584,19 @@ CompositorD3D11::DrawQuad(const gfx::Rect& aRect,
|
||||
|
||||
mVSConstants.textureCoords = ycbcrEffect->mTextureCoords;
|
||||
|
||||
TextureSourceD3D11* source = ycbcrEffect->mTexture->AsSourceD3D11();
|
||||
TextureSourceD3D11::YCbCrTextures textures = source->GetYCbCrTextures();
|
||||
const int Y = 0, Cb = 1, Cr = 2;
|
||||
TextureSource* source = ycbcrEffect->mTexture;
|
||||
TextureSourceD3D11* sourceY = source->GetSubSource(Y)->AsSourceD3D11();
|
||||
TextureSourceD3D11* sourceCb = source->GetSubSource(Cb)->AsSourceD3D11();
|
||||
TextureSourceD3D11* sourceCr = source->GetSubSource(Cr)->AsSourceD3D11();
|
||||
|
||||
RefPtr<ID3D11ShaderResourceView> views[3];
|
||||
mDevice->CreateShaderResourceView(textures.mY, nullptr, byRef(views[0]));
|
||||
mDevice->CreateShaderResourceView(textures.mCb, nullptr, byRef(views[1]));
|
||||
mDevice->CreateShaderResourceView(textures.mCr, nullptr, byRef(views[2]));
|
||||
mDevice->CreateShaderResourceView(sourceY->GetD3D11Texture(),
|
||||
nullptr, byRef(views[0]));
|
||||
mDevice->CreateShaderResourceView(sourceCb->GetD3D11Texture(),
|
||||
nullptr, byRef(views[1]));
|
||||
mDevice->CreateShaderResourceView(sourceCr->GetD3D11Texture(),
|
||||
nullptr, byRef(views[2]));
|
||||
|
||||
ID3D11ShaderResourceView* srViews[3] = { views[0], views[1], views[2] };
|
||||
mContext->PSSetShaderResources(0, 3, srViews);
|
||||
|
@ -49,7 +49,7 @@ public:
|
||||
GetTextureFactoryIdentifier() MOZ_OVERRIDE;
|
||||
|
||||
virtual TemporaryRef<DataTextureSource>
|
||||
CreateDataTextureSource(TextureFlags aFlags = 0) MOZ_OVERRIDE { return nullptr; }
|
||||
CreateDataTextureSource(TextureFlags aFlags = 0) MOZ_OVERRIDE;
|
||||
|
||||
virtual bool CanUseCanvasLayerForSize(const gfx::IntSize& aSize) MOZ_OVERRIDE;
|
||||
virtual int32_t GetMaxTextureSize() const MOZ_FINAL;
|
||||
|
@ -20,6 +20,266 @@ using namespace gfx;
|
||||
|
||||
namespace layers {
|
||||
|
||||
static DXGI_FORMAT
|
||||
SurfaceFormatToDXGIFormat(gfx::SurfaceFormat aFormat)
|
||||
{
|
||||
switch (aFormat) {
|
||||
case FORMAT_B8G8R8A8:
|
||||
return DXGI_FORMAT_B8G8R8A8_UNORM;
|
||||
case FORMAT_B8G8R8X8:
|
||||
return DXGI_FORMAT_B8G8R8A8_UNORM;
|
||||
case FORMAT_A8:
|
||||
return DXGI_FORMAT_A8_UNORM;
|
||||
default:
|
||||
MOZ_ASSERT(false, "unsupported format");
|
||||
}
|
||||
}
|
||||
|
||||
static uint32_t
|
||||
GetRequiredTilesD3D11(uint32_t aSize, uint32_t aMaxSize)
|
||||
{
|
||||
uint32_t requiredTiles = aSize / aMaxSize;
|
||||
if (aSize % aMaxSize) {
|
||||
requiredTiles++;
|
||||
}
|
||||
return requiredTiles;
|
||||
}
|
||||
|
||||
static IntRect
|
||||
GetTileRectD3D11(uint32_t aID, IntSize aSize, uint32_t aMaxSize)
|
||||
{
|
||||
uint32_t horizontalTiles = GetRequiredTilesD3D11(aSize.width, aMaxSize);
|
||||
uint32_t verticalTiles = GetRequiredTilesD3D11(aSize.height, aMaxSize);
|
||||
|
||||
uint32_t verticalTile = aID / horizontalTiles;
|
||||
uint32_t horizontalTile = aID % horizontalTiles;
|
||||
|
||||
return IntRect(horizontalTile * aMaxSize,
|
||||
verticalTile * aMaxSize,
|
||||
horizontalTile < (horizontalTiles - 1) ? aMaxSize : aSize.width % aMaxSize,
|
||||
verticalTile < (verticalTiles - 1) ? aMaxSize : aSize.height % aMaxSize);
|
||||
}
|
||||
|
||||
DataTextureSourceD3D11::DataTextureSourceD3D11(SurfaceFormat aFormat,
|
||||
CompositorD3D11* aCompositor)
|
||||
: mFormat(aFormat)
|
||||
, mCompositor(aCompositor)
|
||||
{
|
||||
MOZ_COUNT_CTOR(DataTextureSourceD3D11);
|
||||
}
|
||||
|
||||
DataTextureSourceD3D11::~DataTextureSourceD3D11()
|
||||
{
|
||||
MOZ_COUNT_DTOR(DataTextureSourceD3D11);
|
||||
}
|
||||
|
||||
|
||||
template<typename T> // ID3D10Texture2D or ID3D11Texture2D
|
||||
static void LockD3DTexture(T* aTexture)
|
||||
{
|
||||
MOZ_ASSERT(aTexture);
|
||||
RefPtr<IDXGIKeyedMutex> mutex;
|
||||
aTexture->QueryInterface((IDXGIKeyedMutex**)byRef(mutex));
|
||||
mutex->AcquireSync(0, INFINITE);
|
||||
}
|
||||
|
||||
template<typename T> // ID3D10Texture2D or ID3D11Texture2D
|
||||
static void UnlockD3DTexture(T* aTexture)
|
||||
{
|
||||
MOZ_ASSERT(aTexture);
|
||||
RefPtr<IDXGIKeyedMutex> mutex;
|
||||
aTexture->QueryInterface((IDXGIKeyedMutex**)byRef(mutex));
|
||||
mutex->ReleaseSync(0);
|
||||
}
|
||||
|
||||
TemporaryRef<TextureHost>
|
||||
CreateTextureHostD3D11(const SurfaceDescriptor& aDesc,
|
||||
ISurfaceAllocator* aDeallocator,
|
||||
TextureFlags aFlags)
|
||||
{
|
||||
RefPtr<TextureHost> result;
|
||||
switch (aDesc.type()) {
|
||||
case SurfaceDescriptor::TSurfaceDescriptorShmem:
|
||||
case SurfaceDescriptor::TSurfaceDescriptorMemory: {
|
||||
result = CreateBackendIndependentTextureHost(aDesc, aDeallocator, aFlags);
|
||||
break;
|
||||
}
|
||||
case SurfaceDescriptor::TSurfaceDescriptorD3D10: {
|
||||
result = new DXGITextureHostD3D11(aFlags,
|
||||
aDesc.get_SurfaceDescriptorD3D10());
|
||||
break;
|
||||
}
|
||||
default: {
|
||||
NS_WARNING("Unsupported SurfaceDescriptor type");
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
bool
|
||||
TextureClientD3D11::Lock(OpenMode aMode)
|
||||
{
|
||||
MOZ_ASSERT(!mIsLocked, "The Texture is already locked!");
|
||||
LockD3DTexture(mTexture.get());
|
||||
mIsLocked = true;
|
||||
return true;
|
||||
}
|
||||
|
||||
void
|
||||
TextureClientD3D11::Unlock()
|
||||
{
|
||||
MOZ_ASSERT(mIsLocked, "Unlocked called while the texture is not locked!");
|
||||
UnlockD3DTexture(mTexture.get());
|
||||
mIsLocked = false;
|
||||
}
|
||||
|
||||
DataTextureSourceD3D11::DataTextureSourceD3D11(ID3D11Texture2D* aTexture,
|
||||
SurfaceFormat aFormat)
|
||||
: mFormat(aFormat)
|
||||
{
|
||||
mTexture = aTexture;
|
||||
D3D11_TEXTURE2D_DESC desc;
|
||||
aTexture->GetDesc(&desc);
|
||||
|
||||
mSize = IntSize(desc.Width, desc.Height);
|
||||
}
|
||||
|
||||
DXGITextureHostD3D11::DXGITextureHostD3D11(TextureFlags aFlags,
|
||||
const SurfaceDescriptorD3D10& aDescriptor)
|
||||
: TextureHost(aFlags)
|
||||
, mHandle(aDescriptor.handle())
|
||||
, mFormat(aDescriptor.hasAlpha() ? FORMAT_B8G8R8A8 : FORMAT_B8G8R8X8)
|
||||
, mIsLocked(false)
|
||||
{}
|
||||
|
||||
void
|
||||
DXGITextureHostD3D11::SetCompositor(Compositor* aCompositor)
|
||||
{
|
||||
CompositorD3D11 *d3dCompositor = static_cast<CompositorD3D11*>(aCompositor);
|
||||
mDevice = d3dCompositor ? d3dCompositor->GetDevice() : nullptr;
|
||||
}
|
||||
|
||||
bool
|
||||
DXGITextureHostD3D11::Lock()
|
||||
{
|
||||
if (!mDevice) {
|
||||
NS_WARNING("trying to lock a TextureHost without a D3D device");
|
||||
return false;
|
||||
}
|
||||
if (!mTextureSource) {
|
||||
RefPtr<ID3D11Texture2D> tex;
|
||||
mDevice->OpenSharedResource((HANDLE)mHandle,
|
||||
__uuidof(ID3D11Texture2D),
|
||||
(void**)(ID3D11Texture2D**)byRef(tex));
|
||||
|
||||
mTextureSource = new DataTextureSourceD3D11(tex, mFormat);
|
||||
D3D11_TEXTURE2D_DESC desc;
|
||||
tex->GetDesc(&desc);
|
||||
mSize = IntSize(desc.Width, desc.Height);
|
||||
}
|
||||
|
||||
LockD3DTexture(mTextureSource->GetD3D11Texture());
|
||||
|
||||
mIsLocked = true;
|
||||
return true;
|
||||
}
|
||||
|
||||
void
|
||||
DXGITextureHostD3D11::Unlock()
|
||||
{
|
||||
MOZ_ASSERT(mIsLocked);
|
||||
UnlockD3DTexture(mTextureSource->GetD3D11Texture());
|
||||
mIsLocked = false;
|
||||
}
|
||||
|
||||
NewTextureSource*
|
||||
DXGITextureHostD3D11::GetTextureSources()
|
||||
{
|
||||
return mTextureSource.get();
|
||||
}
|
||||
|
||||
bool
|
||||
DataTextureSourceD3D11::Update(DataSourceSurface* aSurface,
|
||||
TextureFlags aFlags,
|
||||
nsIntRegion* aDestRegion,
|
||||
IntPoint* aSrcOffset)
|
||||
{
|
||||
// Right now we only support null aDestRegion and aSrcOffset (which means)
|
||||
// full surface update. Incremental update is only used on Mac so it is
|
||||
// not clear that we ever will need to support it for D3D.
|
||||
MOZ_ASSERT(!aDestRegion && !aSrcOffset);
|
||||
MOZ_ASSERT(aSurface);
|
||||
|
||||
if (!mCompositor || !mCompositor->GetDevice()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
uint32_t bpp = BytesPerPixel(aSurface->GetFormat());
|
||||
DXGI_FORMAT dxgiFormat = SurfaceFormatToDXGIFormat(aSurface->GetFormat());
|
||||
|
||||
mSize = aSurface->GetSize();
|
||||
|
||||
CD3D11_TEXTURE2D_DESC desc(dxgiFormat, mSize.width, mSize.height,
|
||||
1, 1, D3D11_BIND_SHADER_RESOURCE,
|
||||
D3D11_USAGE_IMMUTABLE);
|
||||
|
||||
int32_t maxSize = mCompositor->GetMaxTextureSize();
|
||||
if (mSize.width <= maxSize && mSize.height <= maxSize) {
|
||||
D3D11_SUBRESOURCE_DATA initData;
|
||||
initData.pSysMem = aSurface->GetData();
|
||||
initData.SysMemPitch = aSurface->Stride();
|
||||
|
||||
mCompositor->GetDevice()->CreateTexture2D(&desc, &initData, byRef(mTexture));
|
||||
mIsTiled = false;
|
||||
} else {
|
||||
mIsTiled = true;
|
||||
uint32_t tileCount = GetRequiredTilesD3D11(mSize.width, maxSize) *
|
||||
GetRequiredTilesD3D11(mSize.height, maxSize);
|
||||
|
||||
mTileTextures.resize(tileCount);
|
||||
|
||||
for (uint32_t i = 0; i < tileCount; i++) {
|
||||
IntRect tileRect = GetTileRect(i);
|
||||
|
||||
desc.Width = tileRect.width;
|
||||
desc.Height = tileRect.height;
|
||||
|
||||
D3D11_SUBRESOURCE_DATA initData;
|
||||
initData.pSysMem = aSurface->GetData() +
|
||||
tileRect.y * aSurface->Stride() +
|
||||
tileRect.x * bpp;
|
||||
initData.SysMemPitch = aSurface->Stride();
|
||||
|
||||
mCompositor->GetDevice()->CreateTexture2D(&desc, &initData, byRef(mTileTextures[i]));
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
IntRect
|
||||
DataTextureSourceD3D11::GetTileRect(uint32_t aIndex) const
|
||||
{
|
||||
return GetTileRectD3D11(aIndex, mSize, mCompositor->GetMaxTextureSize());
|
||||
}
|
||||
|
||||
nsIntRect
|
||||
DataTextureSourceD3D11::GetTileRect()
|
||||
{
|
||||
IntRect rect = GetTileRect(mCurrentTile);
|
||||
return nsIntRect(rect.x, rect.y, rect.width, rect.height);
|
||||
}
|
||||
|
||||
void
|
||||
DataTextureSourceD3D11::SetCompositor(Compositor* aCompositor)
|
||||
{
|
||||
CompositorD3D11* d3dCompositor = static_cast<CompositorD3D11*>(aCompositor);
|
||||
if (mCompositor != d3dCompositor) {
|
||||
mTexture = nullptr;
|
||||
mTileTextures.resize(0);
|
||||
}
|
||||
mCompositor = d3dCompositor;
|
||||
}
|
||||
|
||||
TemporaryRef<DeprecatedTextureHost>
|
||||
CreateDeprecatedTextureHostD3D11(SurfaceDescriptorType aDescriptorType,
|
||||
uint32_t aDeprecatedTextureHostFlags,
|
||||
@ -46,12 +306,12 @@ CompositingRenderTargetD3D11::CompositingRenderTargetD3D11(ID3D11Texture2D* aTex
|
||||
{
|
||||
MOZ_ASSERT(aTexture);
|
||||
|
||||
mTextures[0] = aTexture;
|
||||
mTexture = aTexture;
|
||||
|
||||
RefPtr<ID3D11Device> device;
|
||||
mTextures[0]->GetDevice(byRef(device));
|
||||
mTexture->GetDevice(byRef(device));
|
||||
|
||||
HRESULT hr = device->CreateRenderTargetView(mTextures[0], nullptr, byRef(mRTView));
|
||||
HRESULT hr = device->CreateRenderTargetView(mTexture, nullptr, byRef(mRTView));
|
||||
|
||||
if (FAILED(hr)) {
|
||||
LOGD3D11("Failed to create RenderTargetView.");
|
||||
@ -286,15 +546,6 @@ DeprecatedTextureHostShmemD3D11::GetTileRect()
|
||||
return nsIntRect(rect.x, rect.y, rect.width, rect.height);
|
||||
}
|
||||
|
||||
static uint32_t GetRequiredTilesD3D11(uint32_t aSize, uint32_t aMaxSize)
|
||||
{
|
||||
uint32_t requiredTiles = aSize / aMaxSize;
|
||||
if (aSize % aMaxSize) {
|
||||
requiredTiles++;
|
||||
}
|
||||
return requiredTiles;
|
||||
}
|
||||
|
||||
void
|
||||
DeprecatedTextureHostShmemD3D11::SetCompositor(Compositor* aCompositor)
|
||||
{
|
||||
@ -351,7 +602,7 @@ DeprecatedTextureHostShmemD3D11::UpdateImpl(const SurfaceDescriptor& aImage,
|
||||
initData.pSysMem = surf->Data();
|
||||
initData.SysMemPitch = surf->Stride();
|
||||
|
||||
mDevice->CreateTexture2D(&desc, &initData, byRef(mTextures[0]));
|
||||
mDevice->CreateTexture2D(&desc, &initData, byRef(mTexture));
|
||||
mIsTiled = false;
|
||||
} else {
|
||||
mIsTiled = true;
|
||||
@ -381,16 +632,7 @@ IntRect
|
||||
DeprecatedTextureHostShmemD3D11::GetTileRect(uint32_t aID) const
|
||||
{
|
||||
uint32_t maxSize = GetMaxTextureSizeForFeatureLevel(mDevice->GetFeatureLevel());
|
||||
uint32_t horizontalTiles = GetRequiredTilesD3D11(mSize.width, maxSize);
|
||||
uint32_t verticalTiles = GetRequiredTilesD3D11(mSize.height, maxSize);
|
||||
|
||||
uint32_t verticalTile = aID / horizontalTiles;
|
||||
uint32_t horizontalTile = aID % horizontalTiles;
|
||||
|
||||
return IntRect(horizontalTile * maxSize,
|
||||
verticalTile * maxSize,
|
||||
horizontalTile < (horizontalTiles - 1) ? maxSize : mSize.width % maxSize,
|
||||
verticalTile < (verticalTiles - 1) ? maxSize : mSize.height % maxSize);
|
||||
return GetTileRectD3D11(aID, mSize, maxSize);
|
||||
}
|
||||
|
||||
void
|
||||
@ -428,8 +670,8 @@ DeprecatedTextureHostDXGID3D11::UpdateImpl(const SurfaceDescriptor& aImage,
|
||||
|
||||
HRESULT hr =mDevice->OpenSharedResource((HANDLE)aImage.get_SurfaceDescriptorD3D10().handle(),
|
||||
__uuidof(ID3D11Texture2D),
|
||||
(void**)(ID3D11Texture2D**)byRef(mTextures[0]));
|
||||
if (!mTextures[0] || FAILED(hr)) {
|
||||
(void**)(ID3D11Texture2D**)byRef(mTexture));
|
||||
if (!mTexture || FAILED(hr)) {
|
||||
NS_WARNING("Could not open shared resource");
|
||||
mSize = IntSize(0, 0);
|
||||
return;
|
||||
@ -438,7 +680,7 @@ DeprecatedTextureHostDXGID3D11::UpdateImpl(const SurfaceDescriptor& aImage,
|
||||
mFormat = aImage.get_SurfaceDescriptorD3D10().hasAlpha() ? FORMAT_B8G8R8A8 : FORMAT_B8G8R8X8;
|
||||
|
||||
D3D11_TEXTURE2D_DESC desc;
|
||||
mTextures[0]->GetDesc(&desc);
|
||||
mTexture->GetDesc(&desc);
|
||||
|
||||
mSize = IntSize(desc.Width, desc.Height);
|
||||
}
|
||||
@ -446,11 +688,11 @@ DeprecatedTextureHostDXGID3D11::UpdateImpl(const SurfaceDescriptor& aImage,
|
||||
void
|
||||
DeprecatedTextureHostDXGID3D11::LockTexture()
|
||||
{
|
||||
if (!mTextures[0]) {
|
||||
if (!mTexture) {
|
||||
return;
|
||||
}
|
||||
RefPtr<IDXGIKeyedMutex> mutex;
|
||||
mTextures[0]->QueryInterface((IDXGIKeyedMutex**)byRef(mutex));
|
||||
mTexture->QueryInterface((IDXGIKeyedMutex**)byRef(mutex));
|
||||
|
||||
mutex->AcquireSync(0, INFINITE);
|
||||
}
|
||||
@ -458,26 +700,45 @@ DeprecatedTextureHostDXGID3D11::LockTexture()
|
||||
void
|
||||
DeprecatedTextureHostDXGID3D11::ReleaseTexture()
|
||||
{
|
||||
if (!mTextures[0]) {
|
||||
if (!mTexture) {
|
||||
return;
|
||||
}
|
||||
RefPtr<IDXGIKeyedMutex> mutex;
|
||||
mTextures[0]->QueryInterface((IDXGIKeyedMutex**)byRef(mutex));
|
||||
mTexture->QueryInterface((IDXGIKeyedMutex**)byRef(mutex));
|
||||
|
||||
mutex->ReleaseSync(0);
|
||||
}
|
||||
|
||||
DeprecatedTextureHostYCbCrD3D11::DeprecatedTextureHostYCbCrD3D11()
|
||||
: mCompositor(nullptr)
|
||||
{
|
||||
mFormat = FORMAT_YUV;
|
||||
}
|
||||
|
||||
DeprecatedTextureHostYCbCrD3D11::~DeprecatedTextureHostYCbCrD3D11()
|
||||
{
|
||||
}
|
||||
|
||||
ID3D11Device*
|
||||
DeprecatedTextureHostYCbCrD3D11::GetDevice()
|
||||
{
|
||||
return mCompositor ? mCompositor->GetDevice() : nullptr;
|
||||
NewTextureSource* source = mFirstSource.get();
|
||||
while (source) {
|
||||
static_cast<DataTextureSourceD3D11*>(source)->SetCompositor(mCompositor);
|
||||
source = source->GetNextSibling();
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
DeprecatedTextureHostYCbCrD3D11::SetCompositor(Compositor* aCompositor)
|
||||
{
|
||||
CompositorD3D11* d3dCompositor = static_cast<CompositorD3D11*>(aCompositor);
|
||||
mDevice = d3dCompositor ? d3dCompositor->GetDevice() : nullptr;
|
||||
}
|
||||
|
||||
IntSize
|
||||
DeprecatedTextureHostYCbCrD3D11::GetSize() const
|
||||
{
|
||||
return TextureSourceD3D11::GetSize();
|
||||
mCompositor = static_cast<CompositorD3D11*>(aCompositor);
|
||||
NewTextureSource* source = mFirstSource.get();
|
||||
while (source) {
|
||||
static_cast<DataTextureSourceD3D11*>(source)->SetCompositor(mCompositor);
|
||||
source = source->GetNextSibling();
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
@ -493,25 +754,49 @@ DeprecatedTextureHostYCbCrD3D11::UpdateImpl(const SurfaceDescriptor& aImage,
|
||||
|
||||
gfx::IntSize size = yuvDeserializer.GetYSize();
|
||||
|
||||
D3D11_SUBRESOURCE_DATA initData;
|
||||
initData.pSysMem = yuvDeserializer.GetYData();
|
||||
initData.SysMemPitch = yuvDeserializer.GetYStride();
|
||||
|
||||
CD3D11_TEXTURE2D_DESC desc(DXGI_FORMAT_A8_UNORM, size.width, size.height,
|
||||
1, 1, D3D11_BIND_SHADER_RESOURCE,
|
||||
D3D11_USAGE_IMMUTABLE);
|
||||
|
||||
mDevice->CreateTexture2D(&desc, &initData, byRef(mTextures[0]));
|
||||
|
||||
initData.pSysMem = yuvDeserializer.GetCbData();
|
||||
initData.SysMemPitch = yuvDeserializer.GetCbCrStride();
|
||||
desc.Width = yuvDeserializer.GetCbCrSize().width;
|
||||
desc.Height = yuvDeserializer.GetCbCrSize().height;
|
||||
|
||||
mDevice->CreateTexture2D(&desc, &initData, byRef(mTextures[1]));
|
||||
|
||||
initData.pSysMem = yuvDeserializer.GetCrData();
|
||||
mDevice->CreateTexture2D(&desc, &initData, byRef(mTextures[2]));
|
||||
RefPtr<DataTextureSource> srcY;
|
||||
RefPtr<DataTextureSource> srcCb;
|
||||
RefPtr<DataTextureSource> srcCr;
|
||||
if (!mFirstSource) {
|
||||
srcY = new DataTextureSourceD3D11(FORMAT_A8, mCompositor);
|
||||
srcCb = new DataTextureSourceD3D11(FORMAT_A8, mCompositor);
|
||||
srcCr = new DataTextureSourceD3D11(FORMAT_A8, mCompositor);
|
||||
mFirstSource = srcY;
|
||||
srcY->SetNextSibling(srcCb);
|
||||
srcCb->SetNextSibling(srcCr);
|
||||
} else {
|
||||
MOZ_ASSERT(mFirstSource->GetNextSibling());
|
||||
MOZ_ASSERT(mFirstSource->GetNextSibling()->GetNextSibling());
|
||||
srcY = mFirstSource;
|
||||
srcCb = mFirstSource->GetNextSibling()->AsDataTextureSource();
|
||||
srcCr = mFirstSource->GetNextSibling()->GetNextSibling()->AsDataTextureSource();
|
||||
}
|
||||
RefPtr<gfx::DataSourceSurface> wrapperY =
|
||||
gfx::Factory::CreateWrappingDataSourceSurface(yuvDeserializer.GetYData(),
|
||||
yuvDeserializer.GetYStride(),
|
||||
yuvDeserializer.GetYSize(),
|
||||
FORMAT_A8);
|
||||
RefPtr<gfx::DataSourceSurface> wrapperCb =
|
||||
gfx::Factory::CreateWrappingDataSourceSurface(yuvDeserializer.GetCbData(),
|
||||
yuvDeserializer.GetCbCrStride(),
|
||||
yuvDeserializer.GetCbCrSize(),
|
||||
FORMAT_A8);
|
||||
RefPtr<gfx::DataSourceSurface> wrapperCr =
|
||||
gfx::Factory::CreateWrappingDataSourceSurface(yuvDeserializer.GetCrData(),
|
||||
yuvDeserializer.GetCbCrStride(),
|
||||
yuvDeserializer.GetCbCrSize(),
|
||||
FORMAT_A8);
|
||||
// We don't support partial updates for Y U V textures
|
||||
NS_ASSERTION(!aRegion, "Unsupported partial updates for YCbCr textures");
|
||||
if (!srcY->Update(wrapperY, TEXTURE_FLAGS_DEFAULT) ||
|
||||
!srcCb->Update(wrapperCb, TEXTURE_FLAGS_DEFAULT) ||
|
||||
!srcCr->Update(wrapperCr, TEXTURE_FLAGS_DEFAULT)) {
|
||||
NS_WARNING("failed to update the DataTextureSource");
|
||||
mFirstSource = nullptr;
|
||||
mSize.width = 0;
|
||||
mSize.height = 0;
|
||||
return;
|
||||
}
|
||||
|
||||
mSize = IntSize(size.width, size.height);
|
||||
}
|
||||
|
@ -19,33 +19,150 @@ class gfxD2DSurface;
|
||||
namespace mozilla {
|
||||
namespace layers {
|
||||
|
||||
class CompositorD3D11;
|
||||
|
||||
/**
|
||||
* A TextureClient to share a D3D10 texture with the compositor thread.
|
||||
* The corresponding TextureHost is DXGITextureHostD3D11
|
||||
*/
|
||||
class TextureClientD3D11 : public TextureClient
|
||||
{
|
||||
public:
|
||||
virtual bool IsAllocated() const MOZ_OVERRIDE;
|
||||
|
||||
virtual bool Lock(OpenMode aOpenMode) MOZ_OVERRIDE;
|
||||
|
||||
virtual void Unlock() MOZ_OVERRIDE;
|
||||
|
||||
virtual bool ToSurfaceDescriptor(SurfaceDescriptor& aOutDescriptor) MOZ_OVERRIDE;
|
||||
protected:
|
||||
RefPtr<ID3D10Texture2D> mTexture;
|
||||
bool mIsLocked;
|
||||
};
|
||||
|
||||
/**
|
||||
* TextureSource that provides with the necessary APIs to be composited by a
|
||||
* CompositorD3D11.
|
||||
*/
|
||||
class TextureSourceD3D11
|
||||
{
|
||||
public:
|
||||
TextureSourceD3D11() {}
|
||||
virtual ~TextureSourceD3D11() {}
|
||||
|
||||
virtual ID3D11Texture2D* GetD3D11Texture() const { return mTextures[0]; }
|
||||
virtual bool IsYCbCrSource() const { return false; }
|
||||
|
||||
struct YCbCrTextures
|
||||
{
|
||||
ID3D11Texture2D *mY;
|
||||
ID3D11Texture2D *mCb;
|
||||
ID3D11Texture2D *mCr;
|
||||
};
|
||||
|
||||
virtual YCbCrTextures GetYCbCrTextures()
|
||||
{
|
||||
YCbCrTextures textures = { mTextures[0], mTextures[1], mTextures[2] };
|
||||
return textures;
|
||||
}
|
||||
virtual ID3D11Texture2D* GetD3D11Texture() const { return mTexture; }
|
||||
|
||||
protected:
|
||||
virtual gfx::IntSize GetSize() const { return mSize; }
|
||||
|
||||
gfx::IntSize mSize;
|
||||
RefPtr<ID3D11Texture2D> mTextures[3];
|
||||
RefPtr<ID3D11Texture2D> mTexture;
|
||||
};
|
||||
|
||||
/**
|
||||
* A TextureSource that implements the DataTextureSource interface.
|
||||
* it can be used without a TextureHost and is able to upload texture data
|
||||
* from a gfx::DataSourceSurface.
|
||||
*/
|
||||
class DataTextureSourceD3D11 : public DataTextureSource
|
||||
, public TextureSourceD3D11
|
||||
, public TileIterator
|
||||
{
|
||||
public:
|
||||
DataTextureSourceD3D11(gfx::SurfaceFormat aFormat, CompositorD3D11* aCompositor);
|
||||
|
||||
DataTextureSourceD3D11(ID3D11Texture2D* aTexture,
|
||||
gfx::SurfaceFormat aFormat);
|
||||
|
||||
virtual ~DataTextureSourceD3D11();
|
||||
|
||||
void SetCompositor(Compositor* aCompositor);
|
||||
|
||||
// DataTextureSource
|
||||
|
||||
virtual bool Update(gfx::DataSourceSurface* aSurface,
|
||||
TextureFlags aFlags,
|
||||
nsIntRegion* aDestRegion = nullptr,
|
||||
gfx::IntPoint* aSrcOffset = nullptr) MOZ_OVERRIDE;
|
||||
|
||||
// TextureSource
|
||||
|
||||
virtual TextureSourceD3D11* AsSourceD3D11() MOZ_OVERRIDE { return this; }
|
||||
|
||||
virtual DataTextureSource* AsDataTextureSource() MOZ_OVERRIDE { return this; }
|
||||
|
||||
virtual void DeallocateDeviceData() MOZ_OVERRIDE { mTexture = nullptr; }
|
||||
|
||||
virtual gfx::IntSize GetSize() const MOZ_OVERRIDE { return mSize; }
|
||||
|
||||
virtual gfx::SurfaceFormat GetFormat() const MOZ_OVERRIDE { return mFormat; }
|
||||
|
||||
// TileIterator
|
||||
|
||||
virtual TileIterator* AsTileIterator() MOZ_OVERRIDE { return mIsTiled ? this : nullptr; }
|
||||
|
||||
virtual size_t GetTileCount() MOZ_OVERRIDE { return mTileTextures.size(); }
|
||||
|
||||
virtual bool NextTile() MOZ_OVERRIDE { return (++mCurrentTile < mTileTextures.size()); }
|
||||
|
||||
virtual nsIntRect GetTileRect() MOZ_OVERRIDE;
|
||||
|
||||
virtual void EndTileIteration() MOZ_OVERRIDE { mIterating = false; }
|
||||
|
||||
virtual void BeginTileIteration() MOZ_OVERRIDE
|
||||
{
|
||||
mIterating = true;
|
||||
mCurrentTile = 0;
|
||||
}
|
||||
|
||||
protected:
|
||||
gfx::IntRect GetTileRect(uint32_t aIndex) const;
|
||||
|
||||
std::vector< RefPtr<ID3D11Texture2D> > mTileTextures;
|
||||
RefPtr<CompositorD3D11> mCompositor;
|
||||
gfx::SurfaceFormat mFormat;
|
||||
TextureFlags mFlags;
|
||||
uint32_t mCurrentTile;
|
||||
bool mIsTiled;
|
||||
bool mIterating;
|
||||
|
||||
};
|
||||
|
||||
/**
|
||||
* A TextureHost for shared D3D11 textures.
|
||||
*/
|
||||
class DXGITextureHostD3D11 : public TextureHost
|
||||
{
|
||||
public:
|
||||
DXGITextureHostD3D11(TextureFlags aFlags,
|
||||
const SurfaceDescriptorD3D10& aDescriptor);
|
||||
|
||||
virtual NewTextureSource* GetTextureSources() MOZ_OVERRIDE;
|
||||
|
||||
virtual void DeallocateDeviceData() MOZ_OVERRIDE {}
|
||||
|
||||
virtual void SetCompositor(Compositor* aCompositor) MOZ_OVERRIDE;
|
||||
|
||||
virtual gfx::SurfaceFormat GetFormat() const MOZ_OVERRIDE { return mFormat; }
|
||||
|
||||
virtual bool Lock() MOZ_OVERRIDE;
|
||||
|
||||
virtual void Unlock() MOZ_OVERRIDE;
|
||||
|
||||
virtual gfx::IntSize GetSize() const MOZ_OVERRIDE { return mSize; }
|
||||
|
||||
virtual TemporaryRef<gfx::DataSourceSurface> GetAsSurface() MOZ_OVERRIDE
|
||||
{
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
protected:
|
||||
RefPtr<DataTextureSourceD3D11> mTextureSource;
|
||||
RefPtr<ID3D11Device> mDevice;
|
||||
gfx::IntSize mSize;
|
||||
WindowsHandle mHandle;
|
||||
gfx::SurfaceFormat mFormat;
|
||||
bool mIsLocked;
|
||||
};
|
||||
|
||||
class CompositingRenderTargetD3D11 : public CompositingRenderTarget,
|
||||
@ -146,7 +263,7 @@ public:
|
||||
|
||||
virtual TemporaryRef<gfx::DataSourceSurface> GetAsSurface() MOZ_OVERRIDE
|
||||
{
|
||||
return nullptr; // TODO: cf bug 872568
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
virtual const char* Name() MOZ_OVERRIDE
|
||||
@ -226,22 +343,24 @@ private:
|
||||
};
|
||||
|
||||
class DeprecatedTextureHostYCbCrD3D11 : public DeprecatedTextureHost
|
||||
, public TextureSourceD3D11
|
||||
{
|
||||
public:
|
||||
DeprecatedTextureHostYCbCrD3D11()
|
||||
: mDevice(nullptr)
|
||||
{
|
||||
mFormat = gfx::FORMAT_YUV;
|
||||
}
|
||||
DeprecatedTextureHostYCbCrD3D11();
|
||||
~DeprecatedTextureHostYCbCrD3D11();
|
||||
|
||||
virtual void SetCompositor(Compositor* aCompositor) MOZ_OVERRIDE;
|
||||
|
||||
virtual TextureSourceD3D11* AsSourceD3D11() MOZ_OVERRIDE { return this; }
|
||||
virtual TextureSourceD3D11* AsSourceD3D11() MOZ_OVERRIDE
|
||||
{
|
||||
return mFirstSource->AsSourceD3D11();
|
||||
}
|
||||
|
||||
virtual gfx::IntSize GetSize() const MOZ_OVERRIDE;
|
||||
virtual gfx::IntSize GetSize() const MOZ_OVERRIDE { return mSize; }
|
||||
|
||||
virtual bool IsYCbCrSource() const MOZ_OVERRIDE { return true; }
|
||||
TextureSource* GetSubSource(int index) MOZ_OVERRIDE
|
||||
{
|
||||
return mFirstSource ? mFirstSource->GetSubSource(index) : nullptr;
|
||||
}
|
||||
|
||||
virtual TemporaryRef<gfx::DataSourceSurface> GetAsSurface() MOZ_OVERRIDE
|
||||
{
|
||||
@ -258,8 +377,12 @@ protected:
|
||||
nsIntRegion* aRegion,
|
||||
nsIntPoint* aOffset = nullptr) MOZ_OVERRIDE;
|
||||
|
||||
ID3D11Device* GetDevice();
|
||||
|
||||
private:
|
||||
RefPtr<ID3D11Device> mDevice;
|
||||
gfx::IntSize mSize;
|
||||
RefPtr<DataTextureSource> mFirstSource;
|
||||
RefPtr<CompositorD3D11> mCompositor;
|
||||
};
|
||||
|
||||
inline uint32_t GetMaxTextureSizeForFeatureLevel(D3D_FEATURE_LEVEL aFeatureLevel)
|
||||
|
Loading…
Reference in New Issue
Block a user