Bug 1313276 - Part 1. Draw clip-path-basic-shape onto mask layer. draft
authorcku <cku@mozilla.com>
Fri, 16 Dec 2016 10:56:07 +0800
changeset 453273 512690da5ab0e562c3cd4f9a964219ffd8447f9c
parent 453266 2785aaf276ba29fb2e1f5607d90d441fee42efb4
child 453274 734d5cd32224a0287f50aa15e0086287e5f349c9
push id39612
push userbmo:cku@mozilla.com
push dateFri, 23 Dec 2016 03:14:31 +0000
bugs1313276
milestone53.0a1
Bug 1313276 - Part 1. Draw clip-path-basic-shape onto mask layer. MozReview-Commit-ID: ICZiy84AFfi
layout/painting/nsDisplayList.cpp
layout/svg/nsSVGIntegrationUtils.cpp
--- a/layout/painting/nsDisplayList.cpp
+++ b/layout/painting/nsDisplayList.cpp
@@ -7348,22 +7348,17 @@ bool nsDisplayMask::ShouldPaintOnMaskLay
 {
   if (!aManager->IsCompositingCheap()) {
     return false;
   }
 
   nsSVGUtils::MaskUsage maskUsage;
   nsSVGUtils::DetermineMaskUsage(mFrame, mHandleOpacity, maskUsage);
 
-  if (!maskUsage.shouldGenerateMaskLayer && !maskUsage.shouldApplyClipPath &&
-      !maskUsage.shouldGenerateClipMaskLayer) {
-    return false;
-  }
-
-  if (maskUsage.opacity != 1.0 || maskUsage.shouldApplyBasicShape) {
+  if (maskUsage.opacity != 1.0) {
     return false;
   }
 
   if (!nsSVGIntegrationUtils::IsMaskResourceReady(mFrame)) {
     return false;
   }
 
   if (gfxPrefs::DrawMaskLayer()) {
--- a/layout/svg/nsSVGIntegrationUtils.cpp
+++ b/layout/svg/nsSVGIntegrationUtils.cpp
@@ -739,19 +739,16 @@ nsSVGIntegrationUtils::IsMaskResourceRea
 }
 
 DrawResult
 nsSVGIntegrationUtils::PaintMask(const PaintFramesParams& aParams)
 {
   nsSVGUtils::MaskUsage maskUsage;
   nsSVGUtils::DetermineMaskUsage(aParams.frame, aParams.handleOpacity,
                                  maskUsage);
-  MOZ_ASSERT(maskUsage.shouldGenerateMaskLayer ||
-             maskUsage.shouldApplyClipPath ||
-             maskUsage.shouldGenerateClipMaskLayer);
 
   nsIFrame* frame = aParams.frame;
   if (!ValidateSVGFrame(frame)) {
     return DrawResult::SUCCESS;
   }
 
   if (maskUsage.opacity == 0.0f) {
     return DrawResult::SUCCESS;
@@ -776,33 +773,61 @@ nsSVGIntegrationUtils::PaintMask(const P
     //
     // Create one extra draw target for drawing positioned mask, so that we do
     // not have to copy the content of maskTarget before painting
     // clip-path into it.
     maskTarget = maskTarget->CreateSimilarDrawTarget(maskTarget->GetSize(),
                                                      SurfaceFormat::A8);
   }
 
+  if (maskUsage.shouldApplyBasicShape) {
+    matSR.SetContext(&ctx);
+
+    SetupContextMatrix(firstFrame, aParams, offsetToBoundingBox,
+                       offsetToUserSpace);
+
+    nsCSSClipPathInstance::ApplyBasicShapeClip(ctx, frame);
+    if (!maskUsage.shouldGenerateMaskLayer) {
+      // Only have basic-shape clip-path effect. Fill clipped region by
+      // opaque white.
+      ctx.SetColor(Color(0.0, 0.0, 0.0, 1.0));
+      ctx.Fill();
+      ctx.PopClip();
+
+      return result;
+    }
+  }
+
   // Paint mask onto ctx.
   if (maskUsage.shouldGenerateMaskLayer) {
+    matSR.Restore();
     matSR.SetContext(&ctx);
 
     SetupContextMatrix(frame, aParams, offsetToBoundingBox,
                        offsetToUserSpace);
     nsTArray<nsSVGMaskFrame *> maskFrames = effectProperties.GetMaskFrames();
     bool opacityApplied = !HasNonSVGMask(maskFrames);
     result = PaintMaskSurface(aParams, maskTarget,
                               opacityApplied ? maskUsage.opacity : 1.0,
                               firstFrame->StyleContext(), maskFrames,
                               ctx.CurrentMatrix(), offsetToUserSpace);
     if (result != DrawResult::SUCCESS) {
+      if (maskUsage.shouldApplyBasicShape) {
+        ctx.PopClip();
+      }
+
       return result;
     }
   }
 
+  if (maskUsage.shouldApplyBasicShape) {
+    ctx.PopClip();
+    return result;
+  }
+
   // Paint clip-path onto ctx.
   if (maskUsage.shouldGenerateClipMaskLayer || maskUsage.shouldApplyClipPath) {
     matSR.Restore();
     matSR.SetContext(&ctx);
 
     SetupContextMatrix(firstFrame, aParams, offsetToBoundingBox,
                        offsetToUserSpace);
     Matrix clipMaskTransform;