OLD | NEW |
---|---|
1 // Copyright 2016 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "core/paint/PaintInvalidator.h" | 5 #include "core/paint/PaintInvalidator.h" |
6 | 6 |
7 #include "core/editing/FrameSelection.h" | 7 #include "core/editing/FrameSelection.h" |
8 #include "core/frame/FrameView.h" | 8 #include "core/frame/FrameView.h" |
9 #include "core/frame/LocalFrame.h" | 9 #include "core/frame/LocalFrame.h" |
10 #include "core/frame/Settings.h" | 10 #include "core/frame/Settings.h" |
(...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
67 // TODO(wangxianzhu): Avoid containingBlock(). | 67 // TODO(wangxianzhu): Avoid containingBlock(). |
68 object.containingBlock()->flipForWritingMode(rect); | 68 object.containingBlock()->flipForWritingMode(rect); |
69 } | 69 } |
70 } | 70 } |
71 | 71 |
72 if (RuntimeEnabledFeatures::slimmingPaintV2Enabled()) { | 72 if (RuntimeEnabledFeatures::slimmingPaintV2Enabled()) { |
73 // In SPv2, visual rects are in the space of their local transform node. | 73 // In SPv2, visual rects are in the space of their local transform node. |
74 // For SVG, the input rect is in local SVG coordinates in which paint | 74 // For SVG, the input rect is in local SVG coordinates in which paint |
75 // offset doesn't apply. | 75 // offset doesn't apply. |
76 if (!object.isSVGChild()) | 76 if (!object.isSVGChild()) |
77 rect.moveBy(FloatPoint(context.treeBuilderContext.current.paintOffset)); | 77 rect.moveBy(FloatPoint(object.paintOffset())); |
Xianzhu
2017/01/06 17:24:39
This is just changed to a shorter form. They are a
| |
78 // Use enclosingIntRect to ensure the final visual rect will cover the | 78 // Use enclosingIntRect to ensure the final visual rect will cover the |
79 // rect in source coordinates no matter if the painting will use pixel | 79 // rect in source coordinates no matter if the painting will use pixel |
80 // snapping. | 80 // snapping. |
81 return LayoutRect(enclosingIntRect(rect)); | 81 return LayoutRect(enclosingIntRect(rect)); |
82 } | 82 } |
83 | 83 |
84 LayoutRect result; | 84 LayoutRect result; |
85 if (context.forcedSubtreeInvalidationFlags & | 85 if (context.forcedSubtreeInvalidationFlags & |
86 PaintInvalidatorContext::ForcedSubtreeSlowPathRect) { | 86 PaintInvalidatorContext::ForcedSubtreeSlowPathRect) { |
87 result = slowMapToVisualRectInAncestorSpace( | 87 result = slowMapToVisualRectInAncestorSpace( |
88 object, *context.paintInvalidationContainer, rect); | 88 object, *context.paintInvalidationContainer, rect); |
89 } else if (object == context.paintInvalidationContainer) { | 89 } else if (object == context.paintInvalidationContainer) { |
90 result = LayoutRect(rect); | 90 result = LayoutRect(rect); |
91 } else { | 91 } else { |
92 // For non-root SVG, the input rect is in local SVG coordinates in which | 92 // For non-root SVG, the input rect is in local SVG coordinates in which |
93 // paint offset doesn't apply. | 93 // paint offset doesn't apply. |
94 if (!object.isSVGChild()) { | 94 if (!object.isSVGChild()) { |
95 rect.moveBy(FloatPoint(context.treeBuilderContext.current.paintOffset)); | 95 rect.moveBy(FloatPoint(object.paintOffset())); |
96 // Use enclosingIntRect to ensure the final visual rect will cover the | 96 // Use enclosingIntRect to ensure the final visual rect will cover the |
97 // rect in source coordinates no matter if the painting will use pixel | 97 // rect in source coordinates no matter if the painting will use pixel |
98 // snapping. | 98 // snapping. |
99 rect = enclosingIntRect(rect); | 99 rect = enclosingIntRect(rect); |
100 } | 100 } |
101 | 101 |
102 PropertyTreeState currentTreeState( | 102 PropertyTreeState currentTreeState( |
103 context.treeBuilderContext.current.transform, | 103 context.treeBuilderContext.current.transform, |
104 context.treeBuilderContext.current.clip, | 104 context.treeBuilderContext.current.clip, |
105 context.treeBuilderContext.currentEffect, | 105 context.treeBuilderContext.currentEffect, |
106 context.treeBuilderContext.current.scroll); | 106 context.treeBuilderContext.current.scroll); |
107 const auto* containerPaintProperties = | 107 const auto* containerPaintProperties = |
108 context.paintInvalidationContainer->paintProperties(); | 108 context.paintInvalidationContainer->paintProperties(); |
109 auto containerContentsProperties = | 109 auto containerContentsProperties = |
110 containerPaintProperties->contentsProperties(); | 110 containerPaintProperties->contentsProperties(); |
111 | 111 |
112 bool success = false; | 112 bool success = false; |
113 result = LayoutRect(geometryMapper.mapToVisualRectInDestinationSpace( | 113 result = LayoutRect(geometryMapper.mapToVisualRectInDestinationSpace( |
114 rect, currentTreeState, containerContentsProperties.propertyTreeState, | 114 rect, currentTreeState, containerContentsProperties, success)); |
115 success)); | |
116 DCHECK(success); | 115 DCHECK(success); |
117 | 116 |
118 // Convert the result to the container's contents space. | 117 // Convert the result to the container's contents space. |
119 result.moveBy(-containerContentsProperties.paintOffset); | 118 result.moveBy(-context.paintInvalidationContainer->paintOffset()); |
120 } | 119 } |
121 | 120 |
122 object.adjustVisualRectForRasterEffects(result); | 121 object.adjustVisualRectForRasterEffects(result); |
123 | 122 |
124 PaintLayer::mapRectInPaintInvalidationContainerToBacking( | 123 PaintLayer::mapRectInPaintInvalidationContainerToBacking( |
125 *context.paintInvalidationContainer, result); | 124 *context.paintInvalidationContainer, result); |
126 | 125 |
127 return result; | 126 return result; |
128 } | 127 } |
129 | 128 |
(...skipping 28 matching lines...) Expand all Loading... | |
158 LayoutPoint PaintInvalidator::computeLocationInBacking( | 157 LayoutPoint PaintInvalidator::computeLocationInBacking( |
159 const LayoutObject& object, | 158 const LayoutObject& object, |
160 const PaintInvalidatorContext& context) { | 159 const PaintInvalidatorContext& context) { |
161 // Use visual rect location for LayoutTexts because it suffices to check | 160 // Use visual rect location for LayoutTexts because it suffices to check |
162 // visual rect change for layout caused invalidation. | 161 // visual rect change for layout caused invalidation. |
163 if (object.isText()) | 162 if (object.isText()) |
164 return context.newVisualRect.location(); | 163 return context.newVisualRect.location(); |
165 | 164 |
166 FloatPoint point; | 165 FloatPoint point; |
167 if (object != context.paintInvalidationContainer) { | 166 if (object != context.paintInvalidationContainer) { |
168 point.moveBy(FloatPoint(context.treeBuilderContext.current.paintOffset)); | 167 point.moveBy(FloatPoint(object.paintOffset())); |
169 | 168 |
170 PropertyTreeState currentTreeState( | 169 PropertyTreeState currentTreeState( |
171 context.treeBuilderContext.current.transform, | 170 context.treeBuilderContext.current.transform, |
172 context.treeBuilderContext.current.clip, | 171 context.treeBuilderContext.current.clip, |
173 context.treeBuilderContext.currentEffect, | 172 context.treeBuilderContext.currentEffect, |
174 context.treeBuilderContext.current.scroll); | 173 context.treeBuilderContext.current.scroll); |
175 const auto* containerPaintProperties = | 174 const auto* containerPaintProperties = |
176 context.paintInvalidationContainer->paintProperties(); | 175 context.paintInvalidationContainer->paintProperties(); |
177 auto containerContentsProperties = | 176 auto containerContentsProperties = |
178 containerPaintProperties->contentsProperties(); | 177 containerPaintProperties->contentsProperties(); |
179 | 178 |
180 bool success = false; | 179 bool success = false; |
181 point = m_geometryMapper | 180 point = m_geometryMapper |
182 .mapRectToDestinationSpace( | 181 .mapRectToDestinationSpace(FloatRect(point, FloatSize()), |
183 FloatRect(point, FloatSize()), currentTreeState, | 182 currentTreeState, |
184 containerContentsProperties.propertyTreeState, success) | 183 containerContentsProperties, success) |
185 .location(); | 184 .location(); |
186 DCHECK(success); | 185 DCHECK(success); |
187 | 186 |
188 // Convert the result to the container's contents space. | 187 // Convert the result to the container's contents space. |
189 point.moveBy(-containerContentsProperties.paintOffset); | 188 point.moveBy(-context.paintInvalidationContainer->paintOffset()); |
190 } | 189 } |
191 | 190 |
192 PaintLayer::mapPointInPaintInvalidationContainerToBacking( | 191 PaintLayer::mapPointInPaintInvalidationContainerToBacking( |
193 *context.paintInvalidationContainer, point); | 192 *context.paintInvalidationContainer, point); |
194 | 193 |
195 return LayoutPoint(point); | 194 return LayoutPoint(point); |
196 } | 195 } |
197 | 196 |
198 void PaintInvalidator::updatePaintingLayer(const LayoutObject& object, | 197 void PaintInvalidator::updatePaintingLayer(const LayoutObject& object, |
199 PaintInvalidatorContext& context) { | 198 PaintInvalidatorContext& context) { |
(...skipping 132 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
332 object.isColumnSpanAll()) { | 331 object.isColumnSpanAll()) { |
333 context.forcedSubtreeInvalidationFlags |= | 332 context.forcedSubtreeInvalidationFlags |= |
334 PaintInvalidatorContext::ForcedSubtreeSlowPathRect; | 333 PaintInvalidatorContext::ForcedSubtreeSlowPathRect; |
335 } | 334 } |
336 | 335 |
337 ObjectPaintInvalidator objectPaintInvalidator(object); | 336 ObjectPaintInvalidator objectPaintInvalidator(object); |
338 context.oldVisualRect = object.previousVisualRect(); | 337 context.oldVisualRect = object.previousVisualRect(); |
339 context.oldLocation = objectPaintInvalidator.previousLocationInBacking(); | 338 context.oldLocation = objectPaintInvalidator.previousLocationInBacking(); |
340 context.newVisualRect = computeVisualRectInBacking(object, context); | 339 context.newVisualRect = computeVisualRectInBacking(object, context); |
341 context.newLocation = computeLocationInBacking(object, context); | 340 context.newLocation = computeLocationInBacking(object, context); |
342 context.oldPaintOffset = object.previousPaintOffset(); | |
343 context.newPaintOffset = context.treeBuilderContext.current.paintOffset; | |
344 | 341 |
345 IntSize adjustment = object.scrollAdjustmentForPaintInvalidation( | 342 IntSize adjustment = object.scrollAdjustmentForPaintInvalidation( |
346 *context.paintInvalidationContainer); | 343 *context.paintInvalidationContainer); |
347 context.newLocation.move(adjustment); | 344 context.newLocation.move(adjustment); |
348 context.newVisualRect.move(adjustment); | 345 context.newVisualRect.move(adjustment); |
349 | 346 |
350 object.getMutableForPainting().setPreviousVisualRect(context.newVisualRect); | 347 object.getMutableForPainting().setPreviousVisualRect(context.newVisualRect); |
351 objectPaintInvalidator.setPreviousLocationInBacking(context.newLocation); | 348 objectPaintInvalidator.setPreviousLocationInBacking(context.newLocation); |
352 object.getMutableForPainting().setPreviousPaintOffset(context.newPaintOffset); | |
353 } | 349 } |
354 | 350 |
355 void PaintInvalidator::invalidatePaintIfNeeded( | 351 void PaintInvalidator::invalidatePaintIfNeeded( |
356 FrameView& frameView, | 352 FrameView& frameView, |
357 PaintInvalidatorContext& context) { | 353 PaintInvalidatorContext& context) { |
358 LayoutView* layoutView = frameView.layoutView(); | 354 LayoutView* layoutView = frameView.layoutView(); |
359 CHECK(layoutView); | 355 CHECK(layoutView); |
360 | 356 |
361 context.paintInvalidationContainer = | 357 context.paintInvalidationContainer = |
362 context.paintInvalidationContainerForStackedContents = | 358 context.paintInvalidationContainerForStackedContents = |
363 &layoutView->containerForPaintInvalidation(); | 359 &layoutView->containerForPaintInvalidation(); |
364 context.paintingLayer = layoutView->layer(); | 360 context.paintingLayer = layoutView->layer(); |
365 | 361 |
366 if (!RuntimeEnabledFeatures::rootLayerScrollingEnabled()) { | 362 if (!RuntimeEnabledFeatures::rootLayerScrollingEnabled()) { |
367 ScopedUndoFrameViewContentClipAndScroll undo(frameView, context); | 363 ScopedUndoFrameViewContentClipAndScroll undo(frameView, context); |
368 frameView.invalidatePaintOfScrollControlsIfNeeded(context); | 364 frameView.invalidatePaintOfScrollControlsIfNeeded(context); |
369 } | 365 } |
370 | 366 |
371 if (frameView.frame().selection().isCaretBoundsDirty()) | 367 if (frameView.frame().selection().isCaretBoundsDirty()) |
372 frameView.frame().selection().invalidateCaretRect(); | 368 frameView.frame().selection().invalidateCaretRect(); |
373 } | 369 } |
374 | 370 |
375 void PaintInvalidator::invalidatePaintIfNeeded( | 371 void PaintInvalidator::invalidatePaintIfNeeded( |
376 const LayoutObject& object, | 372 const LayoutObject& object, |
373 const LayoutPoint& oldPaintOffset, | |
377 PaintInvalidatorContext& context) { | 374 PaintInvalidatorContext& context) { |
378 object.getMutableForPainting().ensureIsReadyForPaintInvalidation(); | 375 object.getMutableForPainting().ensureIsReadyForPaintInvalidation(); |
379 | 376 |
377 DCHECK(context.treeBuilderContext.current.paintOffset == | |
378 object.paintOffset()); | |
379 if (RuntimeEnabledFeatures::slimmingPaintV2Enabled() && | |
380 object.paintOffset() != oldPaintOffset) { | |
381 object.getMutableForPainting().setShouldDoFullPaintInvalidation( | |
382 PaintInvalidationLocationChange); | |
383 } | |
384 | |
380 if (!context.forcedSubtreeInvalidationFlags && | 385 if (!context.forcedSubtreeInvalidationFlags && |
381 !object | 386 !object |
382 .shouldCheckForPaintInvalidationRegardlessOfPaintInvalidationState()) | 387 .shouldCheckForPaintInvalidationRegardlessOfPaintInvalidationState()) |
383 return; | 388 return; |
384 | 389 |
385 updatePaintingLayer(object, context); | 390 updatePaintingLayer(object, context); |
386 | 391 |
387 if (object.document().printing()) | 392 if (object.document().printing()) |
388 return; // Don't invalidate paints if we're printing. | 393 return; // Don't invalidate paints if we're printing. |
389 | 394 |
(...skipping 24 matching lines...) Expand all Loading... | |
414 ForcedSubtreeFullInvalidationForStackedContents); | 419 ForcedSubtreeFullInvalidationForStackedContents); |
415 break; | 420 break; |
416 case PaintInvalidationSVGResourceChange: | 421 case PaintInvalidationSVGResourceChange: |
417 context.forcedSubtreeInvalidationFlags |= | 422 context.forcedSubtreeInvalidationFlags |= |
418 PaintInvalidatorContext::ForcedSubtreeSVGResourceChange; | 423 PaintInvalidatorContext::ForcedSubtreeSVGResourceChange; |
419 break; | 424 break; |
420 default: | 425 default: |
421 break; | 426 break; |
422 } | 427 } |
423 | 428 |
424 if (context.oldLocation != context.newLocation || | 429 if (context.oldLocation != context.newLocation) { |
425 (RuntimeEnabledFeatures::slimmingPaintV2Enabled() && | |
426 context.oldPaintOffset != context.newPaintOffset)) { | |
427 context.forcedSubtreeInvalidationFlags |= | 430 context.forcedSubtreeInvalidationFlags |= |
428 PaintInvalidatorContext::ForcedSubtreeInvalidationChecking; | 431 PaintInvalidatorContext::ForcedSubtreeInvalidationChecking; |
429 } | 432 } |
430 | 433 |
431 // TODO(crbug.com/490725): This is a workaround for the bug, to force | 434 // TODO(crbug.com/490725): This is a workaround for the bug, to force |
432 // descendant to update visual rects on clipping change. | 435 // descendant to update visual rects on clipping change. |
433 if (!RuntimeEnabledFeatures::slimmingPaintV2Enabled() && | 436 if (!RuntimeEnabledFeatures::slimmingPaintV2Enabled() && |
434 context.oldVisualRect != context.newVisualRect | 437 context.oldVisualRect != context.newVisualRect |
435 // Note that isLayoutView() below becomes unnecessary after the launch of | 438 // Note that isLayoutView() below becomes unnecessary after the launch of |
436 // root layer scrolling. | 439 // root layer scrolling. |
437 && (object.hasOverflowClip() || object.isLayoutView()) && | 440 && (object.hasOverflowClip() || object.isLayoutView()) && |
438 !toLayoutBox(object).usesCompositedScrolling()) | 441 !toLayoutBox(object).usesCompositedScrolling()) |
439 context.forcedSubtreeInvalidationFlags |= | 442 context.forcedSubtreeInvalidationFlags |= |
440 PaintInvalidatorContext::ForcedSubtreeInvalidationRectUpdate; | 443 PaintInvalidatorContext::ForcedSubtreeInvalidationRectUpdate; |
441 } | 444 } |
442 | 445 |
443 void PaintInvalidator::processPendingDelayedPaintInvalidations() { | 446 void PaintInvalidator::processPendingDelayedPaintInvalidations() { |
444 for (auto target : m_pendingDelayedPaintInvalidations) | 447 for (auto target : m_pendingDelayedPaintInvalidations) |
445 target->getMutableForPainting().setShouldDoFullPaintInvalidation( | 448 target->getMutableForPainting().setShouldDoFullPaintInvalidation( |
446 PaintInvalidationDelayedFull); | 449 PaintInvalidationDelayedFull); |
447 } | 450 } |
448 | 451 |
449 } // namespace blink | 452 } // namespace blink |
OLD | NEW |