Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(151)

Unified Diff: third_party/WebKit/Source/core/paint/PaintPropertyTreeBuilder.cpp

Issue 1829493002: [SPv2] Implement CSS clip property (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: change argument order & add unit tests Created 4 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: third_party/WebKit/Source/core/paint/PaintPropertyTreeBuilder.cpp
diff --git a/third_party/WebKit/Source/core/paint/PaintPropertyTreeBuilder.cpp b/third_party/WebKit/Source/core/paint/PaintPropertyTreeBuilder.cpp
index bf1341e06917afcfb28654a31892b81382ba8985..0f4ce55544b5ed642f8c6538ac0f7e952678d8da 100644
--- a/third_party/WebKit/Source/core/paint/PaintPropertyTreeBuilder.cpp
+++ b/third_party/WebKit/Source/core/paint/PaintPropertyTreeBuilder.cpp
@@ -214,6 +214,26 @@ static PassRefPtr<EffectPaintPropertyNode> createEffectIfNeeded(const LayoutObje
return newEffectNode.release();
}
+static PassRefPtr<ClipPaintPropertyNode> createCSSClipIfNeeded(const LayoutObject& object, PaintPropertyTreeBuilderContext& context)
+{
+ if (!object.hasClip())
+ return nullptr;
+ ASSERT(object.canContainAbsolutePositionObjects());
+
+ // Create clip node for descendants that are not fixed position.
+ // We don't have to setup context.clipForAbsolutePosition here because this object must be
+ // a container for absolute position descendants, and will copy from in-flow context later
+ // at updateOutOfFlowContext() step.
+ LayoutRect clipRect = toLayoutBox(object).clipRect(context.paintOffset);
+ RefPtr<ClipPaintPropertyNode> newClipNodeForCSSClip = ClipPaintPropertyNode::create(
+ context.currentTransform,
+ FloatRoundedRect(FloatRect(clipRect)),
+ context.currentClip);
+ context.currentClip = newClipNodeForCSSClip.get();
+
+ return newClipNodeForCSSClip.release();
+}
+
// TODO(trchen): Remove this once we bake the paint offset into frameRect.
static PassRefPtr<TransformPaintPropertyNode> createScrollbarPaintOffsetIfNeeded(const LayoutObject& object, PaintPropertyTreeBuilderContext& context)
{
@@ -309,7 +329,7 @@ static PassRefPtr<TransformPaintPropertyNode> createScrollTranslationIfNeeded(co
return newTransformNodeForScrollTranslation.release();
}
-static void updateOutOfFlowContext(const LayoutObject& object, PaintPropertyTreeBuilderContext& context)
+static void updateOutOfFlowContext(const LayoutObject& object, PaintPropertyTreeBuilderContext& context, ClipPaintPropertyNode* newClipNodeForCSSClip, RefPtr<ClipPaintPropertyNode>& newClipNodeForCSSClipFixedPosition)
{
// At the html->svg boundary (see: createPaintOffsetTranslationIfNeeded) the currentTransform is
// up-to-date for all children of the svg root element. Additionally, inside SVG, all positioning
@@ -328,6 +348,25 @@ static void updateOutOfFlowContext(const LayoutObject& object, PaintPropertyTree
context.transformForFixedPosition = context.currentTransform;
context.paintOffsetForFixedPosition = context.paintOffset;
context.clipForFixedPosition = context.currentClip;
+ } else if (newClipNodeForCSSClip) {
+ // CSS clip applies to all descendants, even if this object is not a containing block
+ // ancestor of the descendant. It is okay for absolute-position descendants because
+ // having CSS clip implies being absolute position container. However for fixed-position
+ // descendants we need to insert the clip here if we are not a containing block ancestor
+ // of them.
+
+ // Before we actually create anything, check whether in-flow context and fixed-position
+ // context has exactly the same clip. Reuse if possible.
+ if (context.clipForFixedPosition == newClipNodeForCSSClip->parent()) {
+ context.clipForFixedPosition = newClipNodeForCSSClip;
+ return;
+ }
+
+ newClipNodeForCSSClipFixedPosition = ClipPaintPropertyNode::create(
+ const_cast<TransformPaintPropertyNode*>(newClipNodeForCSSClip->localTransformSpace()),
+ newClipNodeForCSSClip->clipRect(),
+ context.clipForFixedPosition);
+ context.clipForFixedPosition = newClipNodeForCSSClipFixedPosition.get();
}
}
@@ -354,6 +393,7 @@ void PaintPropertyTreeBuilder::walk(LayoutObject& object, const PaintPropertyTre
RefPtr<TransformPaintPropertyNode> newTransformNodeForPaintOffsetTranslation = createPaintOffsetTranslationIfNeeded(object, localContext);
RefPtr<TransformPaintPropertyNode> newTransformNodeForTransform = createTransformIfNeeded(object, localContext);
RefPtr<EffectPaintPropertyNode> newEffectNode = createEffectIfNeeded(object, localContext);
+ RefPtr<ClipPaintPropertyNode> newClipNodeForCSSClip = createCSSClipIfNeeded(object, localContext);
OwnPtr<ObjectPaintProperties::LocalBorderBoxProperties> newRecordedContext = recordTreeContextIfNeeded(object, localContext);
RefPtr<TransformPaintPropertyNode> newTransformNodeForScrollbarPaintOffset = createScrollbarPaintOffsetIfNeeded(object, localContext);
RefPtr<ClipPaintPropertyNode> newClipNodeForOverflowClip = createOverflowClipIfNeeded(object, localContext);
@@ -361,13 +401,16 @@ void PaintPropertyTreeBuilder::walk(LayoutObject& object, const PaintPropertyTre
// http://www.w3.org/TR/css3-transforms/#transform-style-property
RefPtr<TransformPaintPropertyNode> newTransformNodeForPerspective = createPerspectiveIfNeeded(object, localContext);
RefPtr<TransformPaintPropertyNode> newTransformNodeForScrollTranslation = createScrollTranslationIfNeeded(object, localContext);
- updateOutOfFlowContext(object, localContext);
+ RefPtr<ClipPaintPropertyNode> newClipNodeForCSSClipFixedPosition;
+ updateOutOfFlowContext(object, localContext, newClipNodeForCSSClip.get(), newClipNodeForCSSClipFixedPosition);
- if (newTransformNodeForPaintOffsetTranslation || newTransformNodeForTransform || newEffectNode || newClipNodeForOverflowClip || newTransformNodeForPerspective || newTransformNodeForScrollTranslation || newTransformNodeForScrollbarPaintOffset || newRecordedContext) {
+ if (newTransformNodeForPaintOffsetTranslation || newTransformNodeForTransform || newEffectNode || newClipNodeForCSSClip || newClipNodeForCSSClipFixedPosition || newClipNodeForOverflowClip || newTransformNodeForPerspective || newTransformNodeForScrollTranslation || newTransformNodeForScrollbarPaintOffset || newRecordedContext) {
OwnPtr<ObjectPaintProperties> updatedPaintProperties = ObjectPaintProperties::create(
newTransformNodeForPaintOffsetTranslation.release(),
newTransformNodeForTransform.release(),
newEffectNode.release(),
+ newClipNodeForCSSClip.release(),
+ newClipNodeForCSSClipFixedPosition.release(),
newClipNodeForOverflowClip.release(),
newTransformNodeForPerspective.release(),
newTransformNodeForScrollTranslation.release(),

Powered by Google App Engine
This is Rietveld 408576698