mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-10-16 23:05:42 +00:00
Bug 1393031 - Begin moving OpAddExternalImage to IpcResourceUpdateQueue and recycle image keys in WebRenderImageLayer. r=jrmuizel
This commit is contained in:
parent
2e704f3c2c
commit
6721e0dbdc
@ -135,6 +135,7 @@ union OpUpdateResource {
|
||||
OpDeleteFont;
|
||||
OpAddFontInstance;
|
||||
OpDeleteFontInstance;
|
||||
OpAddExternalImage;
|
||||
};
|
||||
|
||||
} // namespace
|
||||
|
@ -172,6 +172,12 @@ IpcResourceUpdateQueue::AddBlobImage(ImageKey key, const ImageDescriptor& aDescr
|
||||
mUpdates.AppendElement(layers::OpAddBlobImage(aDescriptor, bytes, 0, key));
|
||||
}
|
||||
|
||||
void
|
||||
IpcResourceUpdateQueue::AddExternalImage(wr::ExternalImageId aExtId, wr::ImageKey aKey)
|
||||
{
|
||||
mUpdates.AppendElement(layers::OpAddExternalImage(aExtId, aKey));
|
||||
}
|
||||
|
||||
void
|
||||
IpcResourceUpdateQueue::UpdateImageBuffer(ImageKey aKey,
|
||||
const ImageDescriptor& aDescriptor,
|
||||
|
@ -63,6 +63,8 @@ public:
|
||||
const ImageDescriptor& aDescriptor,
|
||||
Range<uint8_t> aBytes);
|
||||
|
||||
void AddExternalImage(wr::ExternalImageId aExtId, wr::ImageKey aKey);
|
||||
|
||||
void UpdateImageBuffer(wr::ImageKey aKey,
|
||||
const ImageDescriptor& aDescriptor,
|
||||
Range<uint8_t> aBytes);
|
||||
|
@ -17,6 +17,7 @@ namespace layers {
|
||||
|
||||
ScrollingLayersHelper::ScrollingLayersHelper(WebRenderLayer* aLayer,
|
||||
wr::DisplayListBuilder& aBuilder,
|
||||
wr::IpcResourceUpdateQueue& aResources,
|
||||
const StackingContextHelper& aStackingContext)
|
||||
: mLayer(aLayer)
|
||||
, mBuilder(&aBuilder)
|
||||
@ -26,7 +27,7 @@ ScrollingLayersHelper::ScrollingLayersHelper(WebRenderLayer* aLayer,
|
||||
if (!mLayer->WrManager()->AsyncPanZoomEnabled()) {
|
||||
// If APZ is disabled then we don't need to push the scrolling clips. We
|
||||
// still want to push the layer's local clip though.
|
||||
PushLayerLocalClip(aStackingContext);
|
||||
PushLayerLocalClip(aStackingContext, aResources);
|
||||
return;
|
||||
}
|
||||
|
||||
@ -39,7 +40,7 @@ ScrollingLayersHelper::ScrollingLayersHelper(WebRenderLayer* aLayer,
|
||||
// corresponding scroll layer, so that when we set an async scroll position
|
||||
// on the scroll layer, the clip isn't affected by it.
|
||||
if (const Maybe<LayerClip>& clip = metadata.GetScrollClip()) {
|
||||
PushLayerClip(clip.ref(), aStackingContext);
|
||||
PushLayerClip(clip.ref(), aStackingContext, aResources);
|
||||
}
|
||||
|
||||
const FrameMetrics& fm = layer->GetFrameMetrics(i - 1);
|
||||
@ -48,7 +49,7 @@ ScrollingLayersHelper::ScrollingLayersHelper(WebRenderLayer* aLayer,
|
||||
// If the layer contents are fixed for this metadata onwards, we need
|
||||
// to insert the layer's local clip at this point in the clip tree,
|
||||
// as a child of whatever's on the stack.
|
||||
PushLayerLocalClip(aStackingContext);
|
||||
PushLayerLocalClip(aStackingContext, aResources);
|
||||
}
|
||||
|
||||
DefineAndPushScrollLayer(fm, aStackingContext);
|
||||
@ -59,7 +60,7 @@ ScrollingLayersHelper::ScrollingLayersHelper(WebRenderLayer* aLayer,
|
||||
// child layers. So we need to apply this after pushing all the scroll layers,
|
||||
// which we do above.
|
||||
if (const Maybe<LayerClip>& scrolledClip = layer->GetScrolledClip()) {
|
||||
PushLayerClip(scrolledClip.ref(), aStackingContext);
|
||||
PushLayerClip(scrolledClip.ref(), aStackingContext, aResources);
|
||||
}
|
||||
|
||||
// If the layer is marked as fixed-position, it is fixed relative to something
|
||||
@ -82,7 +83,7 @@ ScrollingLayersHelper::ScrollingLayersHelper(WebRenderLayer* aLayer,
|
||||
// Default to 0 if there is no ancestor, because 0 refers to the root scrollframe.
|
||||
mBuilder->PushClipAndScrollInfo(scrollsWith.valueOr(0), clipId.ptrOr(nullptr));
|
||||
} else {
|
||||
PushLayerLocalClip(aStackingContext);
|
||||
PushLayerLocalClip(aStackingContext, aResources);
|
||||
}
|
||||
}
|
||||
|
||||
@ -273,7 +274,8 @@ ScrollingLayersHelper::DefineAndPushScrollLayer(const FrameMetrics& aMetrics,
|
||||
}
|
||||
|
||||
void
|
||||
ScrollingLayersHelper::PushLayerLocalClip(const StackingContextHelper& aStackingContext)
|
||||
ScrollingLayersHelper::PushLayerLocalClip(const StackingContextHelper& aStackingContext,
|
||||
wr::IpcResourceUpdateQueue& aResources)
|
||||
{
|
||||
Layer* layer = mLayer->GetLayer();
|
||||
Maybe<ParentLayerRect> clip;
|
||||
@ -285,7 +287,7 @@ ScrollingLayersHelper::PushLayerLocalClip(const StackingContextHelper& aStacking
|
||||
clip = Some(layer->GetLocalTransformTyped().TransformBounds(mLayer->Bounds()));
|
||||
}
|
||||
if (clip) {
|
||||
Maybe<wr::WrImageMask> mask = mLayer->BuildWrMaskLayer(aStackingContext);
|
||||
Maybe<wr::WrImageMask> mask = mLayer->BuildWrMaskLayer(aStackingContext, aResources);
|
||||
LayerRect clipRect = ViewAs<LayerPixel>(clip.ref(),
|
||||
PixelCastJustification::MovingDownToChildren);
|
||||
mBuilder->PushClip(mBuilder->DefineClip(
|
||||
@ -296,7 +298,8 @@ ScrollingLayersHelper::PushLayerLocalClip(const StackingContextHelper& aStacking
|
||||
|
||||
void
|
||||
ScrollingLayersHelper::PushLayerClip(const LayerClip& aClip,
|
||||
const StackingContextHelper& aSc)
|
||||
const StackingContextHelper& aSc,
|
||||
wr::IpcResourceUpdateQueue& aResources)
|
||||
{
|
||||
LayerRect clipRect = IntRectToRect(ViewAs<LayerPixel>(aClip.GetClipRect(),
|
||||
PixelCastJustification::MovingDownToChildren));
|
||||
@ -305,7 +308,7 @@ ScrollingLayersHelper::PushLayerClip(const LayerClip& aClip,
|
||||
Layer* maskLayer = mLayer->GetLayer()->GetAncestorMaskLayerAt(maskLayerIndex.value());
|
||||
WebRenderLayer* maskWrLayer = WebRenderLayer::ToWebRenderLayer(maskLayer);
|
||||
// TODO: check this transform is correct in all cases
|
||||
mask = maskWrLayer->RenderMaskLayer(aSc, maskLayer->GetTransform());
|
||||
mask = maskWrLayer->RenderMaskLayer(aSc, maskLayer->GetTransform(), aResources);
|
||||
}
|
||||
mBuilder->PushClip(mBuilder->DefineClip(
|
||||
aSc.ToRelativeLayoutRect(clipRect), nullptr, mask.ptrOr(nullptr)));
|
||||
|
@ -29,6 +29,7 @@ class MOZ_RAII ScrollingLayersHelper
|
||||
public:
|
||||
ScrollingLayersHelper(WebRenderLayer* aLayer,
|
||||
wr::DisplayListBuilder& aBuilder,
|
||||
wr::IpcResourceUpdateQueue& aResources,
|
||||
const StackingContextHelper& aSc);
|
||||
ScrollingLayersHelper(nsDisplayItem* aItem,
|
||||
wr::DisplayListBuilder& aBuilder,
|
||||
@ -52,9 +53,11 @@ private:
|
||||
WebRenderLayerManager::ClipIdMap& aCache);
|
||||
bool DefineAndPushScrollLayer(const FrameMetrics& aMetrics,
|
||||
const StackingContextHelper& aStackingContext);
|
||||
void PushLayerLocalClip(const StackingContextHelper& aStackingContext);
|
||||
void PushLayerLocalClip(const StackingContextHelper& aStackingContext,
|
||||
wr::IpcResourceUpdateQueue& aResources);
|
||||
void PushLayerClip(const LayerClip& aClip,
|
||||
const StackingContextHelper& aSc);
|
||||
const StackingContextHelper& aSc,
|
||||
wr::IpcResourceUpdateQueue& aResources);
|
||||
|
||||
WebRenderLayer* mLayer;
|
||||
wr::DisplayListBuilder* mBuilder;
|
||||
|
@ -278,6 +278,13 @@ WebRenderBridgeParent::UpdateResources(const nsTArray<OpUpdateResource>& aResour
|
||||
aUpdates.UpdateBlobImage(op.key(), op.descriptor(), bytes);
|
||||
break;
|
||||
}
|
||||
case OpUpdateResource::TOpAddExternalImage: {
|
||||
const auto& op = cmd.get_OpAddExternalImage();
|
||||
if (!AddExternalImage(op.externalImageId(), op.key(), aUpdates)) {
|
||||
return false;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case OpUpdateResource::TOpAddRawFont: {
|
||||
const auto& op = cmd.get_OpAddRawFont();
|
||||
wr::Vec_u8 bytes;
|
||||
@ -317,6 +324,56 @@ WebRenderBridgeParent::UpdateResources(const nsTArray<OpUpdateResource>& aResour
|
||||
return true;
|
||||
}
|
||||
|
||||
bool
|
||||
WebRenderBridgeParent::AddExternalImage(wr::ExternalImageId aExtId, wr::ImageKey aKey,
|
||||
wr::ResourceUpdateQueue& aResources)
|
||||
{
|
||||
Range<const wr::ImageKey> keys(&aKey, 1);
|
||||
// Check if key is obsoleted.
|
||||
if (keys[0].mNamespace != mIdNamespace) {
|
||||
return true;
|
||||
}
|
||||
MOZ_ASSERT(mExternalImageIds.Get(wr::AsUint64(aExtId)).get());
|
||||
|
||||
RefPtr<WebRenderImageHost> host = mExternalImageIds.Get(wr::AsUint64(aExtId));
|
||||
if (!host) {
|
||||
NS_ERROR("CompositableHost does not exist");
|
||||
return false;
|
||||
}
|
||||
if (!gfxEnv::EnableWebRenderRecording()) {
|
||||
TextureHost* texture = host->GetAsTextureHostForComposite();
|
||||
if (!texture) {
|
||||
NS_ERROR("TextureHost does not exist");
|
||||
return false;
|
||||
}
|
||||
WebRenderTextureHost* wrTexture = texture->AsWebRenderTextureHost();
|
||||
if (wrTexture) {
|
||||
wrTexture->AddWRImage(aResources, keys, wrTexture->GetExternalImageKey());
|
||||
return true;
|
||||
}
|
||||
}
|
||||
RefPtr<DataSourceSurface> dSurf = host->GetAsSurface();
|
||||
if (!dSurf) {
|
||||
NS_ERROR("TextureHost does not return DataSourceSurface");
|
||||
return false;
|
||||
}
|
||||
|
||||
DataSourceSurface::MappedSurface map;
|
||||
if (!dSurf->Map(gfx::DataSourceSurface::MapType::READ, &map)) {
|
||||
NS_ERROR("DataSourceSurface failed to map");
|
||||
return false;
|
||||
}
|
||||
|
||||
IntSize size = dSurf->GetSize();
|
||||
wr::ImageDescriptor descriptor(size, map.mStride, dSurf->GetFormat());
|
||||
wr::Vec_u8 data;
|
||||
data.PushBytes(Range<uint8_t>(map.mData, size.height * map.mStride));
|
||||
aResources.AddImage(keys[0], descriptor, data);
|
||||
dSurf->Unmap();
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
mozilla::ipc::IPCResult
|
||||
WebRenderBridgeParent::RecvUpdateResources(nsTArray<OpUpdateResource>&& aResourceUpdates,
|
||||
nsTArray<ipc::Shmem>&& aResourceData)
|
||||
@ -461,12 +518,37 @@ WebRenderBridgeParent::RecvSetDisplayList(const gfx::IntSize& aSize,
|
||||
// to early-return from RecvDPEnd without doing so.
|
||||
AutoWebRenderBridgeParentAsyncMessageSender autoAsyncMessageSender(this, &aToDestroy);
|
||||
|
||||
uint32_t wrEpoch = GetNextWrEpoch();
|
||||
|
||||
|
||||
wr::ResourceUpdateQueue resources;
|
||||
|
||||
mAsyncImageManager->SetCompositionTime(TimeStamp::Now());
|
||||
ProcessWebRenderParentCommands(aCommands, resources);
|
||||
|
||||
UpdateResources(aResourceUpdates, aResourceData, resources);
|
||||
|
||||
uint32_t wrEpoch = GetNextWrEpoch();
|
||||
ProcessWebRenderCommands(aSize, aCommands, wr::NewEpoch(wrEpoch),
|
||||
aContentSize, dl, dlDesc, resources, aIdNamespace);
|
||||
// If id namespaces do not match, it means the command is obsolete, probably
|
||||
// because the tab just moved to a new window.
|
||||
// In that case do not send the commands to webrender.
|
||||
if (mIdNamespace == aIdNamespace) {
|
||||
if (mWidget) {
|
||||
LayoutDeviceIntSize size = mWidget->GetClientSize();
|
||||
mApi->SetWindowParameters(size);
|
||||
}
|
||||
gfx::Color color = mWidget ? gfx::Color(0.3f, 0.f, 0.f, 1.f) : gfx::Color(0.f, 0.f, 0.f, 0.f);
|
||||
mApi->SetDisplayList(color, wr::NewEpoch(wrEpoch), LayerSize(aSize.width, aSize.height),
|
||||
mPipelineId, aContentSize,
|
||||
dlDesc, dl.mData, dl.mLength,
|
||||
resources);
|
||||
|
||||
ScheduleComposition();
|
||||
|
||||
if (ShouldParentObserveEpoch()) {
|
||||
mCompositorBridge->ObserveLayerUpdate(GetLayersId(), GetChildLayerObserverEpoch(), true);
|
||||
}
|
||||
}
|
||||
|
||||
HoldPendingTransactionId(wrEpoch, aTransactionId, aTxnStartTime, aFwdTime);
|
||||
|
||||
mScrollData = aScrollData;
|
||||
@ -527,49 +609,9 @@ WebRenderBridgeParent::ProcessWebRenderParentCommands(const InfallibleTArray<Web
|
||||
switch (cmd.type()) {
|
||||
case WebRenderParentCommand::TOpAddExternalImage: {
|
||||
const OpAddExternalImage& op = cmd.get_OpAddExternalImage();
|
||||
Range<const wr::ImageKey> keys(&op.key(), 1);
|
||||
// Check if key is obsoleted.
|
||||
if (keys[0].mNamespace != mIdNamespace) {
|
||||
break;
|
||||
if (!AddExternalImage(op.externalImageId(), op.key(), aResources)) {
|
||||
NS_ERROR("AddExternalImage failed");
|
||||
}
|
||||
MOZ_ASSERT(mExternalImageIds.Get(wr::AsUint64(op.externalImageId())).get());
|
||||
|
||||
RefPtr<WebRenderImageHost> host = mExternalImageIds.Get(wr::AsUint64(op.externalImageId()));
|
||||
if (!host) {
|
||||
NS_ERROR("CompositableHost does not exist");
|
||||
break;
|
||||
}
|
||||
if (!gfxEnv::EnableWebRenderRecording()) {
|
||||
TextureHost* texture = host->GetAsTextureHostForComposite();
|
||||
if (!texture) {
|
||||
NS_ERROR("TextureHost does not exist");
|
||||
break;
|
||||
}
|
||||
WebRenderTextureHost* wrTexture = texture->AsWebRenderTextureHost();
|
||||
if (wrTexture) {
|
||||
wrTexture->AddWRImage(aResources, keys, wrTexture->GetExternalImageKey());
|
||||
break;
|
||||
}
|
||||
}
|
||||
RefPtr<DataSourceSurface> dSurf = host->GetAsSurface();
|
||||
if (!dSurf) {
|
||||
NS_ERROR("TextureHost does not return DataSourceSurface");
|
||||
break;
|
||||
}
|
||||
|
||||
DataSourceSurface::MappedSurface map;
|
||||
if (!dSurf->Map(gfx::DataSourceSurface::MapType::READ, &map)) {
|
||||
NS_ERROR("DataSourceSurface failed to map");
|
||||
break;
|
||||
}
|
||||
|
||||
IntSize size = dSurf->GetSize();
|
||||
wr::ImageDescriptor descriptor(size, map.mStride, dSurf->GetFormat());
|
||||
wr::Vec_u8 data;
|
||||
data.PushBytes(Range<uint8_t>(map.mData, size.height * map.mStride));
|
||||
aResources.AddImage(keys[0], descriptor, data);
|
||||
|
||||
dSurf->Unmap();
|
||||
break;
|
||||
}
|
||||
case WebRenderParentCommand::TOpUpdateAsyncImagePipeline: {
|
||||
@ -614,40 +656,6 @@ WebRenderBridgeParent::ProcessWebRenderParentCommands(const InfallibleTArray<Web
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
WebRenderBridgeParent::ProcessWebRenderCommands(const gfx::IntSize &aSize,
|
||||
InfallibleTArray<WebRenderParentCommand>& aCommands, const wr::Epoch& aEpoch,
|
||||
const wr::LayoutSize& aContentSize, const wr::ByteBuffer& dl,
|
||||
const wr::BuiltDisplayListDescriptor& dlDesc,
|
||||
wr::ResourceUpdateQueue& aResourceUpdates,
|
||||
const wr::IdNamespace& aIdNamespace)
|
||||
{
|
||||
mAsyncImageManager->SetCompositionTime(TimeStamp::Now());
|
||||
ProcessWebRenderParentCommands(aCommands, aResourceUpdates);
|
||||
|
||||
// The command is obsoleted.
|
||||
// Do not set the command to webrender since it causes crash in webrender.
|
||||
if (mIdNamespace != aIdNamespace) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (mWidget) {
|
||||
LayoutDeviceIntSize size = mWidget->GetClientSize();
|
||||
mApi->SetWindowParameters(size);
|
||||
}
|
||||
gfx::Color color = mWidget ? gfx::Color(0.3f, 0.f, 0.f, 1.f) : gfx::Color(0.f, 0.f, 0.f, 0.f);
|
||||
mApi->SetDisplayList(color, aEpoch, LayerSize(aSize.width, aSize.height),
|
||||
mPipelineId, aContentSize,
|
||||
dlDesc, dl.mData, dl.mLength,
|
||||
aResourceUpdates);
|
||||
|
||||
ScheduleComposition();
|
||||
|
||||
if (ShouldParentObserveEpoch()) {
|
||||
mCompositorBridge->ObserveLayerUpdate(GetLayersId(), GetChildLayerObserverEpoch(), true);
|
||||
}
|
||||
}
|
||||
|
||||
mozilla::ipc::IPCResult
|
||||
WebRenderBridgeParent::RecvGetSnapshot(PTextureParent* aTexture)
|
||||
{
|
||||
|
@ -192,18 +192,13 @@ private:
|
||||
bool UpdateResources(const nsTArray<OpUpdateResource>& aResourceUpdates,
|
||||
const nsTArray<ipc::Shmem>& aResourceData,
|
||||
wr::ResourceUpdateQueue& aUpdates);
|
||||
bool AddExternalImage(wr::ExternalImageId aExtId, wr::ImageKey aKey,
|
||||
wr::ResourceUpdateQueue& aResources);
|
||||
|
||||
uint64_t GetLayersId() const;
|
||||
void ProcessWebRenderParentCommands(const InfallibleTArray<WebRenderParentCommand>& aCommands,
|
||||
wr::ResourceUpdateQueue& aResources);
|
||||
void ProcessWebRenderCommands(const gfx::IntSize &aSize,
|
||||
InfallibleTArray<WebRenderParentCommand>& commands,
|
||||
const wr::Epoch& aEpoch,
|
||||
const wr::LayoutSize& aContentSize,
|
||||
const wr::ByteBuffer& dl,
|
||||
const wr::BuiltDisplayListDescriptor& dlDesc,
|
||||
wr::ResourceUpdateQueue& aResourceUpdates,
|
||||
const wr::IdNamespace& aIdNamespace);
|
||||
|
||||
void ClearResources();
|
||||
uint64_t GetChildLayerObserverEpoch() const { return mChildLayerObserverEpoch; }
|
||||
bool ShouldParentObserveEpoch();
|
||||
|
@ -50,7 +50,7 @@ WebRenderCanvasLayer::RenderLayer(wr::DisplayListBuilder& aBuilder,
|
||||
transform = Some(GetTransform().PreTranslate(0, mBounds.Height(), 0).PreScale(1, -1, 1));
|
||||
}
|
||||
|
||||
ScrollingLayersHelper scroller(this, aBuilder, aSc);
|
||||
ScrollingLayersHelper scroller(this, aBuilder, aResources, aSc);
|
||||
StackingContextHelper sc(aSc, aBuilder, this, transform);
|
||||
|
||||
LayerRect rect(0, 0, mBounds.Width(), mBounds.Height());
|
||||
|
@ -23,7 +23,7 @@ WebRenderColorLayer::RenderLayer(wr::DisplayListBuilder& aBuilder,
|
||||
wr::IpcResourceUpdateQueue& aResources,
|
||||
const StackingContextHelper& aSc)
|
||||
{
|
||||
ScrollingLayersHelper scroller(this, aBuilder, aSc);
|
||||
ScrollingLayersHelper scroller(this, aBuilder, aResources, aSc);
|
||||
StackingContextHelper sc(aSc, aBuilder, this);
|
||||
|
||||
LayerRect rect = Bounds();
|
||||
|
@ -107,7 +107,7 @@ WebRenderContainerLayer::RenderLayer(wr::DisplayListBuilder& aBuilder,
|
||||
filters.AppendElement(wr::ToWrFilterOp(filter));
|
||||
}
|
||||
|
||||
ScrollingLayersHelper scroller(this, aBuilder, aSc);
|
||||
ScrollingLayersHelper scroller(this, aBuilder, aResources, aSc);
|
||||
StackingContextHelper sc(aSc, aBuilder, this, animationsId, opacityForSC, transformForSC, filters);
|
||||
|
||||
LayerRect rect = Bounds();
|
||||
@ -126,7 +126,7 @@ WebRenderRefLayer::RenderLayer(wr::DisplayListBuilder& aBuilder,
|
||||
wr::IpcResourceUpdateQueue& aResources,
|
||||
const StackingContextHelper& aSc)
|
||||
{
|
||||
ScrollingLayersHelper scroller(this, aBuilder, aSc);
|
||||
ScrollingLayersHelper scroller(this, aBuilder, aResources, aSc);
|
||||
|
||||
ParentLayerRect bounds = GetLocalTransformTyped().TransformBounds(Bounds());
|
||||
// As with WebRenderTextLayer, because we don't push a stacking context for
|
||||
|
@ -32,7 +32,7 @@ WebRenderDisplayItemLayer::RenderLayer(wr::DisplayListBuilder& aBuilder,
|
||||
return;
|
||||
}
|
||||
|
||||
ScrollingLayersHelper scroller(this, aBuilder, aSc);
|
||||
ScrollingLayersHelper scroller(this, aBuilder, aResources, aSc);
|
||||
|
||||
if (mItem) {
|
||||
wr::LayoutSize contentSize; // this won't actually be used by anything
|
||||
|
@ -10,6 +10,7 @@
|
||||
#include "mozilla/gfx/gfxVars.h"
|
||||
#include "mozilla/layers/CompositorBridgeChild.h"
|
||||
#include "mozilla/layers/ImageClient.h"
|
||||
#include "mozilla/layers/IpcResourceUpdateQueue.h"
|
||||
#include "mozilla/layers/ScrollingLayersHelper.h"
|
||||
#include "mozilla/layers/StackingContextHelper.h"
|
||||
#include "mozilla/layers/TextureClientRecycleAllocator.h"
|
||||
@ -24,6 +25,7 @@ using namespace gfx;
|
||||
|
||||
WebRenderImageLayer::WebRenderImageLayer(WebRenderLayerManager* aLayerManager)
|
||||
: ImageLayer(aLayerManager, static_cast<WebRenderLayer*>(this))
|
||||
, mKey(Nothing())
|
||||
, mImageClientContainerType(CompositableType::UNKNOWN)
|
||||
{
|
||||
MOZ_COUNT_CTOR(WebRenderImageLayer);
|
||||
@ -108,6 +110,35 @@ WebRenderImageLayer::SupportsAsyncUpdate()
|
||||
return false;
|
||||
}
|
||||
|
||||
Maybe<wr::ImageKey>
|
||||
WebRenderImageLayer::UpdateImageKey(ImageClientSingle* aImageClient,
|
||||
ImageContainer* aContainer,
|
||||
Maybe<wr::ImageKey>& aOldKey,
|
||||
wr::ExternalImageId& aExternalImageId,
|
||||
wr::IpcResourceUpdateQueue& aResources)
|
||||
{
|
||||
MOZ_ASSERT(aImageClient);
|
||||
MOZ_ASSERT(aContainer);
|
||||
|
||||
bool ret = aImageClient->UpdateImage(aContainer, /* unused */0);
|
||||
if (!ret || aImageClient->IsEmpty()) {
|
||||
// Something failed and/or there is no image to show.
|
||||
if (aOldKey.isSome()) {
|
||||
aResources.DeleteImage(aOldKey.value());
|
||||
}
|
||||
return Nothing();
|
||||
}
|
||||
|
||||
if (aOldKey.isSome()) {
|
||||
return aOldKey;
|
||||
}
|
||||
|
||||
wr::WrImageKey key = GenerateImageKey();
|
||||
|
||||
aResources.AddExternalImage(aExternalImageId, key);
|
||||
return Some(key);
|
||||
}
|
||||
|
||||
void
|
||||
WebRenderImageLayer::RenderLayer(wr::DisplayListBuilder& aBuilder,
|
||||
wr::IpcResourceUpdateQueue& aResources,
|
||||
@ -153,7 +184,7 @@ WebRenderImageLayer::RenderLayer(wr::DisplayListBuilder& aBuilder,
|
||||
// Push IFrame for async image pipeline.
|
||||
// XXX Remove this once partial display list update is supported.
|
||||
|
||||
ScrollingLayersHelper scroller(this, aBuilder, aSc);
|
||||
ScrollingLayersHelper scroller(this, aBuilder, aResources, aSc);
|
||||
|
||||
ParentLayerRect bounds = GetLocalTransformTyped().TransformBounds(Bounds());
|
||||
|
||||
@ -209,12 +240,13 @@ WebRenderImageLayer::RenderLayer(wr::DisplayListBuilder& aBuilder,
|
||||
mKey = UpdateImageKey(mImageClient->AsImageClientSingle(),
|
||||
mContainer,
|
||||
mKey,
|
||||
mExternalImageId.ref());
|
||||
mExternalImageId.ref(),
|
||||
aResources);
|
||||
if (mKey.isNothing()) {
|
||||
return;
|
||||
}
|
||||
|
||||
ScrollingLayersHelper scroller(this, aBuilder, aSc);
|
||||
ScrollingLayersHelper scroller(this, aBuilder, aResources, aSc);
|
||||
StackingContextHelper sc(aSc, aBuilder, this);
|
||||
|
||||
LayerRect rect(0, 0, size.width, size.height);
|
||||
@ -238,7 +270,8 @@ WebRenderImageLayer::RenderLayer(wr::DisplayListBuilder& aBuilder,
|
||||
|
||||
Maybe<wr::WrImageMask>
|
||||
WebRenderImageLayer::RenderMaskLayer(const StackingContextHelper& aSc,
|
||||
const gfx::Matrix4x4& aTransform)
|
||||
const gfx::Matrix4x4& aTransform,
|
||||
wr::IpcResourceUpdateQueue& aResources)
|
||||
{
|
||||
if (!mContainer) {
|
||||
return Nothing();
|
||||
@ -278,7 +311,8 @@ WebRenderImageLayer::RenderMaskLayer(const StackingContextHelper& aSc,
|
||||
mKey = UpdateImageKey(mImageClient->AsImageClientSingle(),
|
||||
mContainer,
|
||||
mKey,
|
||||
mExternalImageId.ref());
|
||||
mExternalImageId.ref(),
|
||||
aResources);
|
||||
if (mKey.isNothing()) {
|
||||
return Nothing();
|
||||
}
|
||||
|
@ -35,7 +35,8 @@ public:
|
||||
wr::IpcResourceUpdateQueue& aResources,
|
||||
const StackingContextHelper& aSc) override;
|
||||
Maybe<wr::WrImageMask> RenderMaskLayer(const StackingContextHelper& aSc,
|
||||
const gfx::Matrix4x4& aTransform) override;
|
||||
const gfx::Matrix4x4& aTransform,
|
||||
wr::IpcResourceUpdateQueue& aResources) override;
|
||||
|
||||
protected:
|
||||
CompositableType GetImageClientType();
|
||||
@ -43,6 +44,13 @@ protected:
|
||||
|
||||
void AddWRVideoImage(size_t aChannelNumber);
|
||||
|
||||
Maybe<wr::ImageKey>
|
||||
UpdateImageKey(ImageClientSingle* aImageClient,
|
||||
ImageContainer* aContainer,
|
||||
Maybe<wr::ImageKey>& aOldKey,
|
||||
wr::ExternalImageId& aExternalImageId,
|
||||
wr::IpcResourceUpdateQueue& aResources);
|
||||
|
||||
wr::MaybeExternalImageId mExternalImageId;
|
||||
Maybe<wr::ImageKey> mKey;
|
||||
RefPtr<ImageClient> mImageClient;
|
||||
|
@ -41,12 +41,13 @@ WebRenderLayer::GenerateImageKey()
|
||||
}
|
||||
|
||||
Maybe<wr::WrImageMask>
|
||||
WebRenderLayer::BuildWrMaskLayer(const StackingContextHelper& aRelativeTo)
|
||||
WebRenderLayer::BuildWrMaskLayer(const StackingContextHelper& aRelativeTo,
|
||||
wr::IpcResourceUpdateQueue& aResources)
|
||||
{
|
||||
if (GetLayer()->GetMaskLayer()) {
|
||||
WebRenderLayer* maskLayer = ToWebRenderLayer(GetLayer()->GetMaskLayer());
|
||||
gfx::Matrix4x4 transform = maskLayer->GetLayer()->GetTransform();
|
||||
return maskLayer->RenderMaskLayer(aRelativeTo, transform);
|
||||
return maskLayer->RenderMaskLayer(aRelativeTo, transform, aResources);
|
||||
}
|
||||
|
||||
return Nothing();
|
||||
@ -81,41 +82,6 @@ WebRenderLayer::BoundsForStackingContext()
|
||||
return bounds;
|
||||
}
|
||||
|
||||
Maybe<wr::ImageKey>
|
||||
WebRenderLayer::UpdateImageKey(ImageClientSingle* aImageClient,
|
||||
ImageContainer* aContainer,
|
||||
Maybe<wr::ImageKey>& aOldKey,
|
||||
wr::ExternalImageId& aExternalImageId)
|
||||
{
|
||||
MOZ_ASSERT(aImageClient);
|
||||
MOZ_ASSERT(aContainer);
|
||||
|
||||
uint32_t oldCounter = aImageClient->GetLastUpdateGenerationCounter();
|
||||
|
||||
bool ret = aImageClient->UpdateImage(aContainer, /* unused */0);
|
||||
if (!ret || aImageClient->IsEmpty()) {
|
||||
// Delete old key
|
||||
if (aOldKey.isSome()) {
|
||||
WrManager()->AddImageKeyForDiscard(aOldKey.value());
|
||||
}
|
||||
return Nothing();
|
||||
}
|
||||
|
||||
// Reuse old key if generation is not updated.
|
||||
if (oldCounter == aImageClient->GetLastUpdateGenerationCounter() && aOldKey.isSome()) {
|
||||
return aOldKey;
|
||||
}
|
||||
|
||||
// Delete old key, we are generating a new key.
|
||||
if (aOldKey.isSome()) {
|
||||
WrManager()->AddImageKeyForDiscard(aOldKey.value());
|
||||
}
|
||||
|
||||
wr::WrImageKey key = GenerateImageKey();
|
||||
WrBridge()->AddWebRenderParentCommand(OpAddExternalImage(aExternalImageId, key));
|
||||
return Some(key);
|
||||
}
|
||||
|
||||
void
|
||||
WebRenderLayer::DumpLayerInfo(const char* aLayerType, const LayerRect& aRect)
|
||||
{
|
||||
|
@ -28,7 +28,8 @@ public:
|
||||
wr::IpcResourceUpdateQueue& aResources,
|
||||
const StackingContextHelper& aSc) = 0;
|
||||
virtual Maybe<wr::WrImageMask> RenderMaskLayer(const StackingContextHelper& aSc,
|
||||
const gfx::Matrix4x4& aTransform)
|
||||
const gfx::Matrix4x4& aTransform,
|
||||
wr::IpcResourceUpdateQueue& aResources)
|
||||
{
|
||||
MOZ_ASSERT(false);
|
||||
return Nothing();
|
||||
@ -41,11 +42,6 @@ public:
|
||||
return static_cast<WebRenderLayer*>(aLayer->ImplData());
|
||||
}
|
||||
|
||||
Maybe<wr::ImageKey> UpdateImageKey(ImageClientSingle* aImageClient,
|
||||
ImageContainer* aContainer,
|
||||
Maybe<wr::ImageKey>& aOldKey,
|
||||
wr::ExternalImageId& aExternalImageId);
|
||||
|
||||
WebRenderLayerManager* WrManager();
|
||||
WebRenderBridgeChild* WrBridge();
|
||||
wr::WrImageKey GenerateImageKey();
|
||||
@ -58,7 +54,8 @@ public:
|
||||
// that we want this mask to be relative to. This is usually the stacking
|
||||
// context of the *parent* layer of |this|, because that is what the mask
|
||||
// is relative to in the layer tree.
|
||||
Maybe<wr::WrImageMask> BuildWrMaskLayer(const StackingContextHelper& aRelativeTo);
|
||||
Maybe<wr::WrImageMask> BuildWrMaskLayer(const StackingContextHelper& aRelativeTo,
|
||||
wr::IpcResourceUpdateQueue& aResources);
|
||||
|
||||
protected:
|
||||
BoundsTransformMatrix BoundsTransform();
|
||||
|
@ -91,16 +91,18 @@ WebRenderPaintedLayer::UpdateImageClient()
|
||||
|
||||
void
|
||||
WebRenderPaintedLayer::CreateWebRenderDisplayList(wr::DisplayListBuilder& aBuilder,
|
||||
wr::IpcResourceUpdateQueue& aResources,
|
||||
const StackingContextHelper& aSc)
|
||||
{
|
||||
ScrollingLayersHelper scroller(this, aBuilder, aSc);
|
||||
ScrollingLayersHelper scroller(this, aBuilder, aResources, aSc);
|
||||
StackingContextHelper sc(aSc, aBuilder, this);
|
||||
|
||||
LayerRect rect = Bounds();
|
||||
DumpLayerInfo("PaintedLayer", rect);
|
||||
|
||||
wr::WrImageKey key = GenerateImageKey();
|
||||
WrBridge()->AddWebRenderParentCommand(OpAddExternalImage(mExternalImageId.value(), key));
|
||||
aResources.AddExternalImage(mExternalImageId.value(), key);
|
||||
// TODO: reuse image keys!
|
||||
WrManager()->AddImageKeyForDiscard(key);
|
||||
|
||||
wr::LayoutRect r = sc.ToRelativeLayoutRect(rect);
|
||||
@ -161,7 +163,7 @@ WebRenderPaintedLayer::RenderLayer(wr::DisplayListBuilder& aBuilder,
|
||||
MOZ_ASSERT(mImageContainer->HasCurrentImage());
|
||||
}
|
||||
|
||||
CreateWebRenderDisplayList(aBuilder, aSc);
|
||||
CreateWebRenderDisplayList(aBuilder, aResources, aSc);
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -57,6 +57,7 @@ private:
|
||||
bool SetupExternalImages();
|
||||
bool UpdateImageClient();
|
||||
void CreateWebRenderDisplayList(wr::DisplayListBuilder& aBuilder,
|
||||
wr::IpcResourceUpdateQueue& aResources,
|
||||
const StackingContextHelper& aSc);
|
||||
void ClearWrResources();
|
||||
};
|
||||
|
@ -86,7 +86,7 @@ WebRenderPaintedLayerBlob::RenderLayer(wr::DisplayListBuilder& aBuilder,
|
||||
mImageBounds = visibleRegion.GetBounds();
|
||||
}
|
||||
|
||||
ScrollingLayersHelper scroller(this, aBuilder, aSc);
|
||||
ScrollingLayersHelper scroller(this, aBuilder, aResources, aSc);
|
||||
StackingContextHelper sc(aSc, aBuilder, this);
|
||||
LayerRect rect = Bounds();
|
||||
DumpLayerInfo("PaintedLayer", rect);
|
||||
|
@ -27,7 +27,7 @@ WebRenderTextLayer::RenderLayer(wr::DisplayListBuilder& aBuilder,
|
||||
return;
|
||||
}
|
||||
|
||||
ScrollingLayersHelper scroller(this, aBuilder, aSc);
|
||||
ScrollingLayersHelper scroller(this, aBuilder, aResources, aSc);
|
||||
|
||||
LayerRect rect = LayerRect::FromUnknownRect(
|
||||
// I am not 100% sure this is correct, but it probably is. Because:
|
||||
|
@ -155,7 +155,7 @@ public:
|
||||
// Push IFrame for async image pipeline.
|
||||
// XXX Remove this once partial display list update is supported.
|
||||
|
||||
/* ScrollingLayersHelper scroller(this, aBuilder, aSc); */
|
||||
/* ScrollingLayersHelper scroller(this, aBuilder, aResources, aSc); */
|
||||
nsIntSize canvasSizeInPx = data->GetSize();
|
||||
IntrinsicSize intrinsicSize = IntrinsicSizeFromCanvasSize(canvasSizeInPx);
|
||||
nsSize intrinsicRatio = IntrinsicRatioFromCanvasSize(canvasSizeInPx);
|
||||
|
Loading…
Reference in New Issue
Block a user