Title: [270222] trunk/Source/WebCore
Revision
270222
Author
[email protected]
Date
2020-11-28 20:05:09 -0800 (Sat, 28 Nov 2020)

Log Message

[LFC Display] Add basic transforms support.
https://bugs.webkit.org/show_bug.cgi?id=219313

Reviewed by Zalan Bujtas.

Add Display::BoxRareGeometry which will hold uncommon per-box geometry like
border-radius and transformation matrix.

At tree building time, compute a TransformationMatrix for the transforms on a box,
using a pixel-snapped transform origin. Also store a bit on Display::Style to indicate
that a transform applies (when set, we assume that BoxRareGeometry is non-null).

At paint time, use the computed matrix to adjust the CTM when painting a stacking
context, post-clipping and pre-effects. We adjust the box's matrix to move the
applied origin to the origin of the border box, and to account for the fact that
descendants will continue to paint in absolute coordinates.

* Sources.txt:
* WebCore.xcodeproj/project.pbxproj:
* display/css/DisplayBoxFactory.cpp:
(WebCore::Display::BoxFactory::computeTransformOrigin const):
(WebCore::Display::BoxFactory::computeTransformationMatrix const):
(WebCore::Display::BoxFactory::constructBoxRareGeometry const):
(WebCore::Display::BoxFactory::setupBoxModelBox const):
* display/css/DisplayBoxFactory.h:
* display/css/DisplayBoxModelBox.cpp:
(WebCore::Display::BoxModelBox::setBoxRareGeometry):
(WebCore::Display::BoxModelBox::hasAncestorClip const):
* display/css/DisplayBoxModelBox.h:
(WebCore::Display::BoxModelBox::rareGeometry const):
* display/css/DisplayBoxRareGeometry.cpp: Added.
* display/css/DisplayBoxRareGeometry.h: Copied from Source/WebCore/display/css/DisplayBoxModelBox.h.
(WebCore::Display::BoxRareGeometry::transform const):
(WebCore::Display::BoxRareGeometry::setTransform):
* display/css/DisplayCSSPainter.cpp:
(WebCore::Display::applyAncestorClip):
(WebCore::Display::applyEffects):
(WebCore::Display::CSSPainter::paintAtomicallyPaintedBox):
* display/css/DisplayStyle.cpp:
(WebCore::Display::Style::Style):
* display/css/DisplayStyle.h:
(WebCore::Display::Style::hasTransform const):
(WebCore::Display::Style::setHasTransform):

Modified Paths

Added Paths

Diff

Modified: trunk/Source/WebCore/ChangeLog (270221 => 270222)


--- trunk/Source/WebCore/ChangeLog	2020-11-29 00:19:33 UTC (rev 270221)
+++ trunk/Source/WebCore/ChangeLog	2020-11-29 04:05:09 UTC (rev 270222)
@@ -1,5 +1,51 @@
 2020-11-28  Simon Fraser  <[email protected]>
 
