| OLD | NEW |
| (Empty) | |
| 1 // Copyright 2016 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. |
| 4 |
| 5 #include "core/layout/compositing/CompositingReasonFinder.h" |
| 6 |
| 7 #include "core/frame/FrameView.h" |
| 8 #include "core/layout/LayoutBlock.h" |
| 9 #include "core/layout/LayoutTestHelper.h" |
| 10 #include "core/paint/PaintLayer.h" |
| 11 #include "platform/graphics/GraphicsLayer.h" |
| 12 #include "platform/scroll/ScrollTypes.h" |
| 13 #include "platform/testing/RuntimeEnabledFeaturesTestHelpers.h" |
| 14 |
| 15 namespace blink { |
| 16 |
| 17 class CompositingReasonFinderTest : public RenderingTest { |
| 18 public: |
| 19 CompositingReasonFinderTest() |
| 20 : RenderingTest(SingleChildFrameLoaderClient::create()) {} |
| 21 |
| 22 private: |
| 23 void SetUp() override { |
| 24 RenderingTest::SetUp(); |
| 25 enableCompositing(); |
| 26 } |
| 27 }; |
| 28 |
| 29 TEST_F(CompositingReasonFinderTest, PromoteOpaqueFixedPosition) { |
| 30 ScopedCompositeFixedPositionForTest compositeFixedPosition(true); |
| 31 |
| 32 setBodyInnerHTML( |
| 33 "<div id='translucent' style='width: 20px; height: 20px; position: " |
| 34 "fixed; top: 100px; left: 100px;'></div>" |
| 35 "<div id='opaque' style='width: 20px; height: 20px; position: fixed; " |
| 36 "top: 100px; left: 200px; background: white;'></div>" |
| 37 "<div id='opaque-with-shadow' style='width: 20px; height: 20px; " |
| 38 "position: fixed; top: 100px; left: 300px; background: white; " |
| 39 "box-shadow: 10px 10px 5px #888888;'></div>" |
| 40 "<div id='spacer' style='height: 2000px'></div>"); |
| 41 |
| 42 document().view()->updateAllLifecyclePhases(); |
| 43 |
| 44 // The translucent fixed box should not be promoted. |
| 45 Element* element = document().getElementById("translucent"); |
| 46 PaintLayer* paintLayer = |
| 47 toLayoutBoxModelObject(element->layoutObject())->layer(); |
| 48 EXPECT_EQ(NotComposited, paintLayer->compositingState()); |
| 49 |
| 50 // The opaque fixed box should be promoted and be opaque so that text will be |
| 51 // drawn with subpixel anti-aliasing. |
| 52 element = document().getElementById("opaque"); |
| 53 paintLayer = toLayoutBoxModelObject(element->layoutObject())->layer(); |
| 54 EXPECT_EQ(PaintsIntoOwnBacking, paintLayer->compositingState()); |
| 55 EXPECT_TRUE(paintLayer->graphicsLayerBacking()->contentsOpaque()); |
| 56 |
| 57 // The opaque fixed box with shadow should not be promoted because the layer |
| 58 // will include the shadow which is not opaque. |
| 59 element = document().getElementById("opaque-with-shadow"); |
| 60 paintLayer = toLayoutBoxModelObject(element->layoutObject())->layer(); |
| 61 EXPECT_EQ(NotComposited, paintLayer->compositingState()); |
| 62 } |
| 63 |
| 64 // Tests that a transform on the fixed or an ancestor will prevent promotion |
| 65 // TODO(flackr): Allow integer transforms as long as all of the ancestor |
| 66 // transforms are also integer. |
| 67 TEST_F(CompositingReasonFinderTest, OnlyNonTransformedFixedLayersPromoted) { |
| 68 ScopedCompositeFixedPositionForTest compositeFixedPosition(true); |
| 69 |
| 70 setBodyInnerHTML( |
| 71 "<style>" |
| 72 "#fixed { position: fixed; height: 200px; width: 200px; background: " |
| 73 "white; top: 0; }" |
| 74 "#spacer { height: 3000px; }" |
| 75 "</style>" |
| 76 "<div id=\"parent\">" |
| 77 " <div id=\"fixed\"></div>" |
| 78 " <div id=\"spacer\"></div>" |
| 79 "</div>"); |
| 80 document().view()->updateAllLifecyclePhases(); |
| 81 |
| 82 EXPECT_TRUE(RuntimeEnabledFeatures::compositeOpaqueScrollersEnabled()); |
| 83 Element* parent = document().getElementById("parent"); |
| 84 Element* fixed = document().getElementById("fixed"); |
| 85 PaintLayer* paintLayer = |
| 86 toLayoutBoxModelObject(fixed->layoutObject())->layer(); |
| 87 ASSERT_TRUE(paintLayer); |
| 88 EXPECT_EQ(PaintsIntoOwnBacking, paintLayer->compositingState()); |
| 89 EXPECT_TRUE(paintLayer->graphicsLayerBacking()->contentsOpaque()); |
| 90 |
| 91 // Change the parent to have a transform. |
| 92 parent->setAttribute(HTMLNames::styleAttr, "transform: translate(1px, 0);"); |
| 93 document().view()->updateAllLifecyclePhases(); |
| 94 paintLayer = toLayoutBoxModelObject(fixed->layoutObject())->layer(); |
| 95 ASSERT_TRUE(paintLayer); |
| 96 EXPECT_EQ(NotComposited, paintLayer->compositingState()); |
| 97 |
| 98 // Change the parent to have no transform again. |
| 99 parent->removeAttribute(HTMLNames::styleAttr); |
| 100 document().view()->updateAllLifecyclePhases(); |
| 101 paintLayer = toLayoutBoxModelObject(fixed->layoutObject())->layer(); |
| 102 ASSERT_TRUE(paintLayer); |
| 103 EXPECT_EQ(PaintsIntoOwnBacking, paintLayer->compositingState()); |
| 104 EXPECT_TRUE(paintLayer->graphicsLayerBacking()->contentsOpaque()); |
| 105 |
| 106 // Apply a transform to the fixed directly. |
| 107 fixed->setAttribute(HTMLNames::styleAttr, "transform: translate(1px, 0);"); |
| 108 document().view()->updateAllLifecyclePhases(); |
| 109 paintLayer = toLayoutBoxModelObject(fixed->layoutObject())->layer(); |
| 110 ASSERT_TRUE(paintLayer); |
| 111 EXPECT_EQ(NotComposited, paintLayer->compositingState()); |
| 112 } |
| 113 |
| 114 // Test that opacity applied to the fixed or an ancestor will cause the |
| 115 // scrolling contents layer to not be promoted. |
| 116 TEST_F(CompositingReasonFinderTest, OnlyOpaqueFixedLayersPromoted) { |
| 117 ScopedCompositeFixedPositionForTest compositeFixedPosition(true); |
| 118 |
| 119 setBodyInnerHTML( |
| 120 "<style>" |
| 121 "#fixed { position: fixed; height: 200px; width: 200px; background: " |
| 122 "white; top: 0}" |
| 123 "#spacer { height: 3000px; }" |
| 124 "</style>" |
| 125 "<div id=\"parent\">" |
| 126 " <div id=\"fixed\"></div>" |
| 127 " <div id=\"spacer\"></div>" |
| 128 "</div>"); |
| 129 document().view()->updateAllLifecyclePhases(); |
| 130 |
| 131 EXPECT_TRUE(RuntimeEnabledFeatures::compositeOpaqueScrollersEnabled()); |
| 132 Element* parent = document().getElementById("parent"); |
| 133 Element* fixed = document().getElementById("fixed"); |
| 134 PaintLayer* paintLayer = |
| 135 toLayoutBoxModelObject(fixed->layoutObject())->layer(); |
| 136 ASSERT_TRUE(paintLayer); |
| 137 EXPECT_EQ(PaintsIntoOwnBacking, paintLayer->compositingState()); |
| 138 EXPECT_TRUE(paintLayer->graphicsLayerBacking()->contentsOpaque()); |
| 139 |
| 140 // Change the parent to be partially translucent. |
| 141 parent->setAttribute(HTMLNames::styleAttr, "opacity: 0.5;"); |
| 142 document().view()->updateAllLifecyclePhases(); |
| 143 paintLayer = toLayoutBoxModelObject(fixed->layoutObject())->layer(); |
| 144 ASSERT_TRUE(paintLayer); |
| 145 EXPECT_EQ(NotComposited, paintLayer->compositingState()); |
| 146 |
| 147 // Change the parent to be opaque again. |
| 148 parent->setAttribute(HTMLNames::styleAttr, "opacity: 1;"); |
| 149 document().view()->updateAllLifecyclePhases(); |
| 150 paintLayer = toLayoutBoxModelObject(fixed->layoutObject())->layer(); |
| 151 ASSERT_TRUE(paintLayer); |
| 152 EXPECT_EQ(PaintsIntoOwnBacking, paintLayer->compositingState()); |
| 153 EXPECT_TRUE(paintLayer->graphicsLayerBacking()->contentsOpaque()); |
| 154 |
| 155 // Make the fixed translucent. |
| 156 fixed->setAttribute(HTMLNames::styleAttr, "opacity: 0.5"); |
| 157 document().view()->updateAllLifecyclePhases(); |
| 158 paintLayer = toLayoutBoxModelObject(fixed->layoutObject())->layer(); |
| 159 ASSERT_TRUE(paintLayer); |
| 160 EXPECT_EQ(NotComposited, paintLayer->compositingState()); |
| 161 } |
| 162 } |
| OLD | NEW |