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

Side by Side Diff: Source/core/layout/LayoutGeometryMap.cpp

Issue 1308273010: Adapt and reland old position sticky implementation (Closed) Base URL: https://chromium.googlesource.com/chromium/blink.git@master
Patch Set: Fix style errors and remaining layout tests. Created 5 years, 3 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 unified diff | Download patch
OLDNEW
1 /* 1 /*
2 * Copyright (C) 2012 Apple Inc. All rights reserved. 2 * Copyright (C) 2012 Apple Inc. All rights reserved.
3 * 3 *
4 * Redistribution and use in source and binary forms, with or without 4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions 5 * modification, are permitted provided that the following conditions
6 * are met: 6 * are met:
7 * 1. Redistributions of source code must retain the above copyright 7 * 1. Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer. 8 * notice, this list of conditions and the following disclaimer.
9 * 2. Redistributions in binary form must reproduce the above copyright 9 * 2. Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the 10 * notice, this list of conditions and the following disclaimer in the
(...skipping 20 matching lines...) Expand all
31 #include "core/paint/DeprecatedPaintLayer.h" 31 #include "core/paint/DeprecatedPaintLayer.h"
32 #include "platform/geometry/TransformState.h" 32 #include "platform/geometry/TransformState.h"
33 #include "wtf/TemporaryChange.h" 33 #include "wtf/TemporaryChange.h"
34 34
35 namespace blink { 35 namespace blink {
36 36
37 LayoutGeometryMap::LayoutGeometryMap(MapCoordinatesFlags flags) 37 LayoutGeometryMap::LayoutGeometryMap(MapCoordinatesFlags flags)
38 : m_insertionPosition(kNotFound) 38 : m_insertionPosition(kNotFound)
39 , m_nonUniformStepsCount(0) 39 , m_nonUniformStepsCount(0)
40 , m_transformedStepsCount(0) 40 , m_transformedStepsCount(0)
41 , m_fixedStepsCount(0) 41 , m_viewportConstrainedStepsCount(0)
42 , m_mapCoordinatesFlags(flags) 42 , m_mapCoordinatesFlags(flags)
43 { 43 {
44 } 44 }
45 45
46 LayoutGeometryMap::~LayoutGeometryMap() 46 LayoutGeometryMap::~LayoutGeometryMap()
47 { 47 {
48 } 48 }
49 49
50 void LayoutGeometryMap::mapToContainer(TransformState& transformState, const Lay outBoxModelObject* container) const 50 void LayoutGeometryMap::mapToContainer(TransformState& transformState, const Lay outBoxModelObject* container) const
51 { 51 {
52 // If the mapping includes something like columns, we have to go via layoutO bjects. 52 // If the mapping includes something like columns, we have to go via layoutO bjects.
53 if (hasNonUniformStep()) { 53 if (hasNonUniformStep()) {
54 m_mapping.last().m_layoutObject->mapLocalToContainer(container, transfor mState, ApplyContainerFlip | m_mapCoordinatesFlags); 54 m_mapping.last().m_layoutObject->mapLocalToContainer(container, transfor mState, ApplyContainerFlip | m_mapCoordinatesFlags);
55 transformState.flatten(); 55 transformState.flatten();
56 return; 56 return;
57 } 57 }
58 58
59 bool inFixed = false; 59 bool inFixed = false;
60 #if ENABLE(ASSERT) 60 #if ENABLE(ASSERT)
61 bool foundContainer = !container || (m_mapping.size() && m_mapping[0].m_layo utObject == container); 61 bool foundContainer = !container || (m_mapping.size() && m_mapping[0].m_layo utObject == container);
62 #endif 62 #endif
63 63
64 for (int i = m_mapping.size() - 1; i >= 0; --i) { 64 for (int i = m_mapping.size() - 1; i >= 0; --i) {
65 const LayoutGeometryMapStep& currentStep = m_mapping[i]; 65 const LayoutGeometryMapStep& currentStep = m_mapping[i];
66 66
67 // If container is the root LayoutView (step 0) we want to apply its fix ed position offset. 67 // If container is the root LayoutView (step 0) we want to apply its vie wport constrained position offset.
68 if (i > 0 && currentStep.m_layoutObject == container) { 68 if (i > 0 && currentStep.m_layoutObject == container) {
69 #if ENABLE(ASSERT) 69 #if ENABLE(ASSERT)
70 foundContainer = true; 70 foundContainer = true;
71 #endif 71 #endif
72 break; 72 break;
73 } 73 }
74 74
75 // If this box has a transform, it acts as a fixed position container 75 // If this box has a transform, it acts as a viewport constrained positi on container
76 // for fixed descendants, which prevents the propagation of 'fixed' 76 // for viewport constrained descendants, which prevents the propagation of viewport constrained
77 // unless the layer itself is also fixed position. 77 // unless the layer itself is also a viewport constrained position.
78 if (i && currentStep.m_hasTransform && !currentStep.m_isFixedPosition) 78 // TODO(flackr): Verify how fixed and sticky elements should interact wi th each other.
flackr 2015/09/15 21:13:11 My assumption is that this code should only apply
79 if (i && currentStep.m_hasTransform && !currentStep.m_isViewportConstrai ned)
79 inFixed = false; 80 inFixed = false;
80 else if (currentStep.m_isFixedPosition) 81 else if (currentStep.m_isViewportConstrained)
81 inFixed = true; 82 inFixed = true;
82 83
83 ASSERT(!i == isTopmostLayoutView(currentStep.m_layoutObject)); 84 ASSERT(!i == isTopmostLayoutView(currentStep.m_layoutObject));
84 85
85 if (!i) { 86 if (!i) {
86 // A null container indicates mapping through the root LayoutView, s o including its transform (the page scale). 87 // A null container indicates mapping through the root LayoutView, s o including its transform (the page scale).
87 if (!container && currentStep.m_transform) 88 if (!container && currentStep.m_transform)
88 transformState.applyTransform(*currentStep.m_transform.get()); 89 transformState.applyTransform(*currentStep.m_transform.get());
89 } else { 90 } else {
90 TransformState::TransformAccumulation accumulate = currentStep.m_acc umulatingTransform ? TransformState::AccumulateTransform : TransformState::Flatt enTransform; 91 TransformState::TransformAccumulation accumulate = currentStep.m_acc umulatingTransform ? TransformState::AccumulateTransform : TransformState::Flatt enTransform;
91 if (currentStep.m_transform) 92 if (currentStep.m_transform)
92 transformState.applyTransform(*currentStep.m_transform.get(), ac cumulate); 93 transformState.applyTransform(*currentStep.m_transform.get(), ac cumulate);
93 else 94 else
94 transformState.move(currentStep.m_offset.width(), currentStep.m_ offset.height(), accumulate); 95 transformState.move(currentStep.m_offset.width(), currentStep.m_ offset.height(), accumulate);
95 } 96 }
96 97
97 if (inFixed && !currentStep.m_offsetForFixedPosition.isZero()) { 98 if (inFixed && !currentStep.m_offsetForViewportConstrained.isZero()) {
98 ASSERT(currentStep.m_layoutObject->isLayoutView()); 99 ASSERT(currentStep.m_layoutObject->isLayoutView());
99 transformState.move(currentStep.m_offsetForFixedPosition); 100 transformState.move(currentStep.m_offsetForViewportConstrained);
100 } 101 }
101 } 102 }
102 103
103 ASSERT(foundContainer); 104 ASSERT(foundContainer);
104 transformState.flatten(); 105 transformState.flatten();
105 } 106 }
106 107
107 FloatPoint LayoutGeometryMap::mapToContainer(const FloatPoint& p, const LayoutBo xModelObject* container) const 108 FloatPoint LayoutGeometryMap::mapToContainer(const FloatPoint& p, const LayoutBo xModelObject* container) const
108 { 109 {
109 FloatPoint result; 110 FloatPoint result;
110 111
111 if (!hasFixedPositionStep() && !hasTransformStep() && !hasNonUniformStep() & & (!container || (m_mapping.size() && container == m_mapping[0].m_layoutObject)) ) { 112 if (!hasViewportConstrainedStep() && !hasTransformStep() && !hasNonUniformSt ep() && (!container || (m_mapping.size() && container == m_mapping[0].m_layoutOb ject))) {
112 result = p + m_accumulatedOffset; 113 result = p + m_accumulatedOffset;
113 } else { 114 } else {
114 TransformState transformState(TransformState::ApplyTransformDirection, p ); 115 TransformState transformState(TransformState::ApplyTransformDirection, p );
115 mapToContainer(transformState, container); 116 mapToContainer(transformState, container);
116 result = transformState.lastPlanarPoint(); 117 result = transformState.lastPlanarPoint();
117 } 118 }
118 119
119 #if ENABLE(ASSERT) 120 #if ENABLE(ASSERT)
120 if (m_mapping.size() > 0) { 121 if (m_mapping.size() > 0) {
121 const LayoutObject* lastLayoutObject = m_mapping.last().m_layoutObject; 122 const LayoutObject* lastLayoutObject = m_mapping.last().m_layoutObject;
(...skipping 27 matching lines...) Expand all
149 fprintf(stderr, " hasTransform"); 150 fprintf(stderr, " hasTransform");
150 fprintf(stderr, "\n"); 151 fprintf(stderr, "\n");
151 } 152 }
152 } 153 }
153 #endif 154 #endif
154 155
155 FloatQuad LayoutGeometryMap::mapToContainer(const FloatRect& rect, const LayoutB oxModelObject* container) const 156 FloatQuad LayoutGeometryMap::mapToContainer(const FloatRect& rect, const LayoutB oxModelObject* container) const
156 { 157 {
157 FloatQuad result; 158 FloatQuad result;
158 159
159 if (!hasFixedPositionStep() && !hasTransformStep() && !hasNonUniformStep() & & (!container || (m_mapping.size() && container == m_mapping[0].m_layoutObject)) ) { 160 if (!hasViewportConstrainedStep() && !hasTransformStep() && !hasNonUniformSt ep() && (!container || (m_mapping.size() && container == m_mapping[0].m_layoutOb ject))) {
160 result = rect; 161 result = rect;
161 result.move(m_accumulatedOffset); 162 result.move(m_accumulatedOffset);
162 } else { 163 } else {
163 TransformState transformState(TransformState::ApplyTransformDirection, r ect.center(), rect); 164 TransformState transformState(TransformState::ApplyTransformDirection, r ect.center(), rect);
164 mapToContainer(transformState, container); 165 mapToContainer(transformState, container);
165 result = transformState.lastPlanarQuad(); 166 result = transformState.lastPlanarQuad();
166 } 167 }
167 168
168 #if ENABLE(ASSERT) 169 #if ENABLE(ASSERT)
169 if (m_mapping.size() > 0) { 170 if (m_mapping.size() > 0) {
(...skipping 62 matching lines...) Expand 10 before | Expand all | Expand 10 after
232 layer->convertToLayerCoords(ancestorLayer, layerOffset); 233 layer->convertToLayerCoords(ancestorLayer, layerOffset);
233 234
234 // The LayoutView must be pushed first. 235 // The LayoutView must be pushed first.
235 if (!m_mapping.size()) { 236 if (!m_mapping.size()) {
236 ASSERT(ancestorLayer->layoutObject()->isLayoutView()); 237 ASSERT(ancestorLayer->layoutObject()->isLayoutView());
237 pushMappingsToAncestor(ancestorLayer->layoutObject(), 0); 238 pushMappingsToAncestor(ancestorLayer->layoutObject(), 0);
238 } 239 }
239 240
240 TemporaryChange<size_t> positionChange(m_insertionPosition, m_mapping.si ze()); 241 TemporaryChange<size_t> positionChange(m_insertionPosition, m_mapping.si ze());
241 bool accumulatingTransform = layer->layoutObject()->style()->preserves3D () || ancestorLayer->layoutObject()->style()->preserves3D(); 242 bool accumulatingTransform = layer->layoutObject()->style()->preserves3D () || ancestorLayer->layoutObject()->style()->preserves3D();
242 push(layoutObject, toLayoutSize(layerOffset), accumulatingTransform, /*i sNonUniform*/ false, /*isFixedPosition*/ false, /*hasTransform*/ false); 243 push(layoutObject, toLayoutSize(layerOffset), accumulatingTransform, /*i sNonUniform*/ false, /*isViewportConstrained*/ false, /*hasTransform*/ false);
243 return; 244 return;
244 } 245 }
245 const LayoutBoxModelObject* ancestorLayoutObject = ancestorLayer ? ancestorL ayer->layoutObject() : 0; 246 const LayoutBoxModelObject* ancestorLayoutObject = ancestorLayer ? ancestorL ayer->layoutObject() : 0;
246 pushMappingsToAncestor(layoutObject, ancestorLayoutObject); 247 pushMappingsToAncestor(layoutObject, ancestorLayoutObject);
247 } 248 }
248 249
249 void LayoutGeometryMap::push(const LayoutObject* layoutObject, const LayoutSize& offsetFromContainer, bool accumulatingTransform, bool isNonUniform, bool isFixe dPosition, bool hasTransform, LayoutSize offsetForFixedPosition) 250 void LayoutGeometryMap::push(const LayoutObject* layoutObject, const LayoutSize& offsetFromContainer, bool accumulatingTransform, bool isNonUniform, bool isView portConstrained, bool hasTransform, LayoutSize offsetForViewportConstrained)
250 { 251 {
251 // fprintf(stderr, "LayoutGeometryMap::push %p %d,%d isNonUniform=%d\n", layo utObject, offsetFromContainer.width().toInt(), offsetFromContainer.height().toIn t(), isNonUniform); 252 // fprintf(stderr, "LayoutGeometryMap::push %p %d,%d isNonUniform=%d\n", layo utObject, offsetFromContainer.width().toInt(), offsetFromContainer.height().toIn t(), isNonUniform);
252 253
253 ASSERT(m_insertionPosition != kNotFound); 254 ASSERT(m_insertionPosition != kNotFound);
254 ASSERT(!layoutObject->isLayoutView() || !m_insertionPosition || m_mapCoordin atesFlags & TraverseDocumentBoundaries); 255 ASSERT(!layoutObject->isLayoutView() || !m_insertionPosition || m_mapCoordin atesFlags & TraverseDocumentBoundaries);
255 ASSERT(offsetForFixedPosition.isZero() || layoutObject->isLayoutView()); 256 ASSERT(offsetForViewportConstrained.isZero() || layoutObject->isLayoutView() );
256 257
257 m_mapping.insert(m_insertionPosition, LayoutGeometryMapStep(layoutObject, ac cumulatingTransform, isNonUniform, isFixedPosition, hasTransform)); 258 m_mapping.insert(m_insertionPosition, LayoutGeometryMapStep(layoutObject, ac cumulatingTransform, isNonUniform, isViewportConstrained, hasTransform));
258 259
259 LayoutGeometryMapStep& step = m_mapping[m_insertionPosition]; 260 LayoutGeometryMapStep& step = m_mapping[m_insertionPosition];
260 step.m_offset = offsetFromContainer; 261 step.m_offset = offsetFromContainer;
261 step.m_offsetForFixedPosition = offsetForFixedPosition; 262 step.m_offsetForViewportConstrained = offsetForViewportConstrained;
262 263
263 stepInserted(step); 264 stepInserted(step);
264 } 265 }
265 266
266 void LayoutGeometryMap::push(const LayoutObject* layoutObject, const Transformat ionMatrix& t, bool accumulatingTransform, bool isNonUniform, bool isFixedPositio n, bool hasTransform, LayoutSize offsetForFixedPosition) 267 void LayoutGeometryMap::push(const LayoutObject* layoutObject, const Transformat ionMatrix& t, bool accumulatingTransform, bool isNonUniform, bool isViewportCons trained, bool hasTransform, LayoutSize offsetForViewportConstrained)
267 { 268 {
268 ASSERT(m_insertionPosition != kNotFound); 269 ASSERT(m_insertionPosition != kNotFound);
269 ASSERT(!layoutObject->isLayoutView() || !m_insertionPosition || m_mapCoordin atesFlags & TraverseDocumentBoundaries); 270 ASSERT(!layoutObject->isLayoutView() || !m_insertionPosition || m_mapCoordin atesFlags & TraverseDocumentBoundaries);
270 ASSERT(offsetForFixedPosition.isZero() || layoutObject->isLayoutView()); 271 ASSERT(offsetForViewportConstrained.isZero() || layoutObject->isLayoutView() );
271 272
272 m_mapping.insert(m_insertionPosition, LayoutGeometryMapStep(layoutObject, ac cumulatingTransform, isNonUniform, isFixedPosition, hasTransform)); 273 m_mapping.insert(m_insertionPosition, LayoutGeometryMapStep(layoutObject, ac cumulatingTransform, isNonUniform, isViewportConstrained, hasTransform));
273 274
274 LayoutGeometryMapStep& step = m_mapping[m_insertionPosition]; 275 LayoutGeometryMapStep& step = m_mapping[m_insertionPosition];
275 step.m_offsetForFixedPosition = offsetForFixedPosition; 276 step.m_offsetForViewportConstrained = offsetForViewportConstrained;
276 277
277 if (!t.isIntegerTranslation()) 278 if (!t.isIntegerTranslation())
278 step.m_transform = adoptPtr(new TransformationMatrix(t)); 279 step.m_transform = adoptPtr(new TransformationMatrix(t));
279 else 280 else
280 step.m_offset = LayoutSize(t.e(), t.f()); 281 step.m_offset = LayoutSize(t.e(), t.f());
281 282
282 stepInserted(step); 283 stepInserted(step);
283 } 284 }
284 285
285 void LayoutGeometryMap::popMappingsToAncestor(const LayoutBoxModelObject* ancest orLayoutObject) 286 void LayoutGeometryMap::popMappingsToAncestor(const LayoutBoxModelObject* ancest orLayoutObject)
(...skipping 15 matching lines...) Expand all
301 void LayoutGeometryMap::stepInserted(const LayoutGeometryMapStep& step) 302 void LayoutGeometryMap::stepInserted(const LayoutGeometryMapStep& step)
302 { 303 {
303 m_accumulatedOffset += step.m_offset; 304 m_accumulatedOffset += step.m_offset;
304 305
305 if (step.m_isNonUniform) 306 if (step.m_isNonUniform)
306 ++m_nonUniformStepsCount; 307 ++m_nonUniformStepsCount;
307 308
308 if (step.m_transform) 309 if (step.m_transform)
309 ++m_transformedStepsCount; 310 ++m_transformedStepsCount;
310 311
311 if (step.m_isFixedPosition) 312 if (step.m_isViewportConstrained)
312 ++m_fixedStepsCount; 313 ++m_viewportConstrainedStepsCount;
313 } 314 }
314 315
315 void LayoutGeometryMap::stepRemoved(const LayoutGeometryMapStep& step) 316 void LayoutGeometryMap::stepRemoved(const LayoutGeometryMapStep& step)
316 { 317 {
317 m_accumulatedOffset -= step.m_offset; 318 m_accumulatedOffset -= step.m_offset;
318 319
319 if (step.m_isNonUniform) { 320 if (step.m_isNonUniform) {
320 ASSERT(m_nonUniformStepsCount); 321 ASSERT(m_nonUniformStepsCount);
321 --m_nonUniformStepsCount; 322 --m_nonUniformStepsCount;
322 } 323 }
323 324
324 if (step.m_transform) { 325 if (step.m_transform) {
325 ASSERT(m_transformedStepsCount); 326 ASSERT(m_transformedStepsCount);
326 --m_transformedStepsCount; 327 --m_transformedStepsCount;
327 } 328 }
328 329
329 if (step.m_isFixedPosition) { 330 if (step.m_isViewportConstrained) {
330 ASSERT(m_fixedStepsCount); 331 ASSERT(m_viewportConstrainedStepsCount);
331 --m_fixedStepsCount; 332 --m_viewportConstrainedStepsCount;
332 } 333 }
333 } 334 }
334 335
335 #if ENABLE(ASSERT) 336 #if ENABLE(ASSERT)
336 bool LayoutGeometryMap::isTopmostLayoutView(const LayoutObject* layoutObject) co nst 337 bool LayoutGeometryMap::isTopmostLayoutView(const LayoutObject* layoutObject) co nst
337 { 338 {
338 if (!layoutObject->isLayoutView()) 339 if (!layoutObject->isLayoutView())
339 return false; 340 return false;
340 341
341 // If we're not working with multiple LayoutViews, then any view is consider ed 342 // If we're not working with multiple LayoutViews, then any view is consider ed
342 // "topmost" (to preserve original behavior). 343 // "topmost" (to preserve original behavior).
343 if (!(m_mapCoordinatesFlags & TraverseDocumentBoundaries)) 344 if (!(m_mapCoordinatesFlags & TraverseDocumentBoundaries))
344 return true; 345 return true;
345 346
346 return layoutObject->frame()->isMainFrame(); 347 return layoutObject->frame()->isMainFrame();
347 } 348 }
348 #endif 349 #endif
349 350
350 } // namespace blink 351 } // namespace blink
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698