+        [LFC Display] Add basic transforms support.
+        https://bugs.webkit.org/show_bug.cgi?id=219313
+
+        Reviewed by Zalan Bujtas.
+
+        Add Display::BoxRareGeometry which will hold uncommon per-box geometry like
+        border-radius and transformation matrix.
+
+        At tree building time, compute a TransformationMatrix for the transforms on a box,
+        using a pixel-snapped transform origin. Also store a bit on Display::Style to indicate
+        that a transform applies (when set, we assume that BoxRareGeometry is non-null).
+
+        At paint time, use the computed matrix to adjust the CTM when painting a stacking
+        context, post-clipping and pre-effects. We adjust the box's matrix to move the
+        applied origin to the origin of the border box, and to account for the fact that
+        descendants will continue to paint in absolute coordinates.
+
+        * Sources.txt:
+        * WebCore.xcodeproj/project.pbxproj:
+        * display/css/DisplayBoxFactory.cpp:
+        (WebCore::Display::BoxFactory::computeTransformOrigin const):
+        (WebCore::Display::BoxFactory::computeTransformationMatrix const):
+        (WebCore::Display::BoxFactory::constructBoxRareGeometry const):
+        (WebCore::Display::BoxFactory::setupBoxModelBox const):
+        * display/css/DisplayBoxFactory.h:
+        * display/css/DisplayBoxModelBox.cpp:
+        (WebCore::Display::BoxModelBox::setBoxRareGeometry):
+        (WebCore::Display::BoxModelBox::hasAncestorClip const):
+        * display/css/DisplayBoxModelBox.h:
+        (WebCore::Display::BoxModelBox::rareGeometry const):
+        * display/css/DisplayBoxRareGeometry.cpp: Added.
+        * display/css/DisplayBoxRareGeometry.h: Copied from Source/WebCore/display/css/DisplayBoxModelBox.h.
+        (WebCore::Display::BoxRareGeometry::transform const):
+        (WebCore::Display::BoxRareGeometry::setTransform):
+        * display/css/DisplayCSSPainter.cpp:
+        (WebCore::Display::applyAncestorClip):
+        (WebCore::Display::applyEffects):
+        (WebCore::Display::CSSPainter::paintAtomicallyPaintedBox):
+        * display/css/DisplayStyle.cpp:
+        (WebCore::Display::Style::Style):
+        * display/css/DisplayStyle.h:
+        (WebCore::Display::Style::hasTransform const):
+        (WebCore::Display::Style::setHasTransform):
+
+2020-11-28  Simon Fraser  <[email protected]>
+
         [LFC Display] Add basic opacity support.
         https://bugs.webkit.org/show_bug.cgi?id=219312
 

Modified: trunk/Source/WebCore/Sources.txt (270221 => 270222)


--- trunk/Source/WebCore/Sources.txt	2020-11-29 00:19:33 UTC (rev 270221)
+++ trunk/Source/WebCore/Sources.txt	2020-11-29 04:05:09 UTC (rev 270222)
@@ -840,6 +840,7 @@
 display/css/DisplayBoxFactory.cpp
 display/css/DisplayBoxModelBox.cpp
 display/css/DisplayBoxPainter.cpp
+display/css/DisplayBoxRareGeometry.cpp
 display/css/DisplayContainerBox.cpp
 display/css/DisplayCSSPainter.cpp
 display/css/DisplayFillLayerImageGeometry.cpp

Modified: trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj (270221 => 270222)


--- trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj	2020-11-29 00:19:33 UTC (rev 270221)
+++ trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj	2020-11-29 04:05:09 UTC (rev 270222)
@@ -5966,6 +5966,8 @@
 		0F26A7AB2054FCE10090A141 /* MathMLUnknownElement.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = MathMLUnknownElement.cpp; sourceTree = "<group>"; };
 		0F26A7AC2055C8D70090A141 /* XMLDocument.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = XMLDocument.cpp; sourceTree = "<group>"; };
 		0F26A7AD205626100090A141 /* SVGUnknownElement.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = SVGUnknownElement.cpp; sourceTree = "<group>"; };
+		0F2808612570151700FE6C5A /* DisplayBoxRareGeometry.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = DisplayBoxRareGeometry.h; sourceTree = "<group>"; };
+		0F2808632570151700FE6C5A /* DisplayBoxRareGeometry.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = DisplayBoxRareGeometry.cpp; sourceTree = "<group>"; };
 		0F283A8D235582F8004794CA /* ThemeTypes.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = ThemeTypes.cpp; sourceTree = "<group>"; };
 		0F283A9123563126004794CA /* BorderData.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = BorderData.cpp; sourceTree = "<group>"; };
 		0F32BA41254F3216001AC38E /* DisplayPaintingContext.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = DisplayPaintingContext.h; sourceTree = "<group>"; };
@@ -17827,6 +17829,8 @@
 				0F94721E2534010900F153C8 /* DisplayBoxModelBox.h */,
 				0F656FBD2545FD5700219F4C /* DisplayBoxPainter.cpp */,
 				0F656FBC2545FD5600219F4C /* DisplayBoxPainter.h */,
