1460831cae22925cdaf2eaf1316e1e6e12a40648
[WebKit-https.git] / Source / WebCore / page / FrameView.cpp
1 /*
2  * Copyright (C) 1998, 1999 Torben Weis <weis@kde.org>
3  *                     1999 Lars Knoll <knoll@kde.org>
4  *                     1999 Antti Koivisto <koivisto@kde.org>
5  *                     2000 Dirk Mueller <mueller@kde.org>
6  * Copyright (C) 2004, 2005, 2006, 2007, 2008 Apple Inc. All rights reserved.
7  *           (C) 2006 Graham Dennis (graham.dennis@gmail.com)
8  *           (C) 2006 Alexey Proskuryakov (ap@nypop.com)
9  * Copyright (C) 2009 Google Inc. All rights reserved.
10  *
11  * This library is free software; you can redistribute it and/or
12  * modify it under the terms of the GNU Library General Public
13  * License as published by the Free Software Foundation; either
14  * version 2 of the License, or (at your option) any later version.
15  *
16  * This library is distributed in the hope that it will be useful,
17  * but WITHOUT ANY WARRANTY; without even the implied warranty of
18  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
19  * Library General Public License for more details.
20  *
21  * You should have received a copy of the GNU Library General Public License
22  * along with this library; see the file COPYING.LIB.  If not, write to
23  * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
24  * Boston, MA 02110-1301, USA.
25  */
26
27 #include "config.h"
28 #include "FrameView.h"
29
30 #include "AXObjectCache.h"
31 #include "BackForwardController.h"
32 #include "CachedResourceLoader.h"
33 #include "Chrome.h"
34 #include "ChromeClient.h"
35 #include "DocumentMarkerController.h"
36 #include "EventHandler.h"
37 #include "FloatRect.h"
38 #include "FocusController.h"
39 #include "FontCache.h"
40 #include "FontLoader.h"
41 #include "Frame.h"
42 #include "FrameActionScheduler.h"
43 #include "FrameLoader.h"
44 #include "FrameLoaderClient.h"
45 #include "FrameTree.h"
46 #include "GraphicsContext.h"
47 #include "HTMLDocument.h"
48 #include "HTMLFrameElement.h"
49 #include "HTMLFrameSetElement.h"
50 #include "HTMLNames.h"
51 #include "HTMLPlugInImageElement.h"
52 #include "InspectorClient.h"
53 #include "InspectorController.h"
54 #include "InspectorInstrumentation.h"
55 #include "OverflowEvent.h"
56 #include "RenderArena.h"
57 #include "RenderEmbeddedObject.h"
58 #include "RenderFullScreen.h"
59 #include "RenderIFrame.h"
60 #include "RenderLayer.h"
61 #include "RenderLayerBacking.h"
62 #include "RenderPart.h"
63 #include "RenderScrollbar.h"
64 #include "RenderScrollbarPart.h"
65 #include "RenderTheme.h"
66 #include "RenderView.h"
67 #include "ScrollAnimator.h"
68 #include "ScrollingCoordinator.h"
69 #include "Settings.h"
70 #include "StyleResolver.h"
71 #include "TextResourceDecoder.h"
72 #include "TextStream.h"
73
74 #include <wtf/CurrentTime.h>
75 #include <wtf/TemporaryChange.h>
76 #include <wtf/UnusedParam.h>
77
78 #if USE(ACCELERATED_COMPOSITING)
79 #include "RenderLayerCompositor.h"
80 #include "TiledBacking.h"
81 #endif
82
83 #if ENABLE(SVG)
84 #include "RenderSVGRoot.h"
85 #include "SVGDocument.h"
86 #include "SVGSVGElement.h"
87 #endif
88
89 #if USE(TILED_BACKING_STORE)
90 #include "TiledBackingStore.h"
91 #endif
92
93 #if ENABLE(TEXT_AUTOSIZING)
94 #include "TextAutosizer.h"
95 #endif
96
97 #if PLATFORM(CHROMIUM)
98 #include "TraceEvent.h"
99 #endif
100
101 namespace WebCore {
102
103 using namespace HTMLNames;
104
105 double FrameView::sCurrentPaintTimeStamp = 0.0;
106
107
108 // REPAINT_THROTTLING now chooses default values for throttling parameters.
109 // Should be removed when applications start using runtime configuration.
110 #if ENABLE(REPAINT_THROTTLING)
111 // Normal delay
112 double FrameView::s_normalDeferredRepaintDelay = 0.016;
113 // Negative value would mean that first few repaints happen without a delay
114 double FrameView::s_initialDeferredRepaintDelayDuringLoading = 0;
115 // The delay grows on each repaint to this maximum value
116 double FrameView::s_maxDeferredRepaintDelayDuringLoading = 2.5;
117 // On each repaint the delay increses by this amount
118 double FrameView::s_deferredRepaintDelayIncrementDuringLoading = 0.5;
119 #else
120 // FIXME: Repaint throttling could be good to have on all platform.
121 // The balance between CPU use and repaint frequency will need some tuning for desktop.
122 // More hooks may be needed to reset the delay on things like GIF and CSS animations.
123 double FrameView::s_normalDeferredRepaintDelay = 0;
124 double FrameView::s_initialDeferredRepaintDelayDuringLoading = 0;
125 double FrameView::s_maxDeferredRepaintDelayDuringLoading = 0;
126 double FrameView::s_deferredRepaintDelayIncrementDuringLoading = 0;
127 #endif
128
129 // The maximum number of updateWidgets iterations that should be done before returning.
130 static const unsigned maxUpdateWidgetsIterations = 2;
131
132 static RenderLayer::UpdateLayerPositionsFlags updateLayerPositionFlags(RenderLayer* layer, bool isRelayoutingSubtree, bool didFullRepaint)
133 {
134     RenderLayer::UpdateLayerPositionsFlags flags = RenderLayer::defaultFlags;
135     if (didFullRepaint) {
136         flags &= ~RenderLayer::CheckForRepaint;
137         flags |= RenderLayer::NeedsFullRepaintInBacking;
138     }
139     if (isRelayoutingSubtree && layer->isPaginated())
140         flags |= RenderLayer::UpdatePagination;
141     return flags;
142 }
143
144 Pagination::Mode paginationModeForRenderStyle(RenderStyle* style)
145 {
146     EOverflow overflow = style->overflowY();
147     if (overflow != OPAGEDX && overflow != OPAGEDY)
148         return Pagination::Unpaginated;
149
150     bool isHorizontalWritingMode = style->isHorizontalWritingMode();
151     TextDirection textDirection = style->direction();
152     WritingMode writingMode = style->writingMode();
153
154     // paged-x always corresponds to LeftToRightPaginated or RightToLeftPaginated. If the WritingMode
155     // is horizontal, then we use TextDirection to choose between those options. If the WritingMode
156     // is vertical, then the direction of the verticality dictates the choice.
157     if (overflow == OPAGEDX) {
158         if ((isHorizontalWritingMode && textDirection == LTR) || writingMode == LeftToRightWritingMode)
159             return Pagination::LeftToRightPaginated;
160         return Pagination::RightToLeftPaginated;
161     }
162
163     // paged-y always corresponds to TopToBottomPaginated or BottomToTopPaginated. If the WritingMode
164     // is horizontal, then the direction of the horizontality dictates the choice. If the WritingMode
165     // is vertical, then we use TextDirection to choose between those options. 
166     if (writingMode == TopToBottomWritingMode || (!isHorizontalWritingMode && textDirection == RTL))
167         return Pagination::TopToBottomPaginated;
168     return Pagination::BottomToTopPaginated;
169 }
170
171 FrameView::FrameView(Frame* frame)
172     : m_frame(frame)
173     , m_canHaveScrollbars(true)
174     , m_slowRepaintObjectCount(0)
175     , m_layoutTimer(this, &FrameView::layoutTimerFired)
176     , m_layoutRoot(0)
177     , m_inSynchronousPostLayout(false)
178     , m_postLayoutTasksTimer(this, &FrameView::postLayoutTimerFired)
179     , m_isTransparent(false)
180     , m_baseBackgroundColor(Color::white)
181     , m_mediaType("screen")
182     , m_actionScheduler(adoptPtr(new FrameActionScheduler))
183     , m_overflowStatusDirty(true)
184     , m_viewportRenderer(0)
185     , m_wasScrolledByUser(false)
186     , m_inProgrammaticScroll(false)
187     , m_safeToPropagateScrollToParent(true)
188     , m_deferredRepaintTimer(this, &FrameView::deferredRepaintTimerFired)
189     , m_disableRepaints(0)
190     , m_isTrackingRepaints(false)
191     , m_shouldUpdateWhileOffscreen(true)
192     , m_deferSetNeedsLayouts(0)
193     , m_setNeedsLayoutWasDeferred(false)
194     , m_scrollCorner(0)
195     , m_shouldAutoSize(false)
196     , m_inAutoSize(false)
197     , m_didRunAutosize(false)
198 #if ENABLE(CSS_FILTERS)
199     , m_hasSoftwareFilters(false)
200 #endif
201 {
202     init();
203
204     // FIXME: Can m_frame ever be null here?
205     if (!m_frame)
206         return;
207
208     Page* page = m_frame->page();
209     if (!page)
210         return;
211
212     if (m_frame == page->mainFrame()) {
213         ScrollableArea::setVerticalScrollElasticity(ScrollElasticityAllowed);
214         ScrollableArea::setHorizontalScrollElasticity(ScrollElasticityAllowed);
215     }
216 }
217
218 PassRefPtr<FrameView> FrameView::create(Frame* frame)
219 {
220     RefPtr<FrameView> view = adoptRef(new FrameView(frame));
221     view->show();
222     return view.release();
223 }
224
225 PassRefPtr<FrameView> FrameView::create(Frame* frame, const IntSize& initialSize)
226 {
227     RefPtr<FrameView> view = adoptRef(new FrameView(frame));
228     view->Widget::setFrameRect(IntRect(view->location(), initialSize));
229     view->show();
230     return view.release();
231 }
232
233 FrameView::~FrameView()
234 {
235     if (m_postLayoutTasksTimer.isActive()) {
236         m_postLayoutTasksTimer.stop();
237         m_actionScheduler->clear();
238     }
239     
240     removeFromAXObjectCache();
241     resetScrollbars();
242
243     // Custom scrollbars should already be destroyed at this point
244     ASSERT(!horizontalScrollbar() || !horizontalScrollbar()->isCustomScrollbar());
245     ASSERT(!verticalScrollbar() || !verticalScrollbar()->isCustomScrollbar());
246
247     setHasHorizontalScrollbar(false); // Remove native scrollbars now before we lose the connection to the HostWindow.
248     setHasVerticalScrollbar(false);
249     
250     ASSERT(!m_scrollCorner);
251     ASSERT(m_actionScheduler->isEmpty());
252
253     if (m_frame) {
254         ASSERT(m_frame->view() != this || !m_frame->contentRenderer());
255         RenderPart* renderer = m_frame->ownerRenderer();
256         if (renderer && renderer->widget() == this)
257             renderer->setWidget(0);
258     }
259 }
260
261 void FrameView::reset()
262 {
263     m_cannotBlitToWindow = false;
264     m_isOverlapped = false;
265     m_contentIsOpaque = false;
266     m_borderX = 30;
267     m_borderY = 30;
268     m_layoutTimer.stop();
269     m_layoutRoot = 0;
270     m_delayedLayout = false;
271     m_doFullRepaint = true;
272     m_layoutSchedulingEnabled = true;
273     m_inLayout = false;
274     m_doingPreLayoutStyleUpdate = false;
275     m_inSynchronousPostLayout = false;
276     m_layoutCount = 0;
277     m_nestedLayoutCount = 0;
278     m_postLayoutTasksTimer.stop();
279     m_firstLayout = true;
280     m_firstLayoutCallbackPending = false;
281     m_wasScrolledByUser = false;
282     m_safeToPropagateScrollToParent = true;
283     m_lastViewportSize = IntSize();
284     m_lastZoomFactor = 1.0f;
285     m_deferringRepaints = 0;
286     m_repaintCount = 0;
287     m_repaintRects.clear();
288     m_deferredRepaintDelay = s_initialDeferredRepaintDelayDuringLoading;
289     m_deferredRepaintTimer.stop();
290     m_isTrackingRepaints = false;
291     m_trackedRepaintRects.clear();
292     m_lastPaintTime = 0;
293     m_paintBehavior = PaintBehaviorNormal;
294     m_isPainting = false;
295     m_visuallyNonEmptyCharacterCount = 0;
296     m_visuallyNonEmptyPixelCount = 0;
297     m_isVisuallyNonEmpty = false;
298     m_firstVisuallyNonEmptyLayoutCallbackPending = true;
299     m_maintainScrollPositionAnchor = 0;
300     m_disableRepaints = 0;
301 }
302
303 void FrameView::removeFromAXObjectCache()
304 {
305     if (AXObjectCache::accessibilityEnabled() && axObjectCache())
306         axObjectCache()->remove(this);
307 }
308
309 void FrameView::clearFrame()
310 {
311     m_frame = 0;
312 }
313
314 void FrameView::resetScrollbars()
315 {
316     // Reset the document's scrollbars back to our defaults before we yield the floor.
317     m_firstLayout = true;
318     setScrollbarsSuppressed(true);
319     if (m_canHaveScrollbars)
320         setScrollbarModes(ScrollbarAuto, ScrollbarAuto);
321     else
322         setScrollbarModes(ScrollbarAlwaysOff, ScrollbarAlwaysOff);
323     setScrollbarsSuppressed(false);
324 }
325
326 void FrameView::resetScrollbarsAndClearContentsSize()
327 {
328     resetScrollbars();
329
330     setScrollbarsSuppressed(true);
331     setContentsSize(IntSize());
332     setScrollbarsSuppressed(false);
333 }
334
335 void FrameView::init()
336 {
337     reset();
338
339     m_margins = LayoutSize(-1, -1); // undefined
340     m_size = LayoutSize();
341
342     // Propagate the marginwidth/height and scrolling modes to the view.
343     Element* ownerElement = m_frame ? m_frame->ownerElement() : 0;
344     if (ownerElement && (ownerElement->hasTagName(frameTag) || ownerElement->hasTagName(iframeTag))) {
345         HTMLFrameElementBase* frameElt = static_cast<HTMLFrameElementBase*>(ownerElement);
346         if (frameElt->scrollingMode() == ScrollbarAlwaysOff)
347             setCanHaveScrollbars(false);
348         LayoutUnit marginWidth = frameElt->marginWidth();
349         LayoutUnit marginHeight = frameElt->marginHeight();
350         if (marginWidth != -1)
351             setMarginWidth(marginWidth);
352         if (marginHeight != -1)
353             setMarginHeight(marginHeight);
354     }
355 }
356     
357 void FrameView::prepareForDetach()
358 {
359     detachCustomScrollbars();
360     // When the view is no longer associated with a frame, it needs to be removed from the ax object cache
361     // right now, otherwise it won't be able to reach the topDocument()'s axObject cache later.
362     removeFromAXObjectCache();
363
364     if (m_frame && m_frame->page()) {
365         if (ScrollingCoordinator* scrollingCoordinator = m_frame->page()->scrollingCoordinator())
366             scrollingCoordinator->willDestroyScrollableArea(this);
367     }
368 }
369
370 void FrameView::detachCustomScrollbars()
371 {
372     Scrollbar* horizontalBar = horizontalScrollbar();
373     if (horizontalBar && horizontalBar->isCustomScrollbar())
374         setHasHorizontalScrollbar(false);
375
376     Scrollbar* verticalBar = verticalScrollbar();
377     if (verticalBar && verticalBar->isCustomScrollbar())
378         setHasVerticalScrollbar(false);
379
380     if (m_scrollCorner) {
381         m_scrollCorner->destroy();
382         m_scrollCorner = 0;
383     }
384 }
385
386 void FrameView::recalculateScrollbarOverlayStyle()
387 {
388     ScrollbarOverlayStyle oldOverlayStyle = scrollbarOverlayStyle();
389     ScrollbarOverlayStyle overlayStyle = ScrollbarOverlayStyleDefault;
390
391     Color backgroundColor = documentBackgroundColor();
392     if (backgroundColor.isValid()) {
393         // Reduce the background color from RGB to a lightness value
394         // and determine which scrollbar style to use based on a lightness
395         // heuristic.
396         double hue, saturation, lightness;
397         backgroundColor.getHSL(hue, saturation, lightness);
398         if (lightness <= .5)
399             overlayStyle = ScrollbarOverlayStyleLight;
400     }
401
402     if (oldOverlayStyle != overlayStyle)
403         setScrollbarOverlayStyle(overlayStyle);
404 }
405
406 void FrameView::clear()
407 {
408     setCanBlitOnScroll(true);
409     
410     reset();
411
412     if (m_frame) {
413         if (RenderPart* renderer = m_frame->ownerRenderer())
414             renderer->viewCleared();
415     }
416
417     setScrollbarsSuppressed(true);
418 }
419
420 bool FrameView::didFirstLayout() const
421 {
422     return !m_firstLayout;
423 }
424
425 void FrameView::invalidateRect(const IntRect& rect)
426 {
427     if (!parent()) {
428         if (hostWindow())
429             hostWindow()->invalidateContentsAndRootView(rect, false /*immediate*/);
430         return;
431     }
432
433     if (!m_frame)
434         return;
435
436     RenderPart* renderer = m_frame->ownerRenderer();
437     if (!renderer)
438         return;
439
440     IntRect repaintRect = rect;
441     repaintRect.move(renderer->borderLeft() + renderer->paddingLeft(),
442                      renderer->borderTop() + renderer->paddingTop());
443     renderer->repaintRectangle(repaintRect);
444 }
445
446 void FrameView::setFrameRect(const IntRect& newRect)
447 {
448     IntRect oldRect = frameRect();
449     if (newRect == oldRect)
450         return;
451
452 #if ENABLE(TEXT_AUTOSIZING)
453     // Autosized font sizes depend on the width of the viewing area.
454     if (newRect.width() != oldRect.width()) {
455         Page* page = m_frame ? m_frame->page() : 0;
456         if (page && page->mainFrame() == m_frame && page->settings()->textAutosizingEnabled()) {
457             for (Frame* frame = page->mainFrame(); frame; frame = frame->tree()->traverseNext())
458                 m_frame->document()->textAutosizer()->recalculateMultipliers();
459         }
460     }
461 #endif
462
463     ScrollView::setFrameRect(newRect);
464
465     updateScrollableAreaSet();
466
467 #if USE(ACCELERATED_COMPOSITING)
468     if (RenderView* renderView = this->renderView()) {
469         if (renderView->usesCompositing())
470             renderView->compositor()->frameViewDidChangeSize();
471     }
472 #endif
473 }
474
475 #if ENABLE(REQUEST_ANIMATION_FRAME)
476 bool FrameView::scheduleAnimation()
477 {
478     if (hostWindow()) {
479         hostWindow()->scheduleAnimation();
480         return true;
481     }
482     return false;
483 }
484 #endif
485
486 void FrameView::setMarginWidth(LayoutUnit w)
487 {
488     // make it update the rendering area when set
489     m_margins.setWidth(w);
490 }
491
492 void FrameView::setMarginHeight(LayoutUnit h)
493 {
494     // make it update the rendering area when set
495     m_margins.setHeight(h);
496 }
497
498 bool FrameView::avoidScrollbarCreation() const
499 {
500     ASSERT(m_frame);
501
502     // with frame flattening no subframe can have scrollbars
503     // but we also cannot turn scrollbars off as we determine
504     // our flattening policy using that.
505
506     if (!m_frame->ownerElement())
507         return false;
508
509     if (!m_frame->settings() || m_frame->settings()->frameFlatteningEnabled())
510         return true;
511
512     return false;
513 }
514
515 void FrameView::setCanHaveScrollbars(bool canHaveScrollbars)
516 {
517     m_canHaveScrollbars = canHaveScrollbars;
518     ScrollView::setCanHaveScrollbars(canHaveScrollbars);
519 }
520
521 void FrameView::updateCanHaveScrollbars()
522 {
523     ScrollbarMode hMode;
524     ScrollbarMode vMode;
525     scrollbarModes(hMode, vMode);
526     if (hMode == ScrollbarAlwaysOff && vMode == ScrollbarAlwaysOff)
527         setCanHaveScrollbars(false);
528     else
529         setCanHaveScrollbars(true);
530 }
531
532 PassRefPtr<Scrollbar> FrameView::createScrollbar(ScrollbarOrientation orientation)
533 {
534     if (Settings* settings = m_frame->settings()) {
535         if (!settings->allowCustomScrollbarInMainFrame() && m_frame->page() && m_frame->page()->mainFrame() == m_frame)
536             return ScrollView::createScrollbar(orientation);
537     }
538
539     // FIXME: We need to update the scrollbar dynamically as documents change (or as doc elements and bodies get discovered that have custom styles).
540     Document* doc = m_frame->document();
541
542     // Try the <body> element first as a scrollbar source.
543     Element* body = doc ? doc->body() : 0;
544     if (body && body->renderer() && body->renderer()->style()->hasPseudoStyle(SCROLLBAR))
545         return RenderScrollbar::createCustomScrollbar(this, orientation, body);
546     
547     // If the <body> didn't have a custom style, then the root element might.
548     Element* docElement = doc ? doc->documentElement() : 0;
549     if (docElement && docElement->renderer() && docElement->renderer()->style()->hasPseudoStyle(SCROLLBAR))
550         return RenderScrollbar::createCustomScrollbar(this, orientation, docElement);
551         
552     // If we have an owning iframe/frame element, then it can set the custom scrollbar also.
553     RenderPart* frameRenderer = m_frame->ownerRenderer();
554     if (frameRenderer && frameRenderer->style()->hasPseudoStyle(SCROLLBAR))
555         return RenderScrollbar::createCustomScrollbar(this, orientation, 0, m_frame.get());
556     
557     // Nobody set a custom style, so we just use a native scrollbar.
558     return ScrollView::createScrollbar(orientation);
559 }
560
561 void FrameView::setContentsSize(const IntSize& size)
562 {
563     if (size == contentsSize())
564         return;
565
566     m_deferSetNeedsLayouts++;
567
568     ScrollView::setContentsSize(size);
569     ScrollView::contentsResized();
570     
571     Page* page = frame() ? frame()->page() : 0;
572     if (!page)
573         return;
574
575     updateScrollableAreaSet();
576
577     page->chrome()->contentsSizeChanged(frame(), size); //notify only
578
579     m_deferSetNeedsLayouts--;
580     
581     if (!m_deferSetNeedsLayouts)
582         m_setNeedsLayoutWasDeferred = false; // FIXME: Find a way to make the deferred layout actually happen.
583 }
584
585 void FrameView::adjustViewSize()
586 {
587     RenderView* renderView = this->renderView();
588     if (!renderView)
589         return;
590
591     ASSERT(m_frame->view() == this);
592
593     const IntRect rect = renderView->documentRect();
594     const IntSize& size = rect.size();
595     ScrollView::setScrollOrigin(IntPoint(-rect.x(), -rect.y()), !m_frame->document()->printing(), size == contentsSize());
596     
597     setContentsSize(size);
598 }
599
600 void FrameView::applyOverflowToViewport(RenderObject* o, ScrollbarMode& hMode, ScrollbarMode& vMode)
601 {
602     // Handle the overflow:hidden/scroll case for the body/html elements.  WinIE treats
603     // overflow:hidden and overflow:scroll on <body> as applying to the document's
604     // scrollbars.  The CSS2.1 draft states that HTML UAs should use the <html> or <body> element and XML/XHTML UAs should
605     // use the root element.
606
607     // To combat the inability to scroll on a page with overflow:hidden on the root when scaled, disregard hidden when
608     // there is a frameScaleFactor that is greater than one on the main frame.
609
610     bool overrideHidden = m_frame->page() && m_frame->page()->mainFrame() == m_frame && m_frame->frameScaleFactor() > 1;
611
612     EOverflow overflowX = o->style()->overflowX();
613     EOverflow overflowY = o->style()->overflowY();
614
615 #if ENABLE(SVG)
616     if (o->isSVGRoot()) {
617         // overflow is ignored in stand-alone SVG documents.
618         if (!toRenderSVGRoot(o)->isEmbeddedThroughFrameContainingSVGDocument())
619             return;
620         overflowX = OHIDDEN;
621         overflowY = OHIDDEN;
622     }
623 #endif
624
625     switch (overflowX) {
626         case OHIDDEN:
627             if (overrideHidden)
628                 hMode = ScrollbarAuto;
629             else
630                 hMode = ScrollbarAlwaysOff;
631             break;
632         case OSCROLL:
633             hMode = ScrollbarAlwaysOn;
634             break;
635         case OAUTO:
636             hMode = ScrollbarAuto;
637             break;
638         default:
639             // Don't set it at all.
640             ;
641     }
642     
643      switch (overflowY) {
644         case OHIDDEN:
645             if (overrideHidden)
646                 vMode = ScrollbarAuto;
647             else
648                 vMode = ScrollbarAlwaysOff;
649             break;
650         case OSCROLL:
651             vMode = ScrollbarAlwaysOn;
652             break;
653         case OAUTO:
654             vMode = ScrollbarAuto;
655             break;
656         default:
657             // Don't set it at all. Values of OPAGEDX and OPAGEDY are handled by applyPaginationToViewPort().
658             ;
659     }
660
661     m_viewportRenderer = o;
662 }
663
664 void FrameView::applyPaginationToViewport()
665 {
666     Document* document = m_frame->document();
667     Node* documentElement = document->documentElement();
668     RenderObject* documentRenderer = documentElement ? documentElement->renderer() : 0;
669     RenderObject* documentOrBodyRenderer = documentRenderer;
670     Node* body = document->body();
671     if (body && body->renderer()) {
672         if (body->hasTagName(bodyTag))
673             documentOrBodyRenderer = documentRenderer->style()->overflowX() == OVISIBLE && documentElement->hasTagName(htmlTag) ? body->renderer() : documentRenderer;
674     }
675
676     Pagination pagination;
677
678     if (!documentOrBodyRenderer) {
679         setPagination(pagination);
680         return;
681     }
682
683     EOverflow overflowY = documentOrBodyRenderer->style()->overflowY();
684     if (overflowY == OPAGEDX || overflowY == OPAGEDY) {
685         pagination.mode = WebCore::paginationModeForRenderStyle(documentOrBodyRenderer->style());
686         pagination.gap = static_cast<unsigned>(documentOrBodyRenderer->style()->columnGap());
687     }
688
689     setPagination(pagination);
690 }
691
692 void FrameView::calculateScrollbarModesForLayout(ScrollbarMode& hMode, ScrollbarMode& vMode, ScrollbarModesCalculationStrategy strategy)
693 {
694     m_viewportRenderer = 0;
695
696     const HTMLFrameOwnerElement* owner = m_frame->ownerElement();
697     if (owner && (owner->scrollingMode() == ScrollbarAlwaysOff)) {
698         hMode = ScrollbarAlwaysOff;
699         vMode = ScrollbarAlwaysOff;
700         return;
701     }  
702     
703     if (m_canHaveScrollbars || strategy == RulesFromWebContentOnly) {
704         hMode = ScrollbarAuto;
705         // Seamless documents begin with heights of 0; we special case that here
706         // to correctly render documents that don't need scrollbars.
707         IntSize fullVisibleSize = visibleContentRect(IncludeScrollbars).size();
708         bool isSeamlessDocument = frame() && frame()->document() && frame()->document()->shouldDisplaySeamlesslyWithParent();
709         vMode = (isSeamlessDocument && !fullVisibleSize.height()) ? ScrollbarAlwaysOff : ScrollbarAuto;
710     } else {
711         hMode = ScrollbarAlwaysOff;
712         vMode = ScrollbarAlwaysOff;
713     }
714     
715     if (!m_layoutRoot) {
716         Document* document = m_frame->document();
717         Node* documentElement = document->documentElement();
718         RenderObject* rootRenderer = documentElement ? documentElement->renderer() : 0;
719         Node* body = document->body();
720         if (body && body->renderer()) {
721             if (body->hasTagName(framesetTag) && m_frame->settings() && !m_frame->settings()->frameFlatteningEnabled()) {
722                 vMode = ScrollbarAlwaysOff;
723                 hMode = ScrollbarAlwaysOff;
724             } else if (body->hasTagName(bodyTag)) {
725                 // It's sufficient to just check the X overflow,
726                 // since it's illegal to have visible in only one direction.
727                 RenderObject* o = rootRenderer->style()->overflowX() == OVISIBLE && document->documentElement()->hasTagName(htmlTag) ? body->renderer() : rootRenderer;
728                 applyOverflowToViewport(o, hMode, vMode);
729             }
730         } else if (rootRenderer)
731             applyOverflowToViewport(rootRenderer, hMode, vMode);
732     }    
733 }
734
735 #if USE(ACCELERATED_COMPOSITING)
736 void FrameView::updateCompositingLayersAfterStyleChange()
737 {
738     RenderView* renderView = this->renderView();
739     if (!renderView)
740         return;
741
742     // If we expect to update compositing after an incipient layout, don't do so here.
743     if (m_doingPreLayoutStyleUpdate || layoutPending() || renderView->needsLayout())
744         return;
745
746     // This call will make sure the cached hasAcceleratedCompositing is updated from the pref
747     renderView->compositor()->cacheAcceleratedCompositingFlags();
748     renderView->compositor()->updateCompositingLayers(CompositingUpdateAfterStyleChange);
749 }
750
751 void FrameView::updateCompositingLayersAfterLayout()
752 {
753     RenderView* renderView = this->renderView();
754     if (!renderView)
755         return;
756
757     // This call will make sure the cached hasAcceleratedCompositing is updated from the pref
758     renderView->compositor()->cacheAcceleratedCompositingFlags();
759     renderView->compositor()->updateCompositingLayers(CompositingUpdateAfterLayout);
760 }
761
762 void FrameView::clearBackingStores()
763 {
764     RenderView* renderView = this->renderView();
765     if (!renderView)
766         return;
767
768     RenderLayerCompositor* compositor = renderView->compositor();
769     ASSERT(compositor->inCompositingMode());
770     compositor->enableCompositingMode(false);
771     compositor->clearBackingForAllLayers();
772 }
773
774 void FrameView::restoreBackingStores()
775 {
776     RenderView* renderView = this->renderView();
777     if (!renderView)
778         return;
779
780     RenderLayerCompositor* compositor = renderView->compositor();
781     compositor->enableCompositingMode(true);
782     compositor->updateCompositingLayers(CompositingUpdateAfterLayout);
783 }
784
785 bool FrameView::usesCompositedScrolling() const
786 {
787     RenderView* renderView = this->renderView();
788     if (!renderView)
789         return false;
790     if (m_frame->settings() && m_frame->settings()->compositedScrollingForFramesEnabled())
791         return renderView->compositor()->inForcedCompositingMode();
792     return false;
793 }
794
795 GraphicsLayer* FrameView::layerForScrolling() const
796 {
797     RenderView* renderView = this->renderView();
798     if (!renderView)
799         return 0;
800     return renderView->compositor()->scrollLayer();
801 }
802
803 GraphicsLayer* FrameView::layerForHorizontalScrollbar() const
804 {
805     RenderView* renderView = this->renderView();
806     if (!renderView)
807         return 0;
808     return renderView->compositor()->layerForHorizontalScrollbar();
809 }
810
811 GraphicsLayer* FrameView::layerForVerticalScrollbar() const
812 {
813     RenderView* renderView = this->renderView();
814     if (!renderView)
815         return 0;
816     return renderView->compositor()->layerForVerticalScrollbar();
817 }
818
819 GraphicsLayer* FrameView::layerForScrollCorner() const
820 {
821     RenderView* renderView = this->renderView();
822     if (!renderView)
823         return 0;
824     return renderView->compositor()->layerForScrollCorner();
825 }
826
827 TiledBacking* FrameView::tiledBacking()
828 {
829     RenderView* renderView = this->renderView();
830     if (!renderView)
831         return 0;
832
833     RenderLayerBacking* backing = renderView->layer()->backing();
834     if (!backing)
835         return 0;
836
837     return backing->graphicsLayer()->tiledBacking();
838 }
839
840 uint64_t FrameView::scrollLayerID() const
841 {
842     RenderView* renderView = this->renderView();
843     if (!renderView)
844         return 0;
845
846     RenderLayerBacking* backing = renderView->layer()->backing();
847     if (!backing)
848         return 0;
849
850     return backing->scrollLayerID();
851 }
852
853 #if ENABLE(RUBBER_BANDING)
854 GraphicsLayer* FrameView::layerForOverhangAreas() const
855 {
856     RenderView* renderView = this->renderView();
857     if (!renderView)
858         return 0;
859     return renderView->compositor()->layerForOverhangAreas();
860 }
861
862 GraphicsLayer* FrameView::setWantsLayerForTopOverHangArea(bool wantsLayer) const
863 {
864     RenderView* renderView = this->renderView();
865     if (!renderView)
866         return 0;
867
868 #if USE(ACCELERATED_COMPOSITING)
869     return renderView->compositor()->updateLayerForTopOverhangArea(wantsLayer);
870 #else
871     return 0;
872 #endif
873 }
874
875 GraphicsLayer* FrameView::setWantsLayerForBottomOverHangArea(bool wantsLayer) const
876 {
877     RenderView* renderView = this->renderView();
878     if (!renderView)
879         return 0;
880
881 #if USE(ACCELERATED_COMPOSITING)
882     return renderView->compositor()->updateLayerForBottomOverhangArea(wantsLayer);
883 #else
884     return 0;
885 #endif
886 }
887 #endif
888
889 bool FrameView::flushCompositingStateForThisFrame(Frame* rootFrameForFlush)
890 {
891     RenderView* renderView = this->renderView();
892     if (!renderView)
893         return true; // We don't want to keep trying to update layers if we have no renderer.
894
895     ASSERT(m_frame->view() == this);
896
897     // If we sync compositing layers when a layout is pending, we may cause painting of compositing
898     // layer content to occur before layout has happened, which will cause paintContents() to bail.
899     if (needsLayout())
900         return false;
901
902     // If we sync compositing layers and allow the repaint to be deferred, there is time for a
903     // visible flash to occur. Instead, stop the deferred repaint timer and repaint immediately.
904     flushDeferredRepaints();
905
906     renderView->compositor()->flushPendingLayerChanges(rootFrameForFlush == m_frame);
907
908     return true;
909 }
910
911 void FrameView::setNeedsOneShotDrawingSynchronization()
912 {
913     Page* page = frame() ? frame()->page() : 0;
914     if (page)
915         page->chrome()->client()->setNeedsOneShotDrawingSynchronization();
916 }
917
918 #endif // USE(ACCELERATED_COMPOSITING)
919
920 bool FrameView::hasCompositedContent() const
921 {
922 #if USE(ACCELERATED_COMPOSITING)
923     if (RenderView* renderView = this->renderView())
924         return renderView->compositor()->inCompositingMode();
925 #endif
926     return false;
927 }
928
929 bool FrameView::hasCompositedContentIncludingDescendants() const
930 {
931 #if USE(ACCELERATED_COMPOSITING)
932     for (Frame* frame = m_frame.get(); frame; frame = frame->tree()->traverseNext(m_frame.get())) {
933         RenderView* renderView = frame->contentRenderer();
934         RenderLayerCompositor* compositor = renderView ? renderView->compositor() : 0;
935         if (compositor) {
936             if (compositor->inCompositingMode())
937                 return true;
938
939             if (!RenderLayerCompositor::allowsIndependentlyCompositedFrames(this))
940                 break;
941         }
942     }
943 #endif
944     return false;
945 }
946
947 bool FrameView::hasCompositingAncestor() const
948 {
949 #if USE(ACCELERATED_COMPOSITING)
950     for (Frame* frame = m_frame->tree()->parent(); frame; frame = frame->tree()->parent()) {
951         if (FrameView* view = frame->view()) {
952             if (view->hasCompositedContent())
953                 return true;
954         }
955     }
956 #endif
957     return false;
958 }
959
960 // Sometimes (for plug-ins) we need to eagerly go into compositing mode.
961 void FrameView::enterCompositingMode()
962 {
963 #if USE(ACCELERATED_COMPOSITING)
964     if (RenderView* renderView = this->renderView()) {
965         renderView->compositor()->enableCompositingMode();
966         if (!needsLayout())
967             renderView->compositor()->scheduleCompositingLayerUpdate();
968     }
969 #endif
970 }
971
972 bool FrameView::isEnclosedInCompositingLayer() const
973 {
974 #if USE(ACCELERATED_COMPOSITING)
975     RenderObject* frameOwnerRenderer = m_frame->ownerRenderer();
976     if (frameOwnerRenderer && frameOwnerRenderer->containerForRepaint())
977         return true;
978
979     if (FrameView* parentView = parentFrameView())
980         return parentView->isEnclosedInCompositingLayer();
981 #endif
982     return false;
983 }
984     
985 bool FrameView::flushCompositingStateIncludingSubframes()
986 {
987 #if USE(ACCELERATED_COMPOSITING)
988     bool allFramesFlushed = flushCompositingStateForThisFrame(m_frame.get());
989     
990     for (Frame* child = m_frame->tree()->firstChild(); child; child = child->tree()->traverseNext(m_frame.get())) {
991         bool flushed = child->view()->flushCompositingStateForThisFrame(m_frame.get());
992         allFramesFlushed &= flushed;
993     }
994     return allFramesFlushed;
995 #else // USE(ACCELERATED_COMPOSITING)
996     return true;
997 #endif
998 }
999
1000 bool FrameView::isSoftwareRenderable() const
1001 {
1002 #if USE(ACCELERATED_COMPOSITING)
1003     RenderView* renderView = this->renderView();
1004     return !renderView || !renderView->compositor()->has3DContent();
1005 #else
1006     return true;
1007 #endif
1008 }
1009
1010 void FrameView::didMoveOnscreen()
1011 {
1012     contentAreaDidShow();
1013 }
1014
1015 void FrameView::willMoveOffscreen()
1016 {
1017     contentAreaDidHide();
1018 }
1019
1020 void FrameView::setIsInWindow(bool isInWindow)
1021 {
1022     if (RenderView* renderView = this->renderView())
1023         renderView->setIsInWindow(isInWindow);
1024 }
1025
1026 RenderObject* FrameView::layoutRoot(bool onlyDuringLayout) const
1027 {
1028     return onlyDuringLayout && layoutPending() ? 0 : m_layoutRoot;
1029 }
1030
1031 static inline void collectFrameViewChildren(FrameView* frameView, Vector<RefPtr<FrameView> >& frameViews)
1032 {
1033     const HashSet<RefPtr<Widget> >* viewChildren = frameView->children();
1034     ASSERT(viewChildren);
1035
1036     const HashSet<RefPtr<Widget> >::iterator end = viewChildren->end();
1037     for (HashSet<RefPtr<Widget> >::iterator current = viewChildren->begin(); current != end; ++current) {
1038         Widget* widget = (*current).get();
1039         if (widget->isFrameView())
1040             frameViews.append(toFrameView(widget));
1041     }
1042 }
1043
1044 inline void FrameView::forceLayoutParentViewIfNeeded()
1045 {
1046 #if ENABLE(SVG)
1047     RenderPart* ownerRenderer = m_frame->ownerRenderer();
1048     if (!ownerRenderer || !ownerRenderer->frame())
1049         return;
1050
1051     RenderBox* contentBox = embeddedContentBox();
1052     if (!contentBox)
1053         return;
1054
1055     RenderSVGRoot* svgRoot = toRenderSVGRoot(contentBox);
1056     if (svgRoot->everHadLayout() && !svgRoot->needsLayout())
1057         return;
1058
1059     // If the embedded SVG document appears the first time, the ownerRenderer has already finished
1060     // layout without knowing about the existence of the embedded SVG document, because RenderReplaced
1061     // embeddedContentBox() returns 0, as long as the embedded document isn't loaded yet. Before
1062     // bothering to lay out the SVG document, mark the ownerRenderer needing layout and ask its
1063     // FrameView for a layout. After that the RenderEmbeddedObject (ownerRenderer) carries the
1064     // correct size, which RenderSVGRoot::computeReplacedLogicalWidth/Height rely on, when laying
1065     // out for the first time, or when the RenderSVGRoot size has changed dynamically (eg. via <script>).
1066     RefPtr<FrameView> frameView = ownerRenderer->frame()->view();
1067
1068     // Mark the owner renderer as needing layout.
1069     ownerRenderer->setNeedsLayoutAndPrefWidthsRecalc();
1070
1071     // Synchronously enter layout, to layout the view containing the host object/embed/iframe.
1072     ASSERT(frameView);
1073     frameView->layout();
1074 #endif
1075 }
1076
1077 void FrameView::layout(bool allowSubtree)
1078 {
1079     if (m_inLayout)
1080         return;
1081
1082 #if PLATFORM(CHROMIUM)
1083     TRACE_EVENT0("webkit", "FrameView::layout");
1084 #endif
1085
1086     // Protect the view from being deleted during layout (in recalcStyle)
1087     RefPtr<FrameView> protector(this);
1088
1089     // Every scroll that happens during layout is programmatic.
1090     TemporaryChange<bool> changeInProgrammaticScroll(m_inProgrammaticScroll, true);
1091
1092     bool inChildFrameLayoutWithFrameFlattening = isInChildFrameWithFrameFlattening();
1093
1094     if (inChildFrameLayoutWithFrameFlattening) {
1095         if (doLayoutWithFrameFlattening(allowSubtree))
1096             return;
1097     }
1098
1099     m_layoutTimer.stop();
1100     m_delayedLayout = false;
1101     m_setNeedsLayoutWasDeferred = false;
1102
1103     if (!m_frame) {
1104         // FIXME: Do we need to set m_size.width here?
1105         // FIXME: Should we set m_size.height here too?
1106         m_size.setWidth(layoutWidth());
1107         return;
1108     }
1109     
1110     // we shouldn't enter layout() while painting
1111     ASSERT(!isPainting());
1112     if (isPainting())
1113         return;
1114
1115     InspectorInstrumentationCookie cookie = InspectorInstrumentation::willLayout(m_frame.get());
1116
1117     if (!allowSubtree && m_layoutRoot) {
1118         m_layoutRoot->markContainingBlocksForLayout(false);
1119         m_layoutRoot = 0;
1120     }
1121
1122     ASSERT(m_frame->view() == this);
1123
1124     Document* document = m_frame->document();
1125     ASSERT(!document->inPageCache());
1126     bool subtree;
1127     RenderObject* root;
1128
1129     {
1130         TemporaryChange<bool> changeSchedulingEnabled(m_layoutSchedulingEnabled, false);
1131
1132         if (!m_nestedLayoutCount && !m_inSynchronousPostLayout && m_postLayoutTasksTimer.isActive() && !inChildFrameLayoutWithFrameFlattening) {
1133             // This is a new top-level layout. If there are any remaining tasks from the previous
1134             // layout, finish them now.
1135             m_inSynchronousPostLayout = true;
1136             performPostLayoutTasks();
1137             m_inSynchronousPostLayout = false;
1138         }
1139
1140         // Viewport-dependent media queries may cause us to need completely different style information.
1141         // Check that here.
1142         if (document->styleResolver()->affectedByViewportChange()) {
1143             document->styleResolverChanged(RecalcStyleImmediately);
1144             InspectorInstrumentation::mediaQueryResultChanged(document);
1145         } else
1146             document->evaluateMediaQueryList();
1147
1148         // If there is any pagination to apply, it will affect the RenderView's style, so we should
1149         // take care of that now.
1150         applyPaginationToViewport();
1151
1152         // Always ensure our style info is up-to-date. This can happen in situations where
1153         // the layout beats any sort of style recalc update that needs to occur.
1154         TemporaryChange<bool> changeDoingPreLayoutStyleUpdate(m_doingPreLayoutStyleUpdate, true);
1155         document->updateStyleIfNeeded();
1156
1157         subtree = m_layoutRoot;
1158
1159         // If there is only one ref to this view left, then its going to be destroyed as soon as we exit, 
1160         // so there's no point to continuing to layout
1161         if (protector->hasOneRef())
1162             return;
1163
1164         root = subtree ? m_layoutRoot : document->renderer();
1165         if (!root) {
1166             // FIXME: Do we need to set m_size here?
1167             return;
1168         }
1169     } // Reset m_layoutSchedulingEnabled to its previous value.
1170     // The only reason the scoping was closed here is allow fontCachePurgePreventer
1171     // to outlive the change and reset of m_layoutSchedulingEnabled.
1172
1173     FontCachePurgePreventer fontCachePurgePreventer;
1174     RenderLayer* layer;
1175     {
1176         TemporaryChange<bool> changeSchedulingEnabled(m_layoutSchedulingEnabled, false);
1177
1178         m_nestedLayoutCount++;
1179
1180         if (!m_layoutRoot) {
1181             Document* document = m_frame->document();
1182             Node* body = document->body();
1183             if (body && body->renderer()) {
1184                 if (body->hasTagName(framesetTag) && m_frame->settings() && !m_frame->settings()->frameFlatteningEnabled()) {
1185                     body->renderer()->setChildNeedsLayout(true);
1186                 } else if (body->hasTagName(bodyTag)) {
1187                     if (!m_firstLayout && m_size.height() != layoutHeight() && body->renderer()->enclosingBox()->stretchesToViewport())
1188                         body->renderer()->setChildNeedsLayout(true);
1189                 }
1190             }
1191
1192 #ifdef INSTRUMENT_LAYOUT_SCHEDULING
1193             if (m_firstLayout && !m_frame->ownerElement())
1194                 printf("Elapsed time before first layout: %d\n", document->elapsedTime());
1195 #endif        
1196         }
1197
1198         autoSizeIfEnabled();
1199
1200         ScrollbarMode hMode;
1201         ScrollbarMode vMode;    
1202         calculateScrollbarModesForLayout(hMode, vMode);
1203
1204         m_doFullRepaint = !subtree && (m_firstLayout || toRenderView(root)->printing());
1205
1206         if (!subtree) {
1207             // Now set our scrollbar state for the layout.
1208             ScrollbarMode currentHMode = horizontalScrollbarMode();
1209             ScrollbarMode currentVMode = verticalScrollbarMode();
1210
1211             if (m_firstLayout || (hMode != currentHMode || vMode != currentVMode)) {
1212                 if (m_firstLayout) {
1213                     setScrollbarsSuppressed(true);
1214
1215                     m_firstLayout = false;
1216                     m_firstLayoutCallbackPending = true;
1217                     if (useFixedLayout() && !fixedLayoutSize().isEmpty() && delegatesScrolling())
1218                         m_lastViewportSize = fixedLayoutSize();
1219                     else
1220                         m_lastViewportSize = visibleContentRect(IncludeScrollbars).size();
1221                     m_lastZoomFactor = root->style()->zoom();
1222
1223                     // Set the initial vMode to AlwaysOn if we're auto.
1224                     if (vMode == ScrollbarAuto)
1225                         setVerticalScrollbarMode(ScrollbarAlwaysOn); // This causes a vertical scrollbar to appear.
1226                     // Set the initial hMode to AlwaysOff if we're auto.
1227                     if (hMode == ScrollbarAuto)
1228                         setHorizontalScrollbarMode(ScrollbarAlwaysOff); // This causes a horizontal scrollbar to disappear.
1229
1230                     setScrollbarModes(hMode, vMode);
1231                     setScrollbarsSuppressed(false, true);
1232                 } else
1233                     setScrollbarModes(hMode, vMode);
1234             }
1235
1236             LayoutSize oldSize = m_size;
1237
1238             m_size = LayoutSize(layoutWidth(), layoutHeight());
1239
1240             if (oldSize != m_size) {
1241                 m_doFullRepaint = true;
1242                 if (!m_firstLayout) {
1243                     RenderBox* rootRenderer = document->documentElement() ? document->documentElement()->renderBox() : 0;
1244                     RenderBox* bodyRenderer = rootRenderer && document->body() ? document->body()->renderBox() : 0;
1245                     if (bodyRenderer && bodyRenderer->stretchesToViewport())
1246                         bodyRenderer->setChildNeedsLayout(true);
1247                     else if (rootRenderer && rootRenderer->stretchesToViewport())
1248                         rootRenderer->setChildNeedsLayout(true);
1249                 }
1250             }
1251         }
1252
1253         layer = root->enclosingLayer();
1254
1255         m_actionScheduler->pause();
1256
1257         {
1258             bool disableLayoutState = false;
1259             if (subtree) {
1260                 RenderView* view = root->view();
1261                 disableLayoutState = view->shouldDisableLayoutStateForSubtree(root);
1262                 view->pushLayoutState(root);
1263             }
1264             LayoutStateDisabler layoutStateDisabler(disableLayoutState ? root->view() : 0);
1265
1266             m_inLayout = true;
1267             beginDeferredRepaints();
1268             forceLayoutParentViewIfNeeded();
1269             root->layout();
1270 #if ENABLE(TEXT_AUTOSIZING)
1271             bool autosized = document->textAutosizer()->processSubtree(root);
1272             if (autosized && root->needsLayout())
1273                 root->layout();
1274 #endif
1275             endDeferredRepaints();
1276             m_inLayout = false;
1277
1278             if (subtree)
1279                 root->view()->popLayoutState(root);
1280         }
1281         m_layoutRoot = 0;
1282     } // Reset m_layoutSchedulingEnabled to its previous value.
1283
1284     bool neededFullRepaint = m_doFullRepaint;
1285
1286     if (!subtree && !toRenderView(root)->printing())
1287         adjustViewSize();
1288
1289     m_doFullRepaint = neededFullRepaint;
1290
1291     // Now update the positions of all layers.
1292     beginDeferredRepaints();
1293     if (m_doFullRepaint)
1294         root->view()->repaint(); // FIXME: This isn't really right, since the RenderView doesn't fully encompass the visibleContentRect(). It just happens
1295                                  // to work out most of the time, since first layouts and printing don't have you scrolled anywhere.
1296
1297     layer->updateLayerPositionsAfterLayout(renderView()->layer(), updateLayerPositionFlags(layer, subtree, m_doFullRepaint));
1298
1299     endDeferredRepaints();
1300
1301 #if USE(ACCELERATED_COMPOSITING)
1302     updateCompositingLayersAfterLayout();
1303 #endif
1304     
1305     m_layoutCount++;
1306
1307 #if PLATFORM(MAC) || PLATFORM(CHROMIUM)
1308     if (AXObjectCache::accessibilityEnabled())
1309         root->document()->axObjectCache()->postNotification(root, AXObjectCache::AXLayoutComplete, true);
1310 #endif
1311 #if ENABLE(DASHBOARD_SUPPORT) || ENABLE(DRAGGABLE_REGION)
1312     updateAnnotatedRegions();
1313 #endif
1314
1315     ASSERT(!root->needsLayout());
1316
1317     updateCanBlitOnScrollRecursively();
1318
1319     if (document->hasListenerType(Document::OVERFLOWCHANGED_LISTENER))
1320         updateOverflowStatus(layoutWidth() < contentsWidth(),
1321                              layoutHeight() < contentsHeight());
1322
1323     if (!m_postLayoutTasksTimer.isActive()) {
1324         if (!m_inSynchronousPostLayout) {
1325             if (inChildFrameLayoutWithFrameFlattening) {
1326                 if (RenderView* renderView = this->renderView())
1327                     renderView->updateWidgetPositions();
1328             } else {
1329                 m_inSynchronousPostLayout = true;
1330                 // Calls resumeScheduledEvents()
1331                 performPostLayoutTasks();
1332                 m_inSynchronousPostLayout = false;
1333             }
1334         }
1335         
1336         if (!m_postLayoutTasksTimer.isActive() && (needsLayout() || m_inSynchronousPostLayout || inChildFrameLayoutWithFrameFlattening)) {
1337             // If we need layout or are already in a synchronous call to postLayoutTasks(), 
1338             // defer widget updates and event dispatch until after we return. postLayoutTasks()
1339             // can make us need to update again, and we can get stuck in a nasty cycle unless
1340             // we call it through the timer here.
1341             m_postLayoutTasksTimer.startOneShot(0);
1342             if (needsLayout()) {
1343                 m_actionScheduler->pause();
1344                 layout();
1345             }
1346         }
1347     } else {
1348         m_actionScheduler->resume();
1349     }
1350
1351     InspectorInstrumentation::didLayout(cookie, root);
1352
1353     m_nestedLayoutCount--;
1354     if (m_nestedLayoutCount)
1355         return;
1356
1357     Page* page = frame() ? frame()->page() : 0;
1358     if (!page)
1359         return;
1360
1361     page->chrome()->client()->layoutUpdated(frame());
1362 }
1363
1364 RenderBox* FrameView::embeddedContentBox() const
1365 {
1366 #if ENABLE(SVG)
1367     RenderView* renderView = this->renderView();
1368     if (!renderView)
1369         return 0;
1370
1371     RenderObject* firstChild = renderView->firstChild();
1372     if (!firstChild || !firstChild->isBox())
1373         return 0;
1374
1375     // Curently only embedded SVG documents participate in the size-negotiation logic.
1376     if (firstChild->isSVGRoot())
1377         return toRenderBox(firstChild);
1378 #endif
1379
1380     return 0;
1381 }
1382
1383 void FrameView::addWidgetToUpdate(RenderObject* object)
1384 {
1385     if (!m_widgetUpdateSet)
1386         m_widgetUpdateSet = adoptPtr(new RenderObjectSet);
1387
1388     // Tell the DOM element that it needs a widget update.
1389     Node* node = object->node();
1390     if (node->hasTagName(objectTag) || node->hasTagName(embedTag)) {
1391         HTMLPlugInImageElement* pluginElement = toHTMLPlugInImageElement(node);
1392         pluginElement->setNeedsWidgetUpdate(true);
1393     }
1394
1395     m_widgetUpdateSet->add(object);
1396 }
1397
1398 void FrameView::removeWidgetToUpdate(RenderObject* object)
1399 {
1400     if (!m_widgetUpdateSet)
1401         return;
1402
1403     m_widgetUpdateSet->remove(object);
1404 }
1405
1406 void FrameView::setMediaType(const String& mediaType)
1407 {
1408     m_mediaType = mediaType;
1409 }
1410
1411 String FrameView::mediaType() const
1412 {
1413     // See if we have an override type.
1414     String overrideType = m_frame->loader()->client()->overrideMediaType();
1415     InspectorInstrumentation::applyEmulatedMedia(m_frame.get(), &overrideType);
1416     if (!overrideType.isNull())
1417         return overrideType;
1418     return m_mediaType;
1419 }
1420
1421 void FrameView::adjustMediaTypeForPrinting(bool printing)
1422 {
1423     if (printing) {
1424         if (m_mediaTypeWhenNotPrinting.isNull())
1425             m_mediaTypeWhenNotPrinting = mediaType();
1426             setMediaType("print");
1427     } else {
1428         if (!m_mediaTypeWhenNotPrinting.isNull())
1429             setMediaType(m_mediaTypeWhenNotPrinting);
1430         m_mediaTypeWhenNotPrinting = String();
1431     }
1432 }
1433
1434 bool FrameView::useSlowRepaints(bool considerOverlap) const
1435 {
1436     bool mustBeSlow = m_slowRepaintObjectCount > 0 || (platformWidget() && hasViewportConstrainedObjects());
1437
1438     // FIXME: WidgetMac.mm makes the assumption that useSlowRepaints ==
1439     // m_contentIsOpaque, so don't take the fast path for composited layers
1440     // if they are a platform widget in order to get painting correctness
1441     // for transparent layers. See the comment in WidgetMac::paint.
1442     if (contentsInCompositedLayer() && !platformWidget())
1443         return mustBeSlow;
1444
1445 #if PLATFORM(CHROMIUM)
1446     // The chromium compositor does not support scrolling a non-composited frame within a composited page through
1447     // the fast scrolling path, so force slow scrolling in that case.
1448     if (m_frame->ownerElement() && !hasCompositedContent() && m_frame->page() && m_frame->page()->mainFrame()->view()->hasCompositedContent())
1449         return true;
1450 #endif
1451
1452     bool isOverlapped = m_isOverlapped && considerOverlap;
1453
1454     if (mustBeSlow || m_cannotBlitToWindow || isOverlapped || !m_contentIsOpaque)
1455         return true;
1456
1457     if (FrameView* parentView = parentFrameView())
1458         return parentView->useSlowRepaints(considerOverlap);
1459
1460     return false;
1461 }
1462
1463 bool FrameView::useSlowRepaintsIfNotOverlapped() const
1464 {
1465     return useSlowRepaints(false);
1466 }
1467
1468 void FrameView::updateCanBlitOnScrollRecursively()
1469 {
1470     for (Frame* frame = m_frame.get(); frame; frame = frame->tree()->traverseNext(m_frame.get())) {
1471         if (FrameView* view = frame->view())
1472             view->setCanBlitOnScroll(!view->useSlowRepaints());
1473     }
1474 }
1475
1476 bool FrameView::contentsInCompositedLayer() const
1477 {
1478 #if USE(ACCELERATED_COMPOSITING)
1479     RenderView* renderView = this->renderView();
1480     if (renderView && renderView->isComposited()) {
1481         GraphicsLayer* layer = renderView->layer()->backing()->graphicsLayer();
1482         if (layer && layer->drawsContent())
1483             return true;
1484     }
1485 #endif
1486     return false;
1487 }
1488
1489 void FrameView::setCannotBlitToWindow()
1490 {
1491     m_cannotBlitToWindow = true;
1492     updateCanBlitOnScrollRecursively();
1493 }
1494
1495 void FrameView::addSlowRepaintObject()
1496 {
1497     if (!m_slowRepaintObjectCount++) {
1498         updateCanBlitOnScrollRecursively();
1499
1500         if (Page* page = m_frame->page()) {
1501             if (ScrollingCoordinator* scrollingCoordinator = page->scrollingCoordinator())
1502                 scrollingCoordinator->frameViewHasSlowRepaintObjectsDidChange(this);
1503         }
1504     }
1505 }
1506
1507 void FrameView::removeSlowRepaintObject()
1508 {
1509     ASSERT(m_slowRepaintObjectCount > 0);
1510     m_slowRepaintObjectCount--;
1511     if (!m_slowRepaintObjectCount) {
1512         updateCanBlitOnScrollRecursively();
1513
1514         if (Page* page = m_frame->page()) {
1515             if (ScrollingCoordinator* scrollingCoordinator = page->scrollingCoordinator())
1516                 scrollingCoordinator->frameViewHasSlowRepaintObjectsDidChange(this);
1517         }
1518     }
1519 }
1520
1521 void FrameView::addViewportConstrainedObject(RenderObject* object)
1522 {
1523     if (!m_viewportConstrainedObjects)
1524         m_viewportConstrainedObjects = adoptPtr(new ViewportConstrainedObjectSet);
1525
1526     if (!m_viewportConstrainedObjects->contains(object)) {
1527         m_viewportConstrainedObjects->add(object);
1528         if (platformWidget())
1529             updateCanBlitOnScrollRecursively();
1530
1531         if (Page* page = m_frame->page()) {
1532             if (ScrollingCoordinator* scrollingCoordinator = page->scrollingCoordinator())
1533                 scrollingCoordinator->frameViewFixedObjectsDidChange(this);
1534         }
1535     }
1536 }
1537
1538 void FrameView::removeViewportConstrainedObject(RenderObject* object)
1539 {
1540     if (m_viewportConstrainedObjects && m_viewportConstrainedObjects->contains(object)) {
1541         m_viewportConstrainedObjects->remove(object);
1542         if (Page* page = m_frame->page()) {
1543             if (ScrollingCoordinator* scrollingCoordinator = page->scrollingCoordinator())
1544                 scrollingCoordinator->frameViewFixedObjectsDidChange(this);
1545         }
1546
1547         // FIXME: In addFixedObject() we only call this if there's a platform widget,
1548         // why isn't the same check being made here?
1549         updateCanBlitOnScrollRecursively();
1550     }
1551 }
1552
1553 LayoutRect FrameView::viewportConstrainedVisibleContentRect() const
1554 {
1555     LayoutRect viewportRect = visibleContentRect();
1556     viewportRect.setLocation(toPoint(scrollOffsetForFixedPosition()));
1557     return viewportRect;
1558 }
1559
1560 IntSize FrameView::scrollOffsetForFixedPosition(const IntRect& visibleContentRect, const IntSize& contentsSize, const IntPoint& scrollPosition, const IntPoint& scrollOrigin, float frameScaleFactor, bool fixedElementsLayoutRelativeToFrame)
1561 {
1562     IntPoint constrainedPosition = ScrollableArea::constrainScrollPositionForOverhang(visibleContentRect, contentsSize, scrollPosition, scrollOrigin);
1563
1564     IntSize maxSize = contentsSize - visibleContentRect.size();
1565
1566     float dragFactorX = (fixedElementsLayoutRelativeToFrame || !maxSize.width()) ? 1 : (contentsSize.width() - visibleContentRect.width() * frameScaleFactor) / maxSize.width();
1567     float dragFactorY = (fixedElementsLayoutRelativeToFrame || !maxSize.height()) ? 1 : (contentsSize.height() - visibleContentRect.height() * frameScaleFactor) / maxSize.height();
1568
1569     return IntSize(constrainedPosition.x() * dragFactorX / frameScaleFactor, constrainedPosition.y() * dragFactorY / frameScaleFactor);
1570 }
1571
1572 IntSize FrameView::scrollOffsetForFixedPosition() const
1573 {
1574     IntRect visibleContentRect = this->visibleContentRect();
1575     IntSize contentsSize = this->contentsSize();
1576     IntPoint scrollPosition = this->scrollPosition();
1577     IntPoint scrollOrigin = this->scrollOrigin();
1578     float frameScaleFactor = m_frame ? m_frame->frameScaleFactor() : 1;
1579     return scrollOffsetForFixedPosition(visibleContentRect, contentsSize, scrollPosition, scrollOrigin, frameScaleFactor, fixedElementsLayoutRelativeToFrame());
1580 }
1581
1582 bool FrameView::fixedElementsLayoutRelativeToFrame() const
1583 {
1584     ASSERT(m_frame);
1585     if (!m_frame->settings())
1586         return false;
1587
1588     return m_frame->settings()->fixedElementsLayoutRelativeToFrame();
1589 }
1590
1591 IntPoint FrameView::lastKnownMousePosition() const
1592 {
1593     return m_frame ? m_frame->eventHandler()->lastKnownMousePosition() : IntPoint();
1594 }
1595
1596 bool FrameView::scrollContentsFastPath(const IntSize& scrollDelta, const IntRect& rectToScroll, const IntRect& clipRect)
1597 {
1598     if (!m_viewportConstrainedObjects || m_viewportConstrainedObjects->isEmpty()) {
1599         hostWindow()->scroll(scrollDelta, rectToScroll, clipRect);
1600         return true;
1601     }
1602
1603     const bool isCompositedContentLayer = contentsInCompositedLayer();
1604
1605     // Get the rects of the fixed objects visible in the rectToScroll
1606     Region regionToUpdate;
1607     ViewportConstrainedObjectSet::const_iterator end = m_viewportConstrainedObjects->end();
1608     for (ViewportConstrainedObjectSet::const_iterator it = m_viewportConstrainedObjects->begin(); it != end; ++it) {
1609         RenderObject* renderer = *it;
1610         if (!renderer->style()->hasViewportConstrainedPosition())
1611             continue;
1612 #if USE(ACCELERATED_COMPOSITING)
1613         if (renderer->isComposited())
1614             continue;
1615 #endif
1616     
1617         // Fixed items should always have layers.
1618         ASSERT(renderer->hasLayer());
1619         RenderLayer* layer = toRenderBoxModelObject(renderer)->layer();
1620         
1621 #if ENABLE(CSS_FILTERS)
1622         if (layer->hasAncestorWithFilterOutsets()) {
1623             // If the fixed layer has a blur/drop-shadow filter applied on at least one of its parents, we cannot 
1624             // scroll using the fast path, otherwise the outsets of the filter will be moved around the page.
1625             return false;
1626         }
1627 #endif
1628         IntRect updateRect = pixelSnappedIntRect(layer->repaintRectIncludingNonCompositingDescendants());
1629         updateRect = contentsToRootView(updateRect);
1630         if (!isCompositedContentLayer && clipsRepaints())
1631             updateRect.intersect(rectToScroll);
1632         if (!updateRect.isEmpty())
1633             regionToUpdate.unite(updateRect);
1634     }
1635
1636     // 1) scroll
1637     hostWindow()->scroll(scrollDelta, rectToScroll, clipRect);
1638
1639     // 2) update the area of fixed objects that has been invalidated
1640     Vector<IntRect> subRectsToUpdate = regionToUpdate.rects();
1641     size_t viewportConstrainedObjectsCount = subRectsToUpdate.size();
1642     for (size_t i = 0; i < viewportConstrainedObjectsCount; ++i) {
1643         IntRect updateRect = subRectsToUpdate[i];
1644         IntRect scrolledRect = updateRect;
1645         scrolledRect.move(scrollDelta);
1646         updateRect.unite(scrolledRect);
1647 #if USE(ACCELERATED_COMPOSITING)
1648         if (isCompositedContentLayer) {
1649             updateRect = rootViewToContents(updateRect);
1650             ASSERT(renderView());
1651             renderView()->layer()->setBackingNeedsRepaintInRect(updateRect);
1652             continue;
1653         }
1654 #endif
1655         if (clipsRepaints())
1656             updateRect.intersect(rectToScroll);
1657         hostWindow()->invalidateContentsAndRootView(updateRect, false);
1658     }
1659
1660     return true;
1661 }
1662
1663 void FrameView::scrollContentsSlowPath(const IntRect& updateRect)
1664 {
1665 #if USE(ACCELERATED_COMPOSITING)
1666     if (contentsInCompositedLayer()) {
1667         IntRect updateRect = visibleContentRect();
1668
1669         // Make sure to "apply" the scale factor here since we're converting from frame view
1670         // coordinates to layer backing coordinates.
1671         updateRect.scale(1 / m_frame->frameScaleFactor());
1672
1673         ASSERT(renderView());
1674         renderView()->layer()->setBackingNeedsRepaintInRect(updateRect);
1675     }
1676     if (RenderPart* frameRenderer = m_frame->ownerRenderer()) {
1677         if (isEnclosedInCompositingLayer()) {
1678             LayoutRect rect(frameRenderer->borderLeft() + frameRenderer->paddingLeft(),
1679                             frameRenderer->borderTop() + frameRenderer->paddingTop(),
1680                             visibleWidth(), visibleHeight());
1681             frameRenderer->repaintRectangle(rect);
1682             return;
1683         }
1684     }
1685 #endif
1686
1687     ScrollView::scrollContentsSlowPath(updateRect);
1688 }
1689
1690 // Note that this gets called at painting time.
1691 void FrameView::setIsOverlapped(bool isOverlapped)
1692 {
1693     if (isOverlapped == m_isOverlapped)
1694         return;
1695
1696     m_isOverlapped = isOverlapped;
1697     updateCanBlitOnScrollRecursively();
1698     
1699 #if USE(ACCELERATED_COMPOSITING)
1700     if (hasCompositedContentIncludingDescendants()) {
1701         // Overlap can affect compositing tests, so if it changes, we need to trigger
1702         // a layer update in the parent document.
1703         if (Frame* parentFrame = m_frame->tree()->parent()) {
1704             if (RenderView* parentView = parentFrame->contentRenderer()) {
1705                 RenderLayerCompositor* compositor = parentView->compositor();
1706                 compositor->setCompositingLayersNeedRebuild();
1707                 compositor->scheduleCompositingLayerUpdate();
1708             }
1709         }
1710
1711         if (RenderLayerCompositor::allowsIndependentlyCompositedFrames(this)) {
1712             // We also need to trigger reevaluation for this and all descendant frames,
1713             // since a frame uses compositing if any ancestor is compositing.
1714             for (Frame* frame = m_frame.get(); frame; frame = frame->tree()->traverseNext(m_frame.get())) {
1715                 if (RenderView* view = frame->contentRenderer()) {
1716                     RenderLayerCompositor* compositor = view->compositor();
1717                     compositor->setCompositingLayersNeedRebuild();
1718                     compositor->scheduleCompositingLayerUpdate();
1719                 }
1720             }
1721         }
1722     }
1723 #endif
1724 }
1725
1726 bool FrameView::isOverlappedIncludingAncestors() const
1727 {
1728     if (isOverlapped())
1729         return true;
1730
1731     if (FrameView* parentView = parentFrameView()) {
1732         if (parentView->isOverlapped())
1733             return true;
1734     }
1735
1736     return false;
1737 }
1738
1739 void FrameView::setContentIsOpaque(bool contentIsOpaque)
1740 {
1741     if (contentIsOpaque == m_contentIsOpaque)
1742         return;
1743
1744     m_contentIsOpaque = contentIsOpaque;
1745     updateCanBlitOnScrollRecursively();
1746 }
1747
1748 void FrameView::restoreScrollbar()
1749 {
1750     setScrollbarsSuppressed(false);
1751 }
1752
1753 bool FrameView::scrollToFragment(const KURL& url)
1754 {
1755     // If our URL has no ref, then we have no place we need to jump to.
1756     // OTOH If CSS target was set previously, we want to set it to 0, recalc
1757     // and possibly repaint because :target pseudo class may have been
1758     // set (see bug 11321).
1759     if (!url.hasFragmentIdentifier() && !m_frame->document()->cssTarget())
1760         return false;
1761
1762     String fragmentIdentifier = url.fragmentIdentifier();
1763     if (scrollToAnchor(fragmentIdentifier))
1764         return true;
1765
1766     // Try again after decoding the ref, based on the document's encoding.
1767     if (TextResourceDecoder* decoder = m_frame->document()->decoder())
1768         return scrollToAnchor(decodeURLEscapeSequences(fragmentIdentifier, decoder->encoding()));
1769
1770     return false;
1771 }
1772
1773 bool FrameView::scrollToAnchor(const String& name)
1774 {
1775     ASSERT(m_frame->document());
1776
1777     if (!m_frame->document()->haveStylesheetsLoaded()) {
1778         m_frame->document()->setGotoAnchorNeededAfterStylesheetsLoad(true);
1779         return false;
1780     }
1781
1782     m_frame->document()->setGotoAnchorNeededAfterStylesheetsLoad(false);
1783
1784     Element* anchorNode = m_frame->document()->findAnchor(name);
1785
1786     // Setting to null will clear the current target.
1787     m_frame->document()->setCSSTarget(anchorNode);
1788
1789 #if ENABLE(SVG)
1790     if (m_frame->document()->isSVGDocument()) {
1791         if (SVGSVGElement* svg = toSVGDocument(m_frame->document())->rootElement()) {
1792             svg->setupInitialView(name, anchorNode);
1793             if (!anchorNode)
1794                 return true;
1795         }
1796     }
1797 #endif
1798   
1799     // Implement the rule that "" and "top" both mean top of page as in other browsers.
1800     if (!anchorNode && !(name.isEmpty() || equalIgnoringCase(name, "top")))
1801         return false;
1802
1803     maintainScrollPositionAtAnchor(anchorNode ? static_cast<Node*>(anchorNode) : m_frame->document());
1804     return true;
1805 }
1806
1807 void FrameView::maintainScrollPositionAtAnchor(Node* anchorNode)
1808 {
1809     m_maintainScrollPositionAnchor = anchorNode;
1810     if (!m_maintainScrollPositionAnchor)
1811         return;
1812
1813     // We need to update the layout before scrolling, otherwise we could
1814     // really mess things up if an anchor scroll comes at a bad moment.
1815     m_frame->document()->updateStyleIfNeeded();
1816     // Only do a layout if changes have occurred that make it necessary.
1817     RenderView* renderView = this->renderView();
1818     if (renderView && renderView->needsLayout())
1819         layout();
1820     else
1821         scrollToAnchor();
1822 }
1823
1824 void FrameView::scrollElementToRect(Element* element, const IntRect& rect)
1825 {
1826     m_frame->document()->updateLayoutIgnorePendingStylesheets();
1827
1828     LayoutRect bounds = element->boundingBox();
1829     int centeringOffsetX = (rect.width() - bounds.width()) / 2;
1830     int centeringOffsetY = (rect.height() - bounds.height()) / 2;
1831     setScrollPosition(IntPoint(bounds.x() - centeringOffsetX - rect.x(), bounds.y() - centeringOffsetY - rect.y()));
1832 }
1833
1834 void FrameView::setScrollPosition(const IntPoint& scrollPoint)
1835 {
1836     TemporaryChange<bool> changeInProgrammaticScroll(m_inProgrammaticScroll, true);
1837     m_maintainScrollPositionAnchor = 0;
1838
1839     IntPoint newScrollPosition = adjustScrollPositionWithinRange(scrollPoint);
1840
1841     if (newScrollPosition == scrollPosition())
1842         return;
1843
1844     if (requestScrollPositionUpdate(newScrollPosition))
1845         return;
1846
1847     ScrollView::setScrollPosition(newScrollPosition);
1848 }
1849
1850 void FrameView::delegatesScrollingDidChange()
1851 {
1852 #if USE(ACCELERATED_COMPOSITING)
1853     // When we switch to delgatesScrolling mode, we should destroy the scrolling/clipping layers in RenderLayerCompositor.
1854     if (hasCompositedContent())
1855         clearBackingStores();
1856 #endif
1857 }
1858
1859 void FrameView::setFixedVisibleContentRect(const IntRect& visibleContentRect)
1860 {
1861     bool visibleContentSizeDidChange = false;
1862     if (visibleContentRect.size() != this->fixedVisibleContentRect().size()) {
1863         // When the viewport size changes or the content is scaled, we need to
1864         // reposition the fixed and sticky positioned elements.
1865         setViewportConstrainedObjectsNeedLayout();
1866         visibleContentSizeDidChange = true;
1867     }
1868
1869     IntSize offset = scrollOffset();
1870     ScrollView::setFixedVisibleContentRect(visibleContentRect);
1871     if (offset != scrollOffset()) {
1872         repaintFixedElementsAfterScrolling();
1873         if (m_frame->page()->settings()->acceleratedCompositingForFixedPositionEnabled())
1874             updateFixedElementsAfterScrolling();
1875         scrollAnimator()->setCurrentPosition(scrollPosition());
1876         scrollPositionChanged();
1877     }
1878     if (visibleContentSizeDidChange) {
1879         // Update the scroll-bars to calculate new page-step size.
1880         updateScrollbars(scrollOffset());
1881     }
1882     frame()->loader()->client()->didChangeScrollOffset();
1883 }
1884
1885 void FrameView::setViewportConstrainedObjectsNeedLayout()
1886 {
1887     if (!hasViewportConstrainedObjects())
1888         return;
1889
1890     ViewportConstrainedObjectSet::const_iterator end = m_viewportConstrainedObjects->end();
1891     for (ViewportConstrainedObjectSet::const_iterator it = m_viewportConstrainedObjects->begin(); it != end; ++it) {
1892         RenderObject* renderer = *it;
1893         renderer->setNeedsLayout(true);
1894     }
1895 }
1896
1897
1898 void FrameView::scrollPositionChangedViaPlatformWidget()
1899 {
1900     repaintFixedElementsAfterScrolling();
1901     updateFixedElementsAfterScrolling();
1902     scrollPositionChanged();
1903 }
1904
1905 void FrameView::scrollPositionChanged()
1906 {
1907     frame()->eventHandler()->sendScrollEvent();
1908     frame()->eventHandler()->dispatchFakeMouseMoveEventSoon();
1909
1910 #if USE(ACCELERATED_COMPOSITING)
1911     if (RenderView* renderView = this->renderView()) {
1912         if (renderView->usesCompositing())
1913             renderView->compositor()->frameViewDidScroll();
1914     }
1915 #endif
1916 }
1917
1918 void FrameView::repaintFixedElementsAfterScrolling()
1919 {
1920     // For fixed position elements, update widget positions and compositing layers after scrolling,
1921     // but only if we're not inside of layout.
1922     if (!m_nestedLayoutCount && hasViewportConstrainedObjects()) {
1923         if (RenderView* renderView = this->renderView()) {
1924             renderView->updateWidgetPositions();
1925             renderView->layer()->updateLayerPositionsAfterDocumentScroll();
1926         }
1927     }
1928 }
1929
1930 bool FrameView::shouldUpdateFixedElementsAfterScrolling()
1931 {
1932 #if ENABLE(THREADED_SCROLLING)
1933     Page* page = m_frame->page();
1934     if (!page)
1935         return true;
1936
1937     // If the scrolling thread is updating the fixed elements, then the FrameView should not update them as well.
1938     if (page->mainFrame() != m_frame)
1939         return true;
1940
1941     ScrollingCoordinator* scrollingCoordinator = page->scrollingCoordinator();
1942     if (!scrollingCoordinator)
1943         return true;
1944
1945     if (!scrollingCoordinator->supportsFixedPositionLayers())
1946         return true;
1947
1948     if (scrollingCoordinator->shouldUpdateScrollLayerPositionOnMainThread())
1949         return true;
1950
1951     if (inProgrammaticScroll())
1952         return true;
1953
1954     return false;
1955 #endif
1956     return true;
1957 }
1958
1959 void FrameView::updateFixedElementsAfterScrolling()
1960 {
1961 #if USE(ACCELERATED_COMPOSITING)
1962     if (!shouldUpdateFixedElementsAfterScrolling())
1963         return;
1964
1965     if (m_nestedLayoutCount <= 1 && hasViewportConstrainedObjects()) {
1966         if (RenderView* renderView = this->renderView())
1967             renderView->compositor()->updateCompositingLayers(CompositingUpdateOnScroll);
1968     }
1969 #endif
1970 }
1971
1972 bool FrameView::shouldRubberBandInDirection(ScrollDirection direction) const
1973 {
1974     Page* page = frame() ? frame()->page() : 0;
1975     if (!page)
1976         return ScrollView::shouldRubberBandInDirection(direction);
1977     return page->chrome()->client()->shouldRubberBandInDirection(direction);
1978 }
1979
1980 bool FrameView::isRubberBandInProgress() const
1981 {
1982     if (scrollbarsSuppressed())
1983         return false;
1984
1985     // If the scrolling thread updates the scroll position for this FrameView, then we should return
1986     // ScrollingCoordinator::isRubberBandInProgress().
1987     if (Page* page = m_frame->page()) {
1988         if (ScrollingCoordinator* scrollingCoordinator = page->scrollingCoordinator()) {
1989             if (!scrollingCoordinator->shouldUpdateScrollLayerPositionOnMainThread())
1990                 return scrollingCoordinator->isRubberBandInProgress();
1991         }
1992     }
1993
1994     // If the main thread updates the scroll position for this FrameView, we should return
1995     // ScrollAnimator::isRubberBandInProgress().
1996     if (ScrollAnimator* scrollAnimator = existingScrollAnimator())
1997         return scrollAnimator->isRubberBandInProgress();
1998
1999     return false;
2000 }
2001
2002 bool FrameView::requestScrollPositionUpdate(const IntPoint& position)
2003 {
2004 #if ENABLE(THREADED_SCROLLING)
2005     if (TiledBacking* tiledBacking = this->tiledBacking()) {
2006         IntRect visibleRect = visibleContentRect();
2007         visibleRect.setLocation(position);
2008         tiledBacking->prepopulateRect(visibleRect);
2009     }
2010
2011     if (Page* page = m_frame->page()) {
2012         if (ScrollingCoordinator* scrollingCoordinator = page->scrollingCoordinator())
2013             return scrollingCoordinator->requestScrollPositionUpdate(this, position);
2014     }
2015 #else
2016     UNUSED_PARAM(position);
2017 #endif
2018
2019     return false;
2020 }
2021
2022 HostWindow* FrameView::hostWindow() const
2023 {
2024     Page* page = frame() ? frame()->page() : 0;
2025     if (!page)
2026         return 0;
2027     return page->chrome();
2028 }
2029
2030 const unsigned cRepaintRectUnionThreshold = 25;
2031
2032 void FrameView::repaintContentRectangle(const IntRect& r, bool immediate)
2033 {
2034     ASSERT(!m_frame->ownerElement());
2035
2036     if (m_isTrackingRepaints) {
2037         IntRect repaintRect = r;
2038         repaintRect.move(-scrollOffset());
2039         m_trackedRepaintRects.append(repaintRect);
2040     }
2041
2042     double delay = m_deferringRepaints ? 0 : adjustedDeferredRepaintDelay();
2043     if ((m_deferringRepaints || m_deferredRepaintTimer.isActive() || delay) && !immediate) {
2044         IntRect paintRect = r;
2045         if (clipsRepaints() && !paintsEntireContents())
2046             paintRect.intersect(visibleContentRect());
2047         if (paintRect.isEmpty())
2048             return;
2049         if (m_repaintCount == cRepaintRectUnionThreshold) {
2050             IntRect unionedRect;
2051             for (unsigned i = 0; i < cRepaintRectUnionThreshold; ++i)
2052                 unionedRect.unite(pixelSnappedIntRect(m_repaintRects[i]));
2053             m_repaintRects.clear();
2054             m_repaintRects.append(unionedRect);
2055         }
2056         if (m_repaintCount < cRepaintRectUnionThreshold)
2057             m_repaintRects.append(paintRect);
2058         else
2059             m_repaintRects[0].unite(paintRect);
2060         m_repaintCount++;
2061
2062         if (!m_deferringRepaints)
2063             startDeferredRepaintTimer(delay);
2064
2065         return;
2066     }
2067     
2068     if (!shouldUpdate(immediate))
2069         return;
2070
2071 #if USE(TILED_BACKING_STORE)
2072     if (frame()->tiledBackingStore()) {
2073         frame()->tiledBackingStore()->invalidate(r);
2074         return;
2075     }
2076 #endif
2077     ScrollView::repaintContentRectangle(r, immediate);
2078 }
2079
2080 void FrameView::contentsResized()
2081 {
2082     ScrollView::contentsResized();
2083     setNeedsLayout();
2084 }
2085
2086 void FrameView::visibleContentsResized()
2087 {
2088     // We check to make sure the view is attached to a frame() as this method can
2089     // be triggered before the view is attached by Frame::createView(...) setting
2090     // various values such as setScrollBarModes(...) for example.  An ASSERT is
2091     // triggered when a view is layout before being attached to a frame().
2092     if (!frame()->view())
2093         return;
2094
2095     if (!useFixedLayout() && needsLayout())
2096         layout();
2097
2098 #if USE(ACCELERATED_COMPOSITING)
2099     if (RenderView* renderView = this->renderView()) {
2100         if (renderView->usesCompositing())
2101             renderView->compositor()->frameViewDidChangeSize();
2102     }
2103 #endif
2104 }
2105
2106 void FrameView::beginDeferredRepaints()
2107 {
2108     Page* page = m_frame->page();
2109     if (page->mainFrame() != m_frame) {
2110         page->mainFrame()->view()->beginDeferredRepaints();
2111         return;
2112     }
2113
2114     m_deferringRepaints++;
2115 }
2116
2117 void FrameView::endDeferredRepaints()
2118 {
2119     Page* page = m_frame->page();
2120     if (page->mainFrame() != m_frame) {
2121         page->mainFrame()->view()->endDeferredRepaints();
2122         return;
2123     }
2124
2125     ASSERT(m_deferringRepaints > 0);
2126
2127     if (--m_deferringRepaints)
2128         return;
2129
2130     if (m_deferredRepaintTimer.isActive())
2131         return;
2132
2133     if (double delay = adjustedDeferredRepaintDelay()) {
2134         startDeferredRepaintTimer(delay);
2135         return;
2136     }
2137     
2138     doDeferredRepaints();
2139 }
2140
2141 void FrameView::startDeferredRepaintTimer(double delay)
2142 {
2143     if (m_deferredRepaintTimer.isActive())
2144         return;
2145
2146     if (m_disableRepaints)
2147         return;
2148
2149     m_deferredRepaintTimer.startOneShot(delay);
2150 }
2151
2152 void FrameView::handleLoadCompleted()
2153 {
2154     // Once loading has completed, allow autoSize one last opportunity to
2155     // reduce the size of the frame.
2156     autoSizeIfEnabled();
2157     if (shouldUseLoadTimeDeferredRepaintDelay())
2158         return;
2159     m_deferredRepaintDelay = s_normalDeferredRepaintDelay;
2160     flushDeferredRepaints();
2161 }
2162
2163 void FrameView::flushDeferredRepaints()
2164 {
2165     if (!m_deferredRepaintTimer.isActive())
2166         return;
2167     m_deferredRepaintTimer.stop();
2168     doDeferredRepaints();
2169 }
2170
2171 void FrameView::doDeferredRepaints()
2172 {
2173     if (m_disableRepaints)
2174         return;
2175
2176     ASSERT(!m_deferringRepaints);
2177     if (!shouldUpdate()) {
2178         m_repaintRects.clear();
2179         m_repaintCount = 0;
2180         return;
2181     }
2182     unsigned size = m_repaintRects.size();
2183     for (unsigned i = 0; i < size; i++) {
2184 #if USE(TILED_BACKING_STORE)
2185         if (frame()->tiledBackingStore()) {
2186             frame()->tiledBackingStore()->invalidate(pixelSnappedIntRect(m_repaintRects[i]));
2187             continue;
2188         }
2189 #endif
2190         ScrollView::repaintContentRectangle(pixelSnappedIntRect(m_repaintRects[i]), false);
2191     }
2192     m_repaintRects.clear();
2193     m_repaintCount = 0;
2194     
2195     updateDeferredRepaintDelayAfterRepaint();
2196 }
2197
2198 bool FrameView::shouldUseLoadTimeDeferredRepaintDelay() const
2199 {
2200     // Don't defer after the initial load of the page has been completed.
2201     if (m_frame->tree()->top()->loader()->isComplete())
2202         return false;
2203     Document* document = m_frame->document();
2204     if (!document)
2205         return false;
2206     if (document->parsing())
2207         return true;
2208     if (document->cachedResourceLoader()->requestCount())
2209         return true;
2210     return false;
2211 }
2212
2213 void FrameView::updateDeferredRepaintDelayAfterRepaint()
2214 {
2215     if (!shouldUseLoadTimeDeferredRepaintDelay()) {
2216         m_deferredRepaintDelay = s_normalDeferredRepaintDelay;
2217         return;
2218     }
2219     double incrementedRepaintDelay = m_deferredRepaintDelay + s_deferredRepaintDelayIncrementDuringLoading;
2220     m_deferredRepaintDelay = std::min(incrementedRepaintDelay, s_maxDeferredRepaintDelayDuringLoading);
2221 }
2222
2223 void FrameView::resetDeferredRepaintDelay()
2224 {
2225     m_deferredRepaintDelay = 0;
2226     if (m_deferredRepaintTimer.isActive()) {
2227         m_deferredRepaintTimer.stop();
2228         if (!m_deferringRepaints)
2229             doDeferredRepaints();
2230     }
2231 }
2232
2233 double FrameView::adjustedDeferredRepaintDelay() const
2234 {
2235     ASSERT(!m_deferringRepaints);
2236     if (!m_deferredRepaintDelay)
2237         return 0;
2238     double timeSinceLastPaint = currentTime() - m_lastPaintTime;
2239     return max(0., m_deferredRepaintDelay - timeSinceLastPaint);
2240 }
2241     
2242 void FrameView::deferredRepaintTimerFired(Timer<FrameView>*)
2243 {
2244     doDeferredRepaints();
2245 }
2246
2247 void FrameView::beginDisableRepaints()
2248 {
2249     m_disableRepaints++;
2250 }
2251
2252 void FrameView::endDisableRepaints()
2253 {
2254     ASSERT(m_disableRepaints > 0);
2255     m_disableRepaints--;
2256 }
2257
2258 void FrameView::layoutTimerFired(Timer<FrameView>*)
2259 {
2260 #ifdef INSTRUMENT_LAYOUT_SCHEDULING
2261     if (!m_frame->document()->ownerElement())
2262         printf("Layout timer fired at %d\n", m_frame->document()->elapsedTime());
2263 #endif
2264     layout();
2265 }
2266
2267 void FrameView::scheduleRelayout()
2268 {
2269     // FIXME: We should assert the page is not in the page cache, but that is causing
2270     // too many false assertions.  See <rdar://problem/7218118>.
2271     ASSERT(m_frame->view() == this);
2272
2273     if (m_layoutRoot) {
2274         m_layoutRoot->markContainingBlocksForLayout(false);
2275         m_layoutRoot = 0;
2276     }
2277     if (!m_layoutSchedulingEnabled)
2278         return;
2279     if (!needsLayout())
2280         return;
2281     if (!m_frame->document()->shouldScheduleLayout())
2282         return;
2283     InspectorInstrumentation::didInvalidateLayout(m_frame.get());
2284     // When frame flattening is enabled, the contents of the frame could affect the layout of the parent frames.
2285     // Also invalidate parent frame starting from the owner element of this frame.
2286     if (m_frame->ownerRenderer() && isInChildFrameWithFrameFlattening())
2287         m_frame->ownerRenderer()->setNeedsLayout(true, MarkContainingBlockChain);
2288
2289     int delay = m_frame->document()->minimumLayoutDelay();
2290     if (m_layoutTimer.isActive() && m_delayedLayout && !delay)
2291         unscheduleRelayout();
2292     if (m_layoutTimer.isActive())
2293         return;
2294
2295     m_delayedLayout = delay != 0;
2296
2297 #ifdef INSTRUMENT_LAYOUT_SCHEDULING
2298     if (!m_frame->document()->ownerElement())
2299         printf("Scheduling layout for %d\n", delay);
2300 #endif
2301
2302     m_layoutTimer.startOneShot(delay * 0.001);
2303 }
2304
2305 static bool isObjectAncestorContainerOf(RenderObject* ancestor, RenderObject* descendant)
2306 {
2307     for (RenderObject* r = descendant; r; r = r->container()) {
2308         if (r == ancestor)
2309             return true;
2310     }
2311     return false;
2312 }
2313
2314 void FrameView::scheduleRelayoutOfSubtree(RenderObject* relayoutRoot)
2315 {
2316     ASSERT(m_frame->view() == this);
2317
2318     RenderView* renderView = this->renderView();
2319     if (renderView && renderView->needsLayout()) {
2320         if (relayoutRoot)
2321             relayoutRoot->markContainingBlocksForLayout(false);
2322         return;
2323     }
2324
2325     if (layoutPending() || !m_layoutSchedulingEnabled) {
2326         if (m_layoutRoot != relayoutRoot) {
2327             if (isObjectAncestorContainerOf(m_layoutRoot, relayoutRoot)) {
2328                 // Keep the current root
2329                 relayoutRoot->markContainingBlocksForLayout(false, m_layoutRoot);
2330                 ASSERT(!m_layoutRoot->container() || !m_layoutRoot->container()->needsLayout());
2331             } else if (m_layoutRoot && isObjectAncestorContainerOf(relayoutRoot, m_layoutRoot)) {
2332                 // Re-root at relayoutRoot
2333                 m_layoutRoot->markContainingBlocksForLayout(false, relayoutRoot);
2334                 m_layoutRoot = relayoutRoot;
2335                 ASSERT(!m_layoutRoot->container() || !m_layoutRoot->container()->needsLayout());
2336                 InspectorInstrumentation::didInvalidateLayout(m_frame.get());
2337             } else {
2338                 // Just do a full relayout
2339                 if (m_layoutRoot)
2340                     m_layoutRoot->markContainingBlocksForLayout(false);
2341                 m_layoutRoot = 0;
2342                 relayoutRoot->markContainingBlocksForLayout(false);
2343                 InspectorInstrumentation::didInvalidateLayout(m_frame.get());
2344             }
2345         }
2346     } else if (m_layoutSchedulingEnabled) {
2347         int delay = m_frame->document()->minimumLayoutDelay();
2348         m_layoutRoot = relayoutRoot;
2349         ASSERT(!m_layoutRoot->container() || !m_layoutRoot->container()->needsLayout());
2350         InspectorInstrumentation::didInvalidateLayout(m_frame.get());
2351         m_delayedLayout = delay != 0;
2352         m_layoutTimer.startOneShot(delay * 0.001);
2353     }
2354 }
2355
2356 bool FrameView::layoutPending() const
2357 {
2358     return m_layoutTimer.isActive();
2359 }
2360
2361 bool FrameView::needsLayout() const
2362 {
2363     // This can return true in cases where the document does not have a body yet.
2364     // Document::shouldScheduleLayout takes care of preventing us from scheduling
2365     // layout in that case.
2366     if (!m_frame)
2367         return false;
2368
2369     RenderView* renderView = this->renderView();
2370     return layoutPending()
2371         || (renderView && renderView->needsLayout())
2372         || m_layoutRoot
2373         || (m_deferSetNeedsLayouts && m_setNeedsLayoutWasDeferred);
2374 }
2375
2376 void FrameView::setNeedsLayout()
2377 {
2378     if (m_deferSetNeedsLayouts) {
2379         m_setNeedsLayoutWasDeferred = true;
2380         return;
2381     }
2382
2383     if (RenderView* renderView = this->renderView())
2384         renderView->setNeedsLayout(true);
2385 }
2386
2387 void FrameView::unscheduleRelayout()
2388 {
2389     if (!m_layoutTimer.isActive())
2390         return;
2391
2392 #ifdef INSTRUMENT_LAYOUT_SCHEDULING
2393     if (!m_frame->document()->ownerElement())
2394         printf("Layout timer unscheduled at %d\n", m_frame->document()->elapsedTime());
2395 #endif
2396     
2397     m_layoutTimer.stop();
2398     m_delayedLayout = false;
2399 }
2400
2401 #if ENABLE(REQUEST_ANIMATION_FRAME)
2402 void FrameView::serviceScriptedAnimations(double monotonicAnimationStartTime)
2403 {
2404     for (Frame* frame = m_frame.get(); frame; frame = frame->tree()->traverseNext()) {
2405         frame->view()->serviceScrollAnimations();
2406         frame->animation()->serviceAnimations();
2407     }
2408
2409     Vector<RefPtr<Document> > documents;
2410     for (Frame* frame = m_frame.get(); frame; frame = frame->tree()->traverseNext())
2411         documents.append(frame->document());
2412
2413     for (size_t i = 0; i < documents.size(); ++i)
2414         documents[i]->serviceScriptedAnimations(monotonicAnimationStartTime);
2415 }
2416 #endif
2417
2418 bool FrameView::isTransparent() const
2419 {
2420     return m_isTransparent;
2421 }
2422
2423 void FrameView::setTransparent(bool isTransparent)
2424 {
2425     m_isTransparent = isTransparent;
2426 }
2427
2428 bool FrameView::hasOpaqueBackground() const
2429 {
2430     return !m_isTransparent && !m_baseBackgroundColor.hasAlpha();
2431 }
2432
2433 Color FrameView::baseBackgroundColor() const
2434 {
2435     return m_baseBackgroundColor;
2436 }
2437
2438 void FrameView::setBaseBackgroundColor(const Color& backgroundColor)
2439 {
2440     if (!backgroundColor.isValid())
2441         m_baseBackgroundColor = Color::white;
2442     else
2443         m_baseBackgroundColor = backgroundColor;
2444
2445     recalculateScrollbarOverlayStyle();
2446 }
2447
2448 void FrameView::updateBackgroundRecursively(const Color& backgroundColor, bool transparent)
2449 {
2450     for (Frame* frame = m_frame.get(); frame; frame = frame->tree()->traverseNext(m_frame.get())) {
2451         if (FrameView* view = frame->view()) {
2452             view->setTransparent(transparent);
2453             view->setBaseBackgroundColor(backgroundColor);
2454         }
2455     }
2456 }
2457
2458 bool FrameView::shouldUpdateWhileOffscreen() const
2459 {
2460     return m_shouldUpdateWhileOffscreen;
2461 }
2462
2463 void FrameView::setShouldUpdateWhileOffscreen(bool shouldUpdateWhileOffscreen)
2464 {
2465     m_shouldUpdateWhileOffscreen = shouldUpdateWhileOffscreen;
2466 }
2467
2468 bool FrameView::shouldUpdate(bool immediateRequested) const
2469 {
2470     if (!immediateRequested && isOffscreen() && !shouldUpdateWhileOffscreen())
2471         return false;
2472     return true;
2473 }
2474
2475 void FrameView::scheduleEvent(PassRefPtr<Event> event, PassRefPtr<Node> eventTarget)
2476 {
2477     m_actionScheduler->scheduleEvent(event, eventTarget);
2478 }
2479
2480 void FrameView::pauseScheduledEvents()
2481 {
2482     m_actionScheduler->pause();
2483 }
2484
2485 void FrameView::resumeScheduledEvents()
2486 {
2487     m_actionScheduler->resume();
2488 }
2489
2490 void FrameView::scrollToAnchor()
2491 {
2492     RefPtr<Node> anchorNode = m_maintainScrollPositionAnchor;
2493     if (!anchorNode)
2494         return;
2495
2496     if (!anchorNode->renderer())
2497         return;
2498
2499     LayoutRect rect;
2500     if (anchorNode != m_frame->document())
2501         rect = anchorNode->boundingBox();
2502
2503     // Scroll nested layers and frames to reveal the anchor.
2504     // Align to the top and to the closest side (this matches other browsers).
2505     anchorNode->renderer()->scrollRectToVisible(rect, ScrollAlignment::alignToEdgeIfNeeded, ScrollAlignment::alignTopAlways);
2506
2507     if (AXObjectCache::accessibilityEnabled())
2508         m_frame->document()->axObjectCache()->handleScrolledToAnchor(anchorNode.get());
2509
2510     // scrollRectToVisible can call into setScrollPosition(), which resets m_maintainScrollPositionAnchor.
2511     m_maintainScrollPositionAnchor = anchorNode;
2512 }
2513
2514 void FrameView::updateWidget(RenderObject* object)
2515 {
2516     ASSERT(!object->node() || object->node()->isElementNode());
2517     Element* ownerElement = toElement(object->node());
2518     // The object may have already been destroyed (thus node cleared),
2519     // but FrameView holds a manual ref, so it won't have been deleted.
2520     ASSERT(m_widgetUpdateSet->contains(object));
2521     if (!ownerElement)
2522         return;
2523
2524     if (object->isEmbeddedObject()) {
2525         RenderEmbeddedObject* embeddedObject = static_cast<RenderEmbeddedObject*>(object);
2526         // No need to update if it's already crashed or known to be missing.
2527         if (embeddedObject->showsUnavailablePluginIndicator())
2528             return;
2529
2530         if (object->isSnapshottedPlugIn()) {
2531             if (ownerElement->hasTagName(objectTag) || ownerElement->hasTagName(embedTag)) {
2532                 HTMLPlugInImageElement* pluginElement = toHTMLPlugInImageElement(ownerElement);
2533                 pluginElement->updateSnapshotInfo();
2534             }
2535             return;
2536         }
2537
2538         // FIXME: This could turn into a real virtual dispatch if we defined
2539         // updateWidget(PluginCreationOption) on HTMLElement.
2540         if (ownerElement->hasTagName(objectTag) || ownerElement->hasTagName(embedTag) || ownerElement->hasTagName(appletTag)) {
2541             HTMLPlugInImageElement* pluginElement = toHTMLPlugInImageElement(ownerElement);
2542             if (pluginElement->needsWidgetUpdate())
2543                 pluginElement->updateWidget(CreateAnyWidgetType);
2544         }
2545         // FIXME: It is not clear that Media elements need or want this updateWidget() call.
2546 #if ENABLE(PLUGIN_PROXY_FOR_VIDEO)
2547         else if (ownerElement->isMediaElement())
2548             static_cast<HTMLMediaElement*>(ownerElement)->updateWidget(CreateAnyWidgetType);
2549 #endif
2550         else
2551             ASSERT_NOT_REACHED();
2552
2553         // Caution: it's possible the object was destroyed again, since loading a
2554         // plugin may run any arbitrary JavaScript.
2555         embeddedObject->updateWidgetPosition();
2556     }
2557 }
2558
2559 bool FrameView::updateWidgets()
2560 {
2561     if (m_nestedLayoutCount > 1 || !m_widgetUpdateSet || m_widgetUpdateSet->isEmpty())
2562         return true;
2563     
2564     size_t size = m_widgetUpdateSet->size();
2565
2566     Vector<RenderObject*> objects;
2567     objects.reserveInitialCapacity(size);
2568
2569     RenderObjectSet::const_iterator end = m_widgetUpdateSet->end();
2570     for (RenderObjectSet::const_iterator it = m_widgetUpdateSet->begin(); it != end; ++it) {
2571         RenderObject* object = *it;
2572         objects.uncheckedAppend(object);
2573         if (object->isEmbeddedObject()) {
2574             RenderEmbeddedObject* embeddedObject = static_cast<RenderEmbeddedObject*>(object);
2575             embeddedObject->ref();
2576         }
2577     }
2578
2579     for (size_t i = 0; i < size; ++i) {
2580         RenderObject* object = objects[i];
2581         updateWidget(object);
2582         m_widgetUpdateSet->remove(object);
2583     }
2584
2585     RenderArena* arena = m_frame->document()->renderArena();
2586     for (size_t i = 0; i < size; ++i) {
2587         RenderObject* object = objects[i];
2588         if (object->isEmbeddedObject()) {
2589             RenderEmbeddedObject* embeddedObject = static_cast<RenderEmbeddedObject*>(object);
2590             embeddedObject->deref(arena);
2591         }
2592     }
2593     
2594     return m_widgetUpdateSet->isEmpty();
2595 }
2596
2597 void FrameView::flushAnyPendingPostLayoutTasks()
2598 {
2599     if (!m_postLayoutTasksTimer.isActive())
2600         return;
2601
2602     performPostLayoutTasks();
2603 }
2604
2605 void FrameView::performPostLayoutTasks()
2606 {
2607     m_postLayoutTasksTimer.stop();
2608
2609     m_frame->selection()->setCaretRectNeedsUpdate();
2610     m_frame->selection()->updateAppearance();
2611
2612     LayoutMilestones milestonesOfInterest = 0;
2613     LayoutMilestones milestonesAchieved = 0;
2614     Page* page = m_frame->page();
2615     if (page)
2616         milestonesOfInterest = page->layoutMilestones();
2617
2618     if (m_nestedLayoutCount <= 1) {
2619         if (m_firstLayoutCallbackPending) {
2620             m_firstLayoutCallbackPending = false;
2621             m_frame->loader()->didFirstLayout();
2622             if (milestonesOfInterest & DidFirstLayout)
2623                 milestonesAchieved |= DidFirstLayout;
2624             if (page) {
2625                 if (page->mainFrame() == m_frame)
2626                     page->startCountingRelevantRepaintedObjects();
2627             }
2628         }
2629
2630         // Ensure that we always send this eventually.
2631         if (!m_frame->document()->parsing() && m_frame->loader()->stateMachine()->committedFirstRealDocumentLoad())
2632             m_isVisuallyNonEmpty = true;
2633
2634         // If the layout was done with pending sheets, we are not in fact visually non-empty yet.
2635         if (m_isVisuallyNonEmpty && !m_frame->document()->didLayoutWithPendingStylesheets() && m_firstVisuallyNonEmptyLayoutCallbackPending) {
2636             m_firstVisuallyNonEmptyLayoutCallbackPending = false;
2637             if (milestonesOfInterest & DidFirstVisuallyNonEmptyLayout)
2638                 milestonesAchieved |= DidFirstVisuallyNonEmptyLayout;
2639         }
2640     }
2641
2642     m_frame->loader()->didLayout(milestonesAchieved);
2643 #if ENABLE(FONT_LOAD_EVENTS)
2644     if (RuntimeEnabledFeatures::fontLoadEventsEnabled())
2645         m_frame->document()->fontloader()->didLayout();
2646 #endif
2647     
2648     // FIXME: We should consider adding DidLayout as a LayoutMilestone. That would let us merge this
2649     // with didLayout(LayoutMilestones).
2650     m_frame->loader()->client()->dispatchDidLayout();
2651
2652     RenderView* renderView = this->renderView();
2653     if (renderView)
2654         renderView->updateWidgetPositions();
2655     
2656     for (unsigned i = 0; i < maxUpdateWidgetsIterations; i++) {
2657         if (updateWidgets())
2658             break;
2659     }
2660
2661     if (page) {
2662         if (ScrollingCoordinator* scrollingCoordinator = page->scrollingCoordinator())
2663             scrollingCoordinator->frameViewLayoutUpdated(this);
2664     }
2665
2666 #if USE(ACCELERATED_COMPOSITING)
2667     if (renderView && renderView->usesCompositing())
2668         renderView->compositor()->frameViewDidLayout();
2669 #endif
2670
2671     scrollToAnchor();
2672
2673     m_actionScheduler->resume();
2674
2675     if (renderView && !renderView->printing()) {
2676         IntSize currentSize;
2677         if (useFixedLayout() && !fixedLayoutSize().isEmpty() && delegatesScrolling())
2678             currentSize = fixedLayoutSize();
2679         else
2680             currentSize = visibleContentRect(IncludeScrollbars).size();
2681         float currentZoomFactor = renderView->style()->zoom();
2682         bool resized = !m_firstLayout && (currentSize != m_lastViewportSize || currentZoomFactor != m_lastZoomFactor);
2683         m_lastViewportSize = currentSize;
2684         m_lastZoomFactor = currentZoomFactor;
2685         if (resized) {
2686             m_frame->eventHandler()->sendResizeEvent();
2687
2688 #if ENABLE(INSPECTOR)
2689             if (InspectorInstrumentation::hasFrontends()) {
2690                 if (page) {
2691                     if (page->mainFrame() == m_frame) {
2692                         if (InspectorClient* inspectorClient = page->inspectorController()->inspectorClient())
2693                             inspectorClient->didResizeMainFrame(m_frame.get());
2694                     }
2695                 }
2696             }
2697 #endif
2698         }
2699     }
2700 }
2701
2702 void FrameView::postLayoutTimerFired(Timer<FrameView>*)
2703 {
2704     performPostLayoutTasks();
2705 }
2706
2707 void FrameView::autoSizeIfEnabled()
2708 {
2709     if (!m_shouldAutoSize)
2710         return;
2711
2712     if (m_inAutoSize)
2713         return;
2714
2715     TemporaryChange<bool> changeInAutoSize(m_inAutoSize, true);
2716
2717     Document* document = frame()->document();
2718     if (!document)
2719         return;
2720
2721     RenderView* documentView = document->renderView();
2722     Element* documentElement = document->documentElement();
2723     if (!documentView || !documentElement)
2724         return;
2725
2726     // If this is the first time we run autosize, start from small height and
2727     // allow it to grow.
2728     if (!m_didRunAutosize)
2729         resize(frameRect().width(), m_minAutoSize.height());
2730
2731     IntSize size = frameRect().size();
2732
2733     // Do the resizing twice. The first time is basically a rough calculation using the preferred width
2734     // which may result in a height change during the second iteration.
2735     for (int i = 0; i < 2; i++) {
2736         // Update various sizes including contentsSize, scrollHeight, etc.
2737         document->updateLayoutIgnorePendingStylesheets();
2738         int width = documentView->minPreferredLogicalWidth();
2739         int height = documentView->documentRect().height();
2740         IntSize newSize(width, height);
2741
2742         // Check to see if a scrollbar is needed for a given dimension and
2743         // if so, increase the other dimension to account for the scrollbar.
2744         // Since the dimensions are only for the view rectangle, once a
2745         // dimension exceeds the maximum, there is no need to increase it further.
2746         if (newSize.width() > m_maxAutoSize.width()) {
2747             RefPtr<Scrollbar> localHorizontalScrollbar = horizontalScrollbar();
2748             if (!localHorizontalScrollbar)
2749                 localHorizontalScrollbar = createScrollbar(HorizontalScrollbar);
2750             if (!localHorizontalScrollbar->isOverlayScrollbar())
2751                 newSize.setHeight(newSize.height() + localHorizontalScrollbar->height());
2752
2753             // Don't bother checking for a vertical scrollbar because the width is at
2754             // already greater the maximum.
2755         } else if (newSize.height() > m_maxAutoSize.height()) {
2756             RefPtr<Scrollbar> localVerticalScrollbar = verticalScrollbar();
2757             if (!localVerticalScrollbar)
2758                 localVerticalScrollbar = createScrollbar(VerticalScrollbar);
2759             if (!localVerticalScrollbar->isOverlayScrollbar())
2760                 newSize.setWidth(newSize.width() + localVerticalScrollbar->width());
2761
2762             // Don't bother checking for a horizontal scrollbar because the height is
2763             // already greater the maximum.
2764         }
2765
2766         // Ensure the size is at least the min bounds.
2767         newSize = newSize.expandedTo(m_minAutoSize);
2768
2769         // Bound the dimensions by the max bounds and determine what scrollbars to show.
2770         ScrollbarMode horizonalScrollbarMode = ScrollbarAlwaysOff;
2771         if (newSize.width() > m_maxAutoSize.width()) {
2772             newSize.setWidth(m_maxAutoSize.width());
2773             horizonalScrollbarMode = ScrollbarAlwaysOn;
2774         }
2775         ScrollbarMode verticalScrollbarMode = ScrollbarAlwaysOff;
2776         if (newSize.height() > m_maxAutoSize.height()) {
2777             newSize.setHeight(m_maxAutoSize.height());
2778             verticalScrollbarMode = ScrollbarAlwaysOn;
2779         }
2780
2781         if (newSize == size)
2782             continue;
2783
2784         // While loading only allow the size to increase (to avoid twitching during intermediate smaller states)
2785         // unless autoresize has just been turned on or the maximum size is smaller than the current size.
2786         if (m_didRunAutosize && size.height() <= m_maxAutoSize.height() && size.width() <= m_maxAutoSize.width()
2787             && !frame()->loader()->isComplete() && (newSize.height() < size.height() || newSize.width() < size.width()))
2788             break;
2789
2790         resize(newSize.width(), newSize.height());
2791         // Force the scrollbar state to avoid the scrollbar code adding them and causing them to be needed. For example,
2792         // a vertical scrollbar may cause text to wrap and thus increase the height (which is the only reason the scollbar is needed).
2793         setVerticalScrollbarLock(false);
2794         setHorizontalScrollbarLock(false);
2795         setScrollbarModes(horizonalScrollbarMode, verticalScrollbarMode, true, true);
2796     }
2797     m_didRunAutosize = true;
2798 }
2799
2800 void FrameView::updateOverflowStatus(bool horizontalOverflow, bool verticalOverflow)
2801 {
2802     if (!m_viewportRenderer)
2803         return;
2804     
2805     if (m_overflowStatusDirty) {
2806         m_horizontalOverflow = horizontalOverflow;
2807         m_verticalOverflow = verticalOverflow;
2808         m_overflowStatusDirty = false;
2809         return;
2810     }
2811     
2812     bool horizontalOverflowChanged = (m_horizontalOverflow != horizontalOverflow);
2813     bool verticalOverflowChanged = (m_verticalOverflow != verticalOverflow);
2814     
2815     if (horizontalOverflowChanged || verticalOverflowChanged) {
2816         m_horizontalOverflow = horizontalOverflow;
2817         m_verticalOverflow = verticalOverflow;
2818         
2819         m_actionScheduler->scheduleEvent(OverflowEvent::create(horizontalOverflowChanged, horizontalOverflow,
2820             verticalOverflowChanged, verticalOverflow),
2821             m_viewportRenderer->node());
2822     }
2823     
2824 }
2825
2826 const Pagination& FrameView::pagination() const
2827 {
2828     if (m_pagination != Pagination())
2829         return m_pagination;
2830
2831     if (Page* page = m_frame->page()) {
2832         if (page->mainFrame() == m_frame)
2833             return page->pagination();
2834     }
2835
2836     return m_pagination;
2837 }
2838
2839 void FrameView::setPagination(const Pagination& pagination)
2840 {
2841     if (m_pagination == pagination)
2842         return;
2843
2844     m_pagination = pagination;
2845
2846     if (m_frame)
2847         m_frame->document()->styleResolverChanged(DeferRecalcStyle);
2848 }
2849
2850 IntRect FrameView::windowClipRect(bool clipToContents) const
2851 {
2852     ASSERT(m_frame->view() == this);
2853
2854     if (paintsEntireContents())
2855         return IntRect(IntPoint(), contentsSize());
2856
2857     // Set our clip rect to be our contents.
2858     IntRect clipRect = contentsToWindow(visibleContentRect(clipToContents ? ExcludeScrollbars : IncludeScrollbars));
2859     if (!m_frame || !m_frame->ownerElement())
2860         return clipRect;
2861
2862     // Take our owner element and get its clip rect.
2863     HTMLFrameOwnerElement* ownerElement = m_frame->ownerElement();
2864     FrameView* parentView = ownerElement->document()->view();
2865     if (parentView)
2866         clipRect.intersect(parentView->windowClipRectForFrameOwner(ownerElement, true));
2867     return clipRect;
2868 }
2869
2870 IntRect FrameView::windowClipRectForFrameOwner(const HTMLFrameOwnerElement* ownerElement, bool clipToLayerContents) const
2871 {
2872     // The renderer can sometimes be null when style="display:none" interacts
2873     // with external content and plugins.
2874     if (!ownerElement->renderer())
2875         return windowClipRect();
2876
2877     // If we have no layer, just return our window clip rect.
2878     const RenderLayer* enclosingLayer = ownerElement->renderer()->enclosingLayer();
2879     if (!enclosingLayer)
2880         return windowClipRect();
2881
2882     // Apply the clip from the layer.
2883     IntRect clipRect;
2884     if (clipToLayerContents)
2885         clipRect = pixelSnappedIntRect(enclosingLayer->childrenClipRect());
2886     else
2887         clipRect = pixelSnappedIntRect(enclosingLayer->selfClipRect());
2888     clipRect = contentsToWindow(clipRect); 
2889     return intersection(clipRect, windowClipRect());
2890 }
2891
2892 bool FrameView::isActive() const
2893 {
2894     Page* page = frame()->page();
2895     return page && page->focusController()->isActive();
2896 }
2897
2898 void FrameView::scrollTo(const IntSize& newOffset)
2899 {
2900     LayoutSize offset = scrollOffset();
2901     ScrollView::scrollTo(newOffset);
2902     if (offset != scrollOffset())
2903         scrollPositionChanged();
2904     frame()->loader()->client()->didChangeScrollOffset();
2905 }
2906
2907 void FrameView::invalidateScrollbarRect(Scrollbar* scrollbar, const IntRect& rect)
2908 {
2909     // Add in our offset within the FrameView.
2910     IntRect dirtyRect = rect;
2911     dirtyRect.moveBy(scrollbar->location());
2912     invalidateRect(dirtyRect);
2913 }
2914
2915 void FrameView::getTickmarks(Vector<IntRect>& tickmarks) const
2916 {
2917     tickmarks = frame()->document()->markers()->renderedRectsForMarkers(DocumentMarker::TextMatch);
2918 }
2919
2920 IntRect FrameView::windowResizerRect() const
2921 {
2922     Page* page = frame() ? frame()->page() : 0;
2923     if (!page)
2924         return IntRect();
2925     return page->chrome()->windowResizerRect();
2926 }
2927
2928 float FrameView::visibleContentScaleFactor() const
2929 {
2930     if (!m_frame || !m_frame->page())
2931         return 1;
2932
2933     if (!m_frame->settings()->applyPageScaleFactorInCompositor() || m_frame != m_frame->page()->mainFrame())
2934         return 1;
2935
2936     return m_frame->page()->pageScaleFactor();
2937 }
2938
2939 void FrameView::setVisibleScrollerThumbRect(const IntRect& scrollerThumb)
2940 {
2941     Page* page = m_frame->page();
2942     if (!page)
2943         return;
2944     if (page->mainFrame() != m_frame)
2945         return;
2946     page->chrome()->client()->notifyScrollerThumbIsVisibleInRect(scrollerThumb);
2947 }
2948
2949 bool FrameView::scrollbarsCanBeActive() const
2950 {
2951     if (!m_frame)
2952         return false;
2953
2954     if (m_frame->view() != this)
2955         return false;
2956
2957     if (Page* page = m_frame->page()) {
2958         if (page->shouldSuppressScrollbarAnimations())
2959             return false;
2960     }
2961
2962     if (Document* document = m_frame->document())
2963         return !document->inPageCache();
2964
2965     return false;
2966 }
2967
2968 ScrollableArea* FrameView::enclosingScrollableArea() const
2969 {
2970     // FIXME: Walk up the frame tree and look for a scrollable parent frame or RenderLayer.
2971     return 0;
2972 }
2973
2974 IntRect FrameView::scrollableAreaBoundingBox() const
2975 {
2976     RenderPart* ownerRenderer = frame()->ownerRenderer();
2977     if (!ownerRenderer)
2978         return frameRect();
2979
2980     return ownerRenderer->absoluteContentQuad().enclosingBoundingBox();
2981 }
2982
2983 bool FrameView::isScrollable()
2984 {
2985     // Check for:
2986     // 1) If there an actual overflow.
2987     // 2) display:none or visibility:hidden set to self or inherited.
2988     // 3) overflow{-x,-y}: hidden;
2989     // 4) scrolling: no;
2990
2991     // Covers #1
2992     IntSize contentSize = contentsSize();
2993     IntSize visibleContentSize = visibleContentRect().size();
2994     if ((contentSize.height() <= visibleContentSize.height() && contentSize.width() <= visibleContentSize.width()))
2995         return false;
2996
2997     // Covers #2.
2998     HTMLFrameOwnerElement* owner = m_frame->ownerElement();
2999     if (owner && (!owner->renderer() || !owner->renderer()->visibleToHitTesting()))
3000         return false;
3001
3002     // Cover #3 and #4.
3003     ScrollbarMode horizontalMode;
3004     ScrollbarMode verticalMode;
3005     calculateScrollbarModesForLayout(horizontalMode, verticalMode, RulesFromWebContentOnly);
3006     if (horizontalMode == ScrollbarAlwaysOff && verticalMode == ScrollbarAlwaysOff)
3007         return false;
3008
3009     return true;
3010 }
3011
3012 void FrameView::updateScrollableAreaSet()
3013 {
3014     // That ensures that only inner frames are cached.
3015     FrameView* parentFrameView = this->parentFrameView();
3016     if (!parentFrameView)
3017         return;
3018
3019     if (!isScrollable()) {
3020         parentFrameView->removeScrollableArea(this);
3021         return;
3022     }
3023
3024     parentFrameView->addScrollableArea(this);
3025 }
3026
3027 bool FrameView::shouldSuspendScrollAnimations() const
3028 {
3029     return m_frame->loader()->state() != FrameStateComplete;
3030 }
3031
3032 void FrameView::scrollbarStyleChanged(int newStyle, bool forceUpdate)
3033 {
3034     Page* page = m_frame->page();
3035     if (!page)
3036         return;
3037     if (page->mainFrame() != m_frame)
3038         return;
3039     page->chrome()->client()->recommendedScrollbarStyleDidChange(newStyle);
3040
3041     if (forceUpdate)
3042         ScrollView::scrollbarStyleChanged(newStyle, forceUpdate);
3043 }
3044
3045 void FrameView::setAnimatorsAreActive()
3046 {
3047     Page* page = m_frame->page();
3048     if (!page)
3049         return;
3050
3051     if (ScrollAnimator* scrollAnimator = existingScrollAnimator())
3052         scrollAnimator->setIsActive();
3053
3054     if (!m_scrollableAreas)
3055         return;
3056
3057     for (HashSet<ScrollableArea*>::const_iterator it = m_scrollableAreas->begin(), end = m_scrollableAreas->end(); it != end; ++it) {
3058         ScrollableArea* scrollableArea = *it;
3059
3060         ASSERT(scrollableArea->scrollbarsCanBeActive());
3061         scrollableArea->scrollAnimator()->setIsActive();
3062     }
3063 }
3064
3065 void FrameView::notifyPageThatContentAreaWillPaint() const
3066 {
3067     Page* page = m_frame->page();
3068     if (!page)
3069         return;
3070
3071     contentAreaWillPaint();
3072
3073     if (!m_scrollableAreas)
3074         return;
3075
3076     for (HashSet<ScrollableArea*>::const_iterator it = m_scrollableAreas->begin(), end = m_scrollableAreas->end(); it != end; ++it) {
3077         ScrollableArea* scrollableArea = *it;
3078
3079         if (!scrollableArea->scrollbarsCanBeActive())
3080             continue;
3081
3082         scrollableArea->contentAreaWillPaint();
3083     }
3084 }
3085
3086 bool FrameView::scrollAnimatorEnabled() const
3087 {
3088 #if ENABLE(SMOOTH_SCROLLING)
3089     if (Page* page = m_frame->page())
3090         return page->settings()->scrollAnimatorEnabled();
3091 #endif
3092
3093     return false;
3094 }
3095
3096 #if ENABLE(DASHBOARD_SUPPORT) || ENABLE(DRAGGABLE_REGION)
3097 void FrameView::updateAnnotatedRegions()
3098 {
3099     Document* document = m_frame->document();
3100     if (!document->hasAnnotatedRegions())
3101         return;
3102     Vector<AnnotatedRegionValue> newRegions;
3103     document->renderBox()->collectAnnotatedRegions(newRegions);
3104     if (newRegions == document->annotatedRegions())
3105         return;
3106     document->setAnnotatedRegions(newRegions);
3107     Page* page = m_frame->page();
3108     if (!page)
3109         return;
3110     page->chrome()->client()->annotatedRegionsChanged();
3111 }
3112 #endif
3113
3114 void FrameView::updateScrollCorner()
3115 {
3116     RenderObject* renderer = 0;
3117     RefPtr<RenderStyle> cornerStyle;
3118     IntRect cornerRect = scrollCornerRect();
3119     
3120     if (!cornerRect.isEmpty()) {
3121         // Try the <body> element first as a scroll corner source.
3122         Document* doc = m_frame->document();
3123         Element* body = doc ? doc->body() : 0;
3124         if (body && body->renderer()) {
3125             renderer = body->renderer();
3126             cornerStyle = renderer->getUncachedPseudoStyle(PseudoStyleRequest(SCROLLBAR_CORNER), renderer->style());
3127         }
3128         
3129         if (!cornerStyle) {
3130             // If the <body> didn't have a custom style, then the root element might.
3131             Element* docElement = doc ? doc->documentElement() : 0;
3132             if (docElement && docElement->renderer()) {
3133                 renderer = docElement->renderer();
3134                 cornerStyle = renderer->getUncachedPseudoStyle(PseudoStyleRequest(SCROLLBAR_CORNER), renderer->style());
3135             }
3136         }
3137         
3138         if (!cornerStyle) {
3139             // If we have an owning iframe/frame element, then it can set the custom scrollbar also.
3140             if (RenderPart* renderer = m_frame->ownerRenderer())
3141                 cornerStyle = renderer->getUncachedPseudoStyle(PseudoStyleRequest(SCROLLBAR_CORNER), renderer->style());
3142         }
3143     }
3144
3145     if (cornerStyle) {
3146         if (!m_scrollCorner)
3147             m_scrollCorner = RenderScrollbarPart::createAnonymous(renderer->document());
3148         m_scrollCorner->setStyle(cornerStyle.release());
3149         invalidateScrollCorner(cornerRect);
3150     } else if (m_scrollCorner) {
3151         m_scrollCorner->destroy();
3152         m_scrollCorner = 0;
3153     }
3154
3155     ScrollView::updateScrollCorner();
3156 }
3157
3158 void FrameView::paintScrollCorner(GraphicsContext* context, const IntRect& cornerRect)
3159 {
3160     if (context->updatingControlTints()) {
3161         updateScrollCorner();
3162         return;
3163     }
3164
3165     if (m_scrollCorner) {
3166         bool needsBackgorund = m_frame->page() && m_frame->page()->mainFrame() == m_frame;
3167         if (needsBackgorund)
3168             context->fillRect(cornerRect, baseBackgroundColor(), ColorSpaceDeviceRGB);
3169         m_scrollCorner->paintIntoRect(context, cornerRect.location(), cornerRect);
3170         return;
3171     }
3172
3173     ScrollView::paintScrollCorner(context, cornerRect);
3174 }
3175
3176 void FrameView::paintScrollbar(GraphicsContext* context, Scrollbar* bar, const IntRect& rect)
3177 {
3178     bool needsBackgorund = bar->isCustomScrollbar() && (m_frame->page() && m_frame->page()->mainFrame() == m_frame);
3179     if (needsBackgorund) {
3180         IntRect toFill = bar->frameRect();
3181         toFill.intersect(rect);
3182         context->fillRect(toFill, baseBackgroundColor(), ColorSpaceDeviceRGB);
3183     }
3184
3185     ScrollView::paintScrollbar(context, bar, rect);
3186 }
3187
3188 Color FrameView::documentBackgroundColor() const
3189 {
3190     // <https://bugs.webkit.org/show_bug.cgi?id=59540> We blend the background color of
3191     // the document and the body against the base background color of the frame view.
3192     // Background images are unfortunately impractical to include.
3193
3194     // Return invalid Color objects whenever there is insufficient information.
3195     if (!frame()->document())
3196         return Color();
3197
3198     Element* htmlElement = frame()->document()->documentElement();
3199     Element* bodyElement = frame()->document()->body();
3200
3201     // Start with invalid colors.
3202     Color htmlBackgroundColor;
3203     Color bodyBackgroundColor;
3204     if (htmlElement && htmlElement->renderer())
3205         htmlBackgroundColor = htmlElement->renderer()->style()->visitedDependentColor(CSSPropertyBackgroundColor);
3206     if (bodyElement && bodyElement->renderer())
3207         bodyBackgroundColor = bodyElement->renderer()->style()->visitedDependentColor(CSSPropertyBackgroundColor);
3208
3209     if (!bodyBackgroundColor.isValid()) {
3210         if (!htmlBackgroundColor.isValid())
3211             return Color();
3212         return baseBackgroundColor().blend(htmlBackgroundColor);
3213     }
3214
3215     if (!htmlBackgroundColor.isValid())
3216         return baseBackgroundColor().blend(bodyBackgroundColor);
3217
3218     // We take the aggregate of the base background color
3219     // the <html> background color, and the <body>
3220     // background color to find the document color. The
3221     // addition of the base background color is not
3222     // technically part of the document background, but it
3223     // otherwise poses problems when the aggregate is not
3224     // fully opaque.
3225     return baseBackgroundColor().blend(htmlBackgroundColor).blend(bodyBackgroundColor);
3226 }
3227
3228 bool FrameView::hasCustomScrollbars() const
3229 {
3230     const HashSet<RefPtr<Widget> >* viewChildren = children();
3231     HashSet<RefPtr<Widget> >::const_iterator end = viewChildren->end();
3232     for (HashSet<RefPtr<Widget> >::const_iterator current = viewChildren->begin(); current != end; ++current) {
3233         Widget* widget = current->get();
3234         if (widget->isFrameView()) {
3235             if (toFrameView(widget)->hasCustomScrollbars())
3236                 return true;
3237         } else if (widget->isScrollbar()) {
3238             Scrollbar* scrollbar = static_cast<Scrollbar*>(widget);
3239             if (scrollbar->isCustomScrollbar())
3240                 return true;
3241         }
3242     }
3243
3244     return false;
3245 }
3246
3247 FrameView* FrameView::parentFrameView() const
3248 {
3249     if (!parent())
3250         return 0;
3251
3252     if (Frame* parentFrame = m_frame->tree()->parent())
3253         return parentFrame->view();
3254
3255     return 0;
3256 }
3257
3258 bool FrameView::isInChildFrameWithFrameFlattening() const
3259 {
3260     if (!parent() || !m_frame->ownerElement())
3261         return false;
3262
3263     // Frame flattening applies when the owner element is either in a frameset or
3264     // an iframe with flattening parameters.
3265     if (m_frame->ownerElement()->hasTagName(iframeTag)) {
3266         RenderIFrame* iframeRenderer = toRenderIFrame(m_frame->ownerElement()->renderPart());
3267         if (iframeRenderer->flattenFrame() || iframeRenderer->isSeamless())
3268             return true;
3269     }
3270
3271     if (!m_frame->settings() || !m_frame->settings()->frameFlatteningEnabled())
3272         return false;
3273
3274     if (m_frame->ownerElement()->hasTagName(frameTag))
3275         return true;
3276
3277     return false;
3278 }
3279
3280 bool FrameView::doLayoutWithFrameFlattening(bool allowSubtree)
3281 {
3282     // Try initiating layout from the topmost parent.
3283     FrameView* parentView = parentFrameView();
3284
3285     if (!parentView)
3286         return false;
3287
3288     // In the middle of parent layout, no need to restart from topmost.
3289     if (parentView->m_nestedLayoutCount)
3290         return false;
3291
3292     // Parent tree is clean. Starting layout from it would have no effect.
3293     if (!parentView->needsLayout())
3294         return false;
3295
3296     while (parentView->parentFrameView())
3297         parentView = parentView->parentFrameView();
3298
3299     parentView->layout(allowSubtree);
3300
3301     RenderObject* root = m_layoutRoot ? m_layoutRoot : m_frame->document()->renderer();
3302     ASSERT_UNUSED(root, !root->needsLayout());
3303
3304     return true;
3305 }
3306
3307 void FrameView::updateControlTints()
3308 {
3309     // This is called when control tints are changed from aqua/graphite to clear and vice versa.
3310     // We do a "fake" paint, and when the theme gets a paint call, it can then do an invalidate.
3311     // This is only done if the theme supports control tinting. It's up to the theme and platform
3312     // to define when controls get the tint and to call this function when that changes.
3313     
3314     // Optimize the common case where we bring a window to the front while it's still empty.
3315     if (!m_frame || m_frame->document()->url().isEmpty())
3316         return;
3317
3318     RenderView* renderView = this->renderView();
3319     if ((renderView && renderView->theme()->supportsControlTints()) || hasCustomScrollbars())
3320         paintControlTints();
3321 }
3322
3323 void FrameView::paintControlTints()
3324 {
3325     if (needsLayout())
3326         layout();
3327     PlatformGraphicsContext* const noContext = 0;
3328     GraphicsContext context(noContext);
3329     context.setUpdatingControlTints(true);
3330     if (platformWidget())
3331         paintContents(&context, visibleContentRect());
3332     else
3333         paint(&context, frameRect());
3334 }
3335
3336 bool FrameView::wasScrolledByUser() const
3337 {
3338     return m_wasScrolledByUser;
3339 }
3340
3341 void FrameView::setWasScrolledByUser(bool wasScrolledByUser)
3342 {
3343     if (m_inProgrammaticScroll)
3344         return;
3345     m_maintainScrollPositionAnchor = 0;
3346     m_wasScrolledByUser = wasScrolledByUser;
3347 }
3348
3349 void FrameView::paintContents(GraphicsContext* p, const IntRect& rect)
3350 {
3351     if (!frame())
3352         return;
3353
3354     InspectorInstrumentation::willPaint(m_frame.get());
3355
3356     Document* document = m_frame->document();
3357
3358 #ifndef NDEBUG
3359     bool fillWithRed;
3360     if (document->printing())
3361         fillWithRed = false; // Printing, don't fill with red (can't remember why).
3362     else if (m_frame->ownerElement())
3363         fillWithRed = false; // Subframe, don't fill with red.
3364     else if (isTransparent())
3365         fillWithRed = false; // Transparent, don't fill with red.
3366     else if (m_paintBehavior & PaintBehaviorSelectionOnly)
3367         fillWithRed = false; // Selections are transparent, don't fill with red.
3368     else if (m_nodeToDraw)
3369         fillWithRed = false; // Element images are transparent, don't fill with red.
3370     else
3371         fillWithRed = true;
3372     
3373     if (fillWithRed)
3374         p->fillRect(rect, Color(0xFF, 0, 0), ColorSpaceDeviceRGB);
3375 #endif
3376
3377     RenderView* renderView = this->renderView();
3378     if (!renderView) {
3379         LOG_ERROR("called FrameView::paint with nil renderer");
3380         return;
3381     }
3382
3383     ASSERT(!needsLayout());
3384     if (needsLayout())
3385         return;
3386
3387     bool isTopLevelPainter = !sCurrentPaintTimeStamp;
3388     if (isTopLevelPainter)
3389         sCurrentPaintTimeStamp = currentTime();
3390
3391     FontCachePurgePreventer fontCachePurgePreventer;
3392
3393 #if USE(ACCELERATED_COMPOSITING)
3394     if (!p->paintingDisabled() && !document->printing())
3395         flushCompositingStateForThisFrame(m_frame.get());
3396 #endif
3397
3398     PaintBehavior oldPaintBehavior = m_paintBehavior;
3399     
3400     if (FrameView* parentView = parentFrameView()) {
3401         if (parentView->paintBehavior() & PaintBehaviorFlattenCompositingLayers)
3402             m_paintBehavior |= PaintBehaviorFlattenCompositingLayers;
3403     }
3404     
3405     if (m_paintBehavior == PaintBehaviorNormal)
3406         document->markers()->invalidateRenderedRectsForMarkersInRect(rect);
3407
3408     if (document->printing())
3409         m_paintBehavior |= PaintBehaviorFlattenCompositingLayers;
3410
3411     bool flatteningPaint = m_paintBehavior & PaintBehaviorFlattenCompositingLayers;
3412     bool isRootFrame = !m_frame->ownerElement();
3413     if (flatteningPaint && isRootFrame)
3414         notifyWidgetsInAllFrames(WillPaintFlattened);
3415
3416     ASSERT(!m_isPainting);
3417     m_isPainting = true;
3418
3419     // m_nodeToDraw is used to draw only one element (and its descendants)
3420     RenderObject* eltRenderer = m_nodeToDraw ? m_nodeToDraw->renderer() : 0;
3421     RenderLayer* rootLayer = renderView->layer();
3422
3423 #ifndef NDEBUG
3424     RenderObject::SetLayoutNeededForbiddenScope forbidSetNeedsLayout(rootLayer->renderer());
3425 #endif
3426
3427     rootLayer->paint(p, rect, m_paintBehavior, eltRenderer);
3428
3429     if (rootLayer->containsDirtyOverlayScrollbars())
3430         rootLayer->paintOverlayScrollbars(p, rect, m_paintBehavior, eltRenderer);
3431
3432     m_isPainting = false;
3433
3434     if (flatteningPaint && isRootFrame)
3435         notifyWidgetsInAllFrames(DidPaintFlattened);
3436
3437     m_paintBehavior = oldPaintBehavior;
3438     m_lastPaintTime = currentTime();
3439
3440     // Regions may have changed as a result of the visibility/z-index of element changing.
3441 #if ENABLE(DASHBOARD_SUPPORT) || ENABLE(DRAGGABLE_REGION)
3442     if (document->annotatedRegionsDirty())
3443         updateAnnotatedRegions();
3444 #endif
3445
3446     if (isTopLevelPainter)
3447         sCurrentPaintTimeStamp = 0;
3448
3449     InspectorInstrumentation::didPaint(m_frame.get(), p, rect);
3450 }
3451
3452 void FrameView::setPaintBehavior(PaintBehavior behavior)
3453 {
3454     m_paintBehavior = behavior;
3455 }
3456
3457 PaintBehavior FrameView::paintBehavior() const
3458 {
3459     return m_paintBehavior;
3460 }
3461
3462 bool FrameView::isPainting() const
3463 {
3464     return m_isPainting;
3465 }
3466
3467 void FrameView::setNodeToDraw(Node* node)
3468 {
3469     m_nodeToDraw = node;
3470 }
3471
3472 void FrameView::paintContentsForSnapshot(GraphicsContext* context, const IntRect& imageRect, SelectionInSnaphot shouldPaintSelection, CoordinateSpaceForSnapshot coordinateSpace)
3473 {
3474     updateLayoutAndStyleIfNeededRecursive();
3475
3476     // Cache paint behavior and set a new behavior appropriate for snapshots.
3477     PaintBehavior oldBehavior = paintBehavior();
3478     setPaintBehavior(oldBehavior | PaintBehaviorFlattenCompositingLayers);
3479
3480     // If the snapshot should exclude selection, then we'll clear the current selection
3481     // in the render tree only. This will allow us to restore the selection from the DOM
3482     // after we paint the snapshot.
3483     if (shouldPaintSelection == ExcludeSelection) {
3484         for (Frame* frame = m_frame.get(); frame; frame = frame->tree()->traverseNext(m_frame.get())) {
3485             if (RenderView* root = frame->contentRenderer())
3486                 root->clearSelection();
3487         }
3488     }
3489
3490     if (coordinateSpace == DocumentCoordinates)
3491         paintContents(context, imageRect);
3492     else {
3493         // A snapshot in ViewCoordinates will include a scrollbar, and the snapshot will contain
3494         // whatever content the document is currently scrolled to.
3495         paint(context, imageRect);
3496     }
3497
3498     // Restore selection.
3499     if (shouldPaintSelection == ExcludeSelection) {
3500         for (Frame* frame = m_frame.get(); frame; frame = frame->tree()->traverseNext(m_frame.get()))
3501             frame->selection()->updateAppearance();
3502     }
3503
3504     // Restore cached paint behavior.
3505     setPaintBehavior(oldBehavior);
3506 }
3507
3508 void FrameView::paintOverhangAreas(GraphicsContext* context, const IntRect& horizontalOverhangArea, const IntRect& verticalOverhangArea, const IntRect& dirtyRect)
3509 {
3510     if (context->paintingDisabled())
3511         return;
3512
3513     if (m_frame->document()->printing())
3514         return;
3515
3516     Page* page = m_frame->page();
3517     if (page->mainFrame() == m_frame) {
3518         if (page->chrome()->client()->paintCustomOverhangArea(context, horizontalOverhangArea, verticalOverhangArea, dirtyRect))
3519             return;
3520     }
3521
3522     ScrollView::paintOverhangAreas(context, horizontalOverhangArea, verticalOverhangArea, dirtyRect);
3523 }
3524
3525 void FrameView::updateLayoutAndStyleIfNeededRecursive()
3526 {
3527     // We have to crawl our entire tree looking for any FrameViews that need
3528     // layout and make sure they are up to date.
3529     // Mac actually tests for intersection with the dirty region and tries not to
3530     // update layout for frames that are outside the dirty region.  Not only does this seem
3531     // pointless (since those frames will have set a zero timer to layout anyway), but
3532     // it is also incorrect, since if two frames overlap, the first could be excluded from the dirty
3533     // region but then become included later by the second frame adding rects to the dirty region
3534     // when it lays out.
3535
3536     m_frame->document()->updateStyleIfNeeded();
3537
3538     if (needsLayout())
3539         layout();
3540
3541     // Grab a copy of the children() set, as it may be mutated by the following updateLayoutAndStyleIfNeededRecursive
3542     // calls, as they can potentially re-enter a layout of the parent frame view, which may add/remove scrollbars
3543     // and thus mutates the children() set.
3544     Vector<RefPtr<FrameView> > frameViews;
3545     collectFrameViewChildren(this, frameViews);
3546
3547     const Vector<RefPtr<FrameView> >::iterator end = frameViews.end();
3548     for (Vector<RefPtr<FrameView> >::iterator it = frameViews.begin(); it != end; ++it)
3549         (*it)->updateLayoutAndStyleIfNeededRecursive();
3550
3551     // updateLayoutAndStyleIfNeededRecursive is called when we need to make sure style and layout are up-to-date before
3552     // painting, so we need to flush out any deferred repaints too.
3553     flushDeferredRepaints();
3554
3555     // When frame flattening is on, child frame can mark parent frame dirty. In such case, child frame
3556     // needs to call layout on parent frame recursively.
3557     // This assert ensures that parent frames are clean, when child frames finished updating layout and style.
3558     ASSERT(!needsLayout());
3559 }
3560
3561 void FrameView::enableAutoSizeMode(bool enable, const IntSize& minSize, const IntSize& maxSize)
3562 {
3563     ASSERT(!enable || !minSize.isEmpty());
3564     ASSERT(minSize.width() <= maxSize.width());
3565     ASSERT(minSize.height() <= maxSize.height());
3566
3567     if (m_shouldAutoSize == enable && m_minAutoSize == minSize && m_maxAutoSize == maxSize)
3568         return;
3569
3570     m_shouldAutoSize = enable;
3571     m_minAutoSize = minSize;
3572     m_maxAutoSize = maxSize;
3573     m_didRunAutosize = false;
3574
3575     setNeedsLayout();
3576     scheduleRelayout();
3577     if (m_shouldAutoSize)
3578         return;
3579
3580     // Since autosize mode forces the scrollbar mode, change them to being auto.
3581     setVerticalScrollbarLock(false);
3582     setHorizontalScrollbarLock(false);
3583     setScrollbarModes(ScrollbarAuto, ScrollbarAuto);
3584 }
3585
3586 void FrameView::forceLayout(bool allowSubtree)
3587 {
3588     layout(allowSubtree);
3589 }
3590
3591 void FrameView::forceLayoutForPagination(const FloatSize& pageSize, const FloatSize& originalPageSize, float maximumShrinkFactor, AdjustViewSizeOrNot shouldAdjustViewSize)
3592 {
3593     // Dumping externalRepresentation(m_frame->renderer()).ascii() is a good trick to see
3594     // the state of things before and after the layout
3595     if (RenderView* renderView = this->renderView()) {
3596         float pageLogicalWidth = renderView->style()->isHorizontalWritingMode() ? pageSize.width() : pageSize.height();
3597         float pageLogicalHeight = renderView->style()->isHorizontalWritingMode() ? pageSize.height() : pageSize.width();
3598
3599         LayoutUnit flooredPageLogicalWidth = static_cast<LayoutUnit>(pageLogicalWidth);
3600         LayoutUnit flooredPageLogicalHeight = static_cast<LayoutUnit>(pageLogicalHeight);
3601         renderView->setLogicalWidth(flooredPageLogicalWidth);
3602         renderView->setPageLogicalHeight(flooredPageLogicalHeight);
3603         renderView->setNeedsLayoutAndPrefWidthsRecalc();
3604         forceLayout();
3605
3606         // If we don't fit in the given page width, we'll lay out again. If we don't fit in the
3607         // page width when shrunk, we will lay out at maximum shrink and clip extra content.
3608         // FIXME: We are assuming a shrink-to-fit printing implementation.  A cropping
3609         // implementation should not do this!
3610         bool horizontalWritingMode = renderView->style()->isHorizontalWritingMode();
3611         const LayoutRect& documentRect = renderView->documentRect();
3612         LayoutUnit docLogicalWidth = horizontalWritingMode ? documentRect.width() : documentRect.height();
3613         if (docLogicalWidth > pageLogicalWidth) {
3614             int expectedPageWidth = std::min<float>(documentRect.width(), pageSize.width() * maximumShrinkFactor);
3615             int expectedPageHeight = std::min<float>(documentRect.height(), pageSize.height() * maximumShrinkFactor);
3616             FloatSize maxPageSize = m_frame->resizePageRectsKeepingRatio(FloatSize(originalPageSize.width(), originalPageSize.height()), FloatSize(expectedPageWidth, expectedPageHeight));
3617             pageLogicalWidth = horizontalWritingMode ? maxPageSize.width() : maxPageSize.height();
3618             pageLogicalHeight = horizontalWritingMode ? maxPageSize.height() : maxPageSize.width();
3619
3620             flooredPageLogicalWidth = static_cast<LayoutUnit>(pageLogicalWidth);
3621             flooredPageLogicalHeight = static_cast<LayoutUnit>(pageLogicalHeight);
3622             renderView->setLogicalWidth(flooredPageLogicalWidth);
3623             renderView->setPageLogicalHeight(flooredPageLogicalHeight);
3624             renderView->setNeedsLayoutAndPrefWidthsRecalc();
3625             forceLayout();
3626
3627             const LayoutRect& updatedDocumentRect = renderView->documentRect();
3628             LayoutUnit docLogicalHeight = horizontalWritingMode ? updatedDocumentRect.height() : updatedDocumentRect.width();
3629             LayoutUnit docLogicalTop = horizontalWritingMode ? updatedDocumentRect.y() : updatedDocumentRect.x();
3630             LayoutUnit docLogicalRight = horizontalWritingMode ? updatedDocumentRect.maxX() : updatedDocumentRect.maxY();
3631             LayoutUnit clippedLogicalLeft = 0;
3632             if (!renderView->style()->isLeftToRightDirection())
3633                 clippedLogicalLeft = docLogicalRight - pageLogicalWidth;
3634             LayoutRect overflow(clippedLogicalLeft, docLogicalTop, pageLogicalWidth, docLogicalHeight);
3635
3636             if (!horizontalWritingMode)
3637                 overflow = overflow.transposedRect();
3638             renderView->clearLayoutOverflow();
3639             renderView->addLayoutOverflow(overflow); // This is how we clip in case we overflow again.
3640         }
3641     }
3642
3643     if (shouldAdjustViewSize)
3644         adjustViewSize();
3645 }
3646
3647 void FrameView::adjustPageHeightDeprecated(float *newBottom, float oldTop, float oldBottom, float /*bottomLimit*/)
3648 {
3649     RenderView* renderView = this->renderView();
3650     if (!renderView) {
3651         *newBottom = oldBottom;
3652         return;
3653
3654     }
3655     // Use a context with painting disabled.
3656     GraphicsContext context((PlatformGraphicsContext*)0);
3657     renderView->setTruncatedAt(static_cast<int>(floorf(oldBottom)));
3658     IntRect dirtyRect(0, static_cast<int>(floorf(oldTop)), renderView->layoutOverflowRect().maxX(), static_cast<int>(ceilf(oldBottom - oldTop)));
3659     renderView->setPrintRect(dirtyRect);
3660     renderView->layer()->paint(&context, dirtyRect);
3661     *newBottom = renderView->bestTruncatedAt();
3662     if (!*newBottom)
3663         *newBottom = oldBottom;
3664     renderView->setPrintRect(IntRect());
3665 }
3666
3667 IntRect FrameView::convertFromRenderer(const RenderObject* renderer, const IntRect& rendererRect) const
3668 {
3669     IntRect rect = pixelSnappedIntRect(enclosingLayoutRect(renderer->localToAbsoluteQuad(FloatRect(rendererRect)).boundingBox()));
3670
3671     // Convert from page ("absolute") to FrameView coordinates.
3672     if (!delegatesScrolling())
3673         rect.moveBy(-scrollPosition());
3674
3675     return rect;
3676 }
3677
3678 IntRect FrameView::convertToRenderer(const RenderObject* renderer, const IntRect& viewRect) const
3679 {
3680     IntRect rect = viewRect;
3681     
3682     // Convert from FrameView coords into page ("absolute") coordinates.
3683     if (!delegatesScrolling())
3684         rect.moveBy(scrollPosition());
3685
3686     // FIXME: we don't have a way to map an absolute rect down to a local quad, so just
3687     // move the rect for now.
3688     rect.setLocation(roundedIntPoint(renderer->absoluteToLocal(rect.location(), UseTransforms)));
3689     return rect;
3690 }
3691
3692 IntPoint FrameView::convertFromRenderer(const RenderObject* renderer, const IntPoint& rendererPoint) const
3693 {
3694     IntPoint point = roundedIntPoint(renderer->localToAbsolute(rendererPoint, UseTransforms));
3695
3696     // Convert from page ("absolute") to FrameView coordinates.
3697     if (!delegatesScrolling())
3698         point.moveBy(-scrollPosition());
3699     return point;
3700 }
3701
3702 IntPoint FrameView::convertToRenderer(const RenderObject* renderer, const IntPoint& viewPoint) const
3703 {
3704     IntPoint point = viewPoint;
3705
3706     // Convert from FrameView coords into page ("absolute") coordinates.
3707     if (!delegatesScrolling())
3708         point += IntSize(scrollX(), scrollY());
3709
3710     return roundedIntPoint(renderer->absoluteToLocal(point, UseTransforms));
3711 }
3712
3713 IntRect FrameView::convertToContainingView(const IntRect& localRect) const
3714 {
3715     if (const ScrollView* parentScrollView = parent()) {
3716         if (parentScrollView->isFrameView()) {
3717             const FrameView* parentView = toFrameView(parentScrollView);
3718             // Get our renderer in the parent view
3719             RenderPart* renderer = m_frame->ownerRenderer();
3720             if (!renderer)
3721                 return localRect;
3722                 
3723             IntRect rect(localRect);
3724             // Add borders and padding??
3725             rect.move(renderer->borderLeft() + renderer->paddingLeft(),
3726                       renderer->borderTop() + renderer->paddingTop());
3727             return parentView->convertFromRenderer(renderer, rect);
3728         }
3729         
3730         return Widget::convertToContainingView(localRect);
3731     }
3732     
3733     return localRect;
3734 }
3735
3736 IntRect FrameView::convertFromContainingView(const IntRect& parentRect) const
3737 {
3738     if (const ScrollView* parentScrollView = parent()) {
3739         if (parentScrollView->isFrameView()) {
3740             const FrameView* parentView = toFrameView(parentScrollView);
3741
3742             // Get our renderer in the parent view
3743             RenderPart* renderer = m_frame->ownerRenderer();
3744             if (!renderer)
3745                 return parentRect;
3746
3747             IntRect rect = parentView->convertToRenderer(renderer, parentRect);
3748             // Subtract borders and padding
3749             rect.move(-renderer->borderLeft() - renderer->paddingLeft(),
3750                       -renderer->borderTop() - renderer->paddingTop());
3751             return rect;
3752         }
3753         
3754         return Widget::convertFromContainingView(parentRect);
3755     }
3756     
3757     return parentRect;
3758 }
3759
3760 IntPoint FrameView::convertToContainingView(const IntPoint& localPoint) const
3761 {
3762     if (const ScrollView* parentScrollView = parent()) {
3763         if (parentScrollView->isFrameView()) {
3764             const FrameView* parentView = toFrameView(parentScrollView);
3765
3766             // Get our renderer in the parent view
3767             RenderPart* renderer = m_frame->ownerRenderer();
3768             if (!renderer)
3769                 return localPoint;
3770                 
3771             IntPoint point(localPoint);
3772
3773             // Add borders and padding
3774             point.move(renderer->borderLeft() + renderer->paddingLeft(),
3775                        renderer->borderTop() + renderer->paddingTop());
3776             return parentView->convertFromRenderer(renderer, point);
3777         }
3778         
3779         return Widget::convertToContainingView(localPoint);
3780     }
3781     
3782     return localPoint;
3783 }
3784
3785 IntPoint FrameView::convertFromContainingView(const IntPoint& parentPoint) const
3786 {
3787     if (const ScrollView* parentScrollView = parent()) {
3788         if (parentScrollView->isFrameView()) {
3789             const FrameView* parentView = toFrameView(parentScrollView);
3790
3791             // Get our renderer in the parent view
3792             RenderPart* renderer = m_frame->ownerRenderer();
3793             if (!renderer)
3794                 return parentPoint;
3795
3796             IntPoint point = parentView->convertToRenderer(renderer, parentPoint);
3797             // Subtract borders and padding
3798             point.move(-renderer->borderLeft() - renderer->paddingLeft(),
3799                        -renderer->borderTop() - renderer->paddingTop());
3800             return point;
3801         }
3802         
3803         return Widget::convertFromContainingView(parentPoint);
3804     }
3805     
3806     return parentPoint;
3807 }
3808
3809 // Normal delay
3810 void FrameView::setRepaintThrottlingDeferredRepaintDelay(double p)
3811 {
3812     s_normalDeferredRepaintDelay = p;
3813 }
3814
3815 // Negative value would mean that first few repaints happen without a delay
3816 void FrameView::setRepaintThrottlingnInitialDeferredRepaintDelayDuringLoading(double p)
3817 {
3818     s_initialDeferredRepaintDelayDuringLoading = p;
3819 }
3820
3821 // The delay grows on each repaint to this maximum value
3822 void FrameView::setRepaintThrottlingMaxDeferredRepaintDelayDuringLoading(double p)
3823 {
3824     s_maxDeferredRepaintDelayDuringLoading = p;
3825 }
3826
3827 // On each repaint the delay increases by this amount
3828 void FrameView::setRepaintThrottlingDeferredRepaintDelayIncrementDuringLoading(double p)
3829 {
3830     s_deferredRepaintDelayIncrementDuringLoading = p;
3831 }
3832
3833 void FrameView::setTracksRepaints(bool trackRepaints)
3834 {
3835     if (trackRepaints == m_isTrackingRepaints)
3836         return;
3837
3838 #if USE(ACCELERATED_COMPOSITING)
3839     for (Frame* frame = m_frame->tree()->top(); frame; frame = frame->tree()->traverseNext()) {
3840         if (RenderView* renderView = frame->contentRenderer())
3841             renderView->compositor()->setTracksRepaints(trackRepaints);
3842     }
3843 #endif
3844
3845     resetTrackedRepaints();
3846     m_isTrackingRepaints = trackRepaints;
3847 }
3848
3849 void FrameView::resetTrackedRepaints()
3850 {
3851     m_trackedRepaintRects.clear();
3852 #if USE(ACCELERATED_COMPOSITING)
3853     if (RenderView* renderView = this->renderView())
3854         renderView->compositor()->resetTrackedRepaintRects();
3855 #endif
3856 }
3857
3858 String FrameView::trackedRepaintRectsAsText() const
3859 {
3860     TextStream ts;
3861     if (!m_trackedRepaintRects.isEmpty()) {
3862         ts << "(repaint rects\n";
3863         for (size_t i = 0; i < m_trackedRepaintRects.size(); ++i)
3864             ts << "  (rect " << m_trackedRepaintRects[i].x() << " " << m_trackedRepaintRects[i].y() << " " << m_trackedRepaintRects[i].width() << " " << m_trackedRepaintRects[i].height() << ")\n";
3865         ts << ")\n";
3866     }
3867     return ts.release();
3868 }
3869
3870 bool FrameView::addScrollableArea(ScrollableArea* scrollableArea)
3871 {
3872     if (!m_scrollableAreas)
3873         m_scrollableAreas = adoptPtr(new ScrollableAreaSet);
3874     return m_scrollableAreas->add(scrollableArea).isNewEntry;
3875 }
3876
3877 bool FrameView::removeScrollableArea(ScrollableArea* scrollableArea)
3878 {
3879     if (!m_scrollableAreas)
3880         return false;
3881
3882     ScrollableAreaSet::iterator it = m_scrollableAreas->find(scrollableArea);
3883     if (it == m_scrollableAreas->end())
3884         return false;
3885
3886     m_scrollableAreas->remove(it);
3887     return true;
3888 }
3889
3890 bool FrameView::containsScrollableArea(ScrollableArea* scrollableArea) const
3891 {
3892     if (!m_scrollableAreas)
3893         return false;
3894     return m_scrollableAreas->contains(scrollableArea);
3895 }
3896
3897 void FrameView::removeChild(Widget* widget)
3898 {
3899     if (widget->isFrameView())
3900         removeScrollableArea(toFrameView(widget));
3901
3902     ScrollView::removeChild(widget);
3903 }
3904
3905 bool FrameView::wheelEvent(const PlatformWheelEvent& wheelEvent)
3906 {
3907     // Note that to allow for rubber-band over-scroll behavior, even non-scrollable views
3908     // should handle wheel events.
3909 #if !ENABLE(RUBBER_BANDING)
3910     if (!isScrollable())
3911         return false;
3912 #endif
3913
3914     if (delegatesScrolling()) {
3915         IntSize offset = scrollOffset();
3916         IntSize newOffset = IntSize(offset.width() - wheelEvent.deltaX(), offset.height() - wheelEvent.deltaY());
3917         if (offset != newOffset) {
3918             ScrollView::scrollTo(newOffset);
3919             scrollPositionChanged();
3920             frame()->loader()->client()->didChangeScrollOffset();
3921         }
3922         return true;
3923     }
3924
3925     // We don't allow mouse wheeling to happen in a ScrollView that has had its scrollbars explicitly disabled.
3926     if (!canHaveScrollbars())
3927         return false;
3928
3929 #if !PLATFORM(WX)
3930     if (platformWidget())
3931         return false;
3932 #endif
3933
3934 #if ENABLE(THREADED_SCROLLING)
3935     if (Page* page = m_frame->page()) {
3936         if (ScrollingCoordinator* scrollingCoordinator = page->scrollingCoordinator()) {
3937             if (scrollingCoordinator->coordinatesScrollingForFrameView(this))
3938                 return scrollingCoordinator->handleWheelEvent(this, wheelEvent);
3939         }
3940     }
3941 #endif
3942
3943     return ScrollableArea::handleWheelEvent(wheelEvent);
3944 }
3945
3946
3947 bool FrameView::isVerticalDocument() const
3948 {
3949     RenderView* renderView = this->renderView();
3950     if (!renderView)
3951         return true;
3952
3953     return renderView->style()->isHorizontalWritingMode();
3954 }
3955
3956 bool FrameView::isFlippedDocument() const
3957 {
3958     RenderView* renderView = this->renderView();
3959     if (!renderView)
3960         return false;
3961
3962     return renderView->style()->isFlippedBlocksWritingMode();
3963 }
3964
3965 void FrameView::notifyWidgetsInAllFrames(WidgetNotification notification)
3966 {
3967     for (Frame* frame = m_frame.get(); frame; frame = frame->tree()->traverseNext(m_frame.get())) {
3968         if (RenderView* root = frame->contentRenderer())
3969             root->notifyWidgets(notification);
3970     }
3971 }
3972     
3973 AXObjectCache* FrameView::axObjectCache() const
3974 {
3975     if (frame() && frame()->document() && frame()->document()->axObjectCacheExists())
3976         return frame()->document()->axObjectCache();
3977     return 0;
3978 }
3979     
3980 void FrameView::setScrollingPerformanceLoggingEnabled(bool flag)
3981 {
3982 #if USE(ACCELERATED_COMPOSITING)
3983     if (TiledBacking* tiledBacking = this->tiledBacking())
3984         tiledBacking->setScrollingPerformanceLoggingEnabled(flag);
3985 #else
3986     UNUSED_PARAM(flag);
3987 #endif
3988 }
3989
3990 } // namespace WebCore