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

Side by Side Diff: third_party/WebKit/Source/core/paint/PaintPropertyTreeBuilder.cpp

Issue 1407543003: Preliminary paint property walk implementation for SPv2 (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: revert forAllFrameViews change in FrameView.cpp. I don't know what I was thinking. Created 5 years, 1 month 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 unified diff | Download patch
OLDNEW
(Empty)
1 // Copyright 2015 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 "config.h"
6 #include "core/paint/PaintPropertyTreeBuilder.h"
7
8 #include "core/frame/FrameView.h"
9 #include "core/layout/LayoutView.h"
10 #include "core/paint/ObjectPaintProperties.h"
11 #include "core/paint/PaintLayer.h"
12 #include "platform/graphics/paint/TransformPaintPropertyNode.h"
13 #include "platform/transforms/TransformationMatrix.h"
14
15 namespace blink {
16
17 // The context for layout tree walk.
18 // The walk will be done in the primary tree order (= DOM order), thus the conte xt will also be
19 // responsible for bookkeeping tree state in other order, for example, the most recent position
20 // container seen.
21 struct PaintPropertyTreeBuilderContext {
22 PaintPropertyTreeBuilderContext() : currentTransform(nullptr), transformForO utOfFlowPositioned(nullptr), transformForFixedPositioned(nullptr) { }
23
24 // The combination of a transform and paint offset describes a linear space.
25 // When a layout object recur to its children, the main context is expected to refer
26 // the object's border box, then the callee will derive its own border box b y translating
27 // the space with its own layout location.
28 TransformPaintPropertyNode* currentTransform;
29 LayoutPoint paintOffset;
30
31 // Separate context for out-of-flow positioned and fixed positioned elements are needed
32 // because they don't use DOM parent as their positioning parent (i.e. conta ining block).
33 // These additional contexts normally pass through untouched, and are only c opied from
34 // the main context when the current element serves as the positioning paren t of corresponding
35 // positioned descendants.
36 TransformPaintPropertyNode* transformForOutOfFlowPositioned;
37 LayoutPoint paintOffsetForOutOfFlowPositioned;
38
39 TransformPaintPropertyNode* transformForFixedPositioned;
40 LayoutPoint paintOffsetForFixedPositioned;
41 };
42
43 void PaintPropertyTreeBuilder::buildPropertyTrees(FrameView& rootFrame)
44 {
45 walk(rootFrame, PaintPropertyTreeBuilderContext());
46 }
47
48 void PaintPropertyTreeBuilder::walk(FrameView& frameView, const PaintPropertyTre eBuilderContext& context)
49 {
50 PaintPropertyTreeBuilderContext localContext(context);
51
52 TransformationMatrix frameTranslate;
53 frameTranslate.translate(frameView.x(), frameView.y());
54 // The frame owner applies paint offset already.
55 // This assumption may change in the future.
56 ASSERT(context.paintOffset == LayoutPoint());
57 RefPtr<TransformPaintPropertyNode> newTransformNodeForPreTranslation = Trans formPaintPropertyNode::create(frameTranslate, FloatPoint3D(), context.currentTra nsform);
58 localContext.transformForFixedPositioned = newTransformNodeForPreTranslation .get();
59 localContext.paintOffsetForFixedPositioned = LayoutPoint();
60
61 // This is going away in favor of Settings::rootLayerScrolls.
62 DoubleSize scrollOffset = frameView.scrollOffsetDouble();
63 TransformationMatrix frameScroll;
64 frameScroll.translate(-scrollOffset.width(), -scrollOffset.height());
65 RefPtr<TransformPaintPropertyNode> newTransformNodeForScrollTranslation = Tr ansformPaintPropertyNode::create(frameScroll, FloatPoint3D(), newTransformNodeFo rPreTranslation);
66 localContext.currentTransform = localContext.transformForOutOfFlowPositioned = newTransformNodeForScrollTranslation.get();
67 localContext.paintOffset = localContext.paintOffsetForOutOfFlowPositioned = LayoutPoint();
68
69 frameView.setPreTranslation(newTransformNodeForPreTranslation.release());
70 frameView.setScrollTranslation(newTransformNodeForScrollTranslation.release( ));
71
72 if (LayoutView* layoutView = frameView.layoutView())
73 walk(*layoutView, localContext);
74 }
75
76 static void deriveBorderBoxFromContainerContext(const LayoutBoxModelObject& obje ct, PaintPropertyTreeBuilderContext& context)
77 {
78 // TODO(trchen): There is some insanity going on with tables. Double check r esults.
79 switch (object.styleRef().position()) {
80 case StaticPosition:
81 break;
82 case RelativePosition:
83 context.paintOffset += object.offsetForInFlowPosition();
84 break;
85 case AbsolutePosition:
86 context.currentTransform = context.transformForOutOfFlowPositioned;
87 context.paintOffset = context.paintOffsetForOutOfFlowPositioned;
88 break;
89 case StickyPosition:
90 context.paintOffset += object.offsetForInFlowPosition();
91 break;
92 case FixedPosition:
93 context.currentTransform = context.transformForFixedPositioned;
94 context.paintOffset = context.paintOffsetForFixedPositioned;
95 break;
96 default:
97 ASSERT_NOT_REACHED();
98 }
99 if (object.isBox())
100 context.paintOffset += toLayoutBox(object).locationOffset();
101 }
102
103 static PassRefPtr<TransformPaintPropertyNode> createPaintOffsetTranslationIfNeed ed(const LayoutBoxModelObject& object, PaintPropertyTreeBuilderContext& context)
104 {
105 // TODO(trchen): Eliminate PaintLayer dependency.
106 bool shouldCreatePaintOffsetTranslationNode = object.layer() && object.layer ()->paintsWithTransform(GlobalPaintNormalPhase);
107
108 if (context.paintOffset == LayoutPoint() || !shouldCreatePaintOffsetTranslat ionNode)
109 return nullptr;
110
111 TransformationMatrix matrix;
112 matrix.translate(context.paintOffset.x(), context.paintOffset.y());
113 RefPtr<TransformPaintPropertyNode> newTransformNodeForPaintOffsetTranslation = TransformPaintPropertyNode::create(
114 TransformationMatrix().translate(context.paintOffset.x(), context.paintO ffset.y()),
115 FloatPoint3D(), context.currentTransform);
116 context.currentTransform = newTransformNodeForPaintOffsetTranslation.get();
117 context.paintOffset = LayoutPoint();
118 return newTransformNodeForPaintOffsetTranslation.release();
119 }
120
121 static FloatPoint3D transformOrigin(const LayoutBox& box)
122 {
123 const ComputedStyle& style = box.styleRef();
124 FloatSize borderBoxSize(box.size());
125 return FloatPoint3D(
126 floatValueForLength(style.transformOriginX(), borderBoxSize.width()),
127 floatValueForLength(style.transformOriginY(), borderBoxSize.height()),
128 style.transformOriginZ());
129 }
130
131 static PassRefPtr<TransformPaintPropertyNode> createTransformIfNeeded(const Layo utBoxModelObject& object, PaintPropertyTreeBuilderContext& context)
132 {
133 const ComputedStyle& style = object.styleRef();
134 if (!object.isBox() || !style.hasTransform())
135 return nullptr;
136
137 ASSERT(context.paintOffset == LayoutPoint());
138
139 TransformationMatrix matrix;
140 style.applyTransform(matrix, toLayoutBox(object).size(), ComputedStyle::Excl udeTransformOrigin,
141 ComputedStyle::IncludeMotionPath, ComputedStyle::IncludeIndependentTrans formProperties);
142 RefPtr<TransformPaintPropertyNode> newTransformNodeForTransform = TransformP aintPropertyNode::create(
143 matrix, transformOrigin(toLayoutBox(object)), context.currentTransform);
144 context.currentTransform = newTransformNodeForTransform.get();
145 return newTransformNodeForTransform.release();
146 }
147
148 static FloatPoint perspectiveOrigin(const LayoutBox& box)
149 {
150 const ComputedStyle& style = box.styleRef();
151 FloatSize borderBoxSize(box.size());
152 return FloatPoint(
153 floatValueForLength(style.perspectiveOriginX(), borderBoxSize.width()),
154 floatValueForLength(style.perspectiveOriginY(), borderBoxSize.height())) ;
155 }
156
157 static PassRefPtr<TransformPaintPropertyNode> createPerspectiveIfNeeded(const La youtBoxModelObject& object, PaintPropertyTreeBuilderContext& context)
158 {
159 const ComputedStyle& style = object.styleRef();
160 if (!object.isBox() || !style.hasPerspective())
161 return nullptr;
162
163 RefPtr<TransformPaintPropertyNode> newTransformNodeForPerspective = Transfor mPaintPropertyNode::create(
164 TransformationMatrix().applyPerspective(style.perspective()),
165 perspectiveOrigin(toLayoutBox(object)) + toLayoutSize(context.paintOffse t), context.currentTransform);
166 context.currentTransform = newTransformNodeForPerspective.get();
167
168 return newTransformNodeForPerspective.release();
169 }
170
171 static PassRefPtr<TransformPaintPropertyNode> createScrollTranslationIfNeeded(co nst LayoutBoxModelObject& object, PaintPropertyTreeBuilderContext& context)
172 {
173 if (!object.hasOverflowClip())
174 return nullptr;
175
176 PaintLayer* layer = object.layer();
177 ASSERT(layer);
178 DoubleSize scrollOffset = layer->scrollableArea()->scrollOffset();
179 if (scrollOffset.isZero() && !layer->scrollsOverflow())
180 return nullptr;
181
182 RefPtr<TransformPaintPropertyNode> newTransformNodeForScrollTranslation = Tr ansformPaintPropertyNode::create(
183 TransformationMatrix().translate(-scrollOffset.width(), -scrollOffset.he ight()),
184 FloatPoint3D(), context.currentTransform);
185 context.currentTransform = newTransformNodeForScrollTranslation.get();
186 return newTransformNodeForScrollTranslation.release();
187 }
188
189 static void updateOutOfFlowContext(const LayoutBoxModelObject& object, PaintProp ertyTreeBuilderContext& context)
190 {
191 const ComputedStyle& style = object.styleRef();
192 bool hasTransform = object.isBox() && style.hasTransform();
193 if (style.position() != StaticPosition || hasTransform) {
194 context.transformForOutOfFlowPositioned = context.currentTransform;
195 context.paintOffsetForOutOfFlowPositioned = context.paintOffset;
196 }
197 if (hasTransform) {
198 context.transformForFixedPositioned = context.currentTransform;
199 context.paintOffsetForFixedPositioned = context.paintOffset;
200 }
201 }
202
203 void PaintPropertyTreeBuilder::walk(LayoutBoxModelObject& object, const PaintPro pertyTreeBuilderContext& context)
204 {
205 ASSERT(object.isBox() != object.isLayoutInline()); // Either or.
206
207 PaintPropertyTreeBuilderContext localContext(context);
208
209 deriveBorderBoxFromContainerContext(object, localContext);
210 RefPtr<TransformPaintPropertyNode> newTransformNodeForPaintOffsetTranslation = createPaintOffsetTranslationIfNeeded(object, localContext);
211 RefPtr<TransformPaintPropertyNode> newTransformNodeForTransform = createTran sformIfNeeded(object, localContext);
212 RefPtr<TransformPaintPropertyNode> newTransformNodeForPerspective = createPe rspectiveIfNeeded(object, localContext);
213 RefPtr<TransformPaintPropertyNode> newTransformNodeForScrollTranslation = cr eateScrollTranslationIfNeeded(object, localContext);
214 updateOutOfFlowContext(object, localContext);
215
216 if (newTransformNodeForPaintOffsetTranslation || newTransformNodeForTransfor m || newTransformNodeForPerspective || newTransformNodeForScrollTranslation) {
217 ObjectPaintProperties& properties = object.ensureObjectPaintProperties() ;
218 properties.setPaintOffsetTranslation(newTransformNodeForPaintOffsetTrans lation.release());
219 properties.setTransform(newTransformNodeForTransform.release());
220 properties.setPerspective(newTransformNodeForPerspective.release());
221 properties.setScrollTranslation(newTransformNodeForScrollTranslation.rel ease());
222 } else {
223 object.clearObjectPaintProperties();
224 }
225
226 // TODO(trchen): Walk subframes for LayoutFrame.
227
228 // TODO(trchen): Implement SVG walk.
229 if (object.isSVGRoot()) {
230 return;
231 }
232
233 for (LayoutObject* child = object.slowFirstChild(); child; child = child->ne xtSibling()) {
234 if (child->isText())
235 continue;
236 walk(toLayoutBoxModelObject(*child), localContext);
237 }
238 }
239
240 } // namespace blink
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698