+				0F2808632570151700FE6C5A /* DisplayBoxRareGeometry.cpp */,
+				0F2808612570151700FE6C5A /* DisplayBoxRareGeometry.h */,
 				0FFF1B74251BC6570098795A /* DisplayContainerBox.cpp */,
 				0FFF1B7A251BC6570098795A /* DisplayContainerBox.h */,
 				0FFF1B7D251BC6570098795A /* DisplayCSSPainter.cpp */,

Modified: trunk/Source/WebCore/display/css/DisplayBoxFactory.cpp (270221 => 270222)


--- trunk/Source/WebCore/display/css/DisplayBoxFactory.cpp	2020-11-29 00:19:33 UTC (rev 270221)
+++ trunk/Source/WebCore/display/css/DisplayBoxFactory.cpp	2020-11-29 04:05:09 UTC (rev 270222)
@@ -30,10 +30,12 @@
 
 #include "DisplayBoxDecorationData.h"
 #include "DisplayBoxDecorationPainter.h"
+#include "DisplayBoxRareGeometry.h"
 #include "DisplayContainerBox.h"
 #include "DisplayFillLayerImageGeometry.h"
 #include "DisplayImageBox.h"
 #include "DisplayTextBox.h"
+#include "FloatPoint3D.h"
 #include "InlineLineGeometry.h"
 #include "LayoutBoxGeometry.h"
 #include "LayoutContainerBox.h"
@@ -40,6 +42,7 @@
 #include "LayoutInitialContainingBlock.h"
 #include "LayoutReplacedBox.h"
 #include "Logging.h"
+#include "TransformationMatrix.h"
 
 namespace WebCore {
 namespace Display {
@@ -199,12 +202,62 @@
     return boxDecorationData;
 }
 
+FloatPoint3D BoxFactory::computeTransformOrigin(const BoxModelBox& box, const Layout::BoxGeometry& layoutGeometry, const RenderStyle& renderStyle, LayoutSize offsetFromRoot) const
+{
+    auto transformBoxRect = LayoutRect { Layout::BoxGeometry::borderBoxRect(layoutGeometry) };
+
+    auto absoluteOrigin = LayoutPoint {
+        offsetFromRoot.width() + transformBoxRect.x() + valueForLength(renderStyle.transformOriginX(), transformBoxRect.width()),
+        offsetFromRoot.height() + transformBoxRect.y() + valueForLength(renderStyle.transformOriginY(), transformBoxRect.height())
+    };
+
+    auto snappedAbsoluteOrigin = roundPointToDevicePixels(absoluteOrigin, m_pixelSnappingFactor);
+    auto boxRelativeTransformOriginXY = snappedAbsoluteOrigin - box.absoluteBorderBoxRect().location();
+
+    return { boxRelativeTransformOriginXY.width(), boxRelativeTransformOriginXY.height(), renderStyle.transformOriginZ() };
+}
+
+TransformationMatrix BoxFactory::computeTransformationMatrix(const BoxModelBox& box, const Layout::BoxGeometry& layoutGeometry, const RenderStyle& renderStyle, LayoutSize offsetFromRoot) const
+{
+    auto boxRelativeTransformOrigin = computeTransformOrigin(box, layoutGeometry, renderStyle, offsetFromRoot);
+
+    // FIXME: Respect transform-box.
+    auto transformBoxRect = box.absoluteBorderBoxRect();
+
+    // FIXME: This is similar to RenderStyle::applyTransform(), but that fails to pixel snap transform origin.
+    auto transform = TransformationMatrix { };
+    transform.translate3d(boxRelativeTransformOrigin.x(), boxRelativeTransformOrigin.y(), boxRelativeTransformOrigin.z());
+
+    for (auto& operation : renderStyle.transform().operations())
+        operation->apply(transform, transformBoxRect.size());
+
+    transform.translate3d(-boxRelativeTransformOrigin.x(), -boxRelativeTransformOrigin.y(), -boxRelativeTransformOrigin.z());
+    return transform;
+
+}
+
+std::unique_ptr<BoxRareGeometry> BoxFactory::constructBoxRareGeometry(const BoxModelBox& box, const Layout::Box& layoutBox, const Layout::BoxGeometry& layoutGeometry, LayoutSize offsetFromRoot) const
+{
+    if (!box.style().hasTransform())
+        return nullptr;
+
+    auto boxRareGeometry = makeUnique<BoxRareGeometry>();
+
+    auto transformationMatrix = computeTransformationMatrix(box, layoutGeometry, layoutBox.style(), offsetFromRoot);
+    boxRareGeometry->setTransform(WTFMove(transformationMatrix));
+
+    return boxRareGeometry;
+}
+
 void BoxFactory::setupBoxModelBox(BoxModelBox& box, const Layout::Box& layoutBox, const Layout::BoxGeometry& layoutGeometry, const ContainingBlockContext& containingBlockContext, const RenderStyle* styleForBackground) const
 {
     setupBoxGeometry(box, layoutBox, layoutGeometry, containingBlockContext);
 
+    auto boxRareGeometry = constructBoxRareGeometry(box, layoutBox, layoutGeometry, containingBlockContext.offsetFromRoot);
+    box.setBoxRareGeometry(WTFMove(boxRareGeometry));
+
     auto& renderStyle = layoutBox.style();
-    if (!(styleForBackground && styleForBackground->hasBackground()) && !renderStyle.hasBorder())
+    if (!(styleForBackground && styleForBackground->hasBackground()) && !renderStyle.hasBorder()) // FIXME: Misses border-radius.
         return;
 
     auto boxDecorationData = constructBoxDecorationData(layoutBox, layoutGeometry, styleForBackground, containingBlockContext.offsetFromRoot);

Modified: trunk/Source/WebCore/display/css/DisplayBoxFactory.h (270221 => 270222)


--- trunk/Source/WebCore/display/css/DisplayBoxFactory.h	2020-11-29 00:19:33 UTC (rev 270221)
+++ trunk/Source/WebCore/display/css/DisplayBoxFactory.h	2020-11-29 04:05:09 UTC (rev 270222)
@@ -32,7 +32,9 @@
 
 namespace WebCore {
 
+class FloatPoint3D;
 class RenderStyle;
+class TransformationMatrix;
 
 namespace Layout {
 class Box;
@@ -47,6 +49,7 @@
 class Box;
 class BoxDecorationData;
 class BoxModelBox;
+class BoxRareGeometry;
 class ContainerBox;
 class Style;
 
@@ -80,6 +83,11 @@
 
     std::unique_ptr<BoxDecorationData> constructBoxDecorationData(const Layout::Box&, const Layout::BoxGeometry&, const RenderStyle* styleForBackground, LayoutSize offsetFromRoot) const;
 
+    std::unique_ptr<BoxRareGeometry> constructBoxRareGeometry(const BoxModelBox& box, const Layout::Box&, const Layout::BoxGeometry&, LayoutSize offsetFromRoot) const;
+
+    FloatPoint3D computeTransformOrigin(const BoxModelBox&, const Layout::BoxGeometry&, const RenderStyle&, LayoutSize offsetFromRoot) const;
+    TransformationMatrix computeTransformationMatrix(const BoxModelBox&, const Layout::BoxGeometry&, const RenderStyle&, LayoutSize offsetFromRoot) const;
+
     static const Layout::ContainerBox* documentElementBoxFromRootBox(const Layout::ContainerBox& rootLayoutBox);
     static const Layout::Box* bodyBoxFromRootBox(const Layout::ContainerBox& rootLayoutBox);
 

Modified: trunk/Source/WebCore/display/css/DisplayBoxModelBox.cpp (270221 => 270222)


--- trunk/Source/WebCore/display/css/DisplayBoxModelBox.cpp	2020-11-29 00:19:33 UTC (rev 270221)
+++ trunk/Source/WebCore/display/css/DisplayBoxModelBox.cpp	2020-11-29 04:05:09 UTC (rev 270222)
@@ -30,6 +30,7 @@
 
 #include "DisplayBoxClip.h"
 #include "DisplayBoxDecorationData.h"
+#include "DisplayBoxRareGeometry.h"
 #include <wtf/IsoMallocInlines.h>
 #include <wtf/text/TextStream.h>
 
@@ -48,6 +49,11 @@
     m_boxDecorationData = WTFMove(decorationData);
 }
 
+void BoxModelBox::setBoxRareGeometry(std::unique_ptr<BoxRareGeometry>&& rareGeometry)
+{
+    m_boxRareGeometry = WTFMove(rareGeometry);
+}
+
 FloatRoundedRect BoxModelBox::borderRoundedRect() const
 {
     auto borderRect = FloatRoundedRect { absoluteBorderBoxRect(), { } };
@@ -74,6 +80,11 @@
     m_ancestorClip = WTFMove(clip);
 }
 
+bool BoxModelBox::hasAncestorClip() const
+{
+    return m_ancestorClip && m_ancestorClip->clipRect();
+}
+
 RefPtr<BoxClip> BoxModelBox::clipForDescendants() const
 {
     if (!style().hasClippedOverflow())

Modified: trunk/Source/WebCore/display/css/DisplayBoxModelBox.h (270221 => 270222)


--- trunk/Source/WebCore/display/css/DisplayBoxModelBox.h	2020-11-29 00:19:33 UTC (rev 270221)
+++ trunk/Source/WebCore/display/css/DisplayBoxModelBox.h	2020-11-29 04:05:09 UTC (rev 270222)
@@ -35,6 +35,7 @@
 
 class BoxClip;
 class BoxDecorationData;
+class BoxRareGeometry;
 
 // A box in the sense of the CSS Box Model.
 // This box can draw backgrounds and borders.
@@ -49,7 +50,10 @@
     AbsoluteFloatRect absoluteContentBoxRect() const { return m_contentBoxRect; }
 
     const BoxDecorationData* boxDecorationData() const { return m_boxDecorationData.get(); }
+    const BoxRareGeometry* rareGeometry() const { return m_boxRareGeometry.get(); }
+
     const BoxClip* ancestorClip() const { return m_ancestorClip.get(); }
+    bool hasAncestorClip() const;
 
     FloatRoundedRect borderRoundedRect() const;
     FloatRoundedRect innerBorderRoundedRect() const;
@@ -62,6 +66,7 @@
     void setAbsoluteContentBoxRect(const AbsoluteFloatRect& box) { m_contentBoxRect = box; }
 
     void setBoxDecorationData(std::unique_ptr<BoxDecorationData>&&);
+    void setBoxRareGeometry(std::unique_ptr<BoxRareGeometry>&&);
 
     void setAncestorClip(RefPtr<BoxClip>&&);
     RefPtr<BoxClip> clipForDescendants() const;
@@ -70,6 +75,7 @@
     AbsoluteFloatRect m_contentBoxRect;
 
     std::unique_ptr<BoxDecorationData> m_boxDecorationData;
+    std::unique_ptr<BoxRareGeometry> m_boxRareGeometry;
     RefPtr<BoxClip> m_ancestorClip;
 };
 

Added: trunk/Source/WebCore/display/css/DisplayBoxRareGeometry.cpp (0 => 270222)


--- trunk/Source/WebCore/display/css/DisplayBoxRareGeometry.cpp	                        (rev 0)
+++ trunk/Source/WebCore/display/css/DisplayBoxRareGeometry.cpp	2020-11-29 04:05:09 UTC (rev 270222)
@@ -0,0 +1,40 @@
+/*
+ * Copyright (C) 2020 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "config.h"
+#include "DisplayBoxRareGeometry.h"
+
+#if ENABLE(LAYOUT_FORMATTING_CONTEXT)
+
+#include "RenderStyle.h"
+
+namespace WebCore {
+namespace Display {
+
+
+} // namespace Display
+} // namespace WebCore
+
+#endif // ENABLE(LAYOUT_FORMATTING_CONTEXT)

Copied: trunk/Source/WebCore/display/css/DisplayBoxRareGeometry.h (from rev 270221, trunk/Source/WebCore/display/css/DisplayBoxModelBox.h) (0 => 270222)


--- trunk/Source/WebCore/display/css/DisplayBoxRareGeometry.h	                        (rev 0)
+++ trunk/Source/WebCore/display/css/DisplayBoxRareGeometry.h	2020-11-29 04:05:09 UTC (rev 270222)
@@ -0,0 +1,59 @@
+/*
+ * Copyright (C) 2020 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#pragma once
+
+#if ENABLE(LAYOUT_FORMATTING_CONTEXT)
+
+#include "FloatPoint3D.h"
+#include "FloatRoundedRect.h"
+#include "TransformationMatrix.h"
+#include <wtf/IsoMalloc.h>
+
+namespace WebCore {
+
+namespace Display {
+
+// Storage for box geometry which is only used on boxes with rare style, like transforms or border-radius.
+class BoxRareGeometry {
+    WTF_MAKE_FAST_ALLOCATED_WITH_HEAP_IDENTIFIER(BoxRareGeometry);
+public:
+
+    // FIXME: Move border radii here.
+
+
+    // From transform, translate, rotate, scale properties.
+    const TransformationMatrix& transform() const { return m_transform; }
+    void setTransform(TransformationMatrix&& transform) { m_transform = WTFMove(transform); }
+
+private:
+    TransformationMatrix m_transform;
+};
+
+} // namespace Display
+} // namespace WebCore
+
+
+#endif // ENABLE(LAYOUT_FORMATTING_CONTEXT)

Modified: trunk/Source/WebCore/display/css/DisplayCSSPainter.cpp (270221 => 270222)


--- trunk/Source/WebCore/display/css/DisplayCSSPainter.cpp	2020-11-29 00:19:33 UTC (rev 270221)
+++ trunk/Source/WebCore/display/css/DisplayCSSPainter.cpp	2020-11-29 04:05:09 UTC (rev 270222)
@@ -35,6 +35,7 @@
 #include "DisplayTree.h"
 #include "GraphicsContext.h"
 #include "IntRect.h"
+#include "TransformationMatrix.h"
 
 namespace WebCore {
 namespace Display {
@@ -48,14 +49,12 @@
     }
 }
 
-static void applyAncestorClip(const BoxModelBox& box, PaintingContext& paintingContext, GraphicsContextStateSaver& stateSaver)
+static void applyAncestorClip(const BoxModelBox& box, PaintingContext& paintingContext)
 {
     auto* boxClip = box.ancestorClip();
     if (!boxClip || !boxClip->clipRect())
         return;
 
-    stateSaver.save();
-
     if (!boxClip->affectedByBorderRadius()) {
         paintingContext.context.clip(*boxClip->clipRect());
         return;
@@ -65,7 +64,7 @@
         paintingContext.context.clipRoundedRect(roundedRect);
 }
 
-static void applyEffects(const Box& box, PaintingContext&, GraphicsContextStateSaver&, TransparencyLayerScope& transparencyScope)
+static void applyEffects(const Box& box, PaintingContext&, TransparencyLayerScope& transparencyScope)
 {
     if (box.style().opacity() < 1) {
         // FIXME: Compute and set a clip to avoid creating large transparency layers.
@@ -127,13 +126,34 @@
 {
     UNUSED_PARAM(dirtyRect);
 
-    auto stateSaver = GraphicsContextStateSaver { paintingContext.context, false };
+    auto needToSaveState = [](const Box& box) {
+        if (!is<BoxModelBox>(box))
+            return false;
+        
+        auto& boxModelBox = downcast<BoxModelBox>(box);
+        return boxModelBox.hasAncestorClip() || boxModelBox.style().hasTransform();
+    };
 
+    auto stateSaver = GraphicsContextStateSaver { paintingContext.context, needToSaveState(box) };
+
     if (is<BoxModelBox>(box))
-        applyAncestorClip(downcast<BoxModelBox>(box), paintingContext, stateSaver);
+        applyAncestorClip(downcast<BoxModelBox>(box), paintingContext);
 
+    if (is<BoxModelBox>(box) && box.style().hasTransform()) {
+        auto transformationMatrix = downcast<BoxModelBox>(box).rareGeometry()->transform();
+        auto absoluteBorderBox = box.absoluteBoxRect();
+
+        // Equivalent to adjusting the CTM so that the origin is in the top left of the border box.
+        transformationMatrix.translateRight(absoluteBorderBox.x(), absoluteBorderBox.y());
+        // Allow descendants rendered using absolute coordinates to paint relative to this box.
+        transformationMatrix.translate(-absoluteBorderBox.x(), -absoluteBorderBox.y());
+
+        auto affineTransform = transformationMatrix.toAffineTransform();
+        paintingContext.context.concatCTM(affineTransform);
+    }
+
     auto transparencyScope = TransparencyLayerScope { paintingContext.context, 1, false };
-    applyEffects(box, paintingContext, stateSaver, transparencyScope);
+    applyEffects(box, paintingContext, transparencyScope);
 
     BoxPainter::paintBox(box, paintingContext, dirtyRect);
     if (!is<ContainerBox>(box))

Modified: trunk/Source/WebCore/display/css/DisplayStyle.cpp (270221 => 270222)


--- trunk/Source/WebCore/display/css/DisplayStyle.cpp	2020-11-29 00:19:33 UTC (rev 270221)
+++ trunk/Source/WebCore/display/css/DisplayStyle.cpp	2020-11-29 04:05:09 UTC (rev 270222)
@@ -104,6 +104,7 @@
 
     setIsPositioned(style.position() != PositionType::Static);
     setIsFloating(style.floating() != Float::No);
+    setHasTransform(style.hasTransform());
 }
 
 void Style::setupBackground(const RenderStyle& style)

Modified: trunk/Source/WebCore/display/css/DisplayStyle.h (270221 => 270222)


--- trunk/Source/WebCore/display/css/DisplayStyle.h	2020-11-29 00:19:33 UTC (rev 270221)
+++ trunk/Source/WebCore/display/css/DisplayStyle.h	2020-11-29 04:05:09 UTC (rev 270222)
@@ -33,6 +33,7 @@
 #include "NinePieceImage.h"
 #include "RenderStyleConstants.h"
 #include "TabSize.h"
+#include "TransformOperations.h"
 #include <wtf/IsoMalloc.h>
 #include <wtf/OptionSet.h>
 #include <wtf/Optional.h>
@@ -54,8 +55,9 @@
 public:
 
     enum class Flags : uint8_t {
-        Positioned  = 1 << 0,
-        Floating    = 1 << 1,
+        Positioned      = 1 << 0,
+        Floating        = 1 << 1,
+        HasTransform    = 1 << 2,
     };
 
     explicit Style(const RenderStyle&);
@@ -78,6 +80,9 @@
     bool isPositioned() const { return m_flags.contains(Flags::Positioned); }
     bool isFloating() const { return m_flags.contains(Flags::Floating); }
 
+    // Just the transform property (not translate, rotate, scale).
+    bool hasTransform() const { return m_flags.contains(Flags::HasTransform); }
+
     bool participatesInZOrderSorting() const { return isPositioned() || isStackingContext(); }
 
     const FontCascade& fontCascade() const { return m_fontCascade; }
@@ -101,6 +106,7 @@
 
     void setIsPositioned(bool value) { m_flags.set({ Flags::Positioned }, value); }
     void setIsFloating(bool value) { m_flags.set({ Flags::Floating }, value); }
+    void setHasTransform(bool value) { m_flags.set({ Flags::HasTransform }, value); }
 
     Color m_color;
     Color m_backgroundColor;
@@ -107,7 +113,7 @@
 
     RefPtr<FillLayer> m_backgroundLayers;
     std::unique_ptr<ShadowData> m_boxShadow;
-    
+
     Overflow m_overflowX;
     Overflow m_overflowY;
 
_______________________________________________
webkit-changes mailing list
[email protected]
https://lists.webkit.org/mailman/listinfo/webkit-changes

Reply via email to