Changeset 269822 in webkit
- Timestamp:
- Nov 14, 2020 5:38:12 PM (3 years ago)
- Location:
- trunk/Source/WebCore
- Files:
-
- 9 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/Source/WebCore/ChangeLog
r269821 r269822 1 2020-11-14 Simon Fraser <simon.fraser@apple.com> 2 3 [LFC Display] Implement propagation background style from body to root 4 https://bugs.webkit.org/show_bug.cgi?id=218947 5 6 Reviewed by Zalan Bujtas. 7 8 The root display box needs to get its background style from the document element box, 9 if it has one, otherwise the body box. If the body background style is propagated 10 to the root, then the body box needs to not paint its background. 11 12 Implement by adding BoxFactory::determineRootBackgroundPropagation(), and consulting 13 the result when creating the display boxes for the root and body. This is complicated 14 slightly by the need to pass the correct style to constructBoxDecorationData(), 15 which deals with both backgrounds and other (non-propagating) properties. 16 17 * display/DisplayTreeBuilder.cpp: 18 (WebCore::Display::TreeBuilder::build): 19 (WebCore::Display::TreeBuilder::recursiveBuildDisplayTree const): 20 (WebCore::Display::TreeBuilder::build const): Deleted. 21 * display/DisplayTreeBuilder.h: 22 * display/css/DisplayBoxFactory.cpp: 23 (WebCore::Display::BoxFactory::determineRootBackgroundPropagation): 24 (WebCore::Display::BoxFactory::displayBoxForRootBox const): 25 (WebCore::Display::BoxFactory::displayBoxForBodyBox const): 26 (WebCore::Display::BoxFactory::displayBoxForLayoutBox const): 27 (WebCore::Display::BoxFactory::constructBoxDecorationData const): 28 (WebCore::Display::BoxFactory::setupBoxModelBox const): 29 (WebCore::Display::BoxFactory::documentElementBoxFromRootBox): 30 (WebCore::Display::BoxFactory::bodyBoxFromRootBox): 31 * display/css/DisplayBoxFactory.h: 32 * display/css/DisplayFillLayerImageGeometry.cpp: 33 (WebCore::Display::calculateFillLayerImageGeometry): 34 * display/css/DisplayFillLayerImageGeometry.h: 35 * display/css/DisplayStyle.cpp: 36 (WebCore::Display::Style::Style): 37 (WebCore::Display::Style::setupBackground): 38 * display/css/DisplayStyle.h: 39 1 40 2020-11-14 Zalan Bujtas <zalan@apple.com> 2 41 -
trunk/Source/WebCore/display/DisplayTreeBuilder.cpp
r269181 r269822 52 52 } 53 53 54 std::unique_ptr<Tree> TreeBuilder::build(const Layout::LayoutState& layoutState) const54 std::unique_ptr<Tree> TreeBuilder::build(const Layout::LayoutState& layoutState) 55 55 { 56 56 ASSERT(layoutState.hasRoot()); … … 62 62 #endif 63 63 64 m_rootBackgroundPropgation = BoxFactory::determineRootBackgroundPropagation(rootLayoutBox); 65 64 66 auto geometry = layoutState.geometryForBox(rootLayoutBox); 65 auto rootDisplayBox = m_boxFactory.displayBoxForRootBox(rootLayoutBox, geometry );67 auto rootDisplayBox = m_boxFactory.displayBoxForRootBox(rootLayoutBox, geometry, m_rootBackgroundPropgation); 66 68 auto rootDisplayContainerBox = std::unique_ptr<ContainerBox> { downcast<ContainerBox>(rootDisplayBox.release()) }; 67 69 … … 120 122 { 121 123 auto geometry = layoutState.geometryForBox(layoutBox); 122 auto displayBox = m_boxFactory.displayBoxForLayoutBox(layoutBox, geometry, offsetFromRoot); 124 std::unique_ptr<Box> displayBox; 125 126 if (layoutBox.isBodyBox()) 127 displayBox = m_boxFactory.displayBoxForBodyBox(layoutBox, geometry, m_rootBackgroundPropgation, offsetFromRoot); 128 else 129 displayBox = m_boxFactory.displayBoxForLayoutBox(layoutBox, geometry, offsetFromRoot); 123 130 124 131 insert(WTFMove(displayBox), insertionPosition); -
trunk/Source/WebCore/display/DisplayTreeBuilder.h
r268959 r269822 56 56 explicit TreeBuilder(float pixelSnappingFactor); 57 57 58 std::unique_ptr<Tree> build(const Layout::LayoutState&) const;58 std::unique_ptr<Tree> build(const Layout::LayoutState&); 59 59 60 60 private: … … 71 71 72 72 BoxFactory m_boxFactory; 73 RootBackgroundPropagation m_rootBackgroundPropgation { RootBackgroundPropagation::None }; 73 74 }; 74 75 -
trunk/Source/WebCore/display/css/DisplayBoxFactory.cpp
r269563 r269822 37 37 #include "LayoutBoxGeometry.h" 38 38 #include "LayoutContainerBox.h" 39 #include "LayoutInitialContainingBlock.h" 39 40 #include "LayoutReplacedBox.h" 41 #include "Logging.h" 40 42 41 43 namespace WebCore { … … 47 49 } 48 50 49 std::unique_ptr<Box> BoxFactory::displayBoxForRootBox(const Layout::ContainerBox& rootLayoutBox, const Layout::BoxGeometry& geometry) const 50 { 51 RootBackgroundPropagation BoxFactory::determineRootBackgroundPropagation(const Layout::ContainerBox& rootLayoutBox) 52 { 53 auto* documentElementBox = documentElementBoxFromRootBox(rootLayoutBox); 54 auto* bodyBox = bodyBoxFromRootBox(rootLayoutBox); 55 56 if (documentElementBox && documentElementBox->style().hasBackground()) 57 return RootBackgroundPropagation::None; 58 59 if (bodyBox && bodyBox->style().hasBackground()) 60 return RootBackgroundPropagation::BodyToRoot; 61 62 return RootBackgroundPropagation::None; 63 } 64 65 std::unique_ptr<Box> BoxFactory::displayBoxForRootBox(const Layout::ContainerBox& rootLayoutBox, const Layout::BoxGeometry& geometry, RootBackgroundPropagation rootBackgroundPropagation) const 66 { 67 ASSERT(is<Layout::InitialContainingBlock>(rootLayoutBox)); 68 51 69 // FIXME: Need to do logical -> physical coordinate mapping here. 52 70 auto borderBoxRect = LayoutRect { Layout::BoxGeometry::borderBoxRect(geometry) }; 53 71 54 auto style = Style { rootLayoutBox.style() }; 72 auto* documentElementBox = documentElementBoxFromRootBox(rootLayoutBox); 73 74 const RenderStyle* styleForBackground = documentElementBox ? &documentElementBox->style() : nullptr; 75 76 if (rootBackgroundPropagation == RootBackgroundPropagation::BodyToRoot) { 77 if (auto* bodyBox = bodyBoxFromRootBox(rootLayoutBox)) 78 styleForBackground = &bodyBox->style(); 79 } 80 81 auto style = Style { rootLayoutBox.style(), styleForBackground }; 82 55 83 auto rootBox = makeUnique<ContainerBox>(snapRectToDevicePixels(borderBoxRect, m_pixelSnappingFactor), WTFMove(style)); 56 setupBoxModelBox(*rootBox, rootLayoutBox, geometry, { });84 setupBoxModelBox(*rootBox, rootLayoutBox, styleForBackground, geometry, { }); 57 85 return rootBox; 58 86 } 59 87 88 std::unique_ptr<Box> BoxFactory::displayBoxForBodyBox(const Layout::Box& layoutBox, const Layout::BoxGeometry& geometry, RootBackgroundPropagation rootBackgroundPropagation, LayoutSize offsetFromRoot) const 89 { 90 const RenderStyle* styleForBackground = &layoutBox.style(); 91 92 if (rootBackgroundPropagation == RootBackgroundPropagation::BodyToRoot) 93 styleForBackground = nullptr; 94 95 auto style = Style { layoutBox.style(), styleForBackground }; 96 return displayBoxForLayoutBox(layoutBox, styleForBackground, geometry, offsetFromRoot, WTFMove(style)); 97 } 98 60 99 std::unique_ptr<Box> BoxFactory::displayBoxForLayoutBox(const Layout::Box& layoutBox, const Layout::BoxGeometry& geometry, LayoutSize offsetFromRoot) const 100 { 101 auto style = Style { layoutBox.style() }; 102 return displayBoxForLayoutBox(layoutBox, &layoutBox.style(), geometry, offsetFromRoot, WTFMove(style)); 103 } 104 105 std::unique_ptr<Box> BoxFactory::displayBoxForLayoutBox(const Layout::Box& layoutBox, const RenderStyle* styleForBackground, const Layout::BoxGeometry& geometry, LayoutSize offsetFromRoot, Style&& style) const 61 106 { 62 107 // FIXME: Need to map logical to physical rects. … … 66 111 67 112 // FIXME: Handle isAnonymous() 68 // FIXME: Do hoisting of <body> styles to the root where appropriate.69 70 // FIXME: Need to do logical -> physical coordinate mapping here.71 auto style = Style { layoutBox.style() };72 113 73 114 if (is<Layout::ReplacedBox>(layoutBox)) { … … 78 119 79 120 auto imageBox = makeUnique<ImageBox>(pixelSnappedBorderBoxRect, WTFMove(style), WTFMove(image)); 80 setupBoxModelBox(*imageBox, layoutBox, geometry, offsetFromRoot);121 setupBoxModelBox(*imageBox, layoutBox, styleForBackground, geometry, offsetFromRoot); 81 122 return imageBox; 82 123 } … … 85 126 // FIXME: The decision to make a ContainerBox should be made based on whether this Display::Box will have children. 86 127 auto containerBox = makeUnique<ContainerBox>(pixelSnappedBorderBoxRect, WTFMove(style)); 87 setupBoxModelBox(*containerBox, layoutBox, geometry, offsetFromRoot);128 setupBoxModelBox(*containerBox, layoutBox, styleForBackground, geometry, offsetFromRoot); 88 129 return containerBox; 89 130 } … … 129 170 } 130 171 131 std::unique_ptr<BoxDecorationData> BoxFactory::constructBoxDecorationData(const Layout::Box& layoutBox, const Layout::BoxGeometry& layoutGeometry, LayoutSize offsetFromRoot) const172 std::unique_ptr<BoxDecorationData> BoxFactory::constructBoxDecorationData(const Layout::Box& layoutBox, const RenderStyle* styleForBackground, const Layout::BoxGeometry& layoutGeometry, LayoutSize offsetFromRoot) const 132 173 { 133 174 auto boxDecorationData = makeUnique<BoxDecorationData>(); 134 175 135 auto backgroundImageGeometry = calculateFillLayerImageGeometry(layoutBox, layoutGeometry, offsetFromRoot, m_pixelSnappingFactor); 136 boxDecorationData->setBackgroundImageGeometry(WTFMove(backgroundImageGeometry)); 176 if (styleForBackground) { 177 auto backgroundImageGeometry = calculateFillLayerImageGeometry(*styleForBackground, layoutGeometry, offsetFromRoot, m_pixelSnappingFactor); 178 boxDecorationData->setBackgroundImageGeometry(WTFMove(backgroundImageGeometry)); 179 } 137 180 138 181 bool includeLogicalLeftEdge = true; // FIXME. … … 155 198 } 156 199 157 void BoxFactory::setupBoxModelBox(BoxModelBox& box, const Layout::Box& layoutBox, const Layout::BoxGeometry& layoutGeometry, LayoutSize offsetFromRoot) const200 void BoxFactory::setupBoxModelBox(BoxModelBox& box, const Layout::Box& layoutBox, const RenderStyle* styleForBackground, const Layout::BoxGeometry& layoutGeometry, LayoutSize offsetFromRoot) const 158 201 { 159 202 setupBoxGeometry(box, layoutBox, layoutGeometry, offsetFromRoot); 160 203 161 204 auto& renderStyle = layoutBox.style(); 162 if (! renderStyle.hasBackground() && !renderStyle.hasBorder())205 if (!(styleForBackground && styleForBackground->hasBackground()) && !renderStyle.hasBorder()) 163 206 return; 164 207 165 auto boxDecorationData = constructBoxDecorationData(layoutBox, layoutGeometry, offsetFromRoot);208 auto boxDecorationData = constructBoxDecorationData(layoutBox, styleForBackground, layoutGeometry, offsetFromRoot); 166 209 box.setBoxDecorationData(WTFMove(boxDecorationData)); 167 210 } 168 211 212 const Layout::ContainerBox* BoxFactory::documentElementBoxFromRootBox(const Layout::ContainerBox& rootLayoutBox) 213 { 214 auto* documentBox = rootLayoutBox.firstChild(); 215 if (!documentBox || !documentBox->isDocumentBox() || !is<Layout::ContainerBox>(documentBox)) 216 return nullptr; 217 218 return downcast<Layout::ContainerBox>(documentBox); 219 } 220 221 const Layout::Box* BoxFactory::bodyBoxFromRootBox(const Layout::ContainerBox& rootLayoutBox) 222 { 223 auto* documentBox = rootLayoutBox.firstChild(); 224 if (!documentBox || !documentBox->isDocumentBox() || !is<Layout::ContainerBox>(documentBox)) 225 return nullptr; 226 227 auto* bodyBox = downcast<Layout::ContainerBox>(documentBox)->firstChild(); 228 if (!bodyBox || !bodyBox->isBodyBox()) 229 return nullptr; 230 231 return bodyBox; 232 } 169 233 170 234 } // namespace Display -
trunk/Source/WebCore/display/css/DisplayBoxFactory.h
r269468 r269822 48 48 class BoxModelBox; 49 49 50 enum class RootBackgroundPropagation : uint8_t { 51 None, 52 BodyToRoot, 53 }; 54 50 55 class BoxFactory { 51 56 public: 52 57 explicit BoxFactory(float pixelSnappingFactor); 53 58 54 std::unique_ptr<Box> displayBoxForRootBox(const Layout::ContainerBox&, const Layout::BoxGeometry&) const; 59 static RootBackgroundPropagation determineRootBackgroundPropagation(const Layout::ContainerBox& rootLayoutBox); 60 61 std::unique_ptr<Box> displayBoxForRootBox(const Layout::ContainerBox&, const Layout::BoxGeometry&, RootBackgroundPropagation) const; 62 std::unique_ptr<Box> displayBoxForBodyBox(const Layout::Box&, const Layout::BoxGeometry&, RootBackgroundPropagation, LayoutSize offsetFromRoot) const; 55 63 std::unique_ptr<Box> displayBoxForLayoutBox(const Layout::Box&, const Layout::BoxGeometry&, LayoutSize offsetFromRoot) const; 56 64 57 65 std::unique_ptr<Box> displayBoxForTextRun(const Layout::LineRun&, const Layout::InlineLineGeometry&, LayoutSize offsetFromRoot) const; 66 58 67 private: 68 std::unique_ptr<Box> displayBoxForLayoutBox(const Layout::Box&, const RenderStyle* styleForBackground, const Layout::BoxGeometry&, LayoutSize offsetFromRoot, Style&&) const; 59 69 60 70 void setupBoxGeometry(BoxModelBox&, const Layout::Box&, const Layout::BoxGeometry&, LayoutSize offsetFromRoot) const; 61 void setupBoxModelBox(BoxModelBox&, const Layout::Box&, const Layout::BoxGeometry&, LayoutSize offsetFromRoot) const;71 void setupBoxModelBox(BoxModelBox&, const Layout::Box&, const RenderStyle* styleForBackground, const Layout::BoxGeometry&, LayoutSize offsetFromRoot) const; 62 72 63 std::unique_ptr<BoxDecorationData> constructBoxDecorationData(const Layout::Box&, const Layout::BoxGeometry&, LayoutSize offsetFromRoot) const; 73 std::unique_ptr<BoxDecorationData> constructBoxDecorationData(const Layout::Box&, const RenderStyle* styleForBackground, const Layout::BoxGeometry&, LayoutSize offsetFromRoot) const; 74 75 static const Layout::ContainerBox* documentElementBoxFromRootBox(const Layout::ContainerBox& rootLayoutBox); 76 static const Layout::Box* bodyBoxFromRootBox(const Layout::ContainerBox& rootLayoutBox); 64 77 65 78 float m_pixelSnappingFactor { 1 }; -
trunk/Source/WebCore/display/css/DisplayFillLayerImageGeometry.cpp
r268959 r269822 375 375 } 376 376 377 Vector<FillLayerImageGeometry, 1> calculateFillLayerImageGeometry(const Layout::Box& layoutBox, const Layout::BoxGeometry& boxGeometry, LayoutSize offsetFromRoot, float pixelSnappingFactor) 378 { 379 auto& renderStyle = layoutBox.style(); 380 377 Vector<FillLayerImageGeometry, 1> calculateFillLayerImageGeometry(const RenderStyle& renderStyle, const Layout::BoxGeometry& boxGeometry, LayoutSize offsetFromRoot, float pixelSnappingFactor) 378 { 381 379 // FIXME: Need to map logical to physical rects. 382 380 auto borderBoxRect = LayoutRect { Layout::BoxGeometry::borderBoxRect(boxGeometry) }; -
trunk/Source/WebCore/display/css/DisplayFillLayerImageGeometry.h
r268959 r269822 34 34 namespace WebCore { 35 35 class FillLayer; 36 class RenderStyle; 36 37 class StyleImage; 37 38 … … 81 82 }; 82 83 83 Vector<FillLayerImageGeometry, 1> calculateFillLayerImageGeometry(const Layout::Box&, const Layout::BoxGeometry&, LayoutSize offsetFromRoot, float pixelSnappingFactor);84 Vector<FillLayerImageGeometry, 1> calculateFillLayerImageGeometry(const RenderStyle&, const Layout::BoxGeometry&, LayoutSize offsetFromRoot, float pixelSnappingFactor); 84 85 85 86 } // namespace Display -
trunk/Source/WebCore/display/css/DisplayStyle.cpp
r269601 r269822 58 58 59 59 Style::Style(const RenderStyle& style) 60 : Style(style, &style) 61 { 62 } 63 64 Style::Style(const RenderStyle& style, const RenderStyle* styleForBackground) 60 65 : m_fontCascade(style.fontCascade()) 61 66 , m_whiteSpace(style.whiteSpace()) … … 65 70 m_color = style.visitedDependentColorWithColorFilter(CSSPropertyColor); 66 71 67 m_backgroundColor = style.visitedDependentColorWithColorFilter(CSSPropertyBackgroundColor);68 m_backgroundLayers = deepCopy(style.backgroundLayers());72 if (styleForBackground) 73 setupBackground(*styleForBackground); 69 74 70 75 if (!style.hasAutoUsedZIndex()) … … 73 78 setIsPositioned(style.position() != PositionType::Static); 74 79 setIsFloating(style.floating() != Float::No); 80 } 81 82 void Style::setupBackground(const RenderStyle& style) 83 { 84 m_backgroundColor = style.visitedDependentColorWithColorFilter(CSSPropertyBackgroundColor); 85 m_backgroundLayers = deepCopy(style.backgroundLayers()); 75 86 } 76 87 -
trunk/Source/WebCore/display/css/DisplayStyle.h
r269601 r269822 59 59 60 60 explicit Style(const RenderStyle&); 61 explicit Style(const RenderStyle&, const RenderStyle* styleForBackground); 61 62 62 63 const Color& color() const { return m_color; } … … 88 89 89 90 private: 91 void setupBackground(const RenderStyle&); 92 90 93 void setIsPositioned(bool value) { m_flags.set({ Flags::Positioned }, value); } 91 94 void setIsFloating(bool value) { m_flags.set({ Flags::Floating }, value); }
Note: See TracChangeset
for help on using the changeset viewer.