forked from mirrors/gecko-dev
		
	Bug 1711061 - Part 12. Change the display list to use WebRenderImageProvider. r=tnikkel
Differential Revision: https://phabricator.services.mozilla.com/D126605
This commit is contained in:
		
							parent
							
								
									77d044e944
								
							
						
					
					
						commit
						c6eb106f04
					
				
					 11 changed files with 174 additions and 177 deletions
				
			
		|  | @ -17,6 +17,7 @@ | |||
| #include "mozilla/gfx/2D.h" | ||||
| #include "mozilla/gfx/Logging.h" | ||||
| #include "mozilla/gfx/Types.h" | ||||
| #include "mozilla/image/WebRenderImageProvider.h" | ||||
| #include "mozilla/layers/AnimationHelper.h" | ||||
| #include "mozilla/layers/ClipManager.h" | ||||
| #include "mozilla/layers/ImageClient.h" | ||||
|  | @ -40,6 +41,7 @@ namespace mozilla { | |||
| namespace layers { | ||||
| 
 | ||||
| using namespace gfx; | ||||
| using namespace image; | ||||
| static int sIndent; | ||||
| #include <stdarg.h> | ||||
| #include <stdio.h> | ||||
|  | @ -2009,24 +2011,22 @@ bool WebRenderCommandBuilder::PushImage( | |||
|   return true; | ||||
| } | ||||
| 
 | ||||
| Maybe<wr::BlobImageKey> WebRenderCommandBuilder::CreateBlobImageKey( | ||||
|     nsDisplayItem* aItem, ImageContainer* aContainer, | ||||
| Maybe<wr::ImageKey> WebRenderCommandBuilder::CreateImageProviderKey( | ||||
|     nsDisplayItem* aItem, image::WebRenderImageProvider* aProvider, | ||||
|     mozilla::wr::IpcResourceUpdateQueue& aResources) { | ||||
|   MOZ_ASSERT(!aContainer->IsAsync()); | ||||
| 
 | ||||
|   RefPtr<WebRenderBlobImageData> imageData = | ||||
|       CreateOrRecycleWebRenderUserData<WebRenderBlobImageData>(aItem); | ||||
|   RefPtr<WebRenderImageProviderData> imageData = | ||||
|       CreateOrRecycleWebRenderUserData<WebRenderImageProviderData>(aItem); | ||||
|   MOZ_ASSERT(imageData); | ||||
|   return imageData->UpdateImageKey(aContainer, aResources); | ||||
|   return imageData->UpdateImageKey(aProvider, aResources); | ||||
| } | ||||
| 
 | ||||
| bool WebRenderCommandBuilder::PushBlobImage( | ||||
|     nsDisplayItem* aItem, ImageContainer* aContainer, | ||||
| bool WebRenderCommandBuilder::PushImageProvider( | ||||
|     nsDisplayItem* aItem, image::WebRenderImageProvider* aProvider, | ||||
|     mozilla::wr::DisplayListBuilder& aBuilder, | ||||
|     mozilla::wr::IpcResourceUpdateQueue& aResources, | ||||
|     const LayoutDeviceRect& aRect, const LayoutDeviceRect& aClip) { | ||||
|   Maybe<wr::BlobImageKey> key = | ||||
|       CreateBlobImageKey(aItem, aContainer, aResources); | ||||
|   Maybe<wr::ImageKey> key = | ||||
|       CreateImageProviderKey(aItem, aProvider, aResources); | ||||
|   if (!key) { | ||||
|     return false; | ||||
|   } | ||||
|  | @ -2034,8 +2034,7 @@ bool WebRenderCommandBuilder::PushBlobImage( | |||
|   auto rendering = wr::ToImageRendering(aItem->Frame()->UsedImageRendering()); | ||||
|   auto r = wr::ToLayoutRect(aRect); | ||||
|   auto c = wr::ToLayoutRect(aClip); | ||||
|   aBuilder.PushImage(r, c, !aItem->BackfaceIsHidden(), rendering, | ||||
|                      wr::AsImageKey(key.value())); | ||||
|   aBuilder.PushImage(r, c, !aItem->BackfaceIsHidden(), rendering, key.value()); | ||||
| 
 | ||||
|   return true; | ||||
| } | ||||
|  |  | |||
|  | @ -21,6 +21,10 @@ | |||
| 
 | ||||
| namespace mozilla { | ||||
| 
 | ||||
| namespace image { | ||||
| class WebRenderImageProvider; | ||||
| } | ||||
| 
 | ||||
| namespace layers { | ||||
| 
 | ||||
| class ImageClient; | ||||
|  | @ -65,8 +69,8 @@ class WebRenderCommandBuilder final { | |||
|       mozilla::wr::ImageRendering aRendering, const StackingContextHelper& aSc, | ||||
|       gfx::IntSize& aSize, const Maybe<LayoutDeviceRect>& aAsyncImageBounds); | ||||
| 
 | ||||
|   Maybe<wr::BlobImageKey> CreateBlobImageKey( | ||||
|       nsDisplayItem* aItem, ImageContainer* aContainer, | ||||
|   Maybe<wr::ImageKey> CreateImageProviderKey( | ||||
|       nsDisplayItem* aItem, image::WebRenderImageProvider* aProvider, | ||||
|       mozilla::wr::IpcResourceUpdateQueue& aResources); | ||||
| 
 | ||||
|   WebRenderUserDataRefTable* GetWebRenderUserDataTable() { | ||||
|  | @ -79,11 +83,12 @@ class WebRenderCommandBuilder final { | |||
|                  const StackingContextHelper& aSc, | ||||
|                  const LayoutDeviceRect& aRect, const LayoutDeviceRect& aClip); | ||||
| 
 | ||||
|   bool PushBlobImage(nsDisplayItem* aItem, ImageContainer* aContainer, | ||||
|                      mozilla::wr::DisplayListBuilder& aBuilder, | ||||
|                      mozilla::wr::IpcResourceUpdateQueue& aResources, | ||||
|                      const LayoutDeviceRect& aRect, | ||||
|                      const LayoutDeviceRect& aClip); | ||||
|   bool PushImageProvider(nsDisplayItem* aItem, | ||||
|                          image::WebRenderImageProvider* aProvider, | ||||
|                          mozilla::wr::DisplayListBuilder& aBuilder, | ||||
|                          mozilla::wr::IpcResourceUpdateQueue& aResources, | ||||
|                          const LayoutDeviceRect& aRect, | ||||
|                          const LayoutDeviceRect& aClip); | ||||
| 
 | ||||
|   Maybe<wr::ImageMask> BuildWrMaskImage( | ||||
|       nsDisplayMasksAndClipPaths* aMaskItem, wr::DisplayListBuilder& aBuilder, | ||||
|  |  | |||
|  | @ -6,6 +6,7 @@ | |||
| 
 | ||||
| #include "WebRenderUserData.h" | ||||
| 
 | ||||
| #include "mozilla/image/WebRenderImageProvider.h" | ||||
| #include "mozilla/layers/AnimationHelper.h" | ||||
| #include "mozilla/layers/CompositorBridgeChild.h" | ||||
| #include "mozilla/layers/ImageClient.h" | ||||
|  | @ -19,6 +20,8 @@ | |||
| #include "nsIFrame.h" | ||||
| #include "WebRenderCanvasRenderer.h" | ||||
| 
 | ||||
| using namespace mozilla::image; | ||||
| 
 | ||||
| namespace mozilla { | ||||
| namespace layers { | ||||
| 
 | ||||
|  | @ -42,8 +45,9 @@ bool WebRenderUserData::SupportsAsyncUpdate(nsIFrame* aFrame) { | |||
| } | ||||
| 
 | ||||
| /* static */ | ||||
| bool WebRenderUserData::ProcessInvalidateForImage( | ||||
|     nsIFrame* aFrame, DisplayItemType aType, ContainerProducerID aProducerId) { | ||||
| bool WebRenderUserData::ProcessInvalidateForImage(nsIFrame* aFrame, | ||||
|                                                   DisplayItemType aType, | ||||
|                                                   ImageProviderId aProviderId) { | ||||
|   MOZ_ASSERT(aFrame); | ||||
| 
 | ||||
|   if (!aFrame->HasProperty(WebRenderUserDataProperty::Key())) { | ||||
|  | @ -59,9 +63,9 @@ bool WebRenderUserData::ProcessInvalidateForImage( | |||
|     return true; | ||||
|   } | ||||
| 
 | ||||
|   RefPtr<WebRenderImageData> image = | ||||
|       GetWebRenderUserData<WebRenderImageData>(aFrame, type); | ||||
|   if (image && image->UsingSharedSurface(aProducerId)) { | ||||
|   RefPtr<WebRenderImageProviderData> image = | ||||
|       GetWebRenderUserData<WebRenderImageProviderData>(aFrame, type); | ||||
|   if (image && image->Invalidate(aProviderId)) { | ||||
|     return true; | ||||
|   } | ||||
| 
 | ||||
|  | @ -281,33 +285,43 @@ void WebRenderImageData::CreateImageClientIfNeeded() { | |||
|   } | ||||
| } | ||||
| 
 | ||||
| WebRenderBlobImageData::WebRenderBlobImageData(RenderRootStateManager* aManager, | ||||
|                                                nsDisplayItem* aItem) | ||||
| WebRenderImageProviderData::WebRenderImageProviderData( | ||||
|     RenderRootStateManager* aManager, nsDisplayItem* aItem) | ||||
|     : WebRenderUserData(aManager, aItem) {} | ||||
| 
 | ||||
| WebRenderBlobImageData::WebRenderBlobImageData(RenderRootStateManager* aManager, | ||||
|                                                uint32_t aDisplayItemKey, | ||||
|                                                nsIFrame* aFrame) | ||||
| WebRenderImageProviderData::WebRenderImageProviderData( | ||||
|     RenderRootStateManager* aManager, uint32_t aDisplayItemKey, | ||||
|     nsIFrame* aFrame) | ||||
|     : WebRenderUserData(aManager, aDisplayItemKey, aFrame) {} | ||||
| 
 | ||||
| Maybe<wr::BlobImageKey> WebRenderBlobImageData::UpdateImageKey( | ||||
|     ImageContainer* aContainer, wr::IpcResourceUpdateQueue& aResources) { | ||||
|   MOZ_ASSERT(aContainer); | ||||
| WebRenderImageProviderData::~WebRenderImageProviderData() = default; | ||||
| 
 | ||||
|   if (mContainer != aContainer) { | ||||
|     mContainer = aContainer; | ||||
| Maybe<wr::ImageKey> WebRenderImageProviderData::UpdateImageKey( | ||||
|     WebRenderImageProvider* aProvider, wr::IpcResourceUpdateQueue& aResources) { | ||||
|   MOZ_ASSERT(aProvider); | ||||
| 
 | ||||
|   if (mProvider != aProvider) { | ||||
|     mProvider = aProvider; | ||||
|   } | ||||
| 
 | ||||
|   wr::BlobImageKey key = {}; | ||||
|   wr::ImageKey key = {}; | ||||
|   nsresult rv = mProvider->UpdateKey(mManager, aResources, key); | ||||
|   if (NS_FAILED(rv)) { | ||||
|     return Nothing(); | ||||
|   } | ||||
| 
 | ||||
|   return Some(key); | ||||
| } | ||||
| 
 | ||||
| bool WebRenderImageProviderData::Invalidate(ImageProviderId aProviderId) const { | ||||
|   if (!aProviderId || mProvider->GetProviderId() != aProviderId) { | ||||
|     return false; | ||||
|   } | ||||
| 
 | ||||
|   wr::ImageKey key = {}; | ||||
|   nsresult rv = | ||||
|       SharedSurfacesChild::ShareBlob(aContainer, mManager, aResources, key); | ||||
|   if (NS_SUCCEEDED(rv)) { | ||||
|     mKey = Some(key); | ||||
|   } else { | ||||
|     mKey.reset(); | ||||
|   } | ||||
| 
 | ||||
|   return mKey; | ||||
|       mProvider->UpdateKey(mManager, mManager->AsyncResourceUpdates(), key); | ||||
|   return NS_SUCCEEDED(rv); | ||||
| } | ||||
| 
 | ||||
| WebRenderFallbackData::WebRenderFallbackData(RenderRootStateManager* aManager, | ||||
|  |  | |||
|  | @ -9,6 +9,7 @@ | |||
| 
 | ||||
| #include <vector> | ||||
| #include "mozilla/webrender/WebRenderAPI.h" | ||||
| #include "mozilla/image/WebRenderImageProvider.h" | ||||
| #include "mozilla/layers/AnimationInfo.h" | ||||
| #include "mozilla/dom/RemoteBrowser.h" | ||||
| #include "mozilla/UniquePtr.h" | ||||
|  | @ -44,6 +45,7 @@ class WebRenderCanvasData; | |||
| class WebRenderCanvasRenderer; | ||||
| class WebRenderCanvasRendererAsync; | ||||
| class WebRenderImageData; | ||||
| class WebRenderImageProviderData; | ||||
| class WebRenderFallbackData; | ||||
| class WebRenderLocalCanvasData; | ||||
| class RenderRootStateManager; | ||||
|  | @ -69,7 +71,7 @@ class WebRenderUserData { | |||
|   static bool SupportsAsyncUpdate(nsIFrame* aFrame); | ||||
| 
 | ||||
|   static bool ProcessInvalidateForImage(nsIFrame* aFrame, DisplayItemType aType, | ||||
|                                         ContainerProducerID aProducerId); | ||||
|                                         image::ImageProviderId aProviderId); | ||||
| 
 | ||||
|   NS_INLINE_DECL_REFCOUNTING(WebRenderUserData) | ||||
| 
 | ||||
|  | @ -78,6 +80,7 @@ class WebRenderUserData { | |||
|                     nsIFrame* aFrame); | ||||
| 
 | ||||
|   virtual WebRenderImageData* AsImageData() { return nullptr; } | ||||
|   virtual WebRenderImageProviderData* AsImageProviderData() { return nullptr; } | ||||
|   virtual WebRenderFallbackData* AsFallbackData() { return nullptr; } | ||||
|   virtual WebRenderCanvasData* AsCanvasData() { return nullptr; } | ||||
|   virtual WebRenderLocalCanvasData* AsLocalCanvasData() { return nullptr; } | ||||
|  | @ -93,7 +96,7 @@ class WebRenderUserData { | |||
|     eRemote, | ||||
|     eGroup, | ||||
|     eMask, | ||||
|     eBlobImage,  // SVG image
 | ||||
|     eImageProvider,  // ImageLib
 | ||||
|   }; | ||||
| 
 | ||||
|   virtual UserDataType GetType() = 0; | ||||
|  | @ -186,26 +189,27 @@ class WebRenderImageData : public WebRenderUserData { | |||
|   bool mOwnsKey; | ||||
| }; | ||||
| 
 | ||||
| /// Holds some data used to share blob recordings from VectorImages with the
 | ||||
| /// parent process.
 | ||||
| class WebRenderBlobImageData : public WebRenderUserData { | ||||
| /// Holds some data used to share ImageLib results with the parent process.
 | ||||
| /// This may be either in the form of a blob recording or a rasterized surface.
 | ||||
| class WebRenderImageProviderData final : public WebRenderUserData { | ||||
|  public: | ||||
|   WebRenderBlobImageData(RenderRootStateManager* aManager, | ||||
|                          nsDisplayItem* aItem); | ||||
|   WebRenderBlobImageData(RenderRootStateManager* aManager, | ||||
|                          uint32_t aDisplayItemKey, nsIFrame* aFrame); | ||||
|   virtual ~WebRenderBlobImageData() {} | ||||
|   WebRenderImageProviderData(RenderRootStateManager* aManager, | ||||
|                              nsDisplayItem* aItem); | ||||
|   WebRenderImageProviderData(RenderRootStateManager* aManager, | ||||
|                              uint32_t aDisplayItemKey, nsIFrame* aFrame); | ||||
|   ~WebRenderImageProviderData() override; | ||||
| 
 | ||||
|   UserDataType GetType() override { return UserDataType::eBlobImage; } | ||||
|   static UserDataType Type() { return UserDataType::eBlobImage; } | ||||
|   Maybe<wr::BlobImageKey> GetImageKey() { return mKey; } | ||||
|   WebRenderImageProviderData* AsImageProviderData() override { return this; } | ||||
|   UserDataType GetType() override { return UserDataType::eImageProvider; } | ||||
|   static UserDataType Type() { return UserDataType::eImageProvider; } | ||||
| 
 | ||||
|   Maybe<wr::BlobImageKey> UpdateImageKey( | ||||
|       ImageContainer* aContainer, wr::IpcResourceUpdateQueue& aResources); | ||||
|   Maybe<wr::ImageKey> UpdateImageKey(image::WebRenderImageProvider* aProvider, | ||||
|                                      wr::IpcResourceUpdateQueue& aResources); | ||||
| 
 | ||||
|   bool Invalidate(image::ImageProviderId aProviderId) const; | ||||
| 
 | ||||
|  protected: | ||||
|   Maybe<wr::BlobImageKey> mKey; | ||||
|   RefPtr<ImageContainer> mContainer; | ||||
|   RefPtr<image::WebRenderImageProvider> mProvider; | ||||
| }; | ||||
| 
 | ||||
| /// Used for fallback rendering.
 | ||||
|  |  | |||
|  | @ -6608,26 +6608,32 @@ IntSize nsLayoutUtils::ComputeImageContainerDrawingParameters( | |||
|         imgIContainer::FRAME_CURRENT, samplingFilter, aFlags); | ||||
|   } | ||||
| 
 | ||||
|   // If the dest rect contains the fill rect, then we are only displaying part
 | ||||
|   // of the vector image. We need to calculate the restriction region to avoid
 | ||||
|   // drawing more than we need, and sampling outside the desired bounds.
 | ||||
|   LayerIntRect clipRect = SnapRectForImage(itm, scaleFactors, aFillRect); | ||||
|   if (destRect.Contains(clipRect)) { | ||||
|     LayerIntRect restrictRect = destRect.Intersect(clipRect); | ||||
|     restrictRect.MoveBy(-destRect.TopLeft()); | ||||
|   // We only use the region rect with blob recordings. This is because when we
 | ||||
|   // rasterize an SVG image in process, we always create a complete
 | ||||
|   // rasterization of the whole image which can be given to any caller, while
 | ||||
|   // we support partial rasterization with the blob recordings.
 | ||||
|   if (aFlags & imgIContainer::FLAG_RECORD_BLOB) { | ||||
|     // If the dest rect contains the fill rect, then we are only displaying part
 | ||||
|     // of the vector image. We need to calculate the restriction region to avoid
 | ||||
|     // drawing more than we need, and sampling outside the desired bounds.
 | ||||
|     LayerIntRect clipRect = SnapRectForImage(itm, scaleFactors, aFillRect); | ||||
|     if (destRect.Contains(clipRect)) { | ||||
|       LayerIntRect restrictRect = destRect.Intersect(clipRect); | ||||
|       restrictRect.MoveBy(-destRect.TopLeft()); | ||||
| 
 | ||||
|     if (restrictRect.Width() < 1) { | ||||
|       restrictRect.SetWidth(1); | ||||
|     } | ||||
|     if (restrictRect.Height() < 1) { | ||||
|       restrictRect.SetHeight(1); | ||||
|     } | ||||
|       if (restrictRect.Width() < 1) { | ||||
|         restrictRect.SetWidth(1); | ||||
|       } | ||||
|       if (restrictRect.Height() < 1) { | ||||
|         restrictRect.SetHeight(1); | ||||
|       } | ||||
| 
 | ||||
|     if (restrictRect.X() != 0 || restrictRect.Y() != 0 || | ||||
|         restrictRect.Size() != destRect.Size()) { | ||||
|       IntRect sampleRect = restrictRect.ToUnknownRect(); | ||||
|       aRegion = Some(ImageIntRegion::CreateWithSamplingRestriction( | ||||
|           sampleRect, sampleRect, ExtendMode::CLAMP)); | ||||
|       if (restrictRect.X() != 0 || restrictRect.Y() != 0 || | ||||
|           restrictRect.Size() != destRect.Size()) { | ||||
|         IntRect sampleRect = restrictRect.ToUnknownRect(); | ||||
|         aRegion = Some(ImageIntRegion::CreateWithSamplingRestriction( | ||||
|             sampleRect, sampleRect, ExtendMode::CLAMP)); | ||||
|       } | ||||
|     } | ||||
|   } | ||||
| 
 | ||||
|  |  | |||
|  | @ -26,6 +26,7 @@ | |||
| #include "mozilla/dom/HTMLAreaElement.h" | ||||
| #include "mozilla/dom/HTMLImageElement.h" | ||||
| #include "mozilla/dom/ResponsiveImageSelector.h" | ||||
| #include "mozilla/image/WebRenderImageProvider.h" | ||||
| #include "mozilla/layers/RenderRootStateManager.h" | ||||
| #include "mozilla/layers/WebRenderLayerManager.h" | ||||
| #include "mozilla/MouseEvents.h" | ||||
|  | @ -998,9 +999,8 @@ void nsImageFrame::InvalidateSelf(const nsIntRect* aLayerInvalidRect, | |||
|   // Check if WebRender has interacted with this frame. If it has
 | ||||
|   // we need to let it know that things have changed.
 | ||||
|   const auto type = DisplayItemType::TYPE_IMAGE; | ||||
|   const auto producerId = | ||||
|       mImage ? mImage->GetProducerId() : kContainerProducerID_Invalid; | ||||
|   if (WebRenderUserData::ProcessInvalidateForImage(this, type, producerId)) { | ||||
|   const auto providerId = mImage ? mImage->GetProviderId() : 0; | ||||
|   if (WebRenderUserData::ProcessInvalidateForImage(this, type, providerId)) { | ||||
|     return; | ||||
|   } | ||||
| 
 | ||||
|  | @ -1843,13 +1843,13 @@ ImgDrawResult nsImageFrame::DisplayAltFeedbackWithoutLayer( | |||
|           nsLayoutUtils::ComputeImageContainerDrawingParameters( | ||||
|               imgCon, this, destRect, destRect, aSc, aFlags, svgContext, | ||||
|               region); | ||||
|       RefPtr<ImageContainer> container; | ||||
|       result = imgCon->GetImageContainerAtSize( | ||||
|           aManager->LayerManager(), decodeSize, svgContext, region, aFlags, | ||||
|           getter_AddRefs(container)); | ||||
|       if (container) { | ||||
|         bool wrResult = aManager->CommandBuilder().PushImage( | ||||
|             aItem, container, aBuilder, aResources, aSc, destRect, bounds); | ||||
|       RefPtr<image::WebRenderImageProvider> provider; | ||||
|       result = imgCon->GetImageProvider(aManager->LayerManager(), decodeSize, | ||||
|                                         svgContext, region, aFlags, | ||||
|                                         getter_AddRefs(provider)); | ||||
|       if (provider) { | ||||
|         bool wrResult = aManager->CommandBuilder().PushImageProvider( | ||||
|             aItem, provider, aBuilder, aResources, destRect, bounds); | ||||
|         result &= wrResult ? ImgDrawResult::SUCCESS : ImgDrawResult::NOT_READY; | ||||
|       } else { | ||||
|         // We don't use &= here because we want the result to be NOT_READY so
 | ||||
|  | @ -2098,10 +2098,10 @@ bool nsDisplayImage::CreateWebRenderCommands( | |||
|   IntSize decodeSize = nsLayoutUtils::ComputeImageContainerDrawingParameters( | ||||
|       mImage, mFrame, destRect, destRect, aSc, flags, svgContext, region); | ||||
| 
 | ||||
|   RefPtr<layers::ImageContainer> container; | ||||
|   ImgDrawResult drawResult = mImage->GetImageContainerAtSize( | ||||
|       aManager->LayerManager(), decodeSize, svgContext, region, flags, | ||||
|       getter_AddRefs(container)); | ||||
|   RefPtr<image::WebRenderImageProvider> provider; | ||||
|   ImgDrawResult drawResult = | ||||
|       mImage->GetImageProvider(aManager->LayerManager(), decodeSize, svgContext, | ||||
|                                region, flags, getter_AddRefs(provider)); | ||||
| 
 | ||||
|   // While we got a container, it may not contain a fully decoded surface. If
 | ||||
|   // that is the case, and we have an image we were previously displaying which
 | ||||
|  | @ -2123,13 +2123,13 @@ bool nsDisplayImage::CreateWebRenderCommands( | |||
|           prevFlags &= ~imgIContainer::FLAG_RECORD_BLOB; | ||||
|         } | ||||
| 
 | ||||
|         RefPtr<ImageContainer> prevContainer; | ||||
|         ImgDrawResult newDrawResult = mPrevImage->GetImageContainerAtSize( | ||||
|         RefPtr<image::WebRenderImageProvider> prevProvider; | ||||
|         ImgDrawResult newDrawResult = mPrevImage->GetImageProvider( | ||||
|             aManager->LayerManager(), decodeSize, svgContext, region, prevFlags, | ||||
|             getter_AddRefs(prevContainer)); | ||||
|         if (prevContainer && newDrawResult == ImgDrawResult::SUCCESS) { | ||||
|             getter_AddRefs(prevProvider)); | ||||
|         if (prevProvider && newDrawResult == ImgDrawResult::SUCCESS) { | ||||
|           drawResult = newDrawResult; | ||||
|           container = std::move(prevContainer); | ||||
|           provider = std::move(prevProvider); | ||||
|           flags = prevFlags; | ||||
|           break; | ||||
|         } | ||||
|  | @ -2156,14 +2156,9 @@ bool nsDisplayImage::CreateWebRenderCommands( | |||
|   // If the image container is empty, we don't want to fallback. Any other
 | ||||
|   // failure will be due to resource constraints and fallback is unlikely to
 | ||||
|   // help us. Hence we can ignore the return value from PushImage.
 | ||||
|   if (container) { | ||||
|     if (flags & imgIContainer::FLAG_RECORD_BLOB) { | ||||
|       aManager->CommandBuilder().PushBlobImage(this, container, aBuilder, | ||||
|                                                aResources, destRect, destRect); | ||||
|     } else { | ||||
|       aManager->CommandBuilder().PushImage(this, container, aBuilder, | ||||
|                                            aResources, aSc, destRect, destRect); | ||||
|     } | ||||
|   if (provider) { | ||||
|     aManager->CommandBuilder().PushImageProvider( | ||||
|         this, provider, aBuilder, aResources, destRect, destRect); | ||||
|   } | ||||
| 
 | ||||
|   nsDisplayItemGenericImageGeometry::UpdateDrawResult(this, drawResult); | ||||
|  |  | |||
|  | @ -29,6 +29,7 @@ | |||
| #include "nsStyleStruct.h" | ||||
| #include "gfx2DGlue.h" | ||||
| #include "gfxGradientCache.h" | ||||
| #include "mozilla/image/WebRenderImageProvider.h" | ||||
| #include "mozilla/layers/StackingContextHelper.h" | ||||
| #include "mozilla/layers/RenderRootStateManager.h" | ||||
| #include "mozilla/layers/WebRenderLayerManager.h" | ||||
|  | @ -3628,20 +3629,17 @@ ImgDrawResult nsCSSBorderImageRenderer::CreateWebRenderCommands( | |||
|               img, aForFrame, imageRect, imageRect, aSc, flags, svgContext, | ||||
|               region); | ||||
| 
 | ||||
|       RefPtr<layers::ImageContainer> container; | ||||
|       drawResult = img->GetImageContainerAtSize( | ||||
|           aManager->LayerManager(), decodeSize, svgContext, region, flags, | ||||
|           getter_AddRefs(container)); | ||||
|       if (!container) { | ||||
|       RefPtr<WebRenderImageProvider> provider; | ||||
|       drawResult = img->GetImageProvider(aManager->LayerManager(), decodeSize, | ||||
|                                          svgContext, region, flags, | ||||
|                                          getter_AddRefs(provider)); | ||||
|       if (!provider) { | ||||
|         break; | ||||
|       } | ||||
| 
 | ||||
|       auto rendering = | ||||
|           wr::ToImageRendering(aItem->Frame()->UsedImageRendering()); | ||||
|       gfx::IntSize size; | ||||
|       Maybe<wr::ImageKey> key = aManager->CommandBuilder().CreateImageKey( | ||||
|           aItem, container, aBuilder, aResources, rendering, aSc, size, | ||||
|           Nothing()); | ||||
|       Maybe<wr::ImageKey> key = | ||||
|           aManager->CommandBuilder().CreateImageProviderKey(aItem, provider, | ||||
|                                                             aResources); | ||||
|       if (key.isNothing()) { | ||||
|         break; | ||||
|       } | ||||
|  | @ -3656,6 +3654,8 @@ ImgDrawResult nsCSSBorderImageRenderer::CreateWebRenderCommands( | |||
|         // but there are reftests that are sensible to the test going through a
 | ||||
|         // blob while the reference doesn't.
 | ||||
|         if (noVerticalBorders && noHorizontalBorders) { | ||||
|           auto rendering = | ||||
|               wr::ToImageRendering(aItem->Frame()->UsedImageRendering()); | ||||
|           aBuilder.PushImage(dest, clip, !aItem->BackfaceIsHidden(), rendering, | ||||
|                              key.value()); | ||||
|           break; | ||||
|  |  | |||
|  | @ -14,6 +14,7 @@ | |||
| #include "gfxDrawable.h" | ||||
| #include "ImageOps.h" | ||||
| #include "ImageRegion.h" | ||||
| #include "mozilla/image/WebRenderImageProvider.h" | ||||
| #include "mozilla/layers/RenderRootStateManager.h" | ||||
| #include "mozilla/layers/StackingContextHelper.h" | ||||
| #include "mozilla/layers/WebRenderLayerManager.h" | ||||
|  | @ -621,40 +622,30 @@ ImgDrawResult nsImageRenderer::BuildWebRenderDisplayItems( | |||
|               mImageContainer, mForFrame, destRect, clipRect, aSc, | ||||
|               containerFlags, svgContext, region); | ||||
| 
 | ||||
|       if (extendMode != ExtendMode::CLAMP) { | ||||
|         region = Nothing(); | ||||
|       } | ||||
| 
 | ||||
|       RefPtr<layers::ImageContainer> container; | ||||
|       drawResult = mImageContainer->GetImageContainerAtSize( | ||||
|       RefPtr<image::WebRenderImageProvider> provider; | ||||
|       drawResult = mImageContainer->GetImageProvider( | ||||
|           aManager->LayerManager(), decodeSize, svgContext, region, | ||||
|           containerFlags, getter_AddRefs(container)); | ||||
|       if (!container) { | ||||
|           containerFlags, getter_AddRefs(provider)); | ||||
|       if (!provider) { | ||||
|         NS_WARNING("Failed to get image container"); | ||||
|         break; | ||||
|       } | ||||
| 
 | ||||
|       if (containerFlags & imgIContainer::FLAG_RECORD_BLOB) { | ||||
|         MOZ_ASSERT(extendMode == ExtendMode::CLAMP); | ||||
|         aManager->CommandBuilder().PushBlobImage( | ||||
|             aItem, container, aBuilder, aResources, clipRect, clipRect); | ||||
|       Maybe<wr::ImageKey> key = | ||||
|           aManager->CommandBuilder().CreateImageProviderKey(aItem, provider, | ||||
|                                                             aResources); | ||||
|       if (key.isNothing()) { | ||||
|         break; | ||||
|       } | ||||
| 
 | ||||
|       auto rendering = | ||||
|           wr::ToImageRendering(aItem->Frame()->UsedImageRendering()); | ||||
|       gfx::IntSize size; | ||||
|       Maybe<wr::ImageKey> key = aManager->CommandBuilder().CreateImageKey( | ||||
|           aItem, container, aBuilder, aResources, rendering, aSc, size, | ||||
|           Nothing()); | ||||
| 
 | ||||
|       if (key.isNothing()) { | ||||
|         break; | ||||
|       } | ||||
| 
 | ||||
|       wr::LayoutRect dest = wr::ToLayoutRect(destRect); | ||||
|       wr::LayoutRect clip = wr::ToLayoutRect(clipRect); | ||||
| 
 | ||||
|       // If we provided a region to the provider, then it already took the
 | ||||
|       // dest rect into account when it did the recording.
 | ||||
|       wr::LayoutRect dest = region ? clip : wr::ToLayoutRect(destRect); | ||||
| 
 | ||||
|       if (extendMode == ExtendMode::CLAMP) { | ||||
|         // The image is not repeating. Just push as a regular image.
 | ||||
|         aBuilder.PushImage(dest, clip, !aItem->BackfaceIsHidden(), rendering, | ||||
|  |  | |||
|  | @ -540,9 +540,9 @@ static void InvalidateImages(nsIFrame* aFrame, imgIRequest* aRequest, | |||
|           static_cast<layers::WebRenderMaskData*>(data.get())->Invalidate(); | ||||
|           invalidateFrame = true; | ||||
|           break; | ||||
|         case layers::WebRenderUserData::UserDataType::eImage: | ||||
|           if (static_cast<layers::WebRenderImageData*>(data.get()) | ||||
|                   ->UsingSharedSurface(aRequest->GetProducerId())) { | ||||
|         case layers::WebRenderUserData::UserDataType::eImageProvider: | ||||
|           if (static_cast<layers::WebRenderImageProviderData*>(data.get()) | ||||
|                   ->Invalidate(aRequest->GetProviderId())) { | ||||
|             break; | ||||
|           } | ||||
|           [[fallthrough]]; | ||||
|  |  | |||
|  | @ -10,6 +10,7 @@ | |||
| #include "gfxContext.h" | ||||
| #include "gfxPlatform.h" | ||||
| #include "mozilla/gfx/2D.h" | ||||
| #include "mozilla/image/WebRenderImageProvider.h" | ||||
| #include "mozilla/layers/RenderRootStateManager.h" | ||||
| #include "mozilla/layers/WebRenderLayerManager.h" | ||||
| #include "imgIContainer.h" | ||||
|  | @ -620,10 +621,10 @@ bool SVGImageFrame::CreateWebRenderCommands( | |||
|       mImageContainer, this, destRect, clipRect, aSc, flags, svgContext, | ||||
|       region); | ||||
| 
 | ||||
|   RefPtr<layers::ImageContainer> container; | ||||
|   ImgDrawResult drawResult = mImageContainer->GetImageContainerAtSize( | ||||
|   RefPtr<image::WebRenderImageProvider> provider; | ||||
|   ImgDrawResult drawResult = mImageContainer->GetImageProvider( | ||||
|       aManager->LayerManager(), decodeSize, svgContext, region, flags, | ||||
|       getter_AddRefs(container)); | ||||
|       getter_AddRefs(provider)); | ||||
| 
 | ||||
|   // While we got a container, it may not contain a fully decoded surface. If
 | ||||
|   // that is the case, and we have an image we were previously displaying which
 | ||||
|  | @ -647,14 +648,9 @@ bool SVGImageFrame::CreateWebRenderCommands( | |||
|     // If the image container is empty, we don't want to fallback. Any other
 | ||||
|     // failure will be due to resource constraints and fallback is unlikely to
 | ||||
|     // help us. Hence we can ignore the return value from PushImage.
 | ||||
|     if (container) { | ||||
|       if (flags & imgIContainer::FLAG_RECORD_BLOB) { | ||||
|         aManager->CommandBuilder().PushBlobImage( | ||||
|             aItem, container, aBuilder, aResources, destRect, clipRect); | ||||
|       } else { | ||||
|         aManager->CommandBuilder().PushImage( | ||||
|             aItem, container, aBuilder, aResources, aSc, destRect, clipRect); | ||||
|       } | ||||
|     if (provider) { | ||||
|       aManager->CommandBuilder().PushImageProvider( | ||||
|           aItem, provider, aBuilder, aResources, destRect, clipRect); | ||||
|     } | ||||
| 
 | ||||
|     nsDisplayItemGenericImageGeometry::UpdateDrawResult(aItem, drawResult); | ||||
|  |  | |||
|  | @ -51,6 +51,7 @@ | |||
| #include "mozilla/StaticPrefs_image.h" | ||||
| #include "mozilla/SVGImageContext.h" | ||||
| #include "Units.h" | ||||
| #include "mozilla/image/WebRenderImageProvider.h" | ||||
| #include "mozilla/layers/RenderRootStateManager.h" | ||||
| #include "mozilla/layers/WebRenderLayerManager.h" | ||||
| #include "mozilla/dom/ImageTracker.h" | ||||
|  | @ -428,39 +429,25 @@ ImgDrawResult nsImageBoxFrame::CreateWebRenderCommands( | |||
|           imgCon, aItem->Frame(), fillRect, fillRect, aSc, aFlags, svgContext, | ||||
|           region); | ||||
| 
 | ||||
|   RefPtr<layers::ImageContainer> container; | ||||
|   result = imgCon->GetImageContainerAtSize(aManager->LayerManager(), decodeSize, | ||||
|                                            svgContext, region, aFlags, | ||||
|                                            getter_AddRefs(container)); | ||||
|   if (!container) { | ||||
|     NS_WARNING("Failed to get image container"); | ||||
|   RefPtr<image::WebRenderImageProvider> provider; | ||||
|   result = | ||||
|       imgCon->GetImageProvider(aManager->LayerManager(), decodeSize, svgContext, | ||||
|                                region, aFlags, getter_AddRefs(provider)); | ||||
|   if (!provider) { | ||||
|     NS_WARNING("Failed to get image provider"); | ||||
|     return result; | ||||
|   } | ||||
| 
 | ||||
|   auto rendering = wr::ToImageRendering(aItem->Frame()->UsedImageRendering()); | ||||
|   wr::LayoutRect fill = wr::ToLayoutRect(fillRect); | ||||
| 
 | ||||
|   if (aFlags & imgIContainer::FLAG_RECORD_BLOB) { | ||||
|     Maybe<wr::BlobImageKey> key = aManager->CommandBuilder().CreateBlobImageKey( | ||||
|         aItem, container, aResources); | ||||
|     if (key.isNothing()) { | ||||
|       return result; | ||||
|     } | ||||
| 
 | ||||
|     aBuilder.PushImage(fill, fill, !BackfaceIsHidden(), rendering, | ||||
|                        wr::AsImageKey(key.value())); | ||||
|     return result; | ||||
|   } | ||||
| 
 | ||||
|   gfx::IntSize size; | ||||
|   Maybe<wr::ImageKey> key = aManager->CommandBuilder().CreateImageKey( | ||||
|       aItem, container, aBuilder, aResources, rendering, aSc, size, Nothing()); | ||||
|   Maybe<wr::ImageKey> key = aManager->CommandBuilder().CreateImageProviderKey( | ||||
|       aItem, provider, aResources); | ||||
|   if (key.isNothing()) { | ||||
|     return result; | ||||
|   } | ||||
| 
 | ||||
|   aBuilder.PushImage(fill, fill, !BackfaceIsHidden(), rendering, key.value()); | ||||
| 
 | ||||
|   return result; | ||||
| } | ||||
| 
 | ||||
|  | @ -841,8 +828,8 @@ void nsImageBoxFrame::OnFrameUpdate(imgIRequest* aRequest) { | |||
|   // Check if WebRender has interacted with this frame. If it has
 | ||||
|   // we need to let it know that things have changed.
 | ||||
|   const auto type = DisplayItemType::TYPE_XUL_IMAGE; | ||||
|   const auto producerId = aRequest->GetProducerId(); | ||||
|   if (WebRenderUserData::ProcessInvalidateForImage(this, type, producerId)) { | ||||
|   const auto providerId = aRequest->GetProviderId(); | ||||
|   if (WebRenderUserData::ProcessInvalidateForImage(this, type, providerId)) { | ||||
|     return; | ||||
|   } | ||||
| 
 | ||||
|  |  | |||
		Loading…
	
		Reference in a new issue
	
	 Andrew Osmond
						Andrew Osmond