REGRESSION: Horizontal scrollbar thumbs leave artifacts over page content when scroll...
[WebKit.git] / Source / WebCore / platform / ScrollableArea.cpp
1 /*
2  * Copyright (c) 2010, Google Inc. All rights reserved.
3  * Copyright (C) 2008, 2011 Apple Inc. All Rights Reserved.
4  * 
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions are
7  * met:
8  * 
9  *     * Redistributions of source code must retain the above copyright
10  * notice, this list of conditions and the following disclaimer.
11  *     * Redistributions in binary form must reproduce the above
12  * copyright notice, this list of conditions and the following disclaimer
13  * in the documentation and/or other materials provided with the
14  * distribution.
15  *     * Neither the name of Google Inc. nor the names of its
16  * contributors may be used to endorse or promote products derived from
17  * this software without specific prior written permission.
18  * 
19  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
20  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
21  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
22  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
23  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
24  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
25  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
26  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
27  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
28  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
29  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30  */
31
32 #include "config.h"
33 #include "ScrollableArea.h"
34
35 #include "FloatPoint.h"
36 #include "PlatformWheelEvent.h"
37 #include "ScrollAnimator.h"
38 #include "ScrollbarTheme.h"
39 #include <wtf/PassOwnPtr.h>
40
41 namespace WebCore {
42
43 ScrollableArea::ScrollableArea()
44     : m_scrollAnimator(ScrollAnimator::create(this))
45     , m_constrainsScrollingToContentEdge(true)
46     , m_inLiveResize(false)
47 {
48 }
49
50 ScrollableArea::~ScrollableArea()
51 {
52 }
53
54 bool ScrollableArea::scroll(ScrollDirection direction, ScrollGranularity granularity, float multiplier)
55 {
56     ScrollbarOrientation orientation;
57     Scrollbar* scrollbar;
58     if (direction == ScrollUp || direction == ScrollDown) {
59         orientation = VerticalScrollbar;
60         scrollbar = verticalScrollbar();
61     } else {
62         orientation = HorizontalScrollbar;
63         scrollbar = horizontalScrollbar();
64     }
65
66     if (!scrollbar)
67         return false;
68
69     float step = 0;
70     switch (granularity) {
71     case ScrollByLine:
72         step = scrollbar->lineStep();
73         break;
74     case ScrollByPage:
75         step = scrollbar->pageStep();
76         break;
77     case ScrollByDocument:
78         step = scrollbar->totalSize();
79         break;
80     case ScrollByPixel:
81         step = scrollbar->pixelStep();
82         break;
83     }
84
85     if (direction == ScrollUp || direction == ScrollLeft)
86         multiplier = -multiplier;
87
88     return m_scrollAnimator->scroll(orientation, granularity, step, multiplier);
89 }
90
91 void ScrollableArea::scrollToOffsetWithoutAnimation(const FloatPoint& offset)
92 {
93     m_scrollAnimator->scrollToOffsetWithoutAnimation(offset);
94 }
95
96 void ScrollableArea::scrollToOffsetWithoutAnimation(ScrollbarOrientation orientation, float offset)
97 {
98     if (orientation == HorizontalScrollbar)
99         scrollToXOffsetWithoutAnimation(offset);
100     else
101         scrollToYOffsetWithoutAnimation(offset);
102 }
103
104 void ScrollableArea::scrollToXOffsetWithoutAnimation(float x)
105 {
106     scrollToOffsetWithoutAnimation(FloatPoint(x, m_scrollAnimator->currentPosition().y()));
107 }
108
109 void ScrollableArea::scrollToYOffsetWithoutAnimation(float y)
110 {
111     scrollToOffsetWithoutAnimation(FloatPoint(m_scrollAnimator->currentPosition().x(), y));
112 }
113
114 void ScrollableArea::handleWheelEvent(PlatformWheelEvent& wheelEvent)
115 {
116     m_scrollAnimator->handleWheelEvent(wheelEvent);
117 }
118
119 #if ENABLE(GESTURE_EVENTS)
120 void ScrollableArea::handleGestureEvent(const PlatformGestureEvent& gestureEvent)
121 {
122     m_scrollAnimator->handleGestureEvent(gestureEvent);
123 }
124 #endif
125
126 void ScrollableArea::setScrollOffsetFromAnimation(const IntPoint& offset)
127 {
128     // Tell the derived class to scroll its contents.
129     setScrollOffset(offset);
130
131     bool hasOverlayScrollbars = ScrollbarTheme::nativeTheme()->usesOverlayScrollbars();
132
133     // Tell the scrollbars to update their thumb postions.
134     if (Scrollbar* horizontalScrollbar = this->horizontalScrollbar()) {
135         horizontalScrollbar->offsetDidChange();
136         if (hasOverlayScrollbars)
137             horizontalScrollbar->invalidate();
138     }
139     if (Scrollbar* verticalScrollbar = this->verticalScrollbar()) {
140         verticalScrollbar->offsetDidChange();
141         if (hasOverlayScrollbars)
142             verticalScrollbar->invalidate();
143     }
144 }
145
146 void ScrollableArea::willStartLiveResize()
147 {
148     if (m_inLiveResize)
149         return;
150     m_inLiveResize = true;
151     scrollAnimator()->willStartLiveResize();
152 }
153
154 void ScrollableArea::willEndLiveResize()
155 {
156     if (!m_inLiveResize)
157         return;
158     m_inLiveResize = false;
159     scrollAnimator()->willEndLiveResize();
160 }    
161
162 } // namespace WebCore