Bug 1058040, part 18 - Minimize the cost of context paint when it is not available. r=dholbert
authorJonathan Watt <jwatt@jwatt.org>
Mon, 06 Mar 2017 13:49:21 +0000
changeset 350097 a039ec3178a2d32f0f0955767ccdb2879d08cd78
parent 350096 df0af8f286b7db10e92ccee2a4a97aeeb9406160
child 350098 8000f47b7399d0a18def8a0ecf490398f1624865
push id31568
push userkwierso@gmail.com
push dateTue, 28 Mar 2017 20:31:07 +0000
treeherdermozilla-central@272ce6c25721 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersdholbert
bugs1058040
milestone55.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1058040, part 18 - Minimize the cost of context paint when it is not available. r=dholbert MozReview-Commit-ID: 5MVW37Vd1aK
layout/generic/nsImageFrame.cpp
layout/svg/SVGImageContext.cpp
layout/svg/SVGImageContext.h
layout/xul/nsImageBoxFrame.cpp
--- a/layout/generic/nsImageFrame.cpp
+++ b/layout/generic/nsImageFrame.cpp
@@ -1694,21 +1694,17 @@ nsImageFrame::PaintImage(nsRenderingCont
                                                      &anchorPoint);
 
   uint32_t flags = aFlags;
   if (mForceSyncDecoding) {
     flags |= imgIContainer::FLAG_SYNC_DECODE;
   }
 
   Maybe<SVGImageContext> svgContext;
-  if (aImage->GetType() == imgIContainer::TYPE_VECTOR) {
-    // We avoid this overhead for raster images.
-    svgContext.emplace();
-    svgContext->MaybeStoreContextPaint(this);
-  }
+  SVGImageContext::MaybeInitAndStoreContextPaint(svgContext, this, aImage);
 
   DrawResult result =
     nsLayoutUtils::DrawSingleImage(*aRenderingContext.ThebesContext(),
       PresContext(), aImage,
       nsLayoutUtils::GetSamplingFilterForFrame(this), dest, aDirtyRect,
       svgContext, flags, &anchorPoint);
 
   nsImageMap* map = GetImageMap();
--- a/layout/svg/SVGImageContext.cpp
+++ b/layout/svg/SVGImageContext.cpp
@@ -10,32 +10,41 @@
 // Keep others in (case-insensitive) order:
 #include "gfxUtils.h"
 #include "mozilla/Preferences.h"
 #include "nsIFrame.h"
 #include "nsPresContext.h"
 
 namespace mozilla {
 
-bool
-SVGImageContext::MaybeStoreContextPaint(nsIFrame* aFromFrame)
+/* static */ void
+SVGImageContext::MaybeInitAndStoreContextPaint(Maybe<SVGImageContext>& aContext,
+                                               nsIFrame* aFromFrame,
+                                               imgIContainer* aImgContainer)
 {
   static bool sEnabledForContent = false;
   static bool sEnabledForContentCached = false;
 
+  MOZ_ASSERT(!aContext, "The emplace() call below with overwrite this object");
+
   if (!sEnabledForContentCached) {
     Preferences::AddBoolVarCache(&sEnabledForContent,
                                  "svg.context-properties.content.enabled", false);
     sEnabledForContentCached = true;
   }
 
   if (!sEnabledForContent &&
       !aFromFrame->PresContext()->IsChrome()) {
     // Context paint is pref'ed off for content and this is a content doc.
-    return false;
+    return;
+  }
+
+  if (aImgContainer->GetType() != imgIContainer::TYPE_VECTOR) {
+    // Avoid this overhead for raster images.
+    return;
   }
 
   // XXX return early if the 'context-properties' property is not set.
 
   bool haveContextPaint = false;
 
   RefPtr<SVGEmbeddingContextPaint> contextPaint = new SVGEmbeddingContextPaint();
 
@@ -48,15 +57,14 @@ SVGImageContext::MaybeStoreContextPaint(
     contextPaint->SetFill(style->mFill.GetColor());
   }
   if (style->mStroke.Type() == eStyleSVGPaintType_Color) {
     haveContextPaint = true;
     contextPaint->SetStroke(style->mStroke.GetColor());
   }
 
   if (haveContextPaint) {
-    mContextPaint = contextPaint.forget();
+    aContext.emplace();
+    aContext->mContextPaint = contextPaint.forget();
   }
-
-  return mContextPaint != nullptr;
 }
 
 } // namespace mozilla
--- a/layout/svg/SVGImageContext.h
+++ b/layout/svg/SVGImageContext.h
@@ -52,17 +52,19 @@ public:
                            gfxFloat aOpacity = 1.0,
                            bool aIsPaintingSVGImageElement = false)
     : mViewportSize(aViewportSize)
     , mPreserveAspectRatio(aPreserveAspectRatio)
     , mGlobalOpacity(aOpacity)
     , mIsPaintingSVGImageElement(aIsPaintingSVGImageElement)
   { }
 
-  bool MaybeStoreContextPaint(nsIFrame* aFromFrame);
+  static void MaybeInitAndStoreContextPaint(Maybe<SVGImageContext>& aContext,
+                                            nsIFrame* aFromFrame,
+                                            imgIContainer* aImgContainer);
 
   const Maybe<CSSIntSize>& GetViewportSize() const {
     return mViewportSize;
   }
 
   void SetViewportSize(const Maybe<CSSIntSize>& aSize) {
     mViewportSize = aSize;
   }
--- a/layout/xul/nsImageBoxFrame.cpp
+++ b/layout/xul/nsImageBoxFrame.cpp
@@ -401,21 +401,17 @@ nsImageBoxFrame::PaintImage(nsRenderingC
     dest = nsLayoutUtils::ComputeObjectDestRect(constraintRect,
                                                 intrinsicSize,
                                                 intrinsicRatio,
                                                 StylePosition(),
                                                 anchorPoint.ptr());
   }
 
   Maybe<SVGImageContext> svgContext;
-  if (imgCon->GetType() == imgIContainer::TYPE_VECTOR) {
-    // We avoid this overhead for raster images.
-    svgContext.emplace();
-    svgContext->MaybeStoreContextPaint(this);
-  }
+  SVGImageContext::MaybeInitAndStoreContextPaint(svgContext, this, imgCon);
 
   return nsLayoutUtils::DrawSingleImage(
            *aRenderingContext.ThebesContext(),
            PresContext(), imgCon,
            nsLayoutUtils::GetSamplingFilterForFrame(this),
            dest, dirty,
            svgContext, aFlags,
            anchorPoint.ptrOr(nullptr),