5a8b2d38fe93feea41b498df3a47b1eb8488e294
[WebKit-https.git] / Source / WebCore / rendering / RenderLayer.cpp
1 /*
2  * Copyright (C) 2006-2017 Apple Inc. All rights reserved.
3  *
4  * Portions are Copyright (C) 1998 Netscape Communications Corporation.
5  *
6  * Other contributors:
7  *   Robert O'Callahan <roc+@cs.cmu.edu>
8  *   David Baron <dbaron@fas.harvard.edu>
9  *   Christian Biesinger <cbiesinger@web.de>
10  *   Randall Jesup <rjesup@wgate.com>
11  *   Roland Mainz <roland.mainz@informatik.med.uni-giessen.de>
12  *   Josh Soref <timeless@mac.com>
13  *   Boris Zbarsky <bzbarsky@mit.edu>
14  *
15  * This library is free software; you can redistribute it and/or
16  * modify it under the terms of the GNU Lesser General Public
17  * License as published by the Free Software Foundation; either
18  * version 2.1 of the License, or (at your option) any later version.
19  *
20  * This library is distributed in the hope that it will be useful,
21  * but WITHOUT ANY WARRANTY; without even the implied warranty of
22  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
23  * Lesser General Public License for more details.
24  *
25  * You should have received a copy of the GNU Lesser General Public
26  * License along with this library; if not, write to the Free Software
27  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
28  *
29  * Alternatively, the contents of this file may be used under the terms
30  * of either the Mozilla Public License Version 1.1, found at
31  * http://www.mozilla.org/MPL/ (the "MPL") or the GNU General Public
32  * License Version 2.0, found at http://www.fsf.org/copyleft/gpl.html
33  * (the "GPL"), in which case the provisions of the MPL or the GPL are
34  * applicable instead of those above.  If you wish to allow use of your
35  * version of this file only under the terms of one of those two
36  * licenses (the MPL or the GPL) and not to allow others to use your
37  * version of this file under the LGPL, indicate your decision by
38  * deletingthe provisions above and replace them with the notice and
39  * other provisions required by the MPL or the GPL, as the case may be.
40  * If you do not delete the provisions above, a recipient may use your
41  * version of this file under any of the LGPL, the MPL or the GPL.
42  */
43
44 #include "config.h"
45 #include "RenderLayer.h"
46
47 #include "BoxShape.h"
48 #include "CSSAnimationController.h"
49 #include "CSSFilter.h"
50 #include "CSSPropertyNames.h"
51 #include "Chrome.h"
52 #include "DebugPageOverlays.h"
53 #include "DeprecatedGlobalSettings.h"
54 #include "Document.h"
55 #include "DocumentEventQueue.h"
56 #include "DocumentMarkerController.h"
57 #include "DocumentTimeline.h"
58 #include "Element.h"
59 #include "EventHandler.h"
60 #include "FEColorMatrix.h"
61 #include "FEMerge.h"
62 #include "FloatConversion.h"
63 #include "FloatPoint3D.h"
64 #include "FloatRect.h"
65 #include "FloatRoundedRect.h"
66 #include "FocusController.h"
67 #include "Frame.h"
68 #include "FrameLoader.h"
69 #include "FrameLoaderClient.h"
70 #include "FrameSelection.h"
71 #include "FrameTree.h"
72 #include "FrameView.h"
73 #include "Gradient.h"
74 #include "GraphicsContext.h"
75 #include "HTMLFormControlElement.h"
76 #include "HTMLFrameElement.h"
77 #include "HTMLFrameOwnerElement.h"
78 #include "HTMLIFrameElement.h"
79 #include "HTMLNames.h"
80 #include "HTMLParserIdioms.h"
81 #include "HitTestRequest.h"
82 #include "HitTestResult.h"
83 #include "HitTestingTransformState.h"
84 #include "Logging.h"
85 #include "OverflowEvent.h"
86 #include "OverlapTestRequestClient.h"
87 #include "Page.h"
88 #include "PlatformMouseEvent.h"
89 #include "RenderFlexibleBox.h"
90 #include "RenderFragmentContainer.h"
91 #include "RenderFragmentedFlow.h"
92 #include "RenderGeometryMap.h"
93 #include "RenderImage.h"
94 #include "RenderInline.h"
95 #include "RenderIterator.h"
96 #include "RenderLayerBacking.h"
97 #include "RenderLayerCompositor.h"
98 #include "RenderLayerFilters.h"
99 #include "RenderMarquee.h"
100 #include "RenderMultiColumnFlow.h"
101 #include "RenderReplica.h"
102 #include "RenderSVGResourceClipper.h"
103 #include "RenderSVGRoot.h"
104 #include "RenderScrollbar.h"
105 #include "RenderScrollbarPart.h"
106 #include "RenderTableCell.h"
107 #include "RenderTableRow.h"
108 #include "RenderText.h"
109 #include "RenderTheme.h"
110 #include "RenderTreeAsText.h"
111 #include "RenderView.h"
112 #include "RuntimeEnabledFeatures.h"
113 #include "SVGNames.h"
114 #include "ScaleTransformOperation.h"
115 #include "ScriptDisallowedScope.h"
116 #include "ScrollAnimator.h"
117 #include "Scrollbar.h"
118 #include "ScrollbarTheme.h"
119 #include "ScrollingCoordinator.h"
120 #include "Settings.h"
121 #include "ShadowRoot.h"
122 #include "SourceGraphic.h"
123 #include "StyleProperties.h"
124 #include "StyleResolver.h"
125 #include "TransformationMatrix.h"
126 #include "TranslateTransformOperation.h"
127 #include "WheelEventTestTrigger.h"
128 #include <stdio.h>
129 #include <wtf/MonotonicTime.h>
130 #include <wtf/StdLibExtras.h>
131 #include <wtf/text/CString.h>
132 #include <wtf/text/TextStream.h>
133
134 #if ENABLE(CSS_SCROLL_SNAP)
135 #include "AxisScrollSnapOffsets.h"
136 #endif
137
138 #define MIN_INTERSECT_FOR_REVEAL 32
139
140 namespace WebCore {
141
142 using namespace HTMLNames;
143
144 class ClipRects : public RefCounted<ClipRects> {
145     WTF_MAKE_FAST_ALLOCATED;
146 public:
147     static Ref<ClipRects> create()
148     {
149         return adoptRef(*new ClipRects);
150     }
151
152     static Ref<ClipRects> create(const ClipRects& other)
153     {
154         return adoptRef(*new ClipRects(other));
155     }
156
157     void reset()
158     {
159         m_overflowClipRect.reset();
160         m_fixedClipRect.reset();
161         m_posClipRect.reset();
162         m_fixed = false;
163     }
164
165     const ClipRect& overflowClipRect() const { return m_overflowClipRect; }
166     void setOverflowClipRect(const ClipRect& clipRect) { m_overflowClipRect = clipRect; }
167
168     const ClipRect& fixedClipRect() const { return m_fixedClipRect; }
169     void setFixedClipRect(const ClipRect& clipRect) { m_fixedClipRect = clipRect; }
170
171     const ClipRect& posClipRect() const { return m_posClipRect; }
172     void setPosClipRect(const ClipRect& clipRect) { m_posClipRect = clipRect; }
173
174     bool fixed() const { return m_fixed; }
175     void setFixed(bool fixed) { m_fixed = fixed; }
176
177     bool operator==(const ClipRects& other) const
178     {
179         return m_overflowClipRect == other.overflowClipRect()
180             && m_fixedClipRect == other.fixedClipRect()
181             && m_posClipRect == other.posClipRect()
182             && m_fixed == other.fixed();
183     }
184
185     ClipRects& operator=(const ClipRects& other)
186     {
187         m_overflowClipRect = other.overflowClipRect();
188         m_fixedClipRect = other.fixedClipRect();
189         m_posClipRect = other.posClipRect();
190         m_fixed = other.fixed();
191         return *this;
192     }
193
194 private:
195     ClipRects() = default;
196
197     ClipRects(const LayoutRect& clipRect)
198         : m_overflowClipRect(clipRect)
199         , m_fixedClipRect(clipRect)
200         , m_posClipRect(clipRect)
201     {
202     }
203
204     ClipRects(const ClipRects& other)
205         : RefCounted()
206         , m_fixed(other.fixed())
207         , m_overflowClipRect(other.overflowClipRect())
208         , m_fixedClipRect(other.fixedClipRect())
209         , m_posClipRect(other.posClipRect())
210     {
211     }
212
213     bool m_fixed { false };
214     ClipRect m_overflowClipRect;
215     ClipRect m_fixedClipRect;
216     ClipRect m_posClipRect;
217 };
218
219 class ClipRectsCache {
220     WTF_MAKE_FAST_ALLOCATED;
221 public:
222     ClipRectsCache()
223     {
224 #ifndef NDEBUG
225         for (int i = 0; i < NumCachedClipRectsTypes; ++i) {
226             m_clipRectsRoot[i] = 0;
227             m_scrollbarRelevancy[i] = IgnoreOverlayScrollbarSize;
228         }
229 #endif
230     }
231
232     ClipRects* getClipRects(ClipRectsType clipRectsType, ShouldRespectOverflowClip respectOverflow) const
233     {
234         return m_clipRects[getIndex(clipRectsType, respectOverflow)].get();
235     }
236
237     void setClipRects(ClipRectsType clipRectsType, ShouldRespectOverflowClip respectOverflow, RefPtr<ClipRects>&& clipRects)
238     {
239         m_clipRects[getIndex(clipRectsType, respectOverflow)] = WTFMove(clipRects);
240     }
241
242 #ifndef NDEBUG
243     const RenderLayer* m_clipRectsRoot[NumCachedClipRectsTypes];
244     OverlayScrollbarSizeRelevancy m_scrollbarRelevancy[NumCachedClipRectsTypes];
245 #endif
246
247 private:
248     unsigned getIndex(ClipRectsType clipRectsType, ShouldRespectOverflowClip respectOverflow) const
249     {
250         unsigned index = static_cast<unsigned>(clipRectsType);
251         if (respectOverflow == RespectOverflowClip)
252             index += static_cast<unsigned>(NumCachedClipRectsTypes);
253         ASSERT_WITH_SECURITY_IMPLICATION(index < NumCachedClipRectsTypes * 2);
254         return index;
255     }
256
257     RefPtr<ClipRects> m_clipRects[NumCachedClipRectsTypes * 2];
258 };
259
260 void makeMatrixRenderable(TransformationMatrix& matrix, bool has3DRendering)
261 {
262 #if !ENABLE(3D_TRANSFORMS)
263     UNUSED_PARAM(has3DRendering);
264     matrix.makeAffine();
265 #else
266     if (!has3DRendering)
267         matrix.makeAffine();
268 #endif
269 }
270
271 #if !LOG_DISABLED
272 static TextStream& operator<<(TextStream& ts, const ClipRects& clipRects)
273 {
274     TextStream::GroupScope scope(ts);
275     ts << indent << "ClipRects\n";
276     ts << indent << "  overflow  : " << clipRects.overflowClipRect() << "\n";
277     ts << indent << "  fixed     : " << clipRects.fixedClipRect() << "\n";
278     ts << indent << "  positioned: " << clipRects.posClipRect() << "\n";
279
280     return ts;
281 }
282
283 #endif
284
285 RenderLayer::RenderLayer(RenderLayerModelObject& rendererLayerModelObject)
286     : m_isRenderViewLayer(rendererLayerModelObject.isRenderView())
287     , m_forcedStackingContext(rendererLayerModelObject.isMedia())
288     , m_isOpportunisticStackingContext(false)
289     , m_zOrderListsDirty(false)
290     , m_normalFlowListDirty(true)
291     , m_hadNegativeZOrderList(false)
292     , m_inResizeMode(false)
293     , m_scrollDimensionsDirty(true)
294     , m_hasSelfPaintingLayerDescendant(false)
295     , m_hasSelfPaintingLayerDescendantDirty(false)
296     , m_usedTransparency(false)
297     , m_paintingInsideReflection(false)
298     , m_inOverflowRelayout(false)
299     , m_repaintStatus(NeedsNormalRepaint)
300     , m_visibleContentStatusDirty(true)
301     , m_hasVisibleContent(false)
302     , m_visibleDescendantStatusDirty(false)
303     , m_hasVisibleDescendant(false)
304     , m_registeredScrollableArea(false)
305     , m_isFixedIntersectingViewport(false)
306     , m_3DTransformedDescendantStatusDirty(true)
307     , m_has3DTransformedDescendant(false)
308     , m_hasCompositingDescendant(false)
309     , m_hasCompositedScrollingAncestor(false)
310     , m_hasTransformedAncestor(false)
311     , m_has3DTransformedAncestor(false)
312     , m_indirectCompositingReason(static_cast<unsigned>(IndirectCompositingReason::None))
313     , m_viewportConstrainedNotCompositedReason(NoNotCompositedReason)
314 #if PLATFORM(IOS_FAMILY)
315 #if ENABLE(IOS_TOUCH_EVENTS)
316     , m_registeredAsTouchEventListenerForScrolling(false)
317 #endif
318     , m_adjustForIOSCaretWhenScrolling(false)
319 #endif
320     , m_requiresScrollPositionReconciliation(false)
321     , m_containsDirtyOverlayScrollbars(false)
322     , m_updatingMarqueePosition(false)
323 #if !ASSERT_DISABLED
324     , m_layerListMutationAllowed(true)
325 #endif
326 #if ENABLE(CSS_COMPOSITING)
327     , m_blendMode(static_cast<unsigned>(BlendMode::Normal))
328     , m_hasNotIsolatedCompositedBlendingDescendants(false)
329     , m_hasNotIsolatedBlendingDescendants(false)
330     , m_hasNotIsolatedBlendingDescendantsStatusDirty(false)
331 #endif
332     , m_renderer(rendererLayerModelObject)
333 {
334     setIsNormalFlowOnly(shouldBeNormalFlowOnly());
335     setIsCSSStackingContext(shouldBeCSSStackingContext());
336
337     m_isSelfPaintingLayer = shouldBeSelfPaintingLayer();
338
339     if (!renderer().firstChild()) {
340         m_visibleContentStatusDirty = false;
341         m_hasVisibleContent = renderer().style().visibility() == Visibility::Visible;
342     }
343
344     if (Element* element = renderer().element()) {
345         // We save and restore only the scrollOffset as the other scroll values are recalculated.
346         m_scrollPosition = element->savedLayerScrollPosition();
347         if (!m_scrollPosition.isZero())
348             scrollAnimator().setCurrentPosition(m_scrollPosition);
349         element->setSavedLayerScrollPosition(IntPoint());
350     }
351 }
352
353 RenderLayer::~RenderLayer()
354 {
355     if (inResizeMode())
356         renderer().frame().eventHandler().resizeLayerDestroyed();
357
358     ASSERT(m_registeredScrollableArea == renderer().view().frameView().containsScrollableArea(this));
359
360     if (m_registeredScrollableArea)
361         renderer().view().frameView().removeScrollableArea(this);
362
363 #if ENABLE(IOS_TOUCH_EVENTS)
364     unregisterAsTouchEventListenerForScrolling();
365 #endif
366     if (Element* element = renderer().element())
367         element->setSavedLayerScrollPosition(m_scrollPosition);
368
369     destroyScrollbar(HorizontalScrollbar);
370     destroyScrollbar(VerticalScrollbar);
371
372     if (auto* scrollingCoordinator = renderer().page().scrollingCoordinator())
373         scrollingCoordinator->willDestroyScrollableArea(*this);
374
375     if (m_reflection)
376         removeReflection();
377
378     clearScrollCorner();
379     clearResizer();
380
381     clearLayerFilters();
382
383     if (paintsIntoProvidedBacking()) {
384         auto* backingProviderLayer = this->backingProviderLayer();
385         if (backingProviderLayer->backing())
386             backingProviderLayer->backing()->removeBackingSharingLayer(*this);
387     }
388
389     // Child layers will be deleted by their corresponding render objects, so
390     // we don't need to delete them ourselves.
391
392     clearBacking(true);
393
394     // Layer and all its children should be removed from the tree before destruction.
395     RELEASE_ASSERT_WITH_SECURITY_IMPLICATION(renderer().renderTreeBeingDestroyed() || !parent());
396     RELEASE_ASSERT_WITH_SECURITY_IMPLICATION(renderer().renderTreeBeingDestroyed() || !firstChild());
397 }
398
399 void RenderLayer::addChild(RenderLayer& child, RenderLayer* beforeChild)
400 {
401     RenderLayer* prevSibling = beforeChild ? beforeChild->previousSibling() : lastChild();
402     if (prevSibling) {
403         child.setPreviousSibling(prevSibling);
404         prevSibling->setNextSibling(&child);
405         ASSERT(prevSibling != &child);
406     } else
407         setFirstChild(&child);
408
409     if (beforeChild) {
410         beforeChild->setPreviousSibling(&child);
411         child.setNextSibling(beforeChild);
412         ASSERT(beforeChild != &child);
413     } else
414         setLastChild(&child);
415
416     child.setParent(this);
417
418     dirtyPaintOrderListsOnChildChange(child);
419
420     child.updateDescendantDependentFlags();
421     if (child.m_hasVisibleContent || child.m_hasVisibleDescendant)
422         setAncestorChainHasVisibleDescendant();
423
424     if (child.isSelfPaintingLayer() || child.hasSelfPaintingLayerDescendant())
425         setAncestorChainHasSelfPaintingLayerDescendant();
426
427     if (compositor().hasContentCompositingLayers())
428         setDescendantsNeedCompositingRequirementsTraversal();
429
430     if (child.hasDescendantNeedingCompositingRequirementsTraversal() || child.needsCompositingRequirementsTraversal())
431         child.setAncestorsHaveCompositingDirtyFlag(Compositing::HasDescendantNeedingRequirementsTraversal);
432
433     if (child.hasDescendantNeedingUpdateBackingOrHierarchyTraversal() || child.needsUpdateBackingOrHierarchyTraversal())
434         child.setAncestorsHaveCompositingDirtyFlag(Compositing::HasDescendantNeedingBackingOrHierarchyTraversal);
435
436 #if ENABLE(CSS_COMPOSITING)
437     if (child.hasBlendMode() || (child.hasNotIsolatedBlendingDescendants() && !child.isolatesBlending()))
438         updateAncestorChainHasBlendingDescendants(); // Why not just dirty?
439 #endif
440
441     compositor().layerWasAdded(*this, child);
442 }
443
444 void RenderLayer::removeChild(RenderLayer& oldChild)
445 {
446     if (!renderer().renderTreeBeingDestroyed())
447         compositor().layerWillBeRemoved(*this, oldChild);
448
449     // remove the child
450     if (oldChild.previousSibling())
451         oldChild.previousSibling()->setNextSibling(oldChild.nextSibling());
452     if (oldChild.nextSibling())
453         oldChild.nextSibling()->setPreviousSibling(oldChild.previousSibling());
454
455     if (m_first == &oldChild)
456         m_first = oldChild.nextSibling();
457     if (m_last == &oldChild)
458         m_last = oldChild.previousSibling();
459
460     dirtyPaintOrderListsOnChildChange(oldChild);
461
462     oldChild.setPreviousSibling(nullptr);
463     oldChild.setNextSibling(nullptr);
464     oldChild.setParent(nullptr);
465     
466     oldChild.updateDescendantDependentFlags();
467     if (oldChild.m_hasVisibleContent || oldChild.m_hasVisibleDescendant)
468         dirtyAncestorChainVisibleDescendantStatus();
469
470     if (oldChild.isSelfPaintingLayer() || oldChild.hasSelfPaintingLayerDescendant())
471         dirtyAncestorChainHasSelfPaintingLayerDescendantStatus();
472
473     if (compositor().hasContentCompositingLayers())
474         setDescendantsNeedCompositingRequirementsTraversal();
475
476 #if ENABLE(CSS_COMPOSITING)
477     if (oldChild.hasBlendMode() || (oldChild.hasNotIsolatedBlendingDescendants() && !oldChild.isolatesBlending()))
478         dirtyAncestorChainHasBlendingDescendants();
479 #endif
480 }
481
482 void RenderLayer::dirtyPaintOrderListsOnChildChange(RenderLayer& child)
483 {
484     if (child.isNormalFlowOnly())
485         dirtyNormalFlowList();
486
487     if (!child.isNormalFlowOnly() || child.firstChild()) {
488         // Dirty the z-order list in which we are contained. The stackingContext() can be null in the
489         // case where we're building up generated content layers. This is ok, since the lists will start
490         // off dirty in that case anyway.
491         child.dirtyStackingContextZOrderLists();
492     }
493 }
494
495 void RenderLayer::insertOnlyThisLayer()
496 {
497     if (!m_parent && renderer().parent()) {
498         // We need to connect ourselves when our renderer() has a parent.
499         // Find our enclosingLayer and add ourselves.
500         RenderLayer* parentLayer = renderer().parent()->enclosingLayer();
501         ASSERT(parentLayer);
502         RenderLayer* beforeChild = parentLayer->reflectionLayer() != this ? renderer().parent()->findNextLayer(parentLayer, &renderer()) : nullptr;
503         parentLayer->addChild(*this, beforeChild);
504     }
505
506     // Remove all descendant layers from the hierarchy and add them to the new position.
507     for (auto& child : childrenOfType<RenderElement>(renderer()))
508         child.moveLayers(m_parent, this);
509
510     // Clear out all the clip rects.
511     clearClipRectsIncludingDescendants();
512 }
513
514 void RenderLayer::removeOnlyThisLayer()
515 {
516     if (!m_parent)
517         return;
518
519     // Mark that we are about to lose our layer. This makes render tree
520     // walks ignore this layer while we're removing it.
521     renderer().setHasLayer(false);
522
523     compositor().layerWillBeRemoved(*m_parent, *this);
524
525     // Dirty the clip rects.
526     clearClipRectsIncludingDescendants();
527
528     RenderLayer* nextSib = nextSibling();
529
530     // Remove the child reflection layer before moving other child layers.
531     // The reflection layer should not be moved to the parent.
532     if (reflection())
533         removeChild(*reflectionLayer());
534
535     // Now walk our kids and reattach them to our parent.
536     RenderLayer* current = m_first;
537     while (current) {
538         RenderLayer* next = current->nextSibling();
539         removeChild(*current);
540         m_parent->addChild(*current, nextSib);
541         current->setRepaintStatus(NeedsFullRepaint);
542         current = next;
543     }
544
545     // Remove us from the parent.
546     m_parent->removeChild(*this);
547     renderer().destroyLayer();
548 }
549
550 static bool canCreateStackingContext(const RenderLayer& layer)
551 {
552     auto& renderer = layer.renderer();
553     return renderer.hasTransformRelatedProperty()
554         || renderer.hasClipPath()
555         || renderer.hasFilter()
556         || renderer.hasMask()
557         || renderer.hasBackdropFilter()
558 #if ENABLE(CSS_COMPOSITING)
559         || renderer.hasBlendMode()
560 #endif
561         || renderer.isTransparent()
562         || renderer.isPositioned() // Note that this only creates stacking context in conjunction with explicit z-index.
563         || renderer.hasReflection()
564         || renderer.style().hasIsolation()
565         || !renderer.style().hasAutoZIndex()
566         || (renderer.style().willChange() && renderer.style().willChange()->canCreateStackingContext());
567 }
568
569 bool RenderLayer::shouldBeNormalFlowOnly() const
570 {
571     if (canCreateStackingContext(*this))
572         return false;
573
574     return renderer().hasOverflowClip()
575         || renderer().isCanvas()
576         || renderer().isVideo()
577         || renderer().isEmbeddedObject()
578         || renderer().isRenderIFrame()
579         || (renderer().isRenderImage() && downcast<RenderImage>(renderer()).isEditableImage())
580         || (renderer().style().specifiesColumns() && !isRenderViewLayer())
581         || renderer().isInFlowRenderFragmentedFlow();
582 }
583
584 bool RenderLayer::shouldBeCSSStackingContext() const
585 {
586     return !renderer().style().hasAutoZIndex() || isRenderViewLayer();
587 }
588
589 bool RenderLayer::setIsNormalFlowOnly(bool isNormalFlowOnly)
590 {
591     if (isNormalFlowOnly == m_isNormalFlowOnly)
592         return false;
593     
594     m_isNormalFlowOnly = isNormalFlowOnly;
595
596     if (auto* p = parent())
597         p->dirtyNormalFlowList();
598     dirtyStackingContextZOrderLists();
599     return true;
600 }
601
602 void RenderLayer::isStackingContextChanged()
603 {
604     dirtyStackingContextZOrderLists();
605     if (isStackingContext())
606         dirtyZOrderLists();
607     else
608         clearZOrderLists();
609 }
610
611 bool RenderLayer::setIsOpportunisticStackingContext(bool isStacking)
612 {
613     bool wasStacking = isStackingContext();
614     m_isOpportunisticStackingContext = isStacking;
615     if (wasStacking == isStackingContext())
616         return false;
617
618     isStackingContextChanged();
619     return true;
620 }
621
622 bool RenderLayer::setIsCSSStackingContext(bool isCSSStackingContext)
623 {
624     bool wasStacking = isStackingContext();
625     m_isCSSStackingContext = isCSSStackingContext;
626     if (wasStacking == isStackingContext())
627         return false;
628
629     isStackingContextChanged();
630     return true;
631 }
632
633 void RenderLayer::setParent(RenderLayer* parent)
634 {
635     if (parent == m_parent)
636         return;
637
638     if (m_parent && !renderer().renderTreeBeingDestroyed())
639         compositor().layerWillBeRemoved(*m_parent, *this);
640
641     m_parent = parent;
642
643     if (m_parent && !renderer().renderTreeBeingDestroyed())
644         compositor().layerWasAdded(*m_parent, *this);
645 }
646
647 RenderLayer* RenderLayer::stackingContext() const
648 {
649     auto* layer = parent();
650     while (layer && !layer->isStackingContext())
651         layer = layer->parent();
652
653     ASSERT(!layer || layer->isStackingContext());
654     return layer;
655 }
656
657 void RenderLayer::dirtyZOrderLists()
658 {
659     ASSERT(layerListMutationAllowed());
660     ASSERT(isStackingContext());
661
662     if (m_posZOrderList)
663         m_posZOrderList->clear();
664     if (m_negZOrderList)
665         m_negZOrderList->clear();
666     m_zOrderListsDirty = true;
667
668     // FIXME: Ideally, we'd only dirty if the lists changed.
669     if (hasCompositingDescendant())
670         setNeedsCompositingPaintOrderChildrenUpdate();
671 }
672
673 void RenderLayer::dirtyStackingContextZOrderLists()
674 {
675     if (auto* sc = stackingContext())
676         sc->dirtyZOrderLists();
677 }
678
679 void RenderLayer::dirtyNormalFlowList()
680 {
681     ASSERT(layerListMutationAllowed());
682
683     if (m_normalFlowList)
684         m_normalFlowList->clear();
685     m_normalFlowListDirty = true;
686
687     if (hasCompositingDescendant())
688         setNeedsCompositingPaintOrderChildrenUpdate();
689 }
690
691 void RenderLayer::updateNormalFlowList()
692 {
693     if (!m_normalFlowListDirty)
694         return;
695
696     ASSERT(layerListMutationAllowed());
697
698     for (RenderLayer* child = firstChild(); child; child = child->nextSibling()) {
699         // Ignore non-overflow layers and reflections.
700         if (child->isNormalFlowOnly() && !isReflectionLayer(*child)) {
701             if (!m_normalFlowList)
702                 m_normalFlowList = std::make_unique<Vector<RenderLayer*>>();
703             m_normalFlowList->append(child);
704         }
705     }
706     
707     m_normalFlowListDirty = false;
708 }
709
710 void RenderLayer::rebuildZOrderLists()
711 {
712     ASSERT(layerListMutationAllowed());
713     ASSERT(isDirtyStackingContext());
714     rebuildZOrderLists(m_posZOrderList, m_negZOrderList);
715     m_zOrderListsDirty = false;
716     
717     bool hasNegativeZOrderList = m_negZOrderList && m_negZOrderList->size();
718     // Having negative z-order lists affect whether a compositing layer needs a foreground layer.
719     // Ideally we'd only trigger this when having z-order children changes, but we blow away the old z-order
720     // lists on dirtying so we don't know the old state.
721     if (hasNegativeZOrderList != m_hadNegativeZOrderList) {
722         m_hadNegativeZOrderList = hasNegativeZOrderList;
723         if (isComposited())
724             setNeedsCompositingConfigurationUpdate();
725     }
726 }
727
728 void RenderLayer::rebuildZOrderLists(std::unique_ptr<Vector<RenderLayer*>>& posZOrderList, std::unique_ptr<Vector<RenderLayer*>>& negZOrderList)
729 {
730     bool includeHiddenLayers = compositor().usesCompositing();
731     for (RenderLayer* child = firstChild(); child; child = child->nextSibling()) {
732         if (!isReflectionLayer(*child))
733             child->collectLayers(includeHiddenLayers, posZOrderList, negZOrderList);
734     }
735
736     auto compareZIndex = [] (const RenderLayer* first, const RenderLayer* second) -> bool {
737         return first->zIndex() < second->zIndex();
738     };
739
740     // Sort the two lists.
741     if (posZOrderList)
742         std::stable_sort(posZOrderList->begin(), posZOrderList->end(), compareZIndex);
743
744     if (negZOrderList)
745         std::stable_sort(negZOrderList->begin(), negZOrderList->end(), compareZIndex);
746 }
747
748 void RenderLayer::collectLayers(bool includeHiddenLayers, std::unique_ptr<Vector<RenderLayer*>>& positiveZOrderList, std::unique_ptr<Vector<RenderLayer*>>& negativeZOrderList)
749 {
750     updateDescendantDependentFlags();
751
752     bool isStacking = isStackingContext();
753     // Overflow layers are just painted by their enclosing layers, so they don't get put in zorder lists.
754     bool includeHiddenLayer = includeHiddenLayers || (m_hasVisibleContent || (m_hasVisibleDescendant && isStacking));
755     if (includeHiddenLayer && !isNormalFlowOnly()) {
756         auto& layerList = (zIndex() >= 0) ? positiveZOrderList : negativeZOrderList;
757         if (!layerList)
758             layerList = std::make_unique<Vector<RenderLayer*>>();
759         layerList->append(this);
760     }
761
762     // Recur into our children to collect more layers, but only if we don't establish
763     // a stacking context/container.
764     if ((includeHiddenLayers || m_hasVisibleDescendant) && !isStacking) {
765         for (RenderLayer* child = firstChild(); child; child = child->nextSibling()) {
766             // Ignore reflections.
767             if (!isReflectionLayer(*child))
768                 child->collectLayers(includeHiddenLayers, positiveZOrderList, negativeZOrderList);
769         }
770     }
771 }
772
773 void RenderLayer::setAncestorsHaveCompositingDirtyFlag(Compositing flag)
774 {
775     for (auto* layer = paintOrderParent(); layer; layer = layer->paintOrderParent()) {
776         if (layer->m_compositingDirtyBits.contains(flag))
777             break;
778         layer->m_compositingDirtyBits.add(flag);
779     }
780 }
781
782 void RenderLayer::updateLayerListsIfNeeded()
783 {
784     updateZOrderLists();
785     updateNormalFlowList();
786
787     if (RenderLayer* reflectionLayer = this->reflectionLayer()) {
788         reflectionLayer->updateZOrderLists();
789         reflectionLayer->updateNormalFlowList();
790     }
791 }
792
793 String RenderLayer::name() const
794 {
795     StringBuilder name;
796
797     if (Element* element = renderer().element()) {
798         name.append(" <");
799         name.append(element->tagName().convertToLowercaseWithoutLocale());
800         name.append('>');
801
802         if (element->hasID()) {
803             name.appendLiteral(" id=\'");
804             name.append(element->getIdAttribute());
805             name.append('\'');
806         }
807
808         if (element->hasClass()) {
809             name.appendLiteral(" class=\'");
810             size_t classNamesToDump = element->classNames().size();
811             const size_t maxNumClassNames = 7;
812             bool addEllipsis = false;
813             if (classNamesToDump > maxNumClassNames) {
814                 classNamesToDump = maxNumClassNames;
815                 addEllipsis = true;
816             }
817             
818             for (size_t i = 0; i < classNamesToDump; ++i) {
819                 if (i > 0)
820                     name.append(' ');
821                 name.append(element->classNames()[i]);
822             }
823             if (addEllipsis)
824                 name.append("...");
825             name.append('\'');
826         }
827     } else
828         name.append(renderer().renderName());
829
830     if (isReflection())
831         name.appendLiteral(" (reflection)");
832
833     return name.toString();
834 }
835
836 RenderLayerCompositor& RenderLayer::compositor() const
837 {
838     return renderer().view().compositor();
839 }
840
841 void RenderLayer::contentChanged(ContentChangeType changeType)
842 {
843     if (changeType == CanvasChanged || changeType == VideoChanged || changeType == FullScreenChanged || (isComposited() && changeType == ImageChanged)) {
844         setNeedsPostLayoutCompositingUpdate();
845         setNeedsCompositingConfigurationUpdate();
846     }
847
848     if (auto* backing = this->backing())
849         backing->contentChanged(changeType);
850 }
851
852 bool RenderLayer::canRender3DTransforms() const
853 {
854     return compositor().canRender3DTransforms();
855 }
856
857 bool RenderLayer::paintsWithFilters() const
858 {
859     if (!renderer().hasFilter())
860         return false;
861         
862     if (!isComposited())
863         return true;
864
865     return !m_backing->canCompositeFilters();
866 }
867
868 bool RenderLayer::requiresFullLayerImageForFilters() const 
869 {
870     if (!paintsWithFilters())
871         return false;
872
873     return m_filters && m_filters->hasFilterThatMovesPixels();
874 }
875
876 void RenderLayer::updateLayerPositionsAfterLayout(const RenderLayer* rootLayer, OptionSet<UpdateLayerPositionsFlag> flags)
877 {
878     LOG(Compositing, "RenderLayer %p updateLayerPositionsAfterLayout", this);
879     RenderGeometryMap geometryMap(UseTransforms);
880     if (this != rootLayer)
881         geometryMap.pushMappingsToAncestor(parent(), nullptr);
882     updateLayerPositions(&geometryMap, flags);
883 }
884
885 void RenderLayer::updateLayerPositions(RenderGeometryMap* geometryMap, OptionSet<UpdateLayerPositionsFlag> flags)
886 {
887     updateLayerPosition(&flags);
888     applyPostLayoutScrollPositionIfNeeded();
889
890     if (geometryMap)
891         geometryMap->pushMappingsToAncestor(this, parent());
892
893     // Clear our cached clip rect information.
894     clearClipRects();
895     
896     if (hasOverflowControls()) {
897         LayoutSize offsetFromRoot;
898         if (geometryMap)
899             offsetFromRoot = LayoutSize(toFloatSize(geometryMap->absolutePoint(FloatPoint())));
900         else {
901             // FIXME: It looks suspicious to call convertToLayerCoords here
902             // as canUseConvertToLayerCoords may be true for an ancestor layer.
903             offsetFromRoot = offsetFromAncestor(root());
904         }
905         positionOverflowControls(roundedIntSize(offsetFromRoot));
906     }
907
908     updateDescendantDependentFlags();
909
910     if (flags & UpdatePagination)
911         updatePagination();
912     else
913         m_enclosingPaginationLayer = nullptr;
914     
915     if (m_hasVisibleContent) {
916         // FIXME: Paint offset cache does not work with RenderLayers as there is not a 1-to-1
917         // mapping between them and the RenderObjects. It would be neat to enable
918         // LayoutState outside the layout() phase and use it here.
919         ASSERT(!renderer().view().frameView().layoutContext().isPaintOffsetCacheEnabled());
920
921         RenderLayerModelObject* repaintContainer = renderer().containerForRepaint();
922         
923         auto hadRepaintLayoutRects = renderer().hasRepaintLayoutRects();
924         RepaintLayoutRects oldRects = hadRepaintLayoutRects ? renderer().repaintLayoutRects() : RepaintLayoutRects();
925         computeRepaintRects(repaintContainer, geometryMap);
926         
927         auto hasRepaintLayoutRects = renderer().hasRepaintLayoutRects();
928         RepaintLayoutRects newRects = hasRepaintLayoutRects ? renderer().repaintLayoutRects() : RepaintLayoutRects();
929         // FIXME: Should ASSERT that value calculated for m_outlineBox using the cached offset is the same
930         // as the value not using the cached offset, but we can't due to https://bugs.webkit.org/show_bug.cgi?id=37048
931         if ((flags & CheckForRepaint) && hasRepaintLayoutRects) {
932             if (!renderer().view().printing()) {
933                 if (m_repaintStatus & NeedsFullRepaint) {
934                     if (hadRepaintLayoutRects)
935                         renderer().repaintUsingContainer(repaintContainer, oldRects.m_repaintRect);
936                     if (!hadRepaintLayoutRects || newRects.m_repaintRect != oldRects.m_repaintRect)
937                         renderer().repaintUsingContainer(repaintContainer, newRects.m_repaintRect);
938                 } else if (shouldRepaintAfterLayout()) {
939                     // FIXME: We will convert this to just take the old and new RepaintLayoutRects once
940                     // we change other callers to use RepaintLayoutRects.
941                     renderer().repaintAfterLayoutIfNeeded(repaintContainer, oldRects.m_repaintRect, oldRects.m_outlineBox, &newRects.m_repaintRect, &newRects.m_outlineBox);
942                 }
943             }
944         }
945     } else
946         clearRepaintRects();
947
948     m_repaintStatus = NeedsNormalRepaint;
949     m_hasTransformedAncestor = flags.contains(SeenTransformedLayer);
950     m_has3DTransformedAncestor = flags.contains(Seen3DTransformedLayer);
951     setHasCompositedScrollingAncestor(flags.contains(SeenCompositedScrollingLayer));
952
953     // Update the reflection's position and size.
954     if (m_reflection)
955         m_reflection->layout();
956
957     if (renderer().isInFlowRenderFragmentedFlow()) {
958         updatePagination();
959         flags.add(UpdatePagination);
960     }
961
962     if (transform()) {
963         flags.add(SeenTransformedLayer);
964         if (!transform()->isAffine())
965             flags.add(Seen3DTransformedLayer);
966     }
967     
968     if (hasCompositedScrollableOverflow())
969         flags.add(SeenCompositedScrollingLayer);
970
971     for (RenderLayer* child = firstChild(); child; child = child->nextSibling())
972         child->updateLayerPositions(geometryMap, flags);
973
974     // With all our children positioned, now update our marquee if we need to.
975     if (m_marquee) {
976         // FIXME: would like to use SetForScope<> but it doesn't work with bitfields.
977         bool oldUpdatingMarqueePosition = m_updatingMarqueePosition;
978         m_updatingMarqueePosition = true;
979         m_marquee->updateMarqueePosition();
980         m_updatingMarqueePosition = oldUpdatingMarqueePosition;
981     }
982
983     if (renderer().isFixedPositioned() && renderer().settings().acceleratedCompositingForFixedPositionEnabled()) {
984         bool intersectsViewport = compositor().fixedLayerIntersectsViewport(*this);
985         if (intersectsViewport != m_isFixedIntersectingViewport) {
986             m_isFixedIntersectingViewport = intersectsViewport;
987             setNeedsPostLayoutCompositingUpdate();
988         }
989     }
990
991     if (isComposited())
992         backing()->updateAfterLayout(flags.contains(ContainingClippingLayerChangedSize), flags.contains(NeedsFullRepaintInBacking));
993
994     if (geometryMap)
995         geometryMap->popMappingsToAncestor(parent());
996
997     renderer().document().markers().invalidateRectsForAllMarkers();
998 }
999
1000 LayoutRect RenderLayer::repaintRectIncludingNonCompositingDescendants() const
1001 {
1002     LayoutRect repaintRect = renderer().repaintLayoutRects().m_repaintRect;
1003     for (RenderLayer* child = firstChild(); child; child = child->nextSibling()) {
1004         // Don't include repaint rects for composited child layers; they will paint themselves and have a different origin.
1005         if (child->isComposited())
1006             continue;
1007
1008         repaintRect.uniteIfNonZero(child->repaintRectIncludingNonCompositingDescendants());
1009     }
1010     return repaintRect;
1011 }
1012
1013 void RenderLayer::setAncestorChainHasSelfPaintingLayerDescendant()
1014 {
1015     for (RenderLayer* layer = this; layer; layer = layer->parent()) {
1016         if (!layer->m_hasSelfPaintingLayerDescendantDirty && layer->hasSelfPaintingLayerDescendant())
1017             break;
1018
1019         layer->m_hasSelfPaintingLayerDescendantDirty = false;
1020         layer->m_hasSelfPaintingLayerDescendant = true;
1021     }
1022 }
1023
1024 void RenderLayer::dirtyAncestorChainHasSelfPaintingLayerDescendantStatus()
1025 {
1026     for (RenderLayer* layer = this; layer; layer = layer->parent()) {
1027         layer->m_hasSelfPaintingLayerDescendantDirty = true;
1028         // If we have reached a self-painting layer, we know our parent should have a self-painting descendant
1029         // in this case, there is no need to dirty our ancestors further.
1030         if (layer->isSelfPaintingLayer()) {
1031             ASSERT(!parent() || parent()->m_hasSelfPaintingLayerDescendantDirty || parent()->hasSelfPaintingLayerDescendant());
1032             break;
1033         }
1034     }
1035 }
1036
1037 void RenderLayer::computeRepaintRects(const RenderLayerModelObject* repaintContainer, const RenderGeometryMap* geometryMap)
1038 {
1039     ASSERT(!m_visibleContentStatusDirty);
1040     renderer().computeRepaintLayoutRects(repaintContainer, geometryMap);
1041 }
1042
1043 void RenderLayer::computeRepaintRectsIncludingDescendants()
1044 {
1045     // FIXME: computeRepaintRects() has to walk up the parent chain for every layer to compute the rects.
1046     // We should make this more efficient.
1047     // FIXME: it's wrong to call this when layout is not up-to-date, which we do.
1048     computeRepaintRects(renderer().containerForRepaint());
1049
1050     for (RenderLayer* layer = firstChild(); layer; layer = layer->nextSibling())
1051         layer->computeRepaintRectsIncludingDescendants();
1052 }
1053
1054 void RenderLayer::clearRepaintRects()
1055 {
1056     ASSERT(!m_visibleContentStatusDirty);
1057
1058     renderer().clearRepaintLayoutRects();
1059 }
1060
1061 void RenderLayer::updateLayerPositionsAfterDocumentScroll()
1062 {
1063     ASSERT(this == renderer().view().layer());
1064
1065     LOG(Scrolling, "RenderLayer::updateLayerPositionsAfterDocumentScroll");
1066
1067     RenderGeometryMap geometryMap(UseTransforms);
1068     updateLayerPositionsAfterScroll(&geometryMap);
1069 }
1070
1071 void RenderLayer::updateLayerPositionsAfterOverflowScroll()
1072 {
1073     RenderGeometryMap geometryMap(UseTransforms);
1074     if (this != renderer().view().layer())
1075         geometryMap.pushMappingsToAncestor(parent(), nullptr);
1076
1077     // FIXME: why is it OK to not check the ancestors of this layer in order to
1078     // initialize the HasSeenViewportConstrainedAncestor and HasSeenAncestorWithOverflowClip flags?
1079     updateLayerPositionsAfterScroll(&geometryMap, IsOverflowScroll);
1080 }
1081
1082 void RenderLayer::updateLayerPositionsAfterScroll(RenderGeometryMap* geometryMap, OptionSet<UpdateLayerPositionsAfterScrollFlag> flags)
1083 {
1084     // FIXME: This shouldn't be needed, but there are some corner cases where
1085     // these flags are still dirty. Update so that the check below is valid.
1086     updateDescendantDependentFlags();
1087
1088     // If we have no visible content and no visible descendants, there is no point recomputing
1089     // our rectangles as they will be empty. If our visibility changes, we are expected to
1090     // recompute all our positions anyway.
1091     if (!m_hasVisibleDescendant && !m_hasVisibleContent)
1092         return;
1093
1094     bool positionChanged = updateLayerPosition();
1095     if (positionChanged)
1096         flags.add(HasChangedAncestor);
1097
1098     if (flags.containsAny({ HasChangedAncestor, HasSeenViewportConstrainedAncestor, IsOverflowScroll }))
1099         clearClipRects();
1100
1101     if (renderer().style().hasViewportConstrainedPosition())
1102         flags.add(HasSeenViewportConstrainedAncestor);
1103
1104     if (renderer().hasOverflowClip())
1105         flags.add(HasSeenAncestorWithOverflowClip);
1106     
1107     bool shouldComputeRepaintRects = (flags.contains(HasSeenViewportConstrainedAncestor) || flags.containsAll({ IsOverflowScroll, HasSeenAncestorWithOverflowClip })) && isSelfPaintingLayer();
1108     bool isVisuallyEmpty = !isVisuallyNonEmpty();
1109     bool shouldPushAndPopMappings = geometryMap && ((shouldComputeRepaintRects && !isVisuallyEmpty) || firstChild());
1110     if (shouldPushAndPopMappings)
1111         geometryMap->pushMappingsToAncestor(this, parent());
1112
1113     if (shouldComputeRepaintRects) {
1114         // When scrolling, we don't compute repaint rects for visually non-empty layers.
1115         if (isVisuallyEmpty)
1116             clearRepaintRects();
1117         else // FIXME: We could track the repaint container as we walk down the tree.
1118             computeRepaintRects(renderer().containerForRepaint(), geometryMap);
1119     } else if (!renderer().view().frameView().platformWidget()) {
1120         // When ScrollView's m_paintsEntireContents flag flips due to layer backing changes, the repaint area transitions from
1121         // visual to layout overflow. When this happens the cached repaint rects become invalid and they need to be recomputed (see webkit.org/b/188121).
1122         // Check that our cached rects are correct.
1123         ASSERT(!renderer().hasRepaintLayoutRects() || renderer().repaintLayoutRects().m_repaintRect == renderer().clippedOverflowRectForRepaint(renderer().containerForRepaint()));
1124         ASSERT(!renderer().hasRepaintLayoutRects() || renderer().repaintLayoutRects().m_outlineBox == renderer().outlineBoundsForRepaint(renderer().containerForRepaint()));
1125     }
1126     
1127     for (RenderLayer* child = firstChild(); child; child = child->nextSibling())
1128         child->updateLayerPositionsAfterScroll(geometryMap, flags);
1129
1130     // We don't update our reflection as scrolling is a translation which does not change the size()
1131     // of an object, thus RenderReplica will still repaint itself properly as the layer position was
1132     // updated above.
1133
1134     if (m_marquee) {
1135         bool oldUpdatingMarqueePosition = m_updatingMarqueePosition;
1136         m_updatingMarqueePosition = true;
1137         m_marquee->updateMarqueePosition();
1138         m_updatingMarqueePosition = oldUpdatingMarqueePosition;
1139     }
1140
1141     if (shouldPushAndPopMappings)
1142         geometryMap->popMappingsToAncestor(parent());
1143
1144     renderer().document().markers().invalidateRectsForAllMarkers();
1145 }
1146
1147 #if ENABLE(CSS_COMPOSITING)
1148
1149 void RenderLayer::updateBlendMode()
1150 {
1151     bool hadBlendMode = static_cast<BlendMode>(m_blendMode) != BlendMode::Normal;
1152     if (parent() && hadBlendMode != hasBlendMode()) {
1153         if (hasBlendMode())
1154             parent()->updateAncestorChainHasBlendingDescendants();
1155         else
1156             parent()->dirtyAncestorChainHasBlendingDescendants();
1157     }
1158
1159     BlendMode newBlendMode = renderer().style().blendMode();
1160     if (newBlendMode != static_cast<BlendMode>(m_blendMode))
1161         m_blendMode = static_cast<unsigned>(newBlendMode);
1162 }
1163
1164 void RenderLayer::updateAncestorChainHasBlendingDescendants()
1165 {
1166     for (auto* layer = this; layer; layer = layer->parent()) {
1167         if (!layer->hasNotIsolatedBlendingDescendantsStatusDirty() && layer->hasNotIsolatedBlendingDescendants())
1168             break;
1169         layer->m_hasNotIsolatedBlendingDescendants = true;
1170         layer->m_hasNotIsolatedBlendingDescendantsStatusDirty = false;
1171
1172         layer->updateSelfPaintingLayer();
1173
1174         if (layer->isCSSStackingContext())
1175             break;
1176     }
1177 }
1178
1179 void RenderLayer::dirtyAncestorChainHasBlendingDescendants()
1180 {
1181     for (auto* layer = this; layer; layer = layer->parent()) {
1182         if (layer->hasNotIsolatedBlendingDescendantsStatusDirty())
1183             break;
1184         
1185         layer->m_hasNotIsolatedBlendingDescendantsStatusDirty = true;
1186
1187         if (layer->isCSSStackingContext())
1188             break;
1189     }
1190 }
1191 #endif
1192
1193 void RenderLayer::updateTransform()
1194 {
1195     bool hasTransform = renderer().hasTransform();
1196     bool had3DTransform = has3DTransform();
1197
1198     bool hadTransform = !!m_transform;
1199     if (hasTransform != hadTransform) {
1200         if (hasTransform)
1201             m_transform = std::make_unique<TransformationMatrix>();
1202         else
1203             m_transform = nullptr;
1204         
1205         // Layers with transforms act as clip rects roots, so clear the cached clip rects here.
1206         clearClipRectsIncludingDescendants();
1207     }
1208     
1209     if (hasTransform) {
1210         RenderBox* box = renderBox();
1211         ASSERT(box);
1212         m_transform->makeIdentity();
1213         box->style().applyTransform(*m_transform, snapRectToDevicePixels(box->borderBoxRect(), box->document().deviceScaleFactor()), RenderStyle::IncludeTransformOrigin);
1214         makeMatrixRenderable(*m_transform, canRender3DTransforms());
1215     }
1216
1217     if (had3DTransform != has3DTransform()) {
1218         dirty3DTransformedDescendantStatus();
1219         // Having a 3D transform affects whether enclosing perspective and preserve-3d layers composite, so trigger an update.
1220         setNeedsPostLayoutCompositingUpdateOnAncestors();
1221     }
1222 }
1223
1224 TransformationMatrix RenderLayer::currentTransform(RenderStyle::ApplyTransformOrigin applyOrigin) const
1225 {
1226     if (!m_transform)
1227         return TransformationMatrix();
1228     
1229     RenderBox* box = renderBox();
1230
1231     if (RuntimeEnabledFeatures::sharedFeatures().webAnimationsCSSIntegrationEnabled()) {
1232         if (auto* timeline = renderer().documentTimeline()) {
1233             if (timeline->isRunningAcceleratedAnimationOnRenderer(renderer(), CSSPropertyTransform)) {
1234                 TransformationMatrix currTransform;
1235                 FloatRect pixelSnappedBorderRect = snapRectToDevicePixels(box->borderBoxRect(), box->document().deviceScaleFactor());
1236                 std::unique_ptr<RenderStyle> style = timeline->animatedStyleForRenderer(renderer());
1237                 style->applyTransform(currTransform, pixelSnappedBorderRect, applyOrigin);
1238                 makeMatrixRenderable(currTransform, canRender3DTransforms());
1239                 return currTransform;
1240             }
1241         }
1242     } else {
1243         if (renderer().animation().isRunningAcceleratedAnimationOnRenderer(renderer(), CSSPropertyTransform)) {
1244             TransformationMatrix currTransform;
1245             FloatRect pixelSnappedBorderRect = snapRectToDevicePixels(box->borderBoxRect(), box->document().deviceScaleFactor());
1246             std::unique_ptr<RenderStyle> style = renderer().animation().animatedStyleForRenderer(renderer());
1247             style->applyTransform(currTransform, pixelSnappedBorderRect, applyOrigin);
1248             makeMatrixRenderable(currTransform, canRender3DTransforms());
1249             return currTransform;
1250         }
1251     }
1252
1253
1254     // m_transform includes transform-origin, so we need to recompute the transform here.
1255     if (applyOrigin == RenderStyle::ExcludeTransformOrigin) {
1256         TransformationMatrix currTransform;
1257         FloatRect pixelSnappedBorderRect = snapRectToDevicePixels(box->borderBoxRect(), box->document().deviceScaleFactor());
1258         box->style().applyTransform(currTransform, pixelSnappedBorderRect, RenderStyle::ExcludeTransformOrigin);
1259         makeMatrixRenderable(currTransform, canRender3DTransforms());
1260         return currTransform;
1261     }
1262
1263     return *m_transform;
1264 }
1265
1266 TransformationMatrix RenderLayer::renderableTransform(OptionSet<PaintBehavior> paintBehavior) const
1267 {
1268     if (!m_transform)
1269         return TransformationMatrix();
1270     
1271     if (paintBehavior & PaintBehavior::FlattenCompositingLayers) {
1272         TransformationMatrix matrix = *m_transform;
1273         makeMatrixRenderable(matrix, false /* flatten 3d */);
1274         return matrix;
1275     }
1276
1277     return *m_transform;
1278 }
1279
1280 RenderLayer* RenderLayer::enclosingOverflowClipLayer(IncludeSelfOrNot includeSelf) const
1281 {
1282     const RenderLayer* layer = (includeSelf == IncludeSelf) ? this : parent();
1283     while (layer) {
1284         if (layer->renderer().hasOverflowClip())
1285             return const_cast<RenderLayer*>(layer);
1286
1287         layer = layer->parent();
1288     }
1289     return nullptr;
1290 }
1291
1292 // FIXME: This is terrible. Bring back a cached bit for this someday. This crawl is going to slow down all
1293 // painting of content inside paginated layers.
1294 bool RenderLayer::hasCompositedLayerInEnclosingPaginationChain() const
1295 {
1296     // No enclosing layer means no compositing in the chain.
1297     if (!m_enclosingPaginationLayer)
1298         return false;
1299     
1300     // If the enclosing layer is composited, we don't have to check anything in between us and that
1301     // layer.
1302     if (m_enclosingPaginationLayer->isComposited())
1303         return true;
1304
1305     // If we are the enclosing pagination layer, then we can't be composited or we'd have passed the
1306     // previous check.
1307     if (m_enclosingPaginationLayer == this)
1308         return false;
1309
1310     // The enclosing paginated layer is our ancestor and is not composited, so we have to check
1311     // intermediate layers between us and the enclosing pagination layer. Start with our own layer.
1312     if (isComposited())
1313         return true;
1314     
1315     // For normal flow layers, we can recur up the layer tree.
1316     if (isNormalFlowOnly())
1317         return parent()->hasCompositedLayerInEnclosingPaginationChain();
1318     
1319     // Otherwise we have to go up the containing block chain. Find the first enclosing
1320     // containing block layer ancestor, and check that.
1321     for (const auto* containingBlock = renderer().containingBlock(); containingBlock && !is<RenderView>(*containingBlock); containingBlock = containingBlock->containingBlock()) {
1322         if (containingBlock->hasLayer())
1323             return containingBlock->layer()->hasCompositedLayerInEnclosingPaginationChain();
1324     }
1325     return false;
1326 }
1327
1328 void RenderLayer::updatePagination()
1329 {
1330     m_enclosingPaginationLayer = nullptr;
1331     
1332     if (!parent())
1333         return;
1334     
1335     // Each layer that is inside a multicolumn flow thread has to be checked individually and
1336     // genuinely know if it is going to have to split itself up when painting only its contents (and not any other descendant
1337     // layers). We track an enclosingPaginationLayer instead of using a simple bit, since we want to be able to get back
1338     // to that layer easily.
1339     if (renderer().isInFlowRenderFragmentedFlow()) {
1340         m_enclosingPaginationLayer = makeWeakPtr(*this);
1341         return;
1342     }
1343
1344     if (isNormalFlowOnly()) {
1345         // Content inside a transform is not considered to be paginated, since we simply
1346         // paint the transform multiple times in each column, so we don't have to use
1347         // fragments for the transformed content.
1348         if (parent()->hasTransform())
1349             m_enclosingPaginationLayer = nullptr;
1350         else
1351             m_enclosingPaginationLayer = makeWeakPtr(parent()->enclosingPaginationLayer(IncludeCompositedPaginatedLayers));
1352         return;
1353     }
1354
1355     // For the new columns code, we want to walk up our containing block chain looking for an enclosing layer. Once
1356     // we find one, then we just check its pagination status.
1357     for (const auto* containingBlock = renderer().containingBlock(); containingBlock && !is<RenderView>(*containingBlock); containingBlock = containingBlock->containingBlock()) {
1358         if (containingBlock->hasLayer()) {
1359             // Content inside a transform is not considered to be paginated, since we simply
1360             // paint the transform multiple times in each column, so we don't have to use
1361             // fragments for the transformed content.
1362             if (containingBlock->layer()->hasTransform())
1363                 m_enclosingPaginationLayer = nullptr;
1364             else
1365                 m_enclosingPaginationLayer = makeWeakPtr(containingBlock->layer()->enclosingPaginationLayer(IncludeCompositedPaginatedLayers));
1366             return;
1367         }
1368     }
1369 }
1370
1371 void RenderLayer::setHasVisibleContent()
1372
1373     if (m_hasVisibleContent && !m_visibleContentStatusDirty) {
1374         ASSERT(!parent() || parent()->hasVisibleDescendant());
1375         return;
1376     }
1377
1378     m_visibleContentStatusDirty = false; 
1379     m_hasVisibleContent = true;
1380     computeRepaintRects(renderer().containerForRepaint());
1381     if (!isNormalFlowOnly()) {
1382         // We don't collect invisible layers in z-order lists if we are not in compositing mode.
1383         // As we became visible, we need to dirty our stacking containers ancestors to be properly
1384         // collected. FIXME: When compositing, we could skip this dirtying phase.
1385         for (RenderLayer* sc = stackingContext(); sc; sc = sc->stackingContext()) {
1386             sc->dirtyZOrderLists();
1387             if (sc->hasVisibleContent())
1388                 break;
1389         }
1390     }
1391
1392     if (parent())
1393         parent()->setAncestorChainHasVisibleDescendant();
1394 }
1395
1396 void RenderLayer::dirtyVisibleContentStatus() 
1397
1398     m_visibleContentStatusDirty = true; 
1399     if (parent())
1400         parent()->dirtyAncestorChainVisibleDescendantStatus();
1401 }
1402
1403 void RenderLayer::dirtyAncestorChainVisibleDescendantStatus()
1404 {
1405     for (RenderLayer* layer = this; layer; layer = layer->parent()) {
1406         if (layer->m_visibleDescendantStatusDirty)
1407             break;
1408
1409         layer->m_visibleDescendantStatusDirty = true;
1410     }
1411 }
1412
1413 void RenderLayer::setAncestorChainHasVisibleDescendant()
1414 {
1415     for (RenderLayer* layer = this; layer; layer = layer->parent()) {
1416         if (!layer->m_visibleDescendantStatusDirty && layer->hasVisibleDescendant())
1417             break;
1418
1419         layer->m_hasVisibleDescendant = true;
1420         layer->m_visibleDescendantStatusDirty = false;
1421     }
1422 }
1423
1424 void RenderLayer::updateDescendantDependentFlags()
1425 {
1426     if (m_visibleDescendantStatusDirty || m_hasSelfPaintingLayerDescendantDirty || hasNotIsolatedBlendingDescendantsStatusDirty()) {
1427         bool hasVisibleDescendant = false;
1428         bool hasSelfPaintingLayerDescendant = false;
1429 #if ENABLE(CSS_COMPOSITING)
1430         bool hasNotIsolatedBlendingDescendants = false;
1431 #endif
1432
1433         for (RenderLayer* child = firstChild(); child; child = child->nextSibling()) {
1434             child->updateDescendantDependentFlags();
1435
1436             hasVisibleDescendant |= child->m_hasVisibleContent || child->m_hasVisibleDescendant;
1437             hasSelfPaintingLayerDescendant |= child->isSelfPaintingLayer() || child->hasSelfPaintingLayerDescendant();
1438 #if ENABLE(CSS_COMPOSITING)
1439             hasNotIsolatedBlendingDescendants |= child->hasBlendMode() || (child->hasNotIsolatedBlendingDescendants() && !child->isolatesBlending());
1440 #endif
1441
1442             bool allFlagsSet = hasVisibleDescendant && hasSelfPaintingLayerDescendant;
1443 #if ENABLE(CSS_COMPOSITING)
1444             allFlagsSet &= hasNotIsolatedBlendingDescendants;
1445 #endif
1446             if (allFlagsSet)
1447                 break;
1448         }
1449
1450         m_hasVisibleDescendant = hasVisibleDescendant;
1451         m_visibleDescendantStatusDirty = false;
1452         m_hasSelfPaintingLayerDescendant = hasSelfPaintingLayerDescendant;
1453         m_hasSelfPaintingLayerDescendantDirty = false;
1454
1455 #if ENABLE(CSS_COMPOSITING)
1456         m_hasNotIsolatedBlendingDescendants = hasNotIsolatedBlendingDescendants;
1457         if (m_hasNotIsolatedBlendingDescendantsStatusDirty) {
1458             m_hasNotIsolatedBlendingDescendantsStatusDirty = false;
1459             updateSelfPaintingLayer();
1460         }
1461 #endif
1462     }
1463
1464     if (m_visibleContentStatusDirty) {
1465         if (renderer().style().visibility() == Visibility::Visible)
1466             m_hasVisibleContent = true;
1467         else {
1468             // layer may be hidden but still have some visible content, check for this
1469             m_hasVisibleContent = false;
1470             RenderObject* r = renderer().firstChild();
1471             while (r) {
1472                 if (r->style().visibility() == Visibility::Visible && !r->hasLayer()) {
1473                     m_hasVisibleContent = true;
1474                     break;
1475                 }
1476                 RenderObject* child = nullptr;
1477                 if (!r->hasLayer() && (child = r->firstChildSlow()))
1478                     r = child;
1479                 else if (r->nextSibling())
1480                     r = r->nextSibling();
1481                 else {
1482                     do {
1483                         r = r->parent();
1484                         if (r == &renderer())
1485                             r = nullptr;
1486                     } while (r && !r->nextSibling());
1487                     if (r)
1488                         r = r->nextSibling();
1489                 }
1490             }
1491         }    
1492         m_visibleContentStatusDirty = false; 
1493     }
1494 }
1495
1496 void RenderLayer::dirty3DTransformedDescendantStatus()
1497 {
1498     RenderLayer* curr = stackingContext();
1499     if (curr)
1500         curr->m_3DTransformedDescendantStatusDirty = true;
1501         
1502     // This propagates up through preserve-3d hierarchies to the enclosing flattening layer.
1503     // Note that preserves3D() creates stacking context, so we can just run up the stacking containers.
1504     while (curr && curr->preserves3D()) {
1505         curr->m_3DTransformedDescendantStatusDirty = true;
1506         curr = curr->stackingContext();
1507     }
1508 }
1509
1510 // Return true if this layer or any preserve-3d descendants have 3d.
1511 bool RenderLayer::update3DTransformedDescendantStatus()
1512 {
1513     if (m_3DTransformedDescendantStatusDirty) {
1514         m_has3DTransformedDescendant = false;
1515
1516         updateZOrderLists();
1517
1518         // Transformed or preserve-3d descendants can only be in the z-order lists, not
1519         // in the normal flow list, so we only need to check those.
1520         for (auto* layer : positiveZOrderLayers())
1521             m_has3DTransformedDescendant |= layer->update3DTransformedDescendantStatus();
1522
1523         // Now check our negative z-index children.
1524         for (auto* layer : negativeZOrderLayers())
1525             m_has3DTransformedDescendant |= layer->update3DTransformedDescendantStatus();
1526         
1527         m_3DTransformedDescendantStatusDirty = false;
1528     }
1529     
1530     // If we live in a 3d hierarchy, then the layer at the root of that hierarchy needs
1531     // the m_has3DTransformedDescendant set.
1532     if (preserves3D())
1533         return has3DTransform() || m_has3DTransformedDescendant;
1534
1535     return has3DTransform();
1536 }
1537
1538 bool RenderLayer::updateLayerPosition(OptionSet<UpdateLayerPositionsFlag>* flags)
1539 {
1540     LayoutPoint localPoint;
1541     LayoutSize inlineBoundingBoxOffset; // We don't put this into the RenderLayer x/y for inlines, so we need to subtract it out when done.
1542     if (renderer().isInline() && is<RenderInline>(renderer())) {
1543         auto& inlineFlow = downcast<RenderInline>(renderer());
1544         IntRect lineBox = inlineFlow.linesBoundingBox();
1545         setSize(lineBox.size());
1546         inlineBoundingBoxOffset = toLayoutSize(lineBox.location());
1547         localPoint += inlineBoundingBoxOffset;
1548     } else if (RenderBox* box = renderBox()) {
1549         // FIXME: Is snapping the size really needed here for the RenderBox case?
1550         auto newSize = snappedIntRect(box->frameRect()).size();
1551         if (newSize != size()) {
1552             if (is<RenderWidget>(*box) && downcast<RenderWidget>(*box).requiresAcceleratedCompositing()) {
1553                 // Trigger RenderLayerCompositor::requiresCompositingForFrame() which depends on the contentBoxRect size.
1554                 setNeedsPostLayoutCompositingUpdate();
1555             }
1556
1557             if (flags && renderer().hasOverflowClip())
1558                 flags->add(ContainingClippingLayerChangedSize);
1559
1560             setSize(newSize);
1561         }
1562         
1563         box->applyTopLeftLocationOffset(localPoint);
1564     }
1565
1566     if (!renderer().isOutOfFlowPositioned()) {
1567         auto* ancestor = renderer().parent();
1568         // We must adjust our position by walking up the render tree looking for the
1569         // nearest enclosing object with a layer.
1570         while (ancestor && !ancestor->hasLayer()) {
1571             if (is<RenderBox>(*ancestor) && !is<RenderTableRow>(*ancestor)) {
1572                 // Rows and cells share the same coordinate space (that of the section).
1573                 // Omit them when computing our xpos/ypos.
1574                 localPoint += downcast<RenderBox>(*ancestor).topLeftLocationOffset();
1575             }
1576             ancestor = ancestor->parent();
1577         }
1578         if (is<RenderTableRow>(ancestor)) {
1579             // Put ourselves into the row coordinate space.
1580             localPoint -= downcast<RenderTableRow>(*ancestor).topLeftLocationOffset();
1581         }
1582     }
1583     
1584     // Subtract our parent's scroll offset.
1585     RenderLayer* positionedParent;
1586     if (renderer().isOutOfFlowPositioned() && (positionedParent = enclosingAncestorForPosition(renderer().style().position()))) {
1587         // For positioned layers, we subtract out the enclosing positioned layer's scroll offset.
1588         if (positionedParent->renderer().hasOverflowClip())
1589             localPoint -= toLayoutSize(positionedParent->scrollPosition());
1590         
1591         if (renderer().isOutOfFlowPositioned() && positionedParent->renderer().isInFlowPositioned() && is<RenderInline>(positionedParent->renderer())) {
1592             LayoutSize offset = downcast<RenderInline>(positionedParent->renderer()).offsetForInFlowPositionedInline(&downcast<RenderBox>(renderer()));
1593             localPoint += offset;
1594         }
1595     } else if (parent()) {
1596         if (parent()->renderer().hasOverflowClip())
1597             localPoint -= toLayoutSize(parent()->scrollPosition());
1598     }
1599     
1600     bool positionOrOffsetChanged = false;
1601     if (renderer().isInFlowPositioned()) {
1602         LayoutSize newOffset = downcast<RenderBoxModelObject>(renderer()).offsetForInFlowPosition();
1603         positionOrOffsetChanged = newOffset != m_offsetForInFlowPosition;
1604         m_offsetForInFlowPosition = newOffset;
1605         localPoint.move(m_offsetForInFlowPosition);
1606     } else {
1607         m_offsetForInFlowPosition = LayoutSize();
1608     }
1609
1610     // FIXME: We'd really like to just get rid of the concept of a layer rectangle and rely on the renderers.
1611     localPoint -= inlineBoundingBoxOffset;
1612     
1613     positionOrOffsetChanged |= location() != localPoint;
1614     setLocation(localPoint);
1615     
1616     if (positionOrOffsetChanged && compositor().hasContentCompositingLayers()) {
1617         if (isComposited())
1618             setNeedsCompositingGeometryUpdate();
1619         // This layer's position can affect the location of a composited descendant (which may be a sibling in z-order),
1620         // so trigger a descendant walk from the paint-order parent.
1621         if (auto* paintParent = paintOrderParent())
1622             paintParent->setDescendantsNeedUpdateBackingAndHierarchyTraversal();
1623     }
1624
1625     return positionOrOffsetChanged;
1626 }
1627
1628 TransformationMatrix RenderLayer::perspectiveTransform() const
1629 {
1630     RenderBox* box = renderBox();
1631     if (!box)
1632         return TransformationMatrix();
1633     
1634     if (!box->hasTransformRelatedProperty())
1635         return TransformationMatrix();
1636
1637     const RenderStyle& style = box->style();
1638     if (!style.hasPerspective())
1639         return TransformationMatrix();
1640
1641     // Maybe fetch the perspective from the backing?
1642     const FloatRect borderBox = snapRectToDevicePixels(box->borderBoxRect(), box->document().deviceScaleFactor());
1643     float perspectiveOriginX = floatValueForLength(style.perspectiveOriginX(), borderBox.width());
1644     float perspectiveOriginY = floatValueForLength(style.perspectiveOriginY(), borderBox.height());
1645
1646     // A perspective origin of 0,0 makes the vanishing point in the center of the element.
1647     // We want it to be in the top-left, so subtract half the height and width.
1648     perspectiveOriginX -= borderBox.width() / 2.0f;
1649     perspectiveOriginY -= borderBox.height() / 2.0f;
1650     
1651     TransformationMatrix t;
1652     t.translate(perspectiveOriginX, perspectiveOriginY);
1653     t.applyPerspective(style.perspective());
1654     t.translate(-perspectiveOriginX, -perspectiveOriginY);
1655     
1656     return t;
1657 }
1658
1659 FloatPoint RenderLayer::perspectiveOrigin() const
1660 {
1661     if (!renderer().hasTransformRelatedProperty())
1662         return FloatPoint();
1663
1664     const LayoutRect borderBox = downcast<RenderBox>(renderer()).borderBoxRect();
1665     const RenderStyle& style = renderer().style();
1666
1667     return FloatPoint(floatValueForLength(style.perspectiveOriginX(), borderBox.width()),
1668                       floatValueForLength(style.perspectiveOriginY(), borderBox.height()));
1669 }
1670
1671 static inline bool isContainerForPositioned(RenderLayer& layer, PositionType position)
1672 {
1673     switch (position) {
1674     case PositionType::Fixed:
1675         return layer.renderer().canContainFixedPositionObjects();
1676
1677     case PositionType::Absolute:
1678         return layer.renderer().canContainAbsolutelyPositionedObjects();
1679     
1680     default:
1681         ASSERT_NOT_REACHED();
1682         return false;
1683     }
1684 }
1685
1686 bool RenderLayer::ancestorLayerIsInContainingBlockChain(const RenderLayer& ancestor, const RenderLayer* checkLimit) const
1687 {
1688     if (&ancestor == this)
1689         return true;
1690
1691     for (const auto* currentBlock = renderer().containingBlock(); currentBlock && !is<RenderView>(*currentBlock); currentBlock = currentBlock->containingBlock()) {
1692         auto* currLayer = currentBlock->layer();
1693         if (currLayer == &ancestor)
1694             return true;
1695         
1696         if (currLayer && currLayer == checkLimit)
1697             return false;
1698     }
1699     
1700     return false;
1701 }
1702
1703 RenderLayer* RenderLayer::enclosingAncestorForPosition(PositionType position) const
1704 {
1705     RenderLayer* curr = parent();
1706     while (curr && !isContainerForPositioned(*curr, position))
1707         curr = curr->parent();
1708
1709     return curr;
1710 }
1711
1712 static RenderLayer* enclosingFrameRenderLayer(const RenderLayer& layer)
1713 {
1714     auto* ownerElement = layer.renderer().document().ownerElement();
1715     if (!ownerElement)
1716         return nullptr;
1717
1718     auto* ownerRenderer = ownerElement->renderer();
1719     if (!ownerRenderer)
1720         return nullptr;
1721
1722     return ownerRenderer->enclosingLayer();
1723 }
1724
1725 static RenderLayer* parentLayerCrossFrame(const RenderLayer& layer)
1726 {
1727     if (auto* parent = layer.parent())
1728         return parent;
1729
1730     return enclosingFrameRenderLayer(layer);
1731 }
1732
1733 RenderLayer* RenderLayer::enclosingScrollableLayer() const
1734 {
1735     for (RenderLayer* nextLayer = parentLayerCrossFrame(*this); nextLayer; nextLayer = parentLayerCrossFrame(*nextLayer)) {
1736         if (is<RenderBox>(nextLayer->renderer()) && downcast<RenderBox>(nextLayer->renderer()).canBeScrolledAndHasScrollableArea())
1737             return nextLayer;
1738     }
1739
1740     return nullptr;
1741 }
1742
1743 IntRect RenderLayer::scrollableAreaBoundingBox(bool* isInsideFixed) const
1744 {
1745     return renderer().absoluteBoundingBoxRect(/* useTransforms */ true, isInsideFixed);
1746 }
1747
1748 bool RenderLayer::isRubberBandInProgress() const
1749 {
1750 #if ENABLE(RUBBER_BANDING)
1751     if (!scrollsOverflow())
1752         return false;
1753
1754     if (ScrollAnimator* scrollAnimator = existingScrollAnimator())
1755         return scrollAnimator->isRubberBandInProgress();
1756 #endif
1757
1758     return false;
1759 }
1760
1761 bool RenderLayer::forceUpdateScrollbarsOnMainThreadForPerformanceTesting() const
1762 {
1763     return renderer().settings().forceUpdateScrollbarsOnMainThreadForPerformanceTesting();
1764 }
1765
1766 RenderLayer* RenderLayer::enclosingTransformedAncestor() const
1767 {
1768     RenderLayer* curr = parent();
1769     while (curr && !curr->isRenderViewLayer() && !curr->transform())
1770         curr = curr->parent();
1771
1772     return curr;
1773 }
1774
1775 inline bool RenderLayer::shouldRepaintAfterLayout() const
1776 {
1777     if (m_repaintStatus == NeedsNormalRepaint)
1778         return true;
1779
1780     // Composited layers that were moved during a positioned movement only
1781     // layout, don't need to be repainted. They just need to be recomposited.
1782     ASSERT(m_repaintStatus == NeedsFullRepaintForPositionedMovementLayout);
1783     return !isComposited() || backing()->paintsIntoCompositedAncestor();
1784 }
1785
1786 void RenderLayer::setBackingProviderLayer(RenderLayer* backingProvider)
1787 {
1788     if (backingProvider == m_backingProviderLayer)
1789         return;
1790
1791     if (!renderer().renderTreeBeingDestroyed()) {
1792         clearRepaintRects();
1793         clearClipRectsIncludingDescendants();
1794     }
1795
1796     m_backingProviderLayer = makeWeakPtr(backingProvider);
1797 }
1798
1799 void RenderLayer::disconnectFromBackingProviderLayer()
1800 {
1801     if (!m_backingProviderLayer)
1802         return;
1803     
1804     ASSERT(m_backingProviderLayer->isComposited());
1805     if (m_backingProviderLayer->isComposited())
1806         m_backingProviderLayer->backing()->removeBackingSharingLayer(*this);
1807 }
1808
1809 bool compositedWithOwnBackingStore(const RenderLayer& layer)
1810 {
1811     return layer.isComposited() && !layer.backing()->paintsIntoCompositedAncestor();
1812 }
1813
1814 RenderLayer* RenderLayer::enclosingCompositingLayer(IncludeSelfOrNot includeSelf) const
1815 {
1816     if (includeSelf == IncludeSelf && isComposited())
1817         return const_cast<RenderLayer*>(this);
1818
1819     for (const RenderLayer* curr = paintOrderParent(); curr; curr = curr->paintOrderParent()) {
1820         if (curr->isComposited())
1821             return const_cast<RenderLayer*>(curr);
1822     }
1823          
1824     return nullptr;
1825 }
1826
1827 RenderLayer* RenderLayer::enclosingCompositingLayerForRepaint(IncludeSelfOrNot includeSelf) const
1828 {
1829     auto repaintTargetForLayer = [](const RenderLayer& layer) -> RenderLayer* {
1830         if (compositedWithOwnBackingStore(layer))
1831             return const_cast<RenderLayer*>(&layer);
1832         
1833         if (layer.paintsIntoProvidedBacking())
1834             return layer.backingProviderLayer();
1835         
1836         return nullptr;
1837     };
1838
1839     RenderLayer* repaintTarget = nullptr;
1840     if (includeSelf == IncludeSelf && (repaintTarget = repaintTargetForLayer(*this)))
1841         return repaintTarget;
1842
1843     for (const RenderLayer* curr = paintOrderParent(); curr; curr = curr->paintOrderParent()) {
1844         if ((repaintTarget = repaintTargetForLayer(*curr)))
1845             return repaintTarget;
1846     }
1847          
1848     return nullptr;
1849 }
1850
1851 RenderLayer* RenderLayer::enclosingFilterLayer(IncludeSelfOrNot includeSelf) const
1852 {
1853     const RenderLayer* curr = (includeSelf == IncludeSelf) ? this : parent();
1854     for (; curr; curr = curr->parent()) {
1855         if (curr->requiresFullLayerImageForFilters())
1856             return const_cast<RenderLayer*>(curr);
1857     }
1858     
1859     return nullptr;
1860 }
1861
1862 RenderLayer* RenderLayer::enclosingFilterRepaintLayer() const
1863 {
1864     for (const RenderLayer* curr = this; curr; curr = curr->parent()) {
1865         if ((curr != this && curr->requiresFullLayerImageForFilters()) || compositedWithOwnBackingStore(*curr) || curr->isRenderViewLayer())
1866             return const_cast<RenderLayer*>(curr);
1867     }
1868     return nullptr;
1869 }
1870
1871 // FIXME: This neeeds a better name.
1872 void RenderLayer::setFilterBackendNeedsRepaintingInRect(const LayoutRect& rect)
1873 {
1874     ASSERT(requiresFullLayerImageForFilters());
1875     ASSERT(m_filters);
1876
1877     if (rect.isEmpty())
1878         return;
1879     
1880     LayoutRect rectForRepaint = rect;
1881     renderer().style().filterOutsets().expandRect(rectForRepaint);
1882
1883     m_filters->expandDirtySourceRect(rectForRepaint);
1884     
1885     RenderLayer* parentLayer = enclosingFilterRepaintLayer();
1886     ASSERT(parentLayer);
1887     FloatQuad repaintQuad(rectForRepaint);
1888     LayoutRect parentLayerRect = renderer().localToContainerQuad(repaintQuad, &parentLayer->renderer()).enclosingBoundingBox();
1889
1890     if (parentLayer->isComposited()) {
1891         if (!parentLayer->backing()->paintsIntoWindow()) {
1892             parentLayer->setBackingNeedsRepaintInRect(parentLayerRect);
1893             return;
1894         }
1895         // If the painting goes to window, redirect the painting to the parent RenderView.
1896         parentLayer = renderer().view().layer();
1897         parentLayerRect = renderer().localToContainerQuad(repaintQuad, &parentLayer->renderer()).enclosingBoundingBox();
1898     }
1899
1900     if (parentLayer->paintsWithFilters()) {
1901         parentLayer->setFilterBackendNeedsRepaintingInRect(parentLayerRect);
1902         return;        
1903     }
1904     
1905     if (parentLayer->isRenderViewLayer()) {
1906         downcast<RenderView>(parentLayer->renderer()).repaintViewRectangle(parentLayerRect);
1907         return;
1908     }
1909     
1910     ASSERT_NOT_REACHED();
1911 }
1912
1913 bool RenderLayer::hasAncestorWithFilterOutsets() const
1914 {
1915     for (const RenderLayer* curr = this; curr; curr = curr->parent()) {
1916         if (curr->renderer().style().hasFilterOutsets())
1917             return true;
1918     }
1919     return false;
1920 }
1921
1922 RenderLayer* RenderLayer::clippingRootForPainting() const
1923 {
1924     if (isComposited())
1925         return const_cast<RenderLayer*>(this);
1926
1927     if (paintsIntoProvidedBacking())
1928         return backingProviderLayer();
1929
1930     const RenderLayer* current = this;
1931     while (current) {
1932         if (current->isRenderViewLayer())
1933             return const_cast<RenderLayer*>(current);
1934
1935         current = current->paintOrderParent();
1936         ASSERT(current);
1937         if (current->transform() || compositedWithOwnBackingStore(*current))
1938             return const_cast<RenderLayer*>(current);
1939
1940         if (current->paintsIntoProvidedBacking())
1941             return current->backingProviderLayer();
1942     }
1943
1944     ASSERT_NOT_REACHED();
1945     return nullptr;
1946 }
1947
1948 LayoutPoint RenderLayer::absoluteToContents(const LayoutPoint& absolutePoint) const
1949 {
1950     // We don't use convertToLayerCoords because it doesn't know about transforms
1951     return LayoutPoint(renderer().absoluteToLocal(absolutePoint, UseTransforms));
1952 }
1953
1954 bool RenderLayer::cannotBlitToWindow() const
1955 {
1956     if (isTransparent() || hasReflection() || hasTransform())
1957         return true;
1958     if (!parent())
1959         return false;
1960     return parent()->cannotBlitToWindow();
1961 }
1962
1963 RenderLayer* RenderLayer::transparentPaintingAncestor()
1964 {
1965     if (isComposited())
1966         return nullptr;
1967
1968     for (RenderLayer* curr = parent(); curr; curr = curr->parent()) {
1969         if (curr->isComposited())
1970             return nullptr;
1971         if (curr->isTransparent())
1972             return curr;
1973     }
1974     return nullptr;
1975 }
1976
1977 enum TransparencyClipBoxBehavior {
1978     PaintingTransparencyClipBox,
1979     HitTestingTransparencyClipBox
1980 };
1981
1982 enum TransparencyClipBoxMode {
1983     DescendantsOfTransparencyClipBox,
1984     RootOfTransparencyClipBox
1985 };
1986
1987 static LayoutRect transparencyClipBox(const RenderLayer&, const RenderLayer* rootLayer, TransparencyClipBoxBehavior, TransparencyClipBoxMode, OptionSet<PaintBehavior> = { });
1988
1989 static void expandClipRectForDescendantsAndReflection(LayoutRect& clipRect, const RenderLayer& layer, const RenderLayer* rootLayer,
1990     TransparencyClipBoxBehavior transparencyBehavior, OptionSet<PaintBehavior> paintBehavior)
1991 {
1992     // If we have a mask, then the clip is limited to the border box area (and there is
1993     // no need to examine child layers).
1994     if (!layer.renderer().hasMask()) {
1995         // Note: we don't have to walk z-order lists since transparent elements always establish
1996         // a stacking container. This means we can just walk the layer tree directly.
1997         for (RenderLayer* curr = layer.firstChild(); curr; curr = curr->nextSibling()) {
1998             if (!layer.isReflectionLayer(*curr))
1999                 clipRect.unite(transparencyClipBox(*curr, rootLayer, transparencyBehavior, DescendantsOfTransparencyClipBox, paintBehavior));
2000         }
2001     }
2002
2003     // If we have a reflection, then we need to account for that when we push the clip.  Reflect our entire
2004     // current transparencyClipBox to catch all child layers.
2005     // FIXME: Accelerated compositing will eventually want to do something smart here to avoid incorporating this
2006     // size into the parent layer.
2007     if (layer.renderer().hasReflection()) {
2008         LayoutSize delta = layer.offsetFromAncestor(rootLayer);
2009         clipRect.move(-delta);
2010         clipRect.unite(layer.renderBox()->reflectedRect(clipRect));
2011         clipRect.move(delta);
2012     }
2013 }
2014
2015 static LayoutRect transparencyClipBox(const RenderLayer& layer, const RenderLayer* rootLayer, TransparencyClipBoxBehavior transparencyBehavior,
2016     TransparencyClipBoxMode transparencyMode, OptionSet<PaintBehavior> paintBehavior)
2017 {
2018     // FIXME: Although this function completely ignores CSS-imposed clipping, we did already intersect with the
2019     // paintDirtyRect, and that should cut down on the amount we have to paint.  Still it
2020     // would be better to respect clips.
2021     
2022     if (rootLayer != &layer && ((transparencyBehavior == PaintingTransparencyClipBox && layer.paintsWithTransform(paintBehavior))
2023         || (transparencyBehavior == HitTestingTransparencyClipBox && layer.hasTransform()))) {
2024         // The best we can do here is to use enclosed bounding boxes to establish a "fuzzy" enough clip to encompass
2025         // the transformed layer and all of its children.
2026         RenderLayer::PaginationInclusionMode mode = transparencyBehavior == HitTestingTransparencyClipBox ? RenderLayer::IncludeCompositedPaginatedLayers : RenderLayer::ExcludeCompositedPaginatedLayers;
2027         const RenderLayer* paginationLayer = transparencyMode == DescendantsOfTransparencyClipBox ? layer.enclosingPaginationLayer(mode) : nullptr;
2028         const RenderLayer* rootLayerForTransform = paginationLayer ? paginationLayer : rootLayer;
2029         LayoutSize delta = layer.offsetFromAncestor(rootLayerForTransform);
2030
2031         TransformationMatrix transform;
2032         transform.translate(delta.width(), delta.height());
2033         transform.multiply(*layer.transform());
2034
2035         // We don't use fragment boxes when collecting a transformed layer's bounding box, since it always
2036         // paints unfragmented.
2037         LayoutRect clipRect = layer.boundingBox(&layer);
2038         expandClipRectForDescendantsAndReflection(clipRect, layer, &layer, transparencyBehavior, paintBehavior);
2039         layer.renderer().style().filterOutsets().expandRect(clipRect);
2040         LayoutRect result = transform.mapRect(clipRect);
2041         if (!paginationLayer)
2042             return result;
2043         
2044         // We have to break up the transformed extent across our columns.
2045         // Split our box up into the actual fragment boxes that render in the columns/pages and unite those together to
2046         // get our true bounding box.
2047         auto& enclosingFragmentedFlow = downcast<RenderFragmentedFlow>(paginationLayer->renderer());
2048         result = enclosingFragmentedFlow.fragmentsBoundingBox(result);
2049         result.move(paginationLayer->offsetFromAncestor(rootLayer));
2050         return result;
2051     }
2052     
2053     LayoutRect clipRect = layer.boundingBox(rootLayer, layer.offsetFromAncestor(rootLayer), transparencyBehavior == HitTestingTransparencyClipBox ? RenderLayer::UseFragmentBoxesIncludingCompositing : RenderLayer::UseFragmentBoxesExcludingCompositing);
2054     expandClipRectForDescendantsAndReflection(clipRect, layer, rootLayer, transparencyBehavior, paintBehavior);
2055     layer.renderer().style().filterOutsets().expandRect(clipRect);
2056
2057     return clipRect;
2058 }
2059
2060 static LayoutRect paintingExtent(const RenderLayer& currentLayer, const RenderLayer* rootLayer, const LayoutRect& paintDirtyRect, OptionSet<PaintBehavior> paintBehavior)
2061 {
2062     return intersection(transparencyClipBox(currentLayer, rootLayer, PaintingTransparencyClipBox, RootOfTransparencyClipBox, paintBehavior), paintDirtyRect);
2063 }
2064
2065 void RenderLayer::beginTransparencyLayers(GraphicsContext& context, const LayerPaintingInfo& paintingInfo, const LayoutRect& dirtyRect)
2066 {
2067     if (context.paintingDisabled() || (paintsWithTransparency(paintingInfo.paintBehavior) && m_usedTransparency))
2068         return;
2069
2070     RenderLayer* ancestor = transparentPaintingAncestor();
2071     if (ancestor)
2072         ancestor->beginTransparencyLayers(context, paintingInfo, dirtyRect);
2073     
2074     if (paintsWithTransparency(paintingInfo.paintBehavior)) {
2075         ASSERT(isCSSStackingContext());
2076         m_usedTransparency = true;
2077         context.save();
2078         LayoutRect adjustedClipRect = paintingExtent(*this, paintingInfo.rootLayer, dirtyRect, paintingInfo.paintBehavior);
2079         adjustedClipRect.move(paintingInfo.subpixelOffset);
2080         FloatRect pixelSnappedClipRect = snapRectToDevicePixels(adjustedClipRect, renderer().document().deviceScaleFactor());
2081         context.clip(pixelSnappedClipRect);
2082
2083 #if ENABLE(CSS_COMPOSITING)
2084         bool usesCompositeOperation = hasBlendMode() && !(renderer().isSVGRoot() && parent() && parent()->isRenderViewLayer());
2085         if (usesCompositeOperation)
2086             context.setCompositeOperation(context.compositeOperation(), blendMode());
2087 #endif
2088
2089         context.beginTransparencyLayer(renderer().opacity());
2090
2091 #if ENABLE(CSS_COMPOSITING)
2092         if (usesCompositeOperation)
2093             context.setCompositeOperation(context.compositeOperation(), BlendMode::Normal);
2094 #endif
2095
2096 #ifdef REVEAL_TRANSPARENCY_LAYERS
2097         context.setFillColor(Color(0.0f, 0.0f, 0.5f, 0.2f));
2098         context.fillRect(pixelSnappedClipRect);
2099 #endif
2100     }
2101 }
2102
2103 #if PLATFORM(IOS_FAMILY)
2104 void RenderLayer::willBeDestroyed()
2105 {
2106     if (RenderLayerBacking* layerBacking = backing())
2107         layerBacking->layerWillBeDestroyed();
2108 }
2109 #endif
2110
2111 bool RenderLayer::isDescendantOf(const RenderLayer& layer) const
2112 {
2113     for (auto* ancestor = this; ancestor; ancestor = ancestor->parent()) {
2114         if (&layer == ancestor)
2115             return true;
2116     }
2117     return false;
2118 }
2119
2120 void RenderLayer::convertToPixelSnappedLayerCoords(const RenderLayer* ancestorLayer, IntPoint& roundedLocation, ColumnOffsetAdjustment adjustForColumns) const
2121 {
2122     LayoutPoint location = convertToLayerCoords(ancestorLayer, roundedLocation, adjustForColumns);
2123     roundedLocation = roundedIntPoint(location);
2124 }
2125
2126 // Returns the layer reached on the walk up towards the ancestor.
2127 static inline const RenderLayer* accumulateOffsetTowardsAncestor(const RenderLayer* layer, const RenderLayer* ancestorLayer, LayoutPoint& location, RenderLayer::ColumnOffsetAdjustment adjustForColumns)
2128 {
2129     ASSERT(ancestorLayer != layer);
2130
2131     const RenderLayerModelObject& renderer = layer->renderer();
2132     auto position = renderer.style().position();
2133
2134     // FIXME: Special casing RenderFragmentedFlow so much for fixed positioning here is not great.
2135     RenderFragmentedFlow* fixedFragmentedFlowContainer = position == PositionType::Fixed ? renderer.enclosingFragmentedFlow() : nullptr;
2136     if (fixedFragmentedFlowContainer && !fixedFragmentedFlowContainer->isOutOfFlowPositioned())
2137         fixedFragmentedFlowContainer = nullptr;
2138
2139     // FIXME: Positioning of out-of-flow(fixed, absolute) elements collected in a RenderFragmentedFlow
2140     // may need to be revisited in a future patch.
2141     // If the fixed renderer is inside a RenderFragmentedFlow, we should not compute location using localToAbsolute,
2142     // since localToAbsolute maps the coordinates from named flow to regions coordinates and regions can be
2143     // positioned in a completely different place in the viewport (RenderView).
2144     if (position == PositionType::Fixed && !fixedFragmentedFlowContainer && (!ancestorLayer || ancestorLayer == renderer.view().layer())) {
2145         // If the fixed layer's container is the root, just add in the offset of the view. We can obtain this by calling
2146         // localToAbsolute() on the RenderView.
2147         FloatPoint absPos = renderer.localToAbsolute(FloatPoint(), IsFixed);
2148         location += LayoutSize(absPos.x(), absPos.y());
2149         return ancestorLayer;
2150     }
2151
2152     // For the fixed positioned elements inside a render flow thread, we should also skip the code path below
2153     // Otherwise, for the case of ancestorLayer == rootLayer and fixed positioned element child of a transformed
2154     // element in render flow thread, we will hit the fixed positioned container before hitting the ancestor layer.
2155     if (position == PositionType::Fixed && !fixedFragmentedFlowContainer) {
2156         // For a fixed layers, we need to walk up to the root to see if there's a fixed position container
2157         // (e.g. a transformed layer). It's an error to call offsetFromAncestor() across a layer with a transform,
2158         // so we should always find the ancestor at or before we find the fixed position container.
2159         RenderLayer* fixedPositionContainerLayer = nullptr;
2160         bool foundAncestor = false;
2161         for (RenderLayer* currLayer = layer->parent(); currLayer; currLayer = currLayer->parent()) {
2162             if (currLayer == ancestorLayer)
2163                 foundAncestor = true;
2164
2165             if (isContainerForPositioned(*currLayer, PositionType::Fixed)) {
2166                 fixedPositionContainerLayer = currLayer;
2167                 ASSERT_UNUSED(foundAncestor, foundAncestor);
2168                 break;
2169             }
2170         }
2171         
2172         ASSERT(fixedPositionContainerLayer); // We should have hit the RenderView's layer at least.
2173
2174         if (fixedPositionContainerLayer != ancestorLayer) {
2175             LayoutSize fixedContainerCoords = layer->offsetFromAncestor(fixedPositionContainerLayer);
2176             LayoutSize ancestorCoords = ancestorLayer->offsetFromAncestor(fixedPositionContainerLayer);
2177             location += (fixedContainerCoords - ancestorCoords);
2178             return ancestorLayer;
2179         }
2180     }
2181
2182     if (position == PositionType::Fixed && fixedFragmentedFlowContainer) {
2183         ASSERT(ancestorLayer);
2184         if (ancestorLayer->isOutOfFlowRenderFragmentedFlow()) {
2185             location += toLayoutSize(layer->location());
2186             return ancestorLayer;
2187         }
2188
2189         if (ancestorLayer == renderer.view().layer()) {
2190             // Add location in flow thread coordinates.
2191             location += toLayoutSize(layer->location());
2192
2193             // Add flow thread offset in view coordinates since the view may be scrolled.
2194             FloatPoint absPos = renderer.view().localToAbsolute(FloatPoint(), IsFixed);
2195             location += LayoutSize(absPos.x(), absPos.y());
2196             return ancestorLayer;
2197         }
2198     }
2199
2200     RenderLayer* parentLayer;
2201     if (position == PositionType::Absolute || position == PositionType::Fixed) {
2202         // Do what enclosingAncestorForPosition() does, but check for ancestorLayer along the way.
2203         parentLayer = layer->parent();
2204         bool foundAncestorFirst = false;
2205         while (parentLayer) {
2206             // RenderFragmentedFlow is a positioned container, child of RenderView, positioned at (0,0).
2207             // This implies that, for out-of-flow positioned elements inside a RenderFragmentedFlow,
2208             // we are bailing out before reaching root layer.
2209             if (isContainerForPositioned(*parentLayer, position))
2210                 break;
2211
2212             if (parentLayer == ancestorLayer) {
2213                 foundAncestorFirst = true;
2214                 break;
2215             }
2216
2217             parentLayer = parentLayer->parent();
2218         }
2219
2220         // We should not reach RenderView layer past the RenderFragmentedFlow layer for any
2221         // children of the RenderFragmentedFlow.
2222         if (renderer.enclosingFragmentedFlow() && !layer->isOutOfFlowRenderFragmentedFlow())
2223             ASSERT(parentLayer != renderer.view().layer());
2224
2225         if (foundAncestorFirst) {
2226             // Found ancestorLayer before the abs. positioned container, so compute offset of both relative
2227             // to enclosingAncestorForPosition and subtract.
2228             RenderLayer* positionedAncestor = parentLayer->enclosingAncestorForPosition(position);
2229             LayoutSize thisCoords = layer->offsetFromAncestor(positionedAncestor);
2230             LayoutSize ancestorCoords = ancestorLayer->offsetFromAncestor(positionedAncestor);
2231             location += (thisCoords - ancestorCoords);
2232             return ancestorLayer;
2233         }
2234     } else
2235         parentLayer = layer->parent();
2236     
2237     if (!parentLayer)
2238         return nullptr;
2239
2240     location += toLayoutSize(layer->location());
2241
2242     if (adjustForColumns == RenderLayer::AdjustForColumns) {
2243         if (RenderLayer* parentLayer = layer->parent()) {
2244             if (is<RenderMultiColumnFlow>(parentLayer->renderer())) {
2245                 RenderFragmentContainer* fragment = downcast<RenderMultiColumnFlow>(parentLayer->renderer()).physicalTranslationFromFlowToFragment(location);
2246                 if (fragment)
2247                     location.moveBy(fragment->topLeftLocation() + -parentLayer->renderBox()->topLeftLocation());
2248             }
2249         }
2250     }
2251
2252     return parentLayer;
2253 }
2254
2255 LayoutPoint RenderLayer::convertToLayerCoords(const RenderLayer* ancestorLayer, const LayoutPoint& location, ColumnOffsetAdjustment adjustForColumns) const
2256 {
2257     if (ancestorLayer == this)
2258         return location;
2259
2260     const RenderLayer* currLayer = this;
2261     LayoutPoint locationInLayerCoords = location;
2262     while (currLayer && currLayer != ancestorLayer)
2263         currLayer = accumulateOffsetTowardsAncestor(currLayer, ancestorLayer, locationInLayerCoords, adjustForColumns);
2264     return locationInLayerCoords;
2265 }
2266
2267 LayoutSize RenderLayer::offsetFromAncestor(const RenderLayer* ancestorLayer, ColumnOffsetAdjustment adjustForColumns) const
2268 {
2269     return toLayoutSize(convertToLayerCoords(ancestorLayer, LayoutPoint(), adjustForColumns));
2270 }
2271
2272 bool RenderLayer::canUseCompositedScrolling() const
2273 {
2274     bool isVisible = renderer().style().visibility() == Visibility::Visible;
2275     if (renderer().settings().asyncOverflowScrollingEnabled())
2276         return isVisible && scrollsOverflow();
2277
2278 #if PLATFORM(IOS_FAMILY) && ENABLE(OVERFLOW_SCROLLING_TOUCH)
2279     return isVisible && scrollsOverflow() && (renderer().style().useTouchOverflowScrolling() || renderer().settings().alwaysUseAcceleratedOverflowScroll());
2280 #else
2281     return false;
2282 #endif
2283 }
2284
2285 bool RenderLayer::hasCompositedScrollableOverflow() const
2286 {
2287     return canUseCompositedScrolling() && (hasScrollableHorizontalOverflow() || hasScrollableVerticalOverflow());
2288 }
2289
2290 #if ENABLE(IOS_TOUCH_EVENTS)
2291 bool RenderLayer::handleTouchEvent(const PlatformTouchEvent& touchEvent)
2292 {
2293     // If we have accelerated scrolling, let the scrolling be handled outside of WebKit.
2294     if (hasCompositedScrollableOverflow())
2295         return false;
2296
2297     return ScrollableArea::handleTouchEvent(touchEvent);
2298 }
2299
2300 void RenderLayer::registerAsTouchEventListenerForScrolling()
2301 {
2302     if (!renderer().element() || m_registeredAsTouchEventListenerForScrolling)
2303         return;
2304     
2305     renderer().document().addTouchEventHandler(*renderer().element());
2306     m_registeredAsTouchEventListenerForScrolling = true;
2307 }
2308
2309 void RenderLayer::unregisterAsTouchEventListenerForScrolling()
2310 {
2311     if (!renderer().element() || !m_registeredAsTouchEventListenerForScrolling)
2312         return;
2313
2314     renderer().document().removeTouchEventHandler(*renderer().element());
2315     m_registeredAsTouchEventListenerForScrolling = false;
2316 }
2317 #endif // ENABLE(IOS_TOUCH_EVENTS)
2318
2319 // FIXME: this is only valid after we've made layers.
2320 bool RenderLayer::usesCompositedScrolling() const
2321 {
2322     return isComposited() && backing()->hasScrollingLayer();
2323 }
2324
2325 // FIXME: this is only valid after we've made layers.
2326 bool RenderLayer::usesAsyncScrolling() const
2327 {
2328     return compositor().useCoordinatedScrollingForLayer(*this);
2329 }
2330
2331 static inline int adjustedScrollDelta(int beginningDelta)
2332 {
2333     // This implemention matches Firefox's.
2334     // http://mxr.mozilla.org/firefox/source/toolkit/content/widgets/browser.xml#856.
2335     const int speedReducer = 12;
2336
2337     int adjustedDelta = beginningDelta / speedReducer;
2338     if (adjustedDelta > 1)
2339         adjustedDelta = static_cast<int>(adjustedDelta * sqrt(static_cast<double>(adjustedDelta))) - 1;
2340     else if (adjustedDelta < -1)
2341         adjustedDelta = static_cast<int>(adjustedDelta * sqrt(static_cast<double>(-adjustedDelta))) + 1;
2342
2343     return adjustedDelta;
2344 }
2345
2346 static inline IntSize adjustedScrollDelta(const IntSize& delta)
2347 {
2348     return IntSize(adjustedScrollDelta(delta.width()), adjustedScrollDelta(delta.height()));
2349 }
2350
2351 void RenderLayer::panScrollFromPoint(const IntPoint& sourcePoint)
2352 {
2353     IntPoint lastKnownMousePosition = renderer().frame().eventHandler().lastKnownMousePosition();
2354     
2355     // We need to check if the last known mouse position is out of the window. When the mouse is out of the window, the position is incoherent
2356     static IntPoint previousMousePosition;
2357     if (lastKnownMousePosition.x() < 0 || lastKnownMousePosition.y() < 0)
2358         lastKnownMousePosition = previousMousePosition;
2359     else
2360         previousMousePosition = lastKnownMousePosition;
2361
2362     IntSize delta = lastKnownMousePosition - sourcePoint;
2363
2364     if (abs(delta.width()) <= ScrollView::noPanScrollRadius) // at the center we let the space for the icon
2365         delta.setWidth(0);
2366     if (abs(delta.height()) <= ScrollView::noPanScrollRadius)
2367         delta.setHeight(0);
2368
2369     scrollByRecursively(adjustedScrollDelta(delta));
2370 }
2371
2372 // FIXME: unify with the scrollRectToVisible() code below.
2373 void RenderLayer::scrollByRecursively(const IntSize& delta, ScrollableArea** scrolledArea)
2374 {
2375     if (delta.isZero())
2376         return;
2377
2378     bool restrictedByLineClamp = false;
2379     if (renderer().parent())
2380         restrictedByLineClamp = !renderer().parent()->style().lineClamp().isNone();
2381
2382     if (renderer().hasOverflowClip() && !restrictedByLineClamp) {
2383         ScrollOffset newScrollOffset = scrollOffset() + delta;
2384         scrollToOffset(newScrollOffset);
2385         if (scrolledArea)
2386             *scrolledArea = this;
2387
2388         // If this layer can't do the scroll we ask the next layer up that can scroll to try
2389         IntSize remainingScrollOffset = newScrollOffset - scrollOffset();
2390         if (!remainingScrollOffset.isZero() && renderer().parent()) {
2391             if (RenderLayer* scrollableLayer = enclosingScrollableLayer())
2392                 scrollableLayer->scrollByRecursively(remainingScrollOffset, scrolledArea);
2393
2394             renderer().frame().eventHandler().updateAutoscrollRenderer();
2395         }
2396     } else {
2397         // If we are here, we were called on a renderer that can be programmatically scrolled, but doesn't
2398         // have an overflow clip. Which means that it is a document node that can be scrolled.
2399         renderer().view().frameView().scrollBy(delta);
2400         if (scrolledArea)
2401             *scrolledArea = &renderer().view().frameView();
2402
2403         // FIXME: If we didn't scroll the whole way, do we want to try looking at the frames ownerElement? 
2404         // https://bugs.webkit.org/show_bug.cgi?id=28237
2405     }
2406 }
2407
2408 void RenderLayer::setPostLayoutScrollPosition(Optional<ScrollPosition> position)
2409 {
2410     m_postLayoutScrollPosition = position;
2411 }
2412
2413 void RenderLayer::applyPostLayoutScrollPositionIfNeeded()
2414 {
2415     if (!m_postLayoutScrollPosition)
2416         return;
2417
2418     scrollToOffset(scrollOffsetFromPosition(m_postLayoutScrollPosition.value()));
2419     m_postLayoutScrollPosition = WTF::nullopt;
2420 }
2421
2422 void RenderLayer::scrollToXPosition(int x, ScrollType scrollType, ScrollClamping clamping)
2423 {
2424     ScrollPosition position(x, m_scrollPosition.y());
2425     scrollToOffset(scrollOffsetFromPosition(position), scrollType, clamping);
2426 }
2427
2428 void RenderLayer::scrollToYPosition(int y, ScrollType scrollType, ScrollClamping clamping)
2429 {
2430     ScrollPosition position(m_scrollPosition.x(), y);
2431     scrollToOffset(scrollOffsetFromPosition(position), scrollType, clamping);
2432 }
2433
2434 ScrollOffset RenderLayer::clampScrollOffset(const ScrollOffset& scrollOffset) const
2435 {
2436     return scrollOffset.constrainedBetween(IntPoint(), maximumScrollOffset());
2437 }
2438
2439 void RenderLayer::scrollToOffset(const ScrollOffset& scrollOffset, ScrollType scrollType, ScrollClamping clamping)
2440 {
2441     ScrollOffset clampedScrollOffset = clamping == ScrollClamping::Clamped ? clampScrollOffset(scrollOffset) : scrollOffset;
2442     if (clampedScrollOffset == this->scrollOffset())
2443         return;
2444
2445     auto previousScrollType = currentScrollType();
2446     setCurrentScrollType(scrollType);
2447
2448     bool handled = false;
2449 #if ENABLE(ASYNC_SCROLLING)
2450     if (ScrollingCoordinator* scrollingCoordinator = page().scrollingCoordinator())
2451         handled = scrollingCoordinator->requestScrollPositionUpdate(*this, scrollPositionFromOffset(clampedScrollOffset));
2452 #endif
2453
2454     if (!handled)
2455         scrollToOffsetWithoutAnimation(clampedScrollOffset, clamping);
2456
2457     setCurrentScrollType(previousScrollType);
2458 }
2459
2460 void RenderLayer::scrollTo(const ScrollPosition& position)
2461 {
2462     RenderBox* box = renderBox();
2463     if (!box)
2464         return;
2465
2466     LOG_WITH_STREAM(Scrolling, stream << "RenderLayer::scrollTo " << position << " from " << m_scrollPosition << " (is user scroll " << (currentScrollType() == ScrollType::User) << ")");
2467
2468     ScrollPosition newPosition = position;
2469     if (!box->isHTMLMarquee()) {
2470         // Ensure that the dimensions will be computed if they need to be (for overflow:hidden blocks).
2471         if (m_scrollDimensionsDirty)
2472             computeScrollDimensions();
2473 #if PLATFORM(IOS_FAMILY)
2474         if (adjustForIOSCaretWhenScrolling()) {
2475             // FIXME: It's not clear what this code is trying to do. Behavior seems reasonable with it removed.
2476             int maxOffset = scrollWidth() - roundToInt(box->clientWidth());
2477             ScrollOffset newOffset = scrollOffsetFromPosition(newPosition);
2478             int scrollXOffset = newOffset.x();
2479             if (scrollXOffset > maxOffset - caretWidth) {
2480                 scrollXOffset += caretWidth;
2481                 if (scrollXOffset <= caretWidth)
2482                     scrollXOffset = 0;
2483             } else if (scrollXOffset < m_scrollPosition.x() - caretWidth)
2484                 scrollXOffset -= caretWidth;
2485
2486             newOffset.setX(scrollXOffset);
2487             newPosition = scrollPositionFromOffset(newOffset);
2488         }
2489 #endif
2490     }
2491     
2492     if (m_scrollPosition == newPosition) {
2493         // FIXME: Nothing guarantees we get a scrollTo() with an unchanged position at the end of a user gesture.
2494         // The ScrollingCoordinator probably needs to message the main thread when a gesture ends.
2495         if (requiresScrollPositionReconciliation()) {
2496             setNeedsCompositingGeometryUpdate();
2497             updateCompositingLayersAfterScroll();
2498         }
2499         return;
2500     }
2501
2502     m_scrollPosition = newPosition;
2503
2504     RenderView& view = renderer().view();
2505
2506     // Update the positions of our child layers (if needed as only fixed layers should be impacted by a scroll).
2507     // We don't update compositing layers, because we need to do a deep update from the compositing ancestor.
2508     if (!view.frameView().layoutContext().isInRenderTreeLayout()) {
2509         // If we're in the middle of layout, we'll just update layers once layout has finished.
2510         updateLayerPositionsAfterOverflowScroll();
2511
2512         view.frameView().scheduleUpdateWidgetPositions();
2513
2514         if (!m_updatingMarqueePosition) {
2515             // Avoid updating compositing layers if, higher on the stack, we're already updating layer
2516             // positions. Updating layer positions requires a full walk of up-to-date RenderLayers, and
2517             // in this case we're still updating their positions; we'll update compositing layers later
2518             // when that completes.
2519             if (usesCompositedScrolling()) {
2520                 setNeedsCompositingGeometryUpdate();
2521
2522                 // Scroll position can affect the location of a composited descendant (which may be a sibling in z-order),
2523                 // so trigger a descendant walk from the paint-order parent.
2524                 if (auto* paintParent = paintOrderParent())
2525                     paintParent->setDescendantsNeedUpdateBackingAndHierarchyTraversal();
2526             }
2527
2528             updateCompositingLayersAfterScroll();
2529         }
2530
2531         // Update regions, scrolling may change the clip of a particular region.
2532         renderer().document().invalidateRenderingDependentRegions();
2533         DebugPageOverlays::didLayout(renderer().frame());
2534     }
2535
2536     Frame& frame = renderer().frame();
2537     RenderLayerModelObject* repaintContainer = renderer().containerForRepaint();
2538     // The caret rect needs to be invalidated after scrolling
2539     frame.selection().setCaretRectNeedsUpdate();
2540     
2541     LayoutRect rectForRepaint = renderer().hasRepaintLayoutRects() ? renderer().repaintLayoutRects().m_repaintRect : renderer().clippedOverflowRectForRepaint(repaintContainer);
2542
2543     FloatQuad quadForFakeMouseMoveEvent = FloatQuad(rectForRepaint);
2544     if (repaintContainer)
2545         quadForFakeMouseMoveEvent = repaintContainer->localToAbsoluteQuad(quadForFakeMouseMoveEvent);
2546     frame.eventHandler().dispatchFakeMouseMoveEventSoonInQuad(quadForFakeMouseMoveEvent);
2547
2548     bool requiresRepaint = true;
2549     if (usesCompositedScrolling()) {
2550         setNeedsCompositingGeometryUpdate();
2551         setDescendantsNeedUpdateBackingAndHierarchyTraversal();
2552         requiresRepaint = false;
2553     }
2554
2555     // Just schedule a full repaint of our object.
2556     if (requiresRepaint)
2557         renderer().repaintUsingContainer(repaintContainer, rectForRepaint);
2558
2559     // Schedule the scroll and scroll-related DOM events.
2560     if (Element* element = renderer().element())
2561         element->document().eventQueue().enqueueOrDispatchScrollEvent(*element);
2562
2563     if (scrollsOverflow())
2564         view.frameView().didChangeScrollOffset();
2565
2566     view.frameView().viewportContentsChanged();
2567 }
2568
2569 static inline bool frameElementAndViewPermitScroll(HTMLFrameElementBase* frameElementBase, FrameView& frameView)
2570 {
2571     // If scrollbars aren't explicitly forbidden, permit scrolling.
2572     if (frameElementBase && frameElementBase->scrollingMode() != ScrollbarAlwaysOff)
2573         return true;
2574
2575     // If scrollbars are forbidden, user initiated scrolls should obviously be ignored.
2576     if (frameView.wasScrolledByUser())
2577         return false;
2578
2579     // Forbid autoscrolls when scrollbars are off, but permits other programmatic scrolls,
2580     // like navigation to an anchor.
2581     return !frameView.frame().eventHandler().autoscrollInProgress();
2582 }
2583
2584 bool RenderLayer::allowsCurrentScroll() const
2585 {
2586     if (!renderer().hasOverflowClip())
2587         return false;
2588
2589     // Don't scroll to reveal an overflow layer that is restricted by the -webkit-line-clamp property.
2590     // FIXME: Is this still needed? It used to be relevant for Safari RSS.
2591     if (renderer().parent() && !renderer().parent()->style().lineClamp().isNone())
2592         return false;
2593
2594     RenderBox* box = renderBox();
2595     ASSERT(box); // Only boxes can have overflowClip set.
2596
2597     if (renderer().frame().eventHandler().autoscrollInProgress()) {
2598         // The "programmatically" here is misleading; this asks whether the box has scrollable overflow,
2599         // or is a special case like a form control.
2600         return box->canBeProgramaticallyScrolled();
2601     }
2602
2603     // Programmatic scrolls can scroll overflow:hidden.
2604     return box->hasHorizontalOverflow() || box->hasVerticalOverflow();
2605 }
2606
2607 void RenderLayer::scrollRectToVisible(const LayoutRect& absoluteRect, bool insideFixed, const ScrollRectToVisibleOptions& options)
2608 {
2609     LOG_WITH_STREAM(Scrolling, stream << "Layer " << this << " scrollRectToVisible " << absoluteRect);
2610
2611     RenderLayer* parentLayer = nullptr;
2612     LayoutRect newRect = absoluteRect;
2613
2614     // We may end up propagating a scroll event. It is important that we suspend events until 
2615     // the end of the function since they could delete the layer or the layer's renderer().
2616     FrameView& frameView = renderer().view().frameView();
2617
2618     if (renderer().parent())
2619         parentLayer = renderer().parent()->enclosingLayer();
2620
2621     if (allowsCurrentScroll()) {
2622         // Don't scroll to reveal an overflow layer that is restricted by the -webkit-line-clamp property.
2623         // This will prevent us from revealing text hidden by the slider in Safari RSS.
2624         RenderBox* box = renderBox();
2625         ASSERT(box);
2626         LayoutRect localExposeRect(box->absoluteToLocalQuad(FloatQuad(FloatRect(absoluteRect))).boundingBox());
2627         if (shouldPlaceBlockDirectionScrollbarOnLeft()) {
2628             // For direction: rtl; writing-mode: horizontal-tb box, the scroll bar is on the left side. The visible rect
2629             // starts from the right side of scroll bar. So the x of localExposeRect should start from the same position too.
2630             localExposeRect.moveBy(LayoutPoint(-verticalScrollbarWidth(), 0));
2631         }
2632         LayoutRect layerBounds(0_lu, 0_lu, box->clientWidth(), box->clientHeight());
2633         LayoutRect revealRect = getRectToExpose(layerBounds, localExposeRect, insideFixed, options.alignX, options.alignY);
2634
2635         ScrollOffset clampedScrollOffset = clampScrollOffset(scrollOffset() + toIntSize(roundedIntRect(revealRect).location()));
2636         if (clampedScrollOffset != scrollOffset()) {
2637             ScrollOffset oldScrollOffset = scrollOffset();
2638             scrollToOffset(clampedScrollOffset);
2639             IntSize scrollOffsetDifference = scrollOffset() - oldScrollOffset;
2640             localExposeRect.move(-scrollOffsetDifference);
2641             newRect = LayoutRect(box->localToAbsoluteQuad(FloatQuad(FloatRect(localExposeRect)), UseTransforms).boundingBox());
2642         }
2643     } else if (!parentLayer && renderer().isRenderView()) {
2644         HTMLFrameOwnerElement* ownerElement = renderer().document().ownerElement();
2645
2646         if (ownerElement && ownerElement->renderer()) {
2647             HTMLFrameElementBase* frameElementBase = nullptr;
2648
2649             if (is<HTMLFrameElementBase>(*ownerElement))
2650                 frameElementBase = downcast<HTMLFrameElementBase>(ownerElement);
2651
2652             if (frameElementAndViewPermitScroll(frameElementBase, frameView)) {
2653                 // If this assertion fires we need to protect the ownerElement from being destroyed.
2654                 ScriptDisallowedScope::InMainThread scriptDisallowedScope;
2655
2656                 LayoutRect viewRect = frameView.visibleContentRect(LegacyIOSDocumentVisibleRect);
2657                 LayoutRect exposeRect = getRectToExpose(viewRect, absoluteRect, insideFixed, options.alignX, options.alignY);
2658
2659                 IntPoint scrollOffset(roundedIntPoint(exposeRect.location()));
2660                 // Adjust offsets if they're outside of the allowable range.
2661                 scrollOffset = scrollOffset.constrainedBetween(IntPoint(), IntPoint(frameView.contentsSize()));
2662                 frameView.setScrollPosition(scrollOffset);
2663
2664                 if (options.shouldAllowCrossOriginScrolling == ShouldAllowCrossOriginScrolling::Yes || frameView.safeToPropagateScrollToParent()) {
2665                     parentLayer = ownerElement->renderer()->enclosingLayer();
2666                     // Convert the rect into the coordinate space of the parent frame's document.
2667                     newRect = frameView.contentsToContainingViewContents(enclosingIntRect(newRect));
2668                     insideFixed = false; // FIXME: ideally need to determine if this <iframe> is inside position:fixed.
2669                 } else
2670                     parentLayer = nullptr;
2671             }
2672         } else {
2673             if (options.revealMode == SelectionRevealMode::RevealUpToMainFrame && frameView.frame().isMainFrame())
2674                 return;
2675
2676             auto minScrollPosition = frameView.minimumScrollPosition();
2677             auto maxScrollPosition = frameView.maximumScrollPosition();
2678
2679 #if !PLATFORM(IOS_FAMILY)
2680             LayoutRect viewRect = frameView.visibleContentRect();
2681 #else
2682             // FIXME: ContentInsets should be taken care of in UI process side. webkit.org/b/199682
2683             // To do that, getRectToExpose needs to return the additional scrolling to do beyond content rect.
2684             LayoutRect viewRect = frameView.visualViewportRectExpandedByContentInsets();
2685
2686             // FIXME: webkit.org/b/199683 FrameView::visibleContentRect is wrong when content insets are present
2687             maxScrollPosition = frameView.scrollPositionFromOffset(ScrollPosition(frameView.totalContentsSize() - flooredIntSize(viewRect.size())));
2688
2689             auto contentInsets = page().contentInsets();
2690             minScrollPosition.move(-contentInsets.left(), -contentInsets.top());
2691             maxScrollPosition.move(contentInsets.right(), contentInsets.bottom());
2692 #endif
2693             // Move the target rect into "scrollView contents" coordinates.
2694             LayoutRect targetRect = absoluteRect;
2695             targetRect.move(0, frameView.headerHeight());
2696
2697             LayoutRect revealRect = getRectToExpose(viewRect, targetRect, insideFixed, options.alignX, options.alignY);
2698             ScrollOffset clampedScrollPosition = roundedIntPoint(revealRect.location()).constrainedBetween(minScrollPosition, maxScrollPosition);
2699             frameView.setScrollPosition(clampedScrollPosition);
2700
2701             // This is the outermost view of a web page, so after scrolling this view we
2702             // scroll its container by calling Page::scrollRectIntoView.
2703             // This only has an effect on the Mac platform in applications
2704             // that put web views into scrolling containers, such as Mac OS X Mail.
2705             // The canAutoscroll function in EventHandler also knows about this.
2706             page().chrome().scrollRectIntoView(snappedIntRect(absoluteRect));
2707         }
2708     }
2709     
2710     if (parentLayer)
2711         parentLayer->scrollRectToVisible(newRect, insideFixed, options);
2712 }
2713
2714 void RenderLayer::updateCompositingLayersAfterScroll()
2715 {
2716     if (compositor().hasContentCompositingLayers()) {
2717         // Our stacking container is guaranteed to contain all of our descendants that may need
2718         // repositioning, so update compositing layers from there.
2719         if (RenderLayer* compositingAncestor = stackingContext()->enclosingCompositingLayer()) {
2720             if (usesCompositedScrolling())
2721                 compositor().updateCompositingLayers(CompositingUpdateType::OnCompositedScroll, compositingAncestor);
2722             else {
2723                 // FIXME: would be nice to only dirty layers whose positions were affected by scrolling.
2724                 compositingAncestor->setDescendantsNeedUpdateBackingAndHierarchyTraversal();
2725                 compositor().updateCompositingLayers(CompositingUpdateType::OnScroll, compositingAncestor);
2726             }
2727         }
2728     }
2729 }
2730
2731 LayoutRect RenderLayer::getRectToExpose(const LayoutRect& visibleRect, const LayoutRect& exposeRect, bool insideFixed, const ScrollAlignment& alignX, const ScrollAlignment& alignY) const
2732 {
2733     FrameView& frameView = renderer().view().frameView();
2734     if (renderer().isRenderView() && insideFixed) {
2735         // If the element is inside position:fixed and we're not scaled, no amount of scrolling is going to move things around.
2736         if (frameView.frameScaleFactor() == 1)
2737             return visibleRect;
2738
2739         if (renderer().settings().visualViewportEnabled()) {
2740             // exposeRect is in absolute coords, affected by page scale. Unscale it.
2741             LayoutRect unscaledExposeRect = exposeRect;
2742             unscaledExposeRect.scale(1 / frameView.frameScaleFactor());
2743             unscaledExposeRect.move(0, -frameView.headerHeight());
2744
2745             // These are both in unscaled coordinates.
2746             LayoutRect layoutViewport = frameView.layoutViewportRect();
2747             LayoutRect visualViewport = frameView.visualViewportRect();
2748
2749             // The rect to expose may be partially offscreen, which we can't do anything about with position:fixed.
2750             unscaledExposeRect.intersect(layoutViewport);
2751             // Make sure it's not larger than the visual viewport; if so, we'll just move to the top left.
2752             unscaledExposeRect.setSize(unscaledExposeRect.size().shrunkTo(visualViewport.size()));
2753
2754             // Compute how much we have to move the visualViewport to reveal the part of the layoutViewport that contains exposeRect.
2755             LayoutRect requiredVisualViewport = getRectToExpose(visualViewport, unscaledExposeRect, false, alignX, alignY);
2756             // Scale it back up.
2757             requiredVisualViewport.scale(frameView.frameScaleFactor());
2758             requiredVisualViewport.move(0, frameView.headerHeight());
2759             return requiredVisualViewport;
2760         }
2761     }
2762
2763     // Determine the appropriate X behavior.
2764     ScrollAlignment::Behavior scrollX;
2765     LayoutRect exposeRectX(exposeRect.x(), visibleRect.y(), exposeRect.width(), visibleRect.height());
2766     LayoutUnit intersectWidth = intersection(visibleRect, exposeRectX).width();
2767     if (intersectWidth == exposeRect.width() || intersectWidth >= MIN_INTERSECT_FOR_REVEAL)
2768         // If the rectangle is fully visible, use the specified visible behavior.
2769         // If the rectangle is partially visible, but over a certain threshold,
2770         // then treat it as fully visible to avoid unnecessary horizontal scrolling
2771         scrollX = ScrollAlignment::getVisibleBehavior(alignX);
2772     else if (intersectWidth == visibleRect.width()) {
2773         // If the rect is bigger than the visible area, don't bother trying to center. Other alignments will work.
2774         scrollX = ScrollAlignment::getVisibleBehavior(alignX);
2775         if (scrollX == ScrollAlignment::Behavior::AlignCenter)
2776             scrollX = ScrollAlignment::Behavior::NoScroll;
2777     } else if (intersectWidth > 0)
2778         // If the rectangle is partially visible, but not above the minimum threshold, use the specified partial behavior
2779         scrollX = ScrollAlignment::getPartialBehavior(alignX);
2780     else
2781         scrollX = ScrollAlignment::getHiddenBehavior(alignX);
2782     // If we're trying to align to the closest edge, and the exposeRect is further right
2783     // than the visibleRect, and not bigger than the visible area, then align with the right.
2784     if (scrollX == ScrollAlignment::Behavior::AlignToClosestEdge && exposeRect.maxX() > visibleRect.maxX() && exposeRect.width() < visibleRect.width())
2785         scrollX = ScrollAlignment::Behavior::AlignRight;
2786
2787     // Given the X behavior, compute the X coordinate.
2788     LayoutUnit x;
2789     if (scrollX == ScrollAlignment::Behavior::NoScroll)
2790         x = visibleRect.x();
2791     else if (scrollX == ScrollAlignment::Behavior::AlignRight)
2792         x = exposeRect.maxX() - visibleRect.width();
2793     else if (scrollX == ScrollAlignment::Behavior::AlignCenter)
2794         x = exposeRect.x() + (exposeRect.width() - visibleRect.width()) / 2;
2795     else
2796         x = exposeRect.x();
2797
2798     // Determine the appropriate Y behavior.
2799     ScrollAlignment::Behavior scrollY;
2800     LayoutRect exposeRectY(visibleRect.x(), exposeRect.y(), visibleRect.width(), exposeRect.height());
2801     LayoutUnit intersectHeight = intersection(visibleRect, exposeRectY).height();
2802     if (intersectHeight == exposeRect.height())
2803         // If the rectangle is fully visible, use the specified visible behavior.
2804         scrollY = ScrollAlignment::getVisibleBehavior(alignY);
2805     else if (intersectHeight == visibleRect.height()) {
2806         // If the rect is bigger than the visible area, don't bother trying to center. Other alignments will work.
2807         scrollY = ScrollAlignment::getVisibleBehavior(alignY);
2808         if (scrollY == ScrollAlignment::Behavior::AlignCenter)
2809             scrollY = ScrollAlignment::Behavior::NoScroll;
2810     } else if (intersectHeight > 0)
2811         // If the rectangle is partially visible, use the specified partial behavior
2812         scrollY = ScrollAlignment::getPartialBehavior(alignY);
2813     else
2814         scrollY = ScrollAlignment::getHiddenBehavior(alignY);
2815     // If we're trying to align to the closest edge, and the exposeRect is further down
2816     // than the visibleRect, and not bigger than the visible area, then align with the bottom.
2817     if (scrollY == ScrollAlignment::Behavior::AlignToClosestEdge && exposeRect.maxY() > visibleRect.maxY() && exposeRect.height() < visibleRect.height())
2818         scrollY = ScrollAlignment::Behavior::AlignBottom;
2819
2820     // Given the Y behavior, compute the Y coordinate.
2821     LayoutUnit y;
2822     if (scrollY == ScrollAlignment::Behavior::NoScroll)
2823         y = visibleRect.y();
2824     else if (scrollY == ScrollAlignment::Behavior::AlignBottom)
2825         y = exposeRect.maxY() - visibleRect.height();
2826     else if (scrollY == ScrollAlignment::Behavior::AlignCenter)
2827         y = exposeRect.y() + (exposeRect.height() - visibleRect.height()) / 2;
2828     else
2829         y = exposeRect.y();
2830
2831     return LayoutRect(LayoutPoint(x, y), visibleRect.size());
2832 }
2833
2834 void RenderLayer::autoscroll(const IntPoint& positionInWindow)
2835 {
2836     IntPoint currentDocumentPosition = renderer().view().frameView().windowToContents(positionInWindow);
2837     scrollRectToVisible(LayoutRect(currentDocumentPosition, LayoutSize(1, 1)), false, { SelectionRevealMode::Reveal, ScrollAlignment::alignToEdgeIfNeeded, ScrollAlignment::alignToEdgeIfNeeded, ShouldAllowCrossOriginScrolling::Yes });
2838 }
2839
2840 bool RenderLayer::canResize() const
2841 {
2842     // We need a special case for <iframe> because they never have
2843     // hasOverflowClip(). However, they do "implicitly" clip their contents, so
2844     // we want to allow resizing them also.
2845     return (renderer().hasOverflowClip() || renderer().isRenderIFrame()) && renderer().style().resize() != Resize::None;
2846 }
2847
2848 void RenderLayer::resize(const PlatformMouseEvent& evt, const LayoutSize& oldOffset)
2849 {
2850     // FIXME: This should be possible on generated content but is not right now.
2851     if (!inResizeMode() || !canResize() || !renderer().element())
2852         return;
2853
2854     // FIXME: The only case where renderer->element()->renderer() != renderer is with continuations. Do they matter here?
2855     // If they do it would still be better to deal with them explicitly.
2856     Element* element = renderer().element();
2857     auto* renderer = downcast<RenderBox>(element->renderer());
2858
2859     Document& document = element->document();
2860     if (!document.frame()->eventHandler().mousePressed())
2861         return;
2862
2863     float zoomFactor = renderer->style().effectiveZoom();
2864
2865     LayoutSize newOffset = offsetFromResizeCorner(document.view()->windowToContents(evt.position()));
2866     newOffset.setWidth(newOffset.width() / zoomFactor);
2867     newOffset.setHeight(newOffset.height() / zoomFactor);
2868     
2869     LayoutSize currentSize = LayoutSize(renderer->width() / zoomFactor, renderer->height() / zoomFactor);
2870     LayoutSize minimumSize = element->minimumSizeForResizing().shrunkTo(currentSize);
2871     element->setMinimumSizeForResizing(minimumSize);
2872     
2873     LayoutSize adjustedOldOffset = LayoutSize(oldOffset.width() / zoomFactor, oldOffset.height() / zoomFactor);
2874     if (shouldPlaceBlockDirectionScrollbarOnLeft()) {
2875         newOffset.setWidth(-newOffset.width());
2876         adjustedOldOffset.setWidth(-adjustedOldOffset.width());
2877     }
2878     
2879     LayoutSize difference = (currentSize + newOffset - adjustedOldOffset).expandedTo(minimumSize) - currentSize;
2880
2881     StyledElement* styledElement = downcast<StyledElement>(element);
2882     bool isBoxSizingBorder = renderer->style().boxSizing() == BoxSizing::BorderBox;
2883
2884     Resize resize = renderer->style().resize();
2885     if (resize != Resize::Vertical && difference.width()) {
2886         if (is<HTMLFormControlElement>(*element)) {
2887             // Make implicit margins from the theme explicit (see <http://bugs.webkit.org/show_bug.cgi?id=9547>).
2888             styledElement->setInlineStyleProperty(CSSPropertyMarginLeft, renderer->marginLeft() / zoomFactor, CSSPrimitiveValue::CSS_PX);
2889             styledElement->setInlineStyleProperty(CSSPropertyMarginRight, renderer->marginRight() / zoomFactor, CSSPrimitiveValue::CSS_PX);
2890         }
2891         LayoutUnit baseWidth = renderer->width() - (isBoxSizingBorder ? 0_lu : renderer->horizontalBorderAndPaddingExtent());
2892         baseWidth = baseWidth / zoomFactor;
2893         styledElement->setInlineStyleProperty(CSSPropertyWidth, roundToInt(baseWidth + difference.width()), CSSPrimitiveValue::CSS_PX);
2894     }
2895
2896     if (resize != Resize::Horizontal && difference.height()) {
2897         if (is<HTMLFormControlElement>(*element)) {
2898             // Make implicit margins from the theme explicit (see <http://bugs.webkit.org/show_bug.cgi?id=9547>).
2899             styledElement->setInlineStyleProperty(CSSPropertyMarginTop, renderer->marginTop() / zoomFactor, CSSPrimitiveValue::CSS_PX);
2900             styledElement->setInlineStyleProperty(CSSPropertyMarginBottom, renderer->marginBottom() / zoomFactor, CSSPrimitiveValue::CSS_PX);
2901         }
2902         LayoutUnit baseHeight = renderer->height() - (isBoxSizingBorder ? 0_lu : renderer->verticalBorderAndPaddingExtent());
2903         baseHeight = baseHeight / zoomFactor;
2904         styledElement->setInlineStyleProperty(CSSPropertyHeight, roundToInt(baseHeight + difference.height()), CSSPrimitiveValue::CSS_PX);
2905     }
2906
2907     document.updateLayout();
2908
2909     // FIXME (Radar 4118564): We should also autoscroll the window as necessary to keep the point under the cursor in view.
2910 }
2911
2912 void RenderLayer::setScrollOffset(const ScrollOffset& offset)
2913 {
2914     scrollTo(scrollPositionFromOffset(offset));
2915 }
2916
2917 ScrollingNodeID RenderLayer::scrollingNodeID() const
2918 {
2919     if (!isComposited())
2920         return 0;
2921
2922     return backing()->scrollingNodeIDForRole(ScrollCoordinationRole::Scrolling);
2923 }
2924
2925 IntRect RenderLayer::visibleContentRectInternal(VisibleContentRectIncludesScrollbars scrollbarInclusion, VisibleContentRectBehavior) const
2926 {
2927     IntSize scrollbarSpace;
2928     if (showsOverflowControls() && scrollbarInclusion == IncludeScrollbars)
2929         scrollbarSpace = scrollbarIntrusion();
2930     
2931     auto visibleSize = this->visibleSize();
2932     return { scrollPosition(), { std::max(0, visibleSize.width() - scrollbarSpace.width()), std::max(0, visibleSize.height() - scrollbarSpace.height()) } };
2933 }
2934
2935 IntSize RenderLayer::overhangAmount() const
2936 {
2937 #if ENABLE(RUBBER_BANDING)
2938     if (!renderer().settings().rubberBandingForSubScrollableRegionsEnabled())
2939         return IntSize();
2940
2941     IntSize stretch;
2942
2943     // FIXME: use maximumScrollOffset(), or just move this to ScrollableArea.
2944     ScrollOffset scrollOffset = scrollOffsetFromPosition(scrollPosition());
2945     auto reachableSize = reachableTotalContentsSize();
2946     if (scrollOffset.y() < 0)
2947         stretch.setHeight(scrollOffset.y());
2948     else if (reachableSize.height() && scrollOffset.y() > reachableSize.height() - visibleHeight())
2949         stretch.setHeight(scrollOffset.y() - (reachableSize.height() - visibleHeight()));
2950
2951     if (scrollOffset.x() < 0)
2952         stretch.setWidth(scrollOffset.x());
2953     else if (reachableSize.width() && scrollOffset.x() > reachableSize.width() - visibleWidth())
2954         stretch.setWidth(scrollOffset.x() - (reachableSize.width() - visibleWidth()));
2955
2956     return stretch;
2957 #else
2958     return IntSize();
2959 #endif
2960 }
2961
2962 bool RenderLayer::isActive() const
2963 {
2964     return page().focusController().isActive();
2965 }
2966
2967 static int cornerStart(const RenderLayer& layer, int minX, int maxX, int thickness)
2968 {
2969     if (layer.shouldPlaceBlockDirectionScrollbarOnLeft())
2970         return minX + layer.renderer().style().borderLeftWidth();
2971     return maxX - thickness - layer.renderer().style().borderRightWidth();
2972 }
2973
2974 static LayoutRect cornerRect(const RenderLayer& layer, const LayoutRect& bounds)
2975 {
2976     int horizontalThickness;
2977     int verticalThickness;
2978     if (!layer.verticalScrollbar() && !layer.horizontalScrollbar()) {
2979         // FIXME: This isn't right.  We need to know the thickness of custom scrollbars
2980         // even when they don't exist in order to set the resizer square size properly.
2981         horizontalThickness = ScrollbarTheme::theme().scrollbarThickness();
2982         verticalThickness = horizontalThickness;
2983     } else if (layer.verticalScrollbar() && !layer.horizontalScrollbar()) {
2984         horizontalThickness = layer.verticalScrollbar()->width();
2985         verticalThickness = horizontalThickness;
2986     } else if (layer.horizontalScrollbar() && !layer.verticalScrollbar()) {
2987         verticalThickness = layer.horizontalScrollbar()->height();
2988         horizontalThickness = verticalThickness;
2989     } else {
2990         horizontalThickness = layer.verticalScrollbar()->width();
2991         verticalThickness = layer.horizontalScrollbar()->height();
2992     }
2993     return LayoutRect(cornerStart(layer, bounds.x(), bounds.maxX(), horizontalThickness),
2994         bounds.maxY() - verticalThickness - layer.renderer().style().borderBottomWidth(),
2995         horizontalThickness, verticalThickness);
2996 }
2997
2998 IntRect RenderLayer::scrollCornerRect() const
2999 {
3000     // We have a scrollbar corner when a non overlay scrollbar is visible and not filling the entire length of the box.
3001     // This happens when:
3002     // (a) A resizer is present and at least one non overlay scrollbar is present
3003     // (b) Both non overlay scrollbars are present.
3004     // Overlay scrollbars always fill the entire length of the box so we never have scroll corner in that case.
3005     bool hasHorizontalBar = m_hBar && !m_hBar->isOverlayScrollbar();
3006     bool hasVerticalBar = m_vBar && !m_vBar->isOverlayScrollbar();
3007     bool hasResizer = renderer().style().resize() != Resize::None;
3008     if ((hasHorizontalBar && hasVerticalBar) || (hasResizer && (hasHorizontalBar || hasVerticalBar)))
3009         return snappedIntRect(cornerRect(*this, renderBox()->borderBoxRect()));
3010     return IntRect();
3011 }
3012
3013 static LayoutRect resizerCornerRect(const RenderLayer& layer, const LayoutRect& bounds)
3014 {
3015     ASSERT(layer.renderer().isBox());
3016     if (layer.renderer().style().resize() == Resize::None)
3017         return LayoutRect();
3018     return cornerRect(layer, bounds);
3019 }
3020
3021 LayoutRect RenderLayer::scrollCornerAndResizerRect() const
3022 {
3023     RenderBox* box = renderBox();
3024     if (!box)
3025         return LayoutRect();
3026     LayoutRect scrollCornerAndResizer = scrollCornerRect();
3027     if (scrollCornerAndResizer.isEmpty())
3028         scrollCornerAndResizer = resizerCornerRect(*this, box->borderBoxRect());
3029     return scrollCornerAndResizer;
3030 }
3031
3032 bool RenderLayer::isScrollCornerVisible() const
3033 {
3034     ASSERT(renderer().isBox());
3035     return !scrollCornerRect().isEmpty();
3036 }
3037
3038 IntRect RenderLayer::convertFromScrollbarToContainingView(const Scrollbar& scrollbar, const IntRect& scrollbarRect) const
3039 {
3040     IntRect rect = scrollbarRect;
3041     rect.move(scrollbarOffset(scrollbar));
3042
3043     return renderer().view().frameView().convertFromRendererToContainingView(&renderer(), rect);
3044 }
3045
3046 IntRect RenderLayer::convertFromContainingViewToScrollbar(const Scrollbar& scrollbar, const IntRect& parentRect) const
3047 {
3048     IntRect rect = renderer().view().frameView().convertFromContainingViewToRenderer(&renderer(), parentRect);
3049     rect.move(-scrollbarOffset(scrollbar));
3050     return rect;
3051 }
3052
3053 IntPoint RenderLayer::convertFromScrollbarToContainingView(const Scrollbar& scrollbar, const IntPoint& scrollbarPoint) const
3054 {
3055     IntPoint point = scrollbarPoint;
3056     point.move(scrollbarOffset(scrollbar));
3057     return renderer().view().frameView().convertFromRendererToContainingView(&renderer(), point);
3058 }
3059
3060 IntPoint RenderLayer::convertFromContainingViewToScrollbar(const Scrollbar& scrollbar, const IntPoint& parentPoint) const
3061 {
3062     IntPoint point = renderer().view().frameView().convertFromContainingViewToRenderer(&renderer(), parentPoint);
3063     point.move(-scrollbarOffset(scrollbar));
3064     return point;
3065 }
3066
3067 IntSize RenderLayer::visibleSize() const
3068 {
3069     RenderBox* box = renderBox();
3070     if (!box)
3071         return IntSize();
3072
3073     return IntSize(roundToInt(box->clientWidth()), roundToInt(box->clientHeight()));
3074 }
3075
3076 IntSize RenderLayer::contentsSize() const
3077 {
3078     return IntSize(scrollWidth(), scrollHeight());
3079 }
3080
3081 IntSize RenderLayer::reachableTotalContentsSize() const
3082 {
3083     IntSize contentsSize = this->contentsSize();
3084
3085     if (!hasScrollableHorizontalOverflow())
3086         contentsSize.setWidth(std::min(contentsSize.width(), visibleSize().width()));
3087
3088     if (!hasScrollableVerticalOverflow())
3089         contentsSize.setHeight(std::min(contentsSize.height(), visibleSize().height()));
3090
3091     return contentsSize;
3092 }
3093
3094 void RenderLayer::availableContentSizeChanged(AvailableSizeChangeReason reason)
3095 {
3096     ScrollableArea::availableContentSizeChanged(reason);
3097
3098     if (reason == AvailableSizeChangeReason::ScrollbarsChanged) {
3099         if (is<RenderBlock>(renderer()))
3100             downcast<RenderBlock>(renderer()).setShouldForceRelayoutChildren(true);
3101         renderer().setNeedsLayout();
3102     }
3103 }
3104
3105 bool RenderLayer::shouldSuspendScrollAnimations() const
3106 {
3107     return renderer().view().frameView().shouldSuspendScrollAnimations();
3108 }
3109
3110 #if PLATFORM(IOS_FAMILY)
3111 void RenderLayer::didStartScroll()
3112 {
3113     page().chrome().client().didStartOverflowScroll();
3114 }
3115
3116 void RenderLayer::didEndScroll()
3117 {
3118     page().chrome().client().didEndOverflowScroll();
3119 }
3120     
3121 void RenderLayer::didUpdateScroll()
3122 {
3123     // Send this notification when we scroll, since this is how we keep selection updated.
3124     page().chrome().client().didLayout(ChromeClient::Scroll);
3125 }
3126 #endif
3127
3128 IntPoint RenderLayer::lastKnownMousePosition() const
3129 {
3130     return renderer().frame().eventHandler().lastKnownMousePosition();
3131 }
3132
3133 bool RenderLayer::isHandlingWheelEvent() const
3134 {
3135     return renderer().frame().eventHandler().isHandlingWheelEvent();
3136 }
3137
3138 IntRect RenderLayer::rectForHorizontalScrollbar(const IntRect& borderBoxRect) const
3139 {
3140     if (!m_hBar)
3141         return IntRect();
3142
3143     const RenderBox* box = renderBox();
3144     const IntRect& scrollCorner = scrollCornerRect();
3145
3146     return IntRect(horizontalScrollbarStart(borderBoxRect.x()),
3147         borderBoxRect.maxY() - box->borderBottom() - m_hBar->height(),
3148         borderBoxRect.width() - (box->borderLeft() + box->borderRight()) - scrollCorner.width(),
3149         m_hBar->height());
3150 }
3151
3152 IntRect RenderLayer::rectForVerticalScrollbar(const IntRect& borderBoxRect) const
3153 {
3154     if (!m_vBar)
3155         return IntRect();
3156
3157     const RenderBox* box = renderBox();
3158     const IntRect& scrollCorner = scrollCornerRect();
3159
3160     return IntRect(verticalScrollbarStart(borderBoxRect.x(), borderBoxRect.maxX()),
3161         borderBoxRect.y() + box->borderTop(),
3162         m_vBar->width(),
3163         borderBoxRect.height() - (box->borderTop() + box->borderBottom()) - scrollCorner.height());
3164 }
3165
3166 LayoutUnit RenderLayer::verticalScrollbarStart(int minX, int maxX) const
3167 {
3168     const RenderBox* box = renderBox();
3169     if (shouldPlaceBlockDirectionScrollbarOnLeft())
3170         return minX + box->borderLeft();
3171     return maxX - box->borderRight() - m_vBar->width();
3172 }
3173
3174 LayoutUnit RenderLayer::horizontalScrollbarStart(int minX) const
3175 {
3176     const RenderBox* box = renderBox();
3177     int x = minX + box->borderLeft();
3178     if (shouldPlaceBlockDirectionScrollbarOnLeft())
3179         x += m_vBar ? m_vBar->width() : roundToInt(resizerCornerRect(*this, box->borderBoxRect()).width());
3180     return x;
3181 }
3182
3183 IntSize RenderLayer::scrollbarOffset(const Scrollbar& scrollbar) const
3184 {
3185     RenderBox* box = renderBox();
3186
3187     if (&scrollbar == m_vBar.get())
3188         return IntSize(verticalScrollbarStart(0, box->width()), box->borderTop());
3189
3190     if (&scrollbar == m_hBar.get())
3191         return IntSize(horizontalScrollbarStart(0), box->height() - box->borderBottom() - scrollbar.height());
3192     
3193     ASSERT_NOT_REACHED();
3194     return IntSize();
3195 }
3196
3197 void RenderLayer::invalidateScrollbarRect(Scrollbar& scrollbar, const IntRect& rect)
3198 {
3199     if (!showsOverflowControls())
3200         return;
3201
3202     if (&scrollbar == m_vBar.get()) {
3203         if (GraphicsLayer* layer = layerForVerticalScrollbar()) {
3204             layer->setNeedsDisplayInRect(rect);
3205             return;
3206         }
3207     } else {
3208         if (GraphicsLayer* layer = layerForHorizontalScrollbar()) {
3209             layer->setNeedsDisplayInRect(rect);
3210             return;
3211         }
3212     }
3213
3214     IntRect scrollRect = rect;
3215     RenderBox* box = renderBox();
3216     ASSERT(box);
3217     // If we are not yet inserted into the tree, there is no need to repaint.
3218     if (!box->parent())
3219         return;
3220
3221     if (&scrollbar == m_vBar.get())
3222         scrollRect.move(verticalScrollbarStart(0, box->width()), box->borderTop());
3223     else
3224         scrollRect.move(horizontalScrollbarStart(0), box->height() - box->borderBottom() - scrollbar.height());
3225     LayoutRect repaintRect = scrollRect;
3226     renderBox()->flipForWritingMode(repaintRect);
3227     renderer().repaintRectangle(repaintRect);
3228 }
3229
3230 void RenderLayer::invalidateScrollCornerRect(const IntRect& rect)
3231 {
3232     if (!showsOverflowControls())
3233         return;
3234
3235     if (GraphicsLayer* layer = layerForScrollCorner()) {
3236         layer->setNeedsDisplayInRect(rect);
3237         return;
3238     }
3239
3240     if (m_scrollCorner)
3241         m_scrollCorner->repaintRectangle(rect);
3242     if (m_resizer)
3243         m_resizer->repaintRectangle(rect);
3244 }
3245
3246 static bool scrollbarHiddenByStyle(Scrollbar* scrollbar)
3247 {
3248     if (!scrollbar || !scrollbar->isCustomScrollbar())
3249         return false;
3250
3251     std::unique_ptr<RenderStyle> scrollbarStyle = static_cast<RenderScrollbar*>(scrollbar)->getScrollbarPseudoStyle(ScrollbarBGPart, PseudoId::Scrollbar);
3252
3253     return scrollbarStyle && scrollbarStyle->display() == DisplayType::None;
3254 }
3255
3256 bool RenderLayer::horizontalScrollbarHiddenByStyle() const
3257 {
3258     return scrollbarHiddenByStyle(horizontalScrollbar());
3259 }
3260
3261 bool RenderLayer::verticalScrollbarHiddenByStyle() const
3262 {
3263     return scrollbarHiddenByStyle(verticalScrollbar());
3264 }
3265
3266 static inline RenderElement* rendererForScrollbar(RenderLayerModelObject& renderer)
3267 {
3268     if (Element* element = renderer.element()) {
3269         if (ShadowRoot* shadowRoot = element->containingShadowRoot()) {
3270             if (shadowRoot->mode() == ShadowRootMode::UserAgent)
3271                 return shadowRoot->host()->renderer();
3272         }
3273     }
3274
3275     return &renderer;
3276 }
3277
3278 Ref<Scrollbar> RenderLayer::createScrollbar(ScrollbarOrientation orientation)
3279 {
3280     RefPtr<Scrollbar> widget;
3281     ASSERT(rendererForScrollbar(renderer()));
3282     auto& actualRenderer = *rendererForScrollbar(renderer());
3283     bool hasCustomScrollbarStyle = is<RenderBox>(actualRenderer) && downcast<RenderBox>(actualRenderer).style().hasPseudoStyle(PseudoId::Scrollbar);
3284     if (hasCustomScrollbarStyle)
3285         widget = RenderScrollbar::createCustomScrollbar(*this, orientation, downcast<RenderBox>(actualRenderer).element());
3286     else {
3287         widget = Scrollbar::createNativeScrollbar(*this, orientation, RegularScrollbar);
3288         didAddScrollbar(widget.get(), orientation);
3289         if (page().expectsWheelEventTriggers())
3290             scrollAnimator().setWheelEventTestTrigger(page().testTrigger());
3291     }
3292     renderer().view().frameView().addChild(*widget);
3293     return widget.releaseNonNull();
3294 }
3295
3296 void RenderLayer::destroyScrollbar(ScrollbarOrientation orientation)
3297 {
3298     RefPtr<Scrollbar>& scrollbar = orientation == HorizontalScrollbar ? m_hBar : m_vBar;
3299     if (!scrollbar)
3300         return;
3301
3302     if (!scrollbar->isCustomScrollbar())
3303         willRemoveScrollbar(scrollbar.get(), orientation);
3304
3305     scrollbar->removeFromParent();
3306     scrollbar = nullptr;
3307 }
3308
3309 bool RenderLayer::scrollsOverflow() const
3310 {
3311     if (!is<RenderBox>(renderer()))
3312         return false;
3313
3314     return downcast<RenderBox>(renderer()).scrollsOverflow();
3315 }
3316
3317 void RenderLayer::setHasHorizontalScrollbar(bool hasScrollbar)
3318 {
3319     if (hasScrollbar == hasHorizontalScrollbar())
3320         return;
3321
3322     if (hasScrollbar) {
3323         m_hBar = createScrollbar(HorizontalScrollbar);
3324 #if ENABLE(RUBBER_BANDING)
3325         ScrollElasticity elasticity = scrollsOverflow() && renderer().settings().rubberBandingForSubScrollableRegionsEnabled() ? ScrollElasticityAutomatic : ScrollElasticityNone;
3326         ScrollableArea::setHorizontalScrollElasticity(elasticity);
3327 #endif
3328     } else {
3329         destroyScrollbar(HorizontalScrollbar);
3330 #if ENABLE(RUBBER_BANDING)
3331         ScrollableArea::setHorizontalScrollElasticity(ScrollElasticityNone);
3332 #endif
3333     }
3334
3335     // Destroying or creating one bar can cause our scrollbar corner to come and go.  We need to update the opposite scrollbar's style.
3336     if (m_hBar)
3337         m_hBar->styleChanged();
3338     if (m_vBar)
3339         m_vBar->styleChanged();
3340 }
3341
3342 void RenderLayer::setHasVerticalScrollbar(bool hasScrollbar)
3343 {
3344     if (hasScrollbar == hasVerticalScrollbar())
3345         return;
3346
3347     if (hasScrollbar) {
3348         m_vBar = createScrollbar(VerticalScrollbar);
3349 #if ENABLE(RUBBER_BANDING)
3350         ScrollElasticity elasticity = scrollsOverflow() && renderer().settings().rubberBandingForSubScrollableRegionsEnabled() ? ScrollElasticityAutomatic : ScrollElasticityNone;
3351         ScrollableArea::setVerticalScrollElasticity(elasticity);
3352 #endif
3353     } else {
3354         destroyScrollbar(VerticalScrollbar);
3355 #if ENABLE(RUBBER_BANDING)
3356         ScrollableArea::setVerticalScrollElasticity(ScrollElasticityNone);
3357 #endif
3358     }
3359
3360      // Destroying or creating one bar can cause our scrollbar corner to come and go.  We need to update the opposite scrollbar's style.
3361     if (m_hBar)
3362         m_hBar->styleChanged();
3363     if (m_vBar)
3364         m_vBar->styleChanged();
3365 }
3366
3367 ScrollableArea* RenderLayer::enclosingScrollableArea() const
3368 {
3369     if (RenderLayer* scrollableLayer = enclosingScrollableLayer())
3370         return scrollableLayer;
3371
3372     // FIXME: We should return the frame view here (or possibly an ancestor frame view,
3373     // if the frame view isn't scrollable.
3374     return nullptr;
3375 }
3376
3377 bool RenderLayer::isScrollableOrRubberbandable()
3378 {
3379     return renderer().isScrollableOrRubberbandableBox();
3380 }
3381
3382 bool RenderLayer::hasScrollableOrRubberbandableAncestor()
3383 {
3384     for (RenderLayer* nextLayer = parentLayerCrossFrame(*this); nextLayer; nextLayer = parentLayerCrossFrame(*nextLayer)) {
3385         if (nextLayer->isScrollableOrRubberbandable())
3386             return true;
3387     }
3388
3389     return false;
3390 }
3391
3392 bool RenderLayer::useDarkAppearance() const
3393 {
3394     return renderer().useDarkAppearance();
3395 }
3396
3397 #if ENABLE(CSS_SCROLL_SNAP)
3398 void RenderLayer::updateSnapOffsets()
3399 {
3400     // FIXME: Extend support beyond HTMLElements.
3401     if (!is<HTMLElement>(enclosingElement()) || !enclosingElement()->renderBox())
3402         return;
3403
3404     RenderBox* box = enclosingElement()->renderBox();
3405     updateSnapOffsetsForScrollableArea(*this, *downcast<HTMLElement>(enclosingElement()), *box, box->style());
3406 }
3407
3408 bool RenderLayer::isScrollSnapInProgress() const
3409 {
3410     if (!scrollsOverflow())
3411         return false;
3412     
3413     if (ScrollAnimator* scrollAnimator = existingScrollAnimator())
3414         return scrollAnimator->isScrollSnapInProgress();
3415     
3416     return false;
3417 }
3418 #endif
3419
3420 bool RenderLayer::usesMockScrollAnimator() const
3421 {
3422     return DeprecatedGlobalSettings::usesMockScrollAnimator();
3423 }
3424
3425 void RenderLayer::logMockScrollAnimatorMessage(const String& message) const
3426 {
3427     renderer().document().addConsoleMessage(MessageSource::Other, MessageLevel::Debug, "RenderLayer: " + message);
3428 }
3429
3430 int RenderLayer::verticalScrollbarWidth(OverlayScrollbarSizeRelevancy relevancy) const
3431 {
3432     if (!m_vBar
3433         || !showsOverflowControls()
3434         || (m_vBar->isOverlayScrollbar() && (relevancy == IgnoreOverlayScrollbarSize || !m_vBar->shouldParticipateInHitTesting())))
3435         return 0;
3436
3437     return m_vBar->width();
3438 }
3439
3440 int RenderLayer::horizontalScrollbarHeight(OverlayScrollbarSizeRelevancy relevancy) const
3441 {
3442     if (!m_hBar
3443         || !showsOverflowControls()
3444         || (m_hBar->isOverlayScrollbar() && (relevancy == IgnoreOverlayScrollbarSize || !m_hBar->shouldParticipateInHitTesting())))
3445         return 0;
3446
3447     return m_hBar->height();
3448 }
3449
3450 IntSize RenderLayer::offsetFromResizeCorner(const IntPoint& absolutePoint) const
3451 {
3452     // Currently the resize corner is either the bottom right corner or the bottom left corner.
3453     // FIXME: This assumes the location is 0, 0. Is this guaranteed to always be the case?
3454     IntSize elementSize = size();
3455     if (shouldPlaceBlockDirectionScrollbarOnLeft())
3456         elementSize.setWidth(0);
3457     IntPoint resizerPoint = IntPoint(elementSize);
3458     IntPoint localPoint = roundedIntPoint(absoluteToContents(absolutePoint));
3459     return localPoint - resizerPoint;
3460 }
3461
3462 bool RenderLayer::hasOverflowControls() const
3463 {
3464     return m_hBar || m_vBar || m_scrollCorner || renderer().style().resize() != Resize::None;
3465 }
3466
3467 void RenderLayer::positionOverflowControls(const IntSize& offsetFromRoot)
3468 {
3469     if (!m_hBar && !m_vBar && !canResize())
3470         return;
3471     
3472     RenderBox* box = renderBox();
3473     if (!box)
3474         return;
3475
3476     const IntRect borderBox = snappedIntRect(box->borderBoxRect());
3477     const IntRect& scrollCorner = scrollCornerRect();
3478     IntRect absBounds(borderBox.location() + offsetFromRoot, borderBox.size());
3479     if (m_vBar) {
3480         IntRect vBarRect = rectForVerticalScrollbar(borderBox);
3481         vBarRect.move(offsetFromRoot);
3482         m_vBar->setFrameRect(vBarRect);
3483     }
3484     
3485     if (m_hBar) {
3486         IntRect hBarRect = rectForHorizontalScrollbar(borderBox);
3487         hBarRect.move(offsetFromRoot);
3488         m_hBar->setFrameRect(hBarRect);
3489     }
3490     
3491     if (m_scrollCorner)
3492         m_scrollCorner->setFrameRect(scrollCorner);
3493     if (m_resizer)
3494         m_resizer->setFrameRect(resizerCornerRect(*this, borderBox));
3495
3496     if (isComposited())
3497         backing()->positionOverflowControlsLayers();
3498 }
3499
3500 int RenderLayer::scrollWidth() const
3501 {
3502     ASSERT(renderBox());
3503     if (m_scrollDimensionsDirty)
3504         const_cast<RenderLayer*>(this)->computeScrollDimensions();
3505     // FIXME: This should use snappedIntSize() instead with absolute coordinates.
3506     return m_scrollSize.width();
3507 }
3508
3509 int RenderLayer::scrollHeight() const
3510 {
3511     ASSERT(renderBox());
3512     if (m_scrollDimensionsDirty)
3513         const_cast<RenderLayer*>(this)->computeScrollDimensions();
3514     // FIXME: This should use snappedIntSize() instead with absolute coordinates.
3515     return m_scrollSize.height();
3516 }
3517
3518 LayoutUnit RenderLayer::overflowTop() const
3519 {
3520     RenderBox* box = renderBox();
3521     LayoutRect overflowRect(box->layoutOverflowRect());
3522     box->flipForWritingMode(overflowRect);
3523     return overflowRect.y();
3524 }
3525
3526 LayoutUnit RenderLayer::overflowBottom() const
3527 {
3528     RenderBox* box = renderBox();
3529     LayoutRect overflowRect(box->layoutOverflowRect());
3530     box->flipForWritingMode(overflowRect);
3531     return overflowRect.maxY();
3532 }
3533
3534 LayoutUnit RenderLayer::overflowLeft() const
3535 {
3536     RenderBox* box = renderBox();
3537     LayoutRect overflowRect(box->layoutOverflowRect());
3538     box->flipForWritingMode(overflowRect);
3539     return overflowRect.x();
3540 }
3541
3542 LayoutUnit RenderLayer::overflowRight() const
3543 {
3544     RenderBox* box = renderBox();
3545     LayoutRect overflowRect(box->layoutOverflowRect());
3546     box->flipForWritingMode(overflowRect);
3547     return overflowRect.maxX();
3548 }
3549
3550 void RenderLayer::computeScrollDimensions()
3551 {
3552     RenderBox* box = renderBox();
3553     ASSERT(box);
3554
3555     m_scrollDimensionsDirty = false;
3556
3557     m_scrollSize.setWidth(roundToInt(overflowRight() - overflowLeft()));
3558     m_scrollSize.setHeight(roundToInt(overflowBottom() - overflowTop()));
3559
3560     int scrollableLeftOverflow = roundToInt(overflowLeft() - box->borderLeft());
3561     if (shouldPlaceBlockDirectionScrollbarOnLeft())
3562         scrollableLeftOverflow -= verticalScrollbarWidth();
3563     int scrollableTopOverflow = roundToInt(overflowTop() - box->borderTop());
3564     setScrollOrigin(IntPoint(-scrollableLeftOverflow, -scrollableTopOverflow));
3565 }
3566
3567 bool RenderLayer::hasScrollableHorizontalOverflow() const
3568 {
3569     return hasHorizontalOverflow() && renderBox()->scrollsOverflowX();
3570 }
3571
3572 bool RenderLayer::hasScrollableVerticalOverflow() const
3573 {
3574     return hasVerticalOverflow() && renderBox()->scrollsOverflowY();
3575 }
3576
3577 bool RenderLayer::hasHorizontalOverflow() const
3578 {
3579     ASSERT(!m_scrollDimensionsDirty);
3580
3581     return scrollWidth() > roundToInt(renderBox()->clientWidth());
3582 }
3583
3584 bool RenderLayer::hasVerticalOverflow() const
3585 {
3586     ASSERT(!m_scrollDimensionsDirty);
3587
3588     return scrollHeight() > roundToInt(renderBox()->clientHeight());
3589 }
3590
3591 static bool styleRequiresScrollbar(const RenderStyle& style, ScrollbarOrientation axis)
3592 {
3593     Overflow overflow = axis == ScrollbarOrientation::HorizontalScrollbar ? style.overflowX() : style.overflowY();
3594     bool overflowScrollActsLikeAuto = overflow == Overflow::Scroll && !style.hasPseudoStyle(PseudoId::Scrollbar) && ScrollbarTheme::theme().usesOverlayScrollbars();
3595     return overflow == Overflow::Scroll && !overflowScrollActsLikeAuto;
3596 }
3597
3598 static bool styleDefinesAutomaticScrollbar(const RenderStyle& style, ScrollbarOrientation axis)
3599 {
3600     Overflow overflow = axis == ScrollbarOrientation::HorizontalScrollbar ? style.overflowX() : style.overflowY();
3601     bool overflowScrollActsLikeAuto = overflow == Overflow::Scroll && !style.hasPseudoStyle(PseudoId::Scrollbar) && ScrollbarTheme::theme().usesOverlayScrollbars();
3602     return overflow == Overflow::Auto || overflowScrollActsLikeAuto;
3603 }
3604
3605 void RenderLayer::updateScrollbarsAfterLayout()
3606 {
3607     RenderBox* box = renderBox();
3608     ASSERT(box);
3609
3610     // List box parts handle the scrollbars by themselves so we have nothing to do.
3611     if (box->style().appearance() == ListboxPart)
3612         return;
3613
3614     bool hasHorizontalOverflow = this->hasHorizontalOverflow();
3615     bool hasVerticalOverflow = this->hasVerticalOverflow();
3616
3617     // If overflow requires a scrollbar, then we just need to enable or disable.
3618     if (m_hBar && styleRequiresScrollbar(renderer().style(), HorizontalScrollbar))
3619         m_hBar->setEnabled(hasHorizontalOverflow);
3620     if (m_vBar && styleRequiresScrollbar(renderer().style(), VerticalScrollbar))
3621         m_vBar->setEnabled(hasVerticalOverflow);
3622
3623     // Scrollbars with auto behavior may need to lay out again if scrollbars got added or removed.
3624     bool autoHorizontalScrollBarChanged = box->hasHorizontalScrollbarWithAutoBehavior() && (hasHorizontalScrollbar() != hasHorizontalOverflow);
3625     bool autoVerticalScrollBarChanged = box->hasVerticalScrollbarWithAutoBehavior() && (hasVerticalScrollbar() != hasVerticalOverflow);
3626
3627     if (autoHorizontalScrollBarChanged || autoVerticalScrollBarChanged) {
3628         if (box->hasHorizontalScrollbarWithAutoBehavior())
3629             setHasHorizontalScrollbar(hasHorizontalOverflow);
3630         if (box->hasVerticalScrollbarWithAutoBehavior())
3631             setHasVerticalScrollbar(hasVerticalOverflow);
3632
3633         updateSelfPaintingLayer();
3634
3635         renderer().repaint();
3636
3637         if (renderer().style().overflowX() == Overflow::Auto || renderer().style().overflowY() == Overflow::Auto) {
3638             if (!m_inOverflowRelayout) {
3639                 m_inOverflowRelayout = true;
3640                 renderer().setNeedsLayout(MarkOnlyThis);
3641                 if (is<RenderBlock>(renderer())) {
3642                     RenderBlock& block = downcast<RenderBlock>(renderer());
3643                     block.scrollbarsChanged(autoHorizontalScrollBarChanged, autoVerticalScrollBarChanged);
3644                     block.layoutBlock(true);
3645                 } else
3646                     renderer().layout();
3647                 m_inOverflowRelayout = false;
3648             }
3649         }
3650         
3651         RenderObject* parent = renderer().parent();
3652         if (parent && parent->isFlexibleBox() && renderer().isBox())
3653             downcast<RenderFlexibleBox>(parent)->clearCachedMainSizeForChild(*renderBox());
3654     }
3655
3656     // Set up the range (and page step/line step).
3657     if (m_hBar) {
3658         int clientWidth = roundToInt(box->clientWidth());
3659         int pageStep = Scrollbar::pageStep(clientWidth);
3660         m_hBar->setSteps(Scrollbar::pixelsPerLineStep(), pageStep);
3661         m_hBar->setProportion(clientWidth, m_scrollSize.width());
3662     }
3663     if (m_vBar) {
3664         int clientHeight = roundToInt(box->clientHeight());
3665         int pageStep = Scrollbar::pageStep(clientHeight);
3666         m_vBar->setSteps(Scrollbar::pixelsPerLineStep(), pageStep);
3667         m_vBar->setProportion(clientHeight, m_scrollSize.height());
3668     }
3669
3670     updateScrollableAreaSet(hasScrollableHorizontalOverflow() || hasScrollableVerticalOverflow());
3671 }
3672
3673 // This is called from layout code (before updateLayerPositions).
3674 void RenderLayer::updateScrollInfoAfterLayout()
3675 {
3676     RenderBox* box = renderBox();
3677     if (!box)
3678         return;
3679
3680     m_scrollDimensionsDirty = true;
3681     ScrollOffset originalScrollOffset = scrollOffset();
3682
3683     computeScrollDimensions();
3684
3685 #if ENABLE(CSS_SCROLL_SNAP)
3686     // FIXME: Ensure that offsets are also updated in case of programmatic style changes.
3687     // https://bugs.webkit.org/show_bug.cgi?id=135964
3688     updateSnapOffsets();
3689 #endif
3690
3691     if (!box->isHTMLMarquee() && !isRubberBandInProgress()) {
3692         // Layout may cause us to be at an invalid scroll position. In this case we need
3693         // to pull our scroll offsets back to the max (or push them up to the min).
3694         ScrollOffset clampedScrollOffset = clampScrollOffset(scrollOffset());
3695 #if PLATFORM(IOS_FAMILY)
3696         // FIXME: This looks wrong. The caret adjust mode should only be enabled on editing related entry points.
3697         // This code was added to fix an issue where the text insertion point would always be drawn on the right edge
3698         // of a text field whose content overflowed its bounds. See <rdar://problem/15579797> for more details.
3699         setAdjustForIOSCaretWhenScrolling(true);
3700 #endif
3701         if (clampedScrollOffset != scrollOffset())
3702             scrollToOffset(clampedScrollOffset);
3703
3704 #if PLATFORM(IOS_FAMILY)
3705         setAdjustForIOSCaretWhenScrolling(false);
3706 #endif
3707     }
3708
3709     updateScrollbarsAfterLayout();
3710
3711     if (originalScrollOffset != scrollOffset())
3712         scrollToOffsetWithoutAnimation(IntPoint(scrollOffset()));
3713
3714     if (isComposited()) {
3715         setNeedsCompositingGeometryUpdate();
3716         setNeedsCompositingConfigurationUpdate();
3717     }
3718
3719     if (canUseCompositedScrolling())
3720         setNeedsPostLayoutCompositingUpdate();
3721
3722     updateScrollSnapState();
3723 }
3724
3725 bool RenderLayer::overflowControlsIntersectRect(const IntRect& localRect) const
3726 {
3727     const IntRect borderBox = snappedIntRect(renderBox()->borderBoxRect());
3728
3729     if (rectForHorizontalScrollbar(borderBox).intersects(localRect))
3730         return true;
3731
3732     if (rectForVerticalScrollbar(borderBox).intersects(localRect))
3733         return true;
3734
3735     if (scrollCornerRect().intersects(localRect))
3736         return true;
3737     
3738     if (resizerCornerRect(*this, borderBox).intersects(localRect))
3739         return true;
3740
3741     return false;
3742 }
3743
3744 bool RenderLayer::showsOverflowControls() const
3745 {
3746 #if PLATFORM(IOS_FAMILY)
3747     // On iOS, the scrollbars are made in the UI process.
3748     return !canUseCompositedScrolling();
3749 #endif
3750
3751     return true;
3752 }
3753
3754 void RenderLayer::paintOverflowControls(GraphicsContext& context, const IntPoint& paintOffset, const IntRect& damageRect, bool paintingOverlayControls)
3755 {
3756     // Don't do anything if we have no overflow.
3757     if (!renderer().hasOverflowClip())
3758         return;
3759
3760     if (!showsOverflowControls())
3761         return;
3762
3763     // Overlay scrollbars paint in a second pass through the layer tree so that they will paint
3764     // on top of everything else. If this is the normal painting pass, paintingOverlayControls
3765     // will be false, and we should just tell the root layer that there are overlay scrollbars
3766     // that need to be painted. That will cause the second pass through the layer tree to run,
3767     // and we'll paint the scrollbars then. In the meantime, cache tx and ty so that the 
3768     // second pass doesn't need to re-enter the RenderTree to get it right.
3769     if (hasOverlayScrollbars() && !paintingOverlayControls) {
3770         m_cachedOverlayScrollbarOffset = paintOffset;
3771
3772         // It's not necessary to do the second pass if the scrollbars paint into layers.
3773         if ((m_hBar && layerForHorizontalScrollbar()) || (m_vBar && layerForVerticalScrollbar()))
3774             return;
3775         IntRect localDamgeRect = damageRect;
3776         localDamgeRect.moveBy(-paintOffset);
3777         if (!overflowControlsIntersectRect(localDamgeRect))
3778             return;
3779
3780         RenderLayer* paintingRoot = enclosingCompositingLayer();
3781         if (!paintingRoot)
3782             paintingRoot = renderer().view().layer();
3783
3784         paintingRoot->setContainsDirtyOverlayScrollbars(true);
3785         return;
3786     }
3787
3788     // This check is required to avoid painting custom CSS scrollbars twice.
3789     if (paintingOverlayControls && !hasOverlayScrollbars())
3790         return;
3791
3792     IntPoint adjustedPaintOffset = paintOffset;
3793     if (paintingOverlayControls)
3794         adjustedPaintOffset = m_cachedOverlayScrollbarOffset;
3795
3796     // Move the scrollbar widgets if necessary.  We normally move and resize widgets during layout, but sometimes
3797     // widgets can move without layout occurring (most notably when you scroll a document that
3798     // contains fixed positioned elements).
3799     positionOverflowControls(toIntSize(adjustedPaintOffset));
3800
3801     // Now that we're sure the scrollbars are in the right place, paint them.
3802     if (m_hBar && !layerForHorizontalScrollbar())
3803         m_hBar->paint(context, damageRect);
3804     if (m_vBar && !layerForVerticalScrollbar())
3805         m_vBar->paint(context, damageRect);
3806
3807     if (layerForScrollCorner())
3808         return;
3809
3810     // We fill our scroll corner with white if we have a scrollbar that doesn't run all the way up to the
3811     // edge of the box.
3812     paintScrollCorner(context, adjustedPaintOffset, damageRect);
3813     
3814     // Paint our resizer last, since it sits on top of the scroll corner.
3815     paintResizer(context, adjustedPaintOffset, damageRect);
3816 }
3817
3818 void RenderLayer::paintScrollCorner(GraphicsContext& context, const IntPoint& paintOffset, const IntRect& damageRect)
3819 {
3820     IntRect absRect = scrollCornerRect();
3821     absRect.moveBy(paintOffset);
3822     if (!absRect.intersects(damageRect))
3823         return;
3824
3825     if (context.invalidatingControlTints()) {
3826         updateScrollCornerStyle();
3827         return;
3828     }
3829
3830     if (m_scrollCorner) {
3831         m_scrollCorner->paintIntoRect(context, paintOffset, absRect);
3832         return;
3833     }
3834
3835     // We don't want to paint a corner if we have overlay scrollbars, since we need
3836     // to see what is behind it.
3837     if (!hasOverlayScrollbars())
3838         ScrollbarTheme::theme().paintScrollCorner(context, absRect);
3839 }
3840
3841 void RenderLayer::drawPlatformResizerImage(GraphicsContext& context, const LayoutRect& resizerCornerRect)
3842 {
3843     RefPtr<Image> resizeCornerImage;
3844     FloatSize cornerResizerSize;
3845     if (renderer().document().deviceScaleFactor() >= 2) {
3846         static NeverDestroyed<Image*> resizeCornerImageHiRes(&Image::loadPlatformResource("textAreaResizeCorner@2x").leakRef());
3847         resizeCornerImage = resizeCornerImageHiRes;
3848         cornerResizerSize = resizeCornerImage->size();
3849         cornerResizerSize.scale(0.5f);
3850     } else {
3851         static NeverDestroyed<Image*> resizeCornerImageLoRes(&Image::loadPlatformResource("textAreaResizeCorner").leakRef());
3852         resizeCornerImage = resizeCornerImageLoRes;
3853         cornerResizerSize = resizeCornerImage->size();
3854     }
3855
3856     if (shouldPlaceBlockDirectionScrollbarOnLeft()) {
3857         context.save();
3858         context.translate(resizerCornerRect.x() + cornerResizerSize.width(), resizerCornerRect.y() + resizerCornerRect.height() - cornerResizerSize.height());
3859         context.scale(FloatSize(-1.0, 1.0));
3860         if (resizeCornerImage)
3861             context.drawImage(*resizeCornerImage, FloatRect(FloatPoint(), cornerResizerSize));
3862         context.restore();
3863         return;
3864     }
3865     
3866     if (!resizeCornerImage)
3867         return;
3868     FloatRect imageRect = snapRectToDevicePixels(LayoutRect(resizerCornerRect.maxXMaxYCorner() - cornerResizerSize, cornerResizerSize), renderer().document().deviceScaleFactor());
3869     context.drawImage(*resizeCornerImage, imageRect);
3870 }
3871
3872 void RenderLayer::paintResizer(GraphicsContext& context, const LayoutPoint& paintOffset, const LayoutRect& damageRect)
3873 {
3874     if (renderer().style().resize() == Resize::None)
3875         return;
3876
3877     RenderBox* box = renderBox();
3878     ASSERT(box);
3879
3880     LayoutRect absRect = resizerCornerRect(*this, box->borderBoxRect());
3881     absRect.moveBy(paintOffset);
3882     if (!absRect.intersects(damageRect))
3883         return;
3884
3885     if (context.invalidatingControlTints()) {
3886         updateResizerStyle();
3887         return;
3888     }
3889     
3890     if (m_resizer) {
3891         m_resizer->paintIntoRect(context, paintOffset, absRect);
3892         return;
3893     }
3894
3895     drawPlatformResizerImage(context, absRect);
3896
3897     // Draw a frame around the resizer (1px grey line) if there are any scrollbars present.
3898     // Clipping will exclude the right and bottom edges of this frame.
3899     if (!hasOverlayScrollbars() && (m_vBar || m_hBar)) {
3900         GraphicsContextStateSaver stateSaver(context);
3901         context.clip(absRect);
3902         LayoutRect largerCorner = absRect;
3903         largerCorner.setSize(LayoutSize(largerCorner.width() + 1_lu, largerCorner.height() + 1_lu));
3904         context.setStrokeColor(Color(makeRGB(217, 217, 217)));
3905         context.setStrokeThickness(1.0f);
3906         context.setFillColor(Color::transparent);
3907         context.drawRect(snappedIntRect(largerCorner));
3908     }
3909 }
3910
3911 bool RenderLayer::isPointInResizeControl(const IntPoint& absolutePoint) const
3912 {
3913     if (!canResize())
3914         return false;
3915     
3916     RenderBox* box = renderBox();
3917     ASSERT(box);
3918
3919     IntPoint localPoint = roundedIntPoint(absoluteToContents(absolutePoint));
3920
3921     IntRect localBounds(IntPoint(), snappedIntRect(box->frameRect()).size());
3922     return resizerCornerRect(*this, localBounds).contains(localPoint);
3923 }
3924
3925 bool RenderLayer::hitTestOverflowControls(HitTestResult& result, const IntPoint& localPoint)
3926 {
3927     if (!m_hBar && !m_vBar && !canResize())
3928         return false;
3929
3930     RenderBox* box = renderBox();
3931     ASSERT(box);
3932     
3933     IntRect resizeControlRect;
3934     if (renderer().style().resize() != Resize::None) {
3935         resizeControlRect = snappedIntRect(resizerCornerRect(*this, box->borderBoxRect()));
3936         if (resizeControlRect.contains(localPoint))
3937             return true;
3938     }
3939
3940     int resizeControlSize = std::max(resizeControlRect.height(), 0);
3941
3942     // FIXME: We should hit test the m_scrollCorner and pass it back through the result.
3943
3944     if (m_vBar && m_vBar->shouldParticipateInHitTesting()) {
3945         LayoutRect vBarRect(verticalScrollbarStart(0, box->width()),
3946                             box->borderTop(),
3947                             m_vBar->width(),
3948                             box->height() - (box->borderTop() + box->borderBottom()) - (m_hBar ? m_hBar->height() : resizeControlSize));
3949         if (vBarRect.contains(localPoint)) {
3950             result.setScrollbar(m_vBar.get());
3951             return true;
3952         }
3953     }
3954
3955     resizeControlSize = std::max(resizeControlRect.width(), 0);
3956     if (m_hBar && m_hBar->shouldParticipateInHitTesting()) {
3957         LayoutRect hBarRect(horizontalScrollbarStart(0),
3958                             box->height() - box->borderBottom() - m_hBar->height(),
3959                             box->width() - (box->borderLeft() + box->borderRight()) - (m_vBar ? m_vBar->width() : resizeControlSize),
3960                             m_hBar->height());
3961         if (hBarRect.contains(localPoint)) {
3962             result.setScrollbar(m_hBar.get());
3963             return true;
3964         }
3965     }
3966
3967     return false;
3968 }
3969
3970 bool RenderLayer::scroll(ScrollDirection direction, ScrollGranularity granularity, float multiplier)
3971 {
3972     return ScrollableArea::scroll(direction, granularity, multiplier);
3973 }
3974
3975 void RenderLayer::paint(GraphicsContext& context, const LayoutRect& damageRect, const LayoutSize& subpixelOffset, OptionSet<PaintBehavior> paintBehavior, RenderObject* subtreePaintRoot, OptionSet<PaintLayerFlag> paintFlags, SecurityOriginPaintPolicy paintPolicy)
3976 {
3977     OverlapTestRequestMap overlapTestRequests;
3978
3979     LayerPaintingInfo paintingInfo(this, enclosingIntRect(damageRect), paintBehavior, subpixelOffset, subtreePaintRoot, &overlapTestRequests, paintPolicy == SecurityOriginPaintPolicy::AccessibleOriginOnly);
3980     paintLayer(context, paintingInfo, paintFlags);
3981
3982     for (auto& widget : overlapTestRequests.keys())
3983         widget->setOverlapTestResult(false);
3984 }
3985
3986 void RenderLayer::paintOverlayScrollbars(GraphicsContext& context, const LayoutRect& damageRect, OptionSet<PaintBehavior> paintBehavior, RenderObject* subtreePaintRoot)
3987 {
3988     if (!m_containsDirtyOverlayScrollbars)
3989         return;
3990
3991     LayerPaintingInfo paintingInfo(this, enclosingIntRect(damageRect), paintBehavior, LayoutSize(), subtreePaintRoot);
3992     paintLayer(context, paintingInfo, PaintLayerPaintingOverlayScrollbars);
3993
3994     m_containsDirtyOverlayScrollbars = false;
3995 }
3996
3997 void RenderLayer::clipToRect(GraphicsContext& context, const LayerPaintingInfo& paintingInfo, const ClipRect& clipRect, BorderRadiusClippingRule rule)
3998 {
3999     float deviceScaleFactor = renderer().document().deviceScaleFactor();
4000     bool needsClipping = !clipRect.isInfinite() && clipRect.rect() != paintingInfo.paintDirtyRect;
4001     if (needsClipping || clipRect.affectedByRadius())