<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN"
"http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head><meta http-equiv="content-type" content="text/html; charset=utf-8" />
<title>[195810] trunk/Source/WebCore</title>
</head>
<body>

<style type="text/css"><!--
#msg dl.meta { border: 1px #006 solid; background: #369; padding: 6px; color: #fff; }
#msg dl.meta dt { float: left; width: 6em; font-weight: bold; }
#msg dt:after { content:':';}
#msg dl, #msg dt, #msg ul, #msg li, #header, #footer, #logmsg { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt;  }
#msg dl a { font-weight: bold}
#msg dl a:link    { color:#fc3; }
#msg dl a:active  { color:#ff0; }
#msg dl a:visited { color:#cc6; }
h3 { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt; font-weight: bold; }
#msg pre { overflow: auto; background: #ffc; border: 1px #fa0 solid; padding: 6px; }
#logmsg { background: #ffc; border: 1px #fa0 solid; padding: 1em 1em 0 1em; }
#logmsg p, #logmsg pre, #logmsg blockquote { margin: 0 0 1em 0; }
#logmsg p, #logmsg li, #logmsg dt, #logmsg dd { line-height: 14pt; }
#logmsg h1, #logmsg h2, #logmsg h3, #logmsg h4, #logmsg h5, #logmsg h6 { margin: .5em 0; }
#logmsg h1:first-child, #logmsg h2:first-child, #logmsg h3:first-child, #logmsg h4:first-child, #logmsg h5:first-child, #logmsg h6:first-child { margin-top: 0; }
#logmsg ul, #logmsg ol { padding: 0; list-style-position: inside; margin: 0 0 0 1em; }
#logmsg ul { text-indent: -1em; padding-left: 1em; }#logmsg ol { text-indent: -1.5em; padding-left: 1.5em; }
#logmsg > ul, #logmsg > ol { margin: 0 0 1em 0; }
#logmsg pre { background: #eee; padding: 1em; }
#logmsg blockquote { border: 1px solid #fa0; border-left-width: 10px; padding: 1em 1em 0 1em; background: white;}
#logmsg dl { margin: 0; }
#logmsg dt { font-weight: bold; }
#logmsg dd { margin: 0; padding: 0 0 0.5em 0; }
#logmsg dd:before { content:'\00bb';}
#logmsg table { border-spacing: 0px; border-collapse: collapse; border-top: 4px solid #fa0; border-bottom: 1px solid #fa0; background: #fff; }
#logmsg table th { text-align: left; font-weight: normal; padding: 0.2em 0.5em; border-top: 1px dotted #fa0; }
#logmsg table td { text-align: right; border-top: 1px dotted #fa0; padding: 0.2em 0.5em; }
#logmsg table thead th { text-align: center; border-bottom: 1px solid #fa0; }
#logmsg table th.Corner { text-align: left; }
#logmsg hr { border: none 0; border-top: 2px dashed #fa0; height: 1px; }
#header, #footer { color: #fff; background: #636; border: 1px #300 solid; padding: 6px; }
#patch { width: 100%; }
#patch h4 {font-family: verdana,arial,helvetica,sans-serif;font-size:10pt;padding:8px;background:#369;color:#fff;margin:0;}
#patch .propset h4, #patch .binary h4 {margin:0;}
#patch pre {padding:0;line-height:1.2em;margin:0;}
#patch .diff {width:100%;background:#eee;padding: 0 0 10px 0;overflow:auto;}
#patch .propset .diff, #patch .binary .diff  {padding:10px 0;}
#patch span {display:block;padding:0 10px;}
#patch .modfile, #patch .addfile, #patch .delfile, #patch .propset, #patch .binary, #patch .copfile {border:1px solid #ccc;margin:10px 0;}
#patch ins {background:#dfd;text-decoration:none;display:block;padding:0 10px;}
#patch del {background:#fdd;text-decoration:none;display:block;padding:0 10px;}
#patch .lines, .info {color:#888;background:#fff;}
--></style>
<div id="msg">
<dl class="meta">
<dt>Revision</dt> <dd><a href="http://trac.webkit.org/projects/webkit/changeset/195810">195810</a></dd>
<dt>Author</dt> <dd>carlosgc@webkit.org</dd>
<dt>Date</dt> <dd>2016-01-29 02:58:17 -0800 (Fri, 29 Jan 2016)</dd>
</dl>

<h3>Log Message</h3>
<pre>[GTK] Implement overlay scrollbars
https://bugs.webkit.org/show_bug.cgi?id=153405

Reviewed by Michael Catanzaro.

Add support for overlay scrollbars to GTK+ platform following the
same style and behavior than GtkScrolledWindow. They are only
available for GTK+ &gt;= 3.19, but honoring the GTK_OVERLAY_SCROLLING
environment variable, so they could be disable at run time, except
when threaded compositor is enabled. A new ScrollAnimator class
has been added for GTK+ to implement overlay scrollbars and still
allow smooth scrolling when available.

* PlatformGTK.cmake: Add ScrollAnimatorGtk and stop building ScrollAnimatorSmooth.
* platform/ScrollAnimator.h:
(WebCore::ScrollAnimator::ScrollAnimator::mouseEnteredContentArea):
Remove const to allow the ScrollAnimator to be updated.
(WebCore::ScrollAnimator::ScrollAnimator::mouseExitedContentArea): Ditto.
(WebCore::ScrollAnimator::ScrollAnimator::mouseMovedInContentArea): Ditto.
(WebCore::ScrollAnimator::ScrollAnimator::contentAreaDidShow): Ditto.
(WebCore::ScrollAnimator::ScrollAnimator::contentAreaDidHide): Ditto.
* platform/Scrollbar.h:
(WebCore::Scrollbar::opacity): Get scrollbar opacity.
(WebCore::Scrollbar::setOpacity): Set scrollbar opacity.
* platform/gtk/ScrollAnimatorGtk.cpp: Added.
(WebCore::ScrollAnimator::create): Create a ScrollAnimatorGtk.
(WebCore::ScrollAnimatorGtk::ScrollAnimatorGtk):
(WebCore::ScrollAnimatorGtk::~ScrollAnimatorGtk):
(WebCore::ScrollAnimatorGtk::ensureSmoothScrollingAnimation):
Initialize the ScrollAnimationSmooth if it doesn't exist.
(WebCore::ScrollAnimatorGtk::scroll): Ensure we have a
ScrollAnimationSmooth if smooth scrolling is enabled. This also
fixes the problem of having to reload the page after changing the
smooth scrolling setting.
(WebCore::ScrollAnimatorGtk::scrollToOffsetWithoutAnimation):
(WebCore::ScrollAnimatorGtk::willEndLiveResize):
(WebCore::ScrollAnimatorGtk::didAddVerticalScrollbar): Register
the scrollbar if it's an overlay scrollbar and make it visible
without animating it. Start the hide animation.
(WebCore::ScrollAnimatorGtk::didAddHorizontalScrollbar): Ditto.
(WebCore::ScrollAnimatorGtk::willRemoveVerticalScrollbar):
Unregister the scrollbar if it was registered and resrt the
animation state if it was the only scrollbar.
(WebCore::ScrollAnimatorGtk::willRemoveHorizontalScrollbar): Ditto.
(WebCore::ScrollAnimatorGtk::updateOverlayScrollbarsOpacity): Update
the scrollbars opacity and invalidate the indicator.
(WebCore::easeOutCubic):
(WebCore::ScrollAnimatorGtk::overlayScrollbarAnimationTimerFired):
Update the scrollbars opacity and schedule a next frame if the
animation didn't finish or start the hide animation otherwhise.
(WebCore::ScrollAnimatorGtk::showOverlayScrollbars): Start the
fade animation to show the scrollbars if needed.
(WebCore::ScrollAnimatorGtk::hideOverlayScrollbars): Start the
dafe animation to hide the scrollbars if needed.
(WebCore::ScrollAnimatorGtk::mouseEnteredContentArea): Call
showOverlayScrollbars().
(WebCore::ScrollAnimatorGtk::mouseExitedContentArea): Call
hideOverlayScrollbars().
(WebCore::ScrollAnimatorGtk::mouseMovedInContentArea): Call
showOverlayScrollbars().
(WebCore::ScrollAnimatorGtk::contentAreaDidShow): Ditto.
(WebCore::ScrollAnimatorGtk::contentAreaDidHide): Hide the
scrollbars without animations.
(WebCore::ScrollAnimatorGtk::notifyContentAreaScrolled): Call
showOverlayScrollbars().
(WebCore::ScrollAnimatorGtk::lockOverlayScrollbarStateToHidden):
Update the lock state and hide or show the scrollbars when locked
or unlocked.
* platform/gtk/ScrollAnimatorGtk.h: Added.
* platform/gtk/ScrollbarThemeGtk.cpp:
(WebCore::ScrollbarThemeGtk::backButtonRect): Pass
StyleContextMode to getOrCreateStyleContext depending on the
painting parameter.
(WebCore::ScrollbarThemeGtk::forwardButtonRect): Ditto.
(WebCore::ScrollbarThemeGtk::trackRect): Ditto.
(WebCore::ScrollbarThemeGtk::getOrCreateStyleContext): Add
StyleContextMode parameter to add the hovering class
unconditionally when using overlay scrollbars in layout mode. In
paint mode we add the hovering clas only when the scrollbar is
hovered. This way we always claim the size of the scrollbar when
hovered to be able to show the full scrollbar when the mouse is
close enough to the indicator.
(WebCore::ScrollbarThemeGtk::ScrollbarThemeGtk): Initialize
m_usesOverlayScrollbars.
(WebCore::ScrollbarThemeGtk::thumbRect): Pass the scrollbar to
getOrCreateStyleContext().
(WebCore::adjustRectAccordingToMargin): Fix the top margin.
(WebCore::ScrollbarThemeGtk::paintTrackBackground): Pass the
scrollbar and paint mode to getOrCreateStyleContext().
(WebCore::ScrollbarThemeGtk::paintScrollbarBackground): Ditto.
(WebCore::ScrollbarThemeGtk::paintThumb): Adjust the thumb
rectangle when overlay scrollbar is not hovered to its current
size, since we always claim the size of the scrollbar in hovered
mode.
(WebCore::ScrollbarThemeGtk::paintButton): Pass the scrollbar and
paint mode to getOrCreateStyleContext().
(WebCore::ScrollbarThemeGtk::paint): Take the scrollbar opacity
into account when rendering overlay scrollbars as indicators. Also
get the scrollbar opacity from the GTK+ theme and use a
transparency group when the global opacity is not full opaque.
(WebCore::ScrollbarThemeGtk::buttonSize): Pass the scrollbar to
getOrCreateStyleContext().
* platform/gtk/ScrollbarThemeGtk.h:
* platform/mac/ScrollAnimatorMac.h:
* platform/mac/ScrollAnimatorMac.mm:
(WebCore::ScrollAnimatorMac::mouseEnteredContentArea):
(WebCore::ScrollAnimatorMac::mouseExitedContentArea):
(WebCore::ScrollAnimatorMac::mouseMovedInContentArea):
(WebCore::ScrollAnimatorMac::contentAreaDidShow):
(WebCore::ScrollAnimatorMac::contentAreaDidHide):</pre>

<h3>Modified Paths</h3>
<ul>
<li><a href="#trunkSourceWebCoreChangeLog">trunk/Source/WebCore/ChangeLog</a></li>
<li><a href="#trunkSourceWebCorePlatformGTKcmake">trunk/Source/WebCore/PlatformGTK.cmake</a></li>
<li><a href="#trunkSourceWebCoreplatformScrollAnimatorh">trunk/Source/WebCore/platform/ScrollAnimator.h</a></li>
<li><a href="#trunkSourceWebCoreplatformScrollbarh">trunk/Source/WebCore/platform/Scrollbar.h</a></li>
<li><a href="#trunkSourceWebCoreplatformgtkScrollbarThemeGtkcpp">trunk/Source/WebCore/platform/gtk/ScrollbarThemeGtk.cpp</a></li>
<li><a href="#trunkSourceWebCoreplatformgtkScrollbarThemeGtkh">trunk/Source/WebCore/platform/gtk/ScrollbarThemeGtk.h</a></li>
<li><a href="#trunkSourceWebCoreplatformmacScrollAnimatorMach">trunk/Source/WebCore/platform/mac/ScrollAnimatorMac.h</a></li>
<li><a href="#trunkSourceWebCoreplatformmacScrollAnimatorMacmm">trunk/Source/WebCore/platform/mac/ScrollAnimatorMac.mm</a></li>
</ul>

<h3>Added Paths</h3>
<ul>
<li><a href="#trunkSourceWebCoreplatformgtkScrollAnimatorGtkcpp">trunk/Source/WebCore/platform/gtk/ScrollAnimatorGtk.cpp</a></li>
<li><a href="#trunkSourceWebCoreplatformgtkScrollAnimatorGtkh">trunk/Source/WebCore/platform/gtk/ScrollAnimatorGtk.h</a></li>
</ul>

</div>
<div id="patch">
<h3>Diff</h3>
<a id="trunkSourceWebCoreChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/ChangeLog (195809 => 195810)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/ChangeLog        2016-01-29 09:58:02 UTC (rev 195809)
+++ trunk/Source/WebCore/ChangeLog        2016-01-29 10:58:17 UTC (rev 195810)
</span><span class="lines">@@ -1,3 +1,116 @@
</span><ins>+2016-01-29  Carlos Garcia Campos  &lt;cgarcia@igalia.com&gt;
+
+        [GTK] Implement overlay scrollbars
+        https://bugs.webkit.org/show_bug.cgi?id=153405
+
+        Reviewed by Michael Catanzaro.
+
+        Add support for overlay scrollbars to GTK+ platform following the
+        same style and behavior than GtkScrolledWindow. They are only
+        available for GTK+ &gt;= 3.19, but honoring the GTK_OVERLAY_SCROLLING
+        environment variable, so they could be disable at run time, except
+        when threaded compositor is enabled. A new ScrollAnimator class
+        has been added for GTK+ to implement overlay scrollbars and still
+        allow smooth scrolling when available.
+
+        * PlatformGTK.cmake: Add ScrollAnimatorGtk and stop building ScrollAnimatorSmooth.
+        * platform/ScrollAnimator.h:
+        (WebCore::ScrollAnimator::ScrollAnimator::mouseEnteredContentArea):
+        Remove const to allow the ScrollAnimator to be updated.
+        (WebCore::ScrollAnimator::ScrollAnimator::mouseExitedContentArea): Ditto.
+        (WebCore::ScrollAnimator::ScrollAnimator::mouseMovedInContentArea): Ditto.
+        (WebCore::ScrollAnimator::ScrollAnimator::contentAreaDidShow): Ditto.
+        (WebCore::ScrollAnimator::ScrollAnimator::contentAreaDidHide): Ditto.
+        * platform/Scrollbar.h:
+        (WebCore::Scrollbar::opacity): Get scrollbar opacity.
+        (WebCore::Scrollbar::setOpacity): Set scrollbar opacity.
+        * platform/gtk/ScrollAnimatorGtk.cpp: Added.
+        (WebCore::ScrollAnimator::create): Create a ScrollAnimatorGtk.
+        (WebCore::ScrollAnimatorGtk::ScrollAnimatorGtk):
+        (WebCore::ScrollAnimatorGtk::~ScrollAnimatorGtk):
+        (WebCore::ScrollAnimatorGtk::ensureSmoothScrollingAnimation):
+        Initialize the ScrollAnimationSmooth if it doesn't exist.
+        (WebCore::ScrollAnimatorGtk::scroll): Ensure we have a
+        ScrollAnimationSmooth if smooth scrolling is enabled. This also
+        fixes the problem of having to reload the page after changing the
+        smooth scrolling setting.
+        (WebCore::ScrollAnimatorGtk::scrollToOffsetWithoutAnimation):
+        (WebCore::ScrollAnimatorGtk::willEndLiveResize):
+        (WebCore::ScrollAnimatorGtk::didAddVerticalScrollbar): Register
+        the scrollbar if it's an overlay scrollbar and make it visible
+        without animating it. Start the hide animation.
+        (WebCore::ScrollAnimatorGtk::didAddHorizontalScrollbar): Ditto.
+        (WebCore::ScrollAnimatorGtk::willRemoveVerticalScrollbar):
+        Unregister the scrollbar if it was registered and resrt the
+        animation state if it was the only scrollbar.
+        (WebCore::ScrollAnimatorGtk::willRemoveHorizontalScrollbar): Ditto.
+        (WebCore::ScrollAnimatorGtk::updateOverlayScrollbarsOpacity): Update
+        the scrollbars opacity and invalidate the indicator.
+        (WebCore::easeOutCubic):
+        (WebCore::ScrollAnimatorGtk::overlayScrollbarAnimationTimerFired):
+        Update the scrollbars opacity and schedule a next frame if the
+        animation didn't finish or start the hide animation otherwhise.
+        (WebCore::ScrollAnimatorGtk::showOverlayScrollbars): Start the
+        fade animation to show the scrollbars if needed.
+        (WebCore::ScrollAnimatorGtk::hideOverlayScrollbars): Start the
+        dafe animation to hide the scrollbars if needed.
+        (WebCore::ScrollAnimatorGtk::mouseEnteredContentArea): Call
+        showOverlayScrollbars().
+        (WebCore::ScrollAnimatorGtk::mouseExitedContentArea): Call
+        hideOverlayScrollbars().
+        (WebCore::ScrollAnimatorGtk::mouseMovedInContentArea): Call
+        showOverlayScrollbars().
+        (WebCore::ScrollAnimatorGtk::contentAreaDidShow): Ditto.
+        (WebCore::ScrollAnimatorGtk::contentAreaDidHide): Hide the
+        scrollbars without animations.
+        (WebCore::ScrollAnimatorGtk::notifyContentAreaScrolled): Call
+        showOverlayScrollbars().
+        (WebCore::ScrollAnimatorGtk::lockOverlayScrollbarStateToHidden):
+        Update the lock state and hide or show the scrollbars when locked
+        or unlocked.
+        * platform/gtk/ScrollAnimatorGtk.h: Added.
+        * platform/gtk/ScrollbarThemeGtk.cpp:
+        (WebCore::ScrollbarThemeGtk::backButtonRect): Pass
+        StyleContextMode to getOrCreateStyleContext depending on the
+        painting parameter.
+        (WebCore::ScrollbarThemeGtk::forwardButtonRect): Ditto.
+        (WebCore::ScrollbarThemeGtk::trackRect): Ditto.
+        (WebCore::ScrollbarThemeGtk::getOrCreateStyleContext): Add
+        StyleContextMode parameter to add the hovering class
+        unconditionally when using overlay scrollbars in layout mode. In
+        paint mode we add the hovering clas only when the scrollbar is
+        hovered. This way we always claim the size of the scrollbar when
+        hovered to be able to show the full scrollbar when the mouse is
+        close enough to the indicator.
+        (WebCore::ScrollbarThemeGtk::ScrollbarThemeGtk): Initialize
+        m_usesOverlayScrollbars.
+        (WebCore::ScrollbarThemeGtk::thumbRect): Pass the scrollbar to
+        getOrCreateStyleContext().
+        (WebCore::adjustRectAccordingToMargin): Fix the top margin.
+        (WebCore::ScrollbarThemeGtk::paintTrackBackground): Pass the
+        scrollbar and paint mode to getOrCreateStyleContext().
+        (WebCore::ScrollbarThemeGtk::paintScrollbarBackground): Ditto.
+        (WebCore::ScrollbarThemeGtk::paintThumb): Adjust the thumb
+        rectangle when overlay scrollbar is not hovered to its current
+        size, since we always claim the size of the scrollbar in hovered
+        mode.
+        (WebCore::ScrollbarThemeGtk::paintButton): Pass the scrollbar and
+        paint mode to getOrCreateStyleContext().
+        (WebCore::ScrollbarThemeGtk::paint): Take the scrollbar opacity
+        into account when rendering overlay scrollbars as indicators. Also
+        get the scrollbar opacity from the GTK+ theme and use a
+        transparency group when the global opacity is not full opaque.
+        (WebCore::ScrollbarThemeGtk::buttonSize): Pass the scrollbar to
+        getOrCreateStyleContext().
+        * platform/gtk/ScrollbarThemeGtk.h:
+        * platform/mac/ScrollAnimatorMac.h:
+        * platform/mac/ScrollAnimatorMac.mm:
+        (WebCore::ScrollAnimatorMac::mouseEnteredContentArea):
+        (WebCore::ScrollAnimatorMac::mouseExitedContentArea):
+        (WebCore::ScrollAnimatorMac::mouseMovedInContentArea):
+        (WebCore::ScrollAnimatorMac::contentAreaDidShow):
+        (WebCore::ScrollAnimatorMac::contentAreaDidHide):
+
</ins><span class="cx"> 2016-01-29  ChangSeok Oh  &lt;changseok.oh@collabora.com&gt;
</span><span class="cx"> 
</span><span class="cx">         [GStreamer] built-in media player doesn't update
</span></span></pre></div>
<a id="trunkSourceWebCorePlatformGTKcmake"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/PlatformGTK.cmake (195809 => 195810)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/PlatformGTK.cmake        2016-01-29 09:58:02 UTC (rev 195809)
+++ trunk/Source/WebCore/PlatformGTK.cmake        2016-01-29 10:58:17 UTC (rev 195810)
</span><span class="lines">@@ -163,6 +163,7 @@
</span><span class="cx">     platform/gtk/LanguageGtk.cpp
</span><span class="cx">     platform/gtk/LoggingGtk.cpp
</span><span class="cx">     platform/gtk/MIMETypeRegistryGtk.cpp
</span><ins>+    platform/gtk/ScrollAnimatorGtk.cpp
</ins><span class="cx">     platform/gtk/SharedBufferGtk.cpp
</span><span class="cx">     platform/gtk/TemporaryLinkStubs.cpp
</span><span class="cx">     platform/gtk/UserAgentGtk.cpp
</span><span class="lines">@@ -936,7 +937,6 @@
</span><span class="cx"> if (ENABLE_SMOOTH_SCROLLING)
</span><span class="cx">     list(APPEND WebCore_SOURCES
</span><span class="cx">         platform/ScrollAnimationSmooth.cpp
</span><del>-        platform/ScrollAnimatorSmooth.cpp
</del><span class="cx">     )
</span><span class="cx"> endif ()
</span><span class="cx"> 
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformScrollAnimatorh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/ScrollAnimator.h (195809 => 195810)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/ScrollAnimator.h        2016-01-29 09:58:02 UTC (rev 195809)
+++ trunk/Source/WebCore/platform/ScrollAnimator.h        2016-01-29 10:58:17 UTC (rev 195810)
</span><span class="lines">@@ -91,17 +91,17 @@
</span><span class="cx">     virtual void serviceScrollAnimations() { }
</span><span class="cx"> 
</span><span class="cx">     virtual void contentAreaWillPaint() const { }
</span><del>-    virtual void mouseEnteredContentArea() const { }
-    virtual void mouseExitedContentArea() const { }
-    virtual void mouseMovedInContentArea() const { }
</del><ins>+    virtual void mouseEnteredContentArea() { }
+    virtual void mouseExitedContentArea() { }
+    virtual void mouseMovedInContentArea() { }
</ins><span class="cx">     virtual void mouseEnteredScrollbar(Scrollbar*) const { }
</span><span class="cx">     virtual void mouseExitedScrollbar(Scrollbar*) const { }
</span><span class="cx">     virtual void mouseIsDownInScrollbar(Scrollbar*, bool) const { }
</span><span class="cx">     virtual void willStartLiveResize() { }
</span><span class="cx">     virtual void contentsResized() const { }
</span><span class="cx">     virtual void willEndLiveResize() { }
</span><del>-    virtual void contentAreaDidShow() const { }
-    virtual void contentAreaDidHide() const { }
</del><ins>+    virtual void contentAreaDidShow() { }
+    virtual void contentAreaDidHide() { }
</ins><span class="cx"> 
</span><span class="cx">     virtual void lockOverlayScrollbarStateToHidden(bool) { }
</span><span class="cx">     virtual bool scrollbarsCanBeActive() const { return true; }
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformScrollbarh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/Scrollbar.h (195809 => 195810)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/Scrollbar.h        2016-01-29 09:58:02 UTC (rev 195809)
+++ trunk/Source/WebCore/platform/Scrollbar.h        2016-01-29 10:58:17 UTC (rev 195810)
</span><span class="lines">@@ -130,6 +130,9 @@
</span><span class="cx">     bool isAlphaLocked() const { return m_isAlphaLocked; }
</span><span class="cx">     void setIsAlphaLocked(bool flag) { m_isAlphaLocked = flag; }
</span><span class="cx"> 
</span><ins>+    float opacity() const { return m_opacity; }
+    void setOpacity(float opacity) { m_opacity = opacity; }
+
</ins><span class="cx">     bool supportsUpdateOnSecondaryThread() const;
</span><span class="cx"> 
</span><span class="cx">     WeakPtr&lt;Scrollbar&gt; createWeakPtr() { return m_weakPtrFactory.createWeakPtr(); }
</span><span class="lines">@@ -178,6 +181,8 @@
</span><span class="cx"> 
</span><span class="cx">     bool m_isCustomScrollbar;
</span><span class="cx"> 
</span><ins>+    float m_opacity { 1 };
+
</ins><span class="cx"> private:
</span><span class="cx">     virtual bool isScrollbar() const override { return true; }
</span><span class="cx"> 
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformgtkScrollAnimatorGtkcpp"></a>
<div class="addfile"><h4>Added: trunk/Source/WebCore/platform/gtk/ScrollAnimatorGtk.cpp (0 => 195810)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/gtk/ScrollAnimatorGtk.cpp                                (rev 0)
+++ trunk/Source/WebCore/platform/gtk/ScrollAnimatorGtk.cpp        2016-01-29 10:58:17 UTC (rev 195810)
</span><span class="lines">@@ -0,0 +1,300 @@
</span><ins>+/*
+ * Copyright (c) 2016 Igalia S.L.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ *     * Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ *     * Redistributions in binary form must reproduce the above
+ * copyright notice, this list of conditions and the following disclaimer
+ * in the documentation and/or other materials provided with the
+ * distribution.
+ *     * Neither the name of Google Inc. nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * &quot;AS IS&quot; AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include &quot;config.h&quot;
+#include &quot;ScrollAnimatorGtk.h&quot;
+
+#include &quot;ScrollAnimationSmooth.h&quot;
+#include &quot;ScrollableArea.h&quot;
+#include &quot;ScrollbarTheme.h&quot;
+#include &lt;wtf/CurrentTime.h&gt;
+
+namespace WebCore {
+
+static const double overflowScrollbarsAnimationDuration = 1;
+static const double overflowScrollbarsAnimationHideDelay = 2;
+
+std::unique_ptr&lt;ScrollAnimator&gt; ScrollAnimator::create(ScrollableArea&amp; scrollableArea)
+{
+    return std::make_unique&lt;ScrollAnimatorGtk&gt;(scrollableArea);
+}
+
+ScrollAnimatorGtk::ScrollAnimatorGtk(ScrollableArea&amp; scrollableArea)
+    : ScrollAnimator(scrollableArea)
+    , m_overlayScrollbarAnimationTimer(*this, &amp;ScrollAnimatorGtk::overlayScrollbarAnimationTimerFired)
+{
+#if ENABLE(SMOOTH_SCROLLING)
+    if (scrollableArea.scrollAnimatorEnabled())
+        ensureSmoothScrollingAnimation();
+#endif
+}
+
+ScrollAnimatorGtk::~ScrollAnimatorGtk()
+{
+}
+
+#if ENABLE(SMOOTH_SCROLLING)
+void ScrollAnimatorGtk::ensureSmoothScrollingAnimation()
+{
+    if (m_animation)
+        return;
+
+    m_animation = std::make_unique&lt;ScrollAnimationSmooth&gt;(m_scrollableArea, [this](FloatPoint&amp;&amp; position) {
+        FloatSize delta = position - m_currentPosition;
+        m_currentPosition = WTFMove(position);
+        notifyPositionChanged(delta);
+    });
+    m_animation-&gt;setCurrentPosition(m_currentPosition);
+}
+
+bool ScrollAnimatorGtk::scroll(ScrollbarOrientation orientation, ScrollGranularity granularity, float step, float multiplier)
+{
+    if (!m_scrollableArea.scrollAnimatorEnabled() || granularity == ScrollByPrecisePixel)
+        return ScrollAnimator::scroll(orientation, granularity, step, multiplier);
+
+    ensureSmoothScrollingAnimation();
+    return m_animation-&gt;scroll(orientation, granularity, step, multiplier);
+}
+
+void ScrollAnimatorGtk::scrollToOffsetWithoutAnimation(const FloatPoint&amp; offset)
+{
+    FloatPoint position = ScrollableArea::scrollPositionFromOffset(offset, toFloatSize(m_scrollableArea.scrollOrigin()));
+    if (m_animation)
+        m_animation-&gt;setCurrentPosition(position);
+
+    FloatSize delta = position - m_currentPosition;
+    m_currentPosition = position;
+    notifyPositionChanged(delta);
+}
+
+void ScrollAnimatorGtk::willEndLiveResize()
+{
+    if (m_animation)
+        m_animation-&gt;updateVisibleLengths();
+}
+#endif
+
+void ScrollAnimatorGtk::didAddVerticalScrollbar(Scrollbar* scrollbar)
+{
+#if ENABLE(SMOOTH_SCROLLING)
+    if (m_animation)
+        m_animation-&gt;updateVisibleLengths();
+#endif
+    if (!scrollbar-&gt;isOverlayScrollbar())
+        return;
+    m_verticalOverlayScrollbar = scrollbar;
+    if (!m_horizontalOverlayScrollbar)
+        m_overlayScrollbarAnimationCurrent = 1;
+    m_verticalOverlayScrollbar-&gt;setOpacity(m_overlayScrollbarAnimationCurrent);
+    hideOverlayScrollbars();
+}
+
+void ScrollAnimatorGtk::didAddHorizontalScrollbar(Scrollbar* scrollbar)
+{
+#if ENABLE(SMOOTH_SCROLLING)
+    if (m_animation)
+        m_animation-&gt;updateVisibleLengths();
+#endif
+    if (!scrollbar-&gt;isOverlayScrollbar())
+        return;
+    m_horizontalOverlayScrollbar = scrollbar;
+    if (!m_verticalOverlayScrollbar)
+        m_overlayScrollbarAnimationCurrent = 1;
+    m_horizontalOverlayScrollbar-&gt;setOpacity(m_overlayScrollbarAnimationCurrent);
+    hideOverlayScrollbars();
+}
+
+void ScrollAnimatorGtk::willRemoveVerticalScrollbar(Scrollbar* scrollbar)
+{
+    if (m_verticalOverlayScrollbar != scrollbar)
+        return;
+    m_verticalOverlayScrollbar = nullptr;
+    if (!m_horizontalOverlayScrollbar)
+        m_overlayScrollbarAnimationCurrent = 0;
+}
+
+void ScrollAnimatorGtk::willRemoveHorizontalScrollbar(Scrollbar* scrollbar)
+{
+    if (m_horizontalOverlayScrollbar != scrollbar)
+        return;
+    m_horizontalOverlayScrollbar = nullptr;
+    if (!m_verticalOverlayScrollbar)
+        m_overlayScrollbarAnimationCurrent = 0;
+}
+
+void ScrollAnimatorGtk::updateOverlayScrollbarsOpacity()
+{
+    if (m_verticalOverlayScrollbar &amp;&amp; m_overlayScrollbarAnimationCurrent != m_verticalOverlayScrollbar-&gt;opacity()) {
+        m_verticalOverlayScrollbar-&gt;setOpacity(m_overlayScrollbarAnimationCurrent);
+        if (m_verticalOverlayScrollbar-&gt;hoveredPart() == NoPart)
+            ScrollbarTheme::theme().invalidatePart(*m_verticalOverlayScrollbar, ThumbPart);
+    }
+
+    if (m_horizontalOverlayScrollbar &amp;&amp; m_overlayScrollbarAnimationCurrent != m_horizontalOverlayScrollbar-&gt;opacity()) {
+        m_horizontalOverlayScrollbar-&gt;setOpacity(m_overlayScrollbarAnimationCurrent);
+        if (m_horizontalOverlayScrollbar-&gt;hoveredPart() == NoPart)
+            ScrollbarTheme::theme().invalidatePart(*m_horizontalOverlayScrollbar, ThumbPart);
+    }
+}
+
+static inline double easeOutCubic(double t)
+{
+    double p = t - 1;
+    return p * p * p + 1;
+}
+
+void ScrollAnimatorGtk::overlayScrollbarAnimationTimerFired()
+{
+    if (!m_horizontalOverlayScrollbar &amp;&amp; !m_verticalOverlayScrollbar)
+        return;
+    if (m_overlayScrollbarsLocked)
+        return;
+
+    double currentTime = monotonicallyIncreasingTime();
+    double progress = 1;
+    if (currentTime &lt; m_overlayScrollbarAnimationEndTime)
+        progress = (currentTime - m_overlayScrollbarAnimationStartTime) / (m_overlayScrollbarAnimationEndTime - m_overlayScrollbarAnimationStartTime);
+    progress = m_overlayScrollbarAnimationSource + (easeOutCubic(progress) * (m_overlayScrollbarAnimationTarget - m_overlayScrollbarAnimationSource));
+    if (progress != m_overlayScrollbarAnimationCurrent) {
+        m_overlayScrollbarAnimationCurrent = progress;
+        updateOverlayScrollbarsOpacity();
+    }
+
+    if (m_overlayScrollbarAnimationCurrent != m_overlayScrollbarAnimationTarget) {
+        static const double frameRate = 60;
+        static const double tickTime = 1 / frameRate;
+        static const double minimumTimerInterval = .001;
+        double deltaToNextFrame = std::max(tickTime - (monotonicallyIncreasingTime() - currentTime), minimumTimerInterval);
+        m_overlayScrollbarAnimationTimer.startOneShot(deltaToNextFrame);
+    } else
+        hideOverlayScrollbars();
+}
+
+void ScrollAnimatorGtk::showOverlayScrollbars()
+{
+    if (m_overlayScrollbarsLocked)
+        return;
+
+    if (m_overlayScrollbarAnimationTimer.isActive() &amp;&amp; m_overlayScrollbarAnimationTarget == 1)
+        return;
+    m_overlayScrollbarAnimationTimer.stop();
+
+    if (!m_horizontalOverlayScrollbar &amp;&amp; !m_verticalOverlayScrollbar)
+        return;
+
+    m_overlayScrollbarAnimationSource = m_overlayScrollbarAnimationCurrent;
+    m_overlayScrollbarAnimationTarget = 1;
+    if (m_overlayScrollbarAnimationTarget != m_overlayScrollbarAnimationCurrent) {
+        m_overlayScrollbarAnimationStartTime = monotonicallyIncreasingTime();
+        m_overlayScrollbarAnimationEndTime = m_overlayScrollbarAnimationStartTime + overflowScrollbarsAnimationDuration;
+        m_overlayScrollbarAnimationTimer.startOneShot(0);
+    } else
+        hideOverlayScrollbars();
+}
+
+void ScrollAnimatorGtk::hideOverlayScrollbars()
+{
+    if (m_overlayScrollbarAnimationTimer.isActive() &amp;&amp; !m_overlayScrollbarAnimationTarget)
+        return;
+    m_overlayScrollbarAnimationTimer.stop();
+
+    if (!m_horizontalOverlayScrollbar &amp;&amp; !m_verticalOverlayScrollbar)
+        return;
+
+    m_overlayScrollbarAnimationSource = m_overlayScrollbarAnimationCurrent;
+    m_overlayScrollbarAnimationTarget = 0;
+    if (m_overlayScrollbarAnimationTarget == m_overlayScrollbarAnimationCurrent)
+        return;
+    m_overlayScrollbarAnimationStartTime = monotonicallyIncreasingTime() + overflowScrollbarsAnimationHideDelay;
+    m_overlayScrollbarAnimationEndTime = m_overlayScrollbarAnimationStartTime + overflowScrollbarsAnimationDuration + overflowScrollbarsAnimationHideDelay;
+    m_overlayScrollbarAnimationTimer.startOneShot(overflowScrollbarsAnimationHideDelay);
+}
+
+void ScrollAnimatorGtk::mouseEnteredContentArea()
+{
+    showOverlayScrollbars();
+}
+
+void ScrollAnimatorGtk::mouseExitedContentArea()
+{
+    hideOverlayScrollbars();
+}
+
+void ScrollAnimatorGtk::mouseMovedInContentArea()
+{
+    showOverlayScrollbars();
+}
+
+void ScrollAnimatorGtk::contentAreaDidShow()
+{
+    showOverlayScrollbars();
+}
+
+void ScrollAnimatorGtk::contentAreaDidHide()
+{
+    if (m_overlayScrollbarsLocked)
+        return;
+    m_overlayScrollbarAnimationTimer.stop();
+    if (m_overlayScrollbarAnimationCurrent) {
+        m_overlayScrollbarAnimationCurrent = 0;
+        updateOverlayScrollbarsOpacity();
+    }
+}
+
+void ScrollAnimatorGtk::notifyContentAreaScrolled(const FloatSize&amp;)
+{
+    showOverlayScrollbars();
+}
+
+void ScrollAnimatorGtk::lockOverlayScrollbarStateToHidden(bool shouldLockState)
+{
+    if (m_overlayScrollbarsLocked == shouldLockState)
+        return;
+    m_overlayScrollbarsLocked = shouldLockState;
+
+    if (!m_horizontalOverlayScrollbar &amp;&amp; !m_verticalOverlayScrollbar)
+        return;
+
+    if (m_overlayScrollbarsLocked) {
+        m_overlayScrollbarAnimationTimer.stop();
+        if (m_horizontalOverlayScrollbar)
+            m_horizontalOverlayScrollbar-&gt;setOpacity(0);
+        if (m_verticalOverlayScrollbar)
+            m_verticalOverlayScrollbar-&gt;setOpacity(0);
+    } else {
+        if (m_overlayScrollbarAnimationCurrent == 1)
+            updateOverlayScrollbarsOpacity();
+        else
+            showOverlayScrollbars();
+    }
+}
+
+} // namespace WebCore
+
</ins></span></pre></div>
<a id="trunkSourceWebCoreplatformgtkScrollAnimatorGtkh"></a>
<div class="addfile"><h4>Added: trunk/Source/WebCore/platform/gtk/ScrollAnimatorGtk.h (0 => 195810)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/gtk/ScrollAnimatorGtk.h                                (rev 0)
+++ trunk/Source/WebCore/platform/gtk/ScrollAnimatorGtk.h        2016-01-29 10:58:17 UTC (rev 195810)
</span><span class="lines">@@ -0,0 +1,89 @@
</span><ins>+/*
+ * Copyright (c) 2016 Igalia S.L.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ *     * Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ *     * Redistributions in binary form must reproduce the above
+ * copyright notice, this list of conditions and the following disclaimer
+ * in the documentation and/or other materials provided with the
+ * distribution.
+ *     * Neither the name of Google Inc. nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * &quot;AS IS&quot; AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef ScrollAnimatorGtk_h
+#define ScrollAnimatorGtk_h
+
+#include &quot;ScrollAnimator.h&quot;
+#include &quot;Timer.h&quot;
+
+namespace WebCore {
+
+class ScrollAnimation;
+
+class ScrollAnimatorGtk final : public ScrollAnimator {
+public:
+    explicit ScrollAnimatorGtk(ScrollableArea&amp;);
+    virtual ~ScrollAnimatorGtk();
+
+private:
+#if ENABLE(SMOOTH_SCROLLING)
+    virtual bool scroll(ScrollbarOrientation, ScrollGranularity, float step, float multiplier) override;
+    virtual void scrollToOffsetWithoutAnimation(const FloatPoint&amp;) override;
+    virtual void willEndLiveResize() override;
+#endif
+
+    virtual void didAddVerticalScrollbar(Scrollbar*) override;
+    virtual void didAddHorizontalScrollbar(Scrollbar*) override;
+    virtual void willRemoveVerticalScrollbar(Scrollbar*) override;
+    virtual void willRemoveHorizontalScrollbar(Scrollbar*) override;
+
+    virtual void mouseEnteredContentArea() override;
+    virtual void mouseExitedContentArea() override;
+    virtual void mouseMovedInContentArea() override;
+    virtual void contentAreaDidShow() override;
+    virtual void contentAreaDidHide() override;
+    virtual void notifyContentAreaScrolled(const FloatSize&amp; delta) override;
+    virtual void lockOverlayScrollbarStateToHidden(bool) override;
+
+    void overlayScrollbarAnimationTimerFired();
+    void showOverlayScrollbars();
+    void hideOverlayScrollbars();
+    void updateOverlayScrollbarsOpacity();
+
+#if ENABLE(SMOOTH_SCROLLING)
+    void ensureSmoothScrollingAnimation();
+
+    std::unique_ptr&lt;ScrollAnimation&gt; m_animation;
+#endif
+    Scrollbar* m_horizontalOverlayScrollbar { nullptr };
+    Scrollbar* m_verticalOverlayScrollbar { nullptr };
+    bool m_overlayScrollbarsLocked { false };
+    Timer m_overlayScrollbarAnimationTimer;
+    double m_overlayScrollbarAnimationSource { 0 };
+    double m_overlayScrollbarAnimationTarget { 0 };
+    double m_overlayScrollbarAnimationCurrent { 0 };
+    double m_overlayScrollbarAnimationStartTime { 0 };
+    double m_overlayScrollbarAnimationEndTime { 0 };
+};
+
+} // namespace WebCore
+
+#endif // ScrollAnimatorGtk_h
</ins></span></pre></div>
<a id="trunkSourceWebCoreplatformgtkScrollbarThemeGtkcpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/gtk/ScrollbarThemeGtk.cpp (195809 => 195810)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/gtk/ScrollbarThemeGtk.cpp        2016-01-29 09:58:02 UTC (rev 195809)
+++ trunk/Source/WebCore/platform/gtk/ScrollbarThemeGtk.cpp        2016-01-29 10:58:17 UTC (rev 195810)
</span><span class="lines">@@ -59,7 +59,7 @@
</span><span class="cx"> #endif
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-IntRect ScrollbarThemeGtk::backButtonRect(Scrollbar&amp; scrollbar, ScrollbarPart part, bool)
</del><ins>+IntRect ScrollbarThemeGtk::backButtonRect(Scrollbar&amp; scrollbar, ScrollbarPart part, bool painting)
</ins><span class="cx"> {
</span><span class="cx"> #ifndef GTK_API_VERSION_2
</span><span class="cx">     if (part == BackButtonEndPart &amp;&amp; !m_hasBackButtonEndPart)
</span><span class="lines">@@ -67,7 +67,7 @@
</span><span class="cx">     if (part == BackButtonStartPart &amp;&amp; !m_hasBackButtonStartPart)
</span><span class="cx">         return IntRect();
</span><span class="cx"> 
</span><del>-    GRefPtr&lt;GtkStyleContext&gt; styleContext = getOrCreateStyleContext();
</del><ins>+    GRefPtr&lt;GtkStyleContext&gt; styleContext = getOrCreateStyleContext(&amp;scrollbar, painting ? StyleContextMode::Paint : StyleContextMode::Layout);
</ins><span class="cx">     int x = scrollbar.x() + m_cachedProperties.troughBorderWidth;
</span><span class="cx">     int y = scrollbar.y() + m_cachedProperties.troughBorderWidth;
</span><span class="cx">     IntSize size = buttonSize(scrollbar);
</span><span class="lines">@@ -83,11 +83,12 @@
</span><span class="cx"> #else
</span><span class="cx">     UNUSED_PARAM(scrollbar);
</span><span class="cx">     UNUSED_PARAM(part);
</span><ins>+    UNUSED_PARAM(painting);
</ins><span class="cx">     return IntRect();
</span><span class="cx"> #endif
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-IntRect ScrollbarThemeGtk::forwardButtonRect(Scrollbar&amp; scrollbar, ScrollbarPart part, bool)
</del><ins>+IntRect ScrollbarThemeGtk::forwardButtonRect(Scrollbar&amp; scrollbar, ScrollbarPart part, bool painting)
</ins><span class="cx"> {
</span><span class="cx"> #ifndef GTK_API_VERSION_2
</span><span class="cx">     if (part == ForwardButtonStartPart &amp;&amp; !m_hasForwardButtonStartPart)
</span><span class="lines">@@ -95,7 +96,7 @@
</span><span class="cx">     if (part == ForwardButtonEndPart &amp;&amp; !m_hasForwardButtonEndPart)
</span><span class="cx">         return IntRect();
</span><span class="cx"> 
</span><del>-    GRefPtr&lt;GtkStyleContext&gt; styleContext = getOrCreateStyleContext();
</del><ins>+    GRefPtr&lt;GtkStyleContext&gt; styleContext = getOrCreateStyleContext(&amp;scrollbar, painting ? StyleContextMode::Paint : StyleContextMode::Layout);
</ins><span class="cx">     IntSize size = buttonSize(scrollbar);
</span><span class="cx">     if (scrollbar.orientation() == HorizontalScrollbar) {
</span><span class="cx">         int y = scrollbar.y() + m_cachedProperties.troughBorderWidth;
</span><span class="lines">@@ -116,14 +117,15 @@
</span><span class="cx"> #else
</span><span class="cx">     UNUSED_PARAM(scrollbar);
</span><span class="cx">     UNUSED_PARAM(part);
</span><ins>+    UNUSED_PARAM(painting);
</ins><span class="cx">     return IntRect();
</span><span class="cx"> #endif
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-IntRect ScrollbarThemeGtk::trackRect(Scrollbar&amp; scrollbar, bool)
</del><ins>+IntRect ScrollbarThemeGtk::trackRect(Scrollbar&amp; scrollbar, bool painting)
</ins><span class="cx"> {
</span><span class="cx"> #ifndef GTK_API_VERSION_2
</span><del>-    GRefPtr&lt;GtkStyleContext&gt; styleContext = getOrCreateStyleContext();
</del><ins>+    GRefPtr&lt;GtkStyleContext&gt; styleContext = getOrCreateStyleContext(&amp;scrollbar, painting ? StyleContextMode::Paint : StyleContextMode::Layout);
</ins><span class="cx">     // The padding along the thumb movement axis includes the trough border
</span><span class="cx">     // plus the size of stepper spacing (the space between the stepper and
</span><span class="cx">     // the place where the thumb stops). There is often no stepper spacing.
</span><span class="lines">@@ -162,6 +164,7 @@
</span><span class="cx">                    thickness, scrollbar.height() - (2 * movementAxisPadding) - buttonsWidth);
</span><span class="cx"> #else
</span><span class="cx">     UNUSED_PARAM(scrollbar);
</span><ins>+    UNUSED_PARAM(painting);
</ins><span class="cx">     return IntRect();
</span><span class="cx"> #endif
</span><span class="cx"> }
</span><span class="lines">@@ -175,8 +178,9 @@
</span><span class="cx"> // The GtkStyleContext returned by this function is cached by ScrollbarThemeGtk::paint for the
</span><span class="cx"> // duration of its scope, so a different GtkStyleContext with updated theme properties will be
</span><span class="cx"> // used for each call to paint.
</span><del>-GRefPtr&lt;GtkStyleContext&gt; ScrollbarThemeGtk::getOrCreateStyleContext(ScrollbarOrientation orientation)
</del><ins>+GRefPtr&lt;GtkStyleContext&gt; ScrollbarThemeGtk::getOrCreateStyleContext(Scrollbar* scrollbar, StyleContextMode mode)
</ins><span class="cx"> {
</span><ins>+    ASSERT(scrollbar || mode == StyleContextMode::Layout);
</ins><span class="cx">     if (m_cachedStyleContext)
</span><span class="cx">         return m_cachedStyleContext;
</span><span class="cx"> 
</span><span class="lines">@@ -185,10 +189,15 @@
</span><span class="cx">     gtk_widget_path_append_type(path.get(), GTK_TYPE_SCROLLBAR);
</span><span class="cx"> #if GTK_CHECK_VERSION(3, 19, 2)
</span><span class="cx">     gtk_widget_path_iter_set_object_name(path.get(), -1, &quot;scrollbar&quot;);
</span><ins>+    if (m_usesOverlayScrollbars) {
+        gtk_widget_path_iter_add_class(path.get(), -1, &quot;overlay-indicator&quot;);
+        if (mode == StyleContextMode::Layout || scrollbar-&gt;hoveredPart() != NoPart)
+            gtk_widget_path_iter_add_class(path.get(), -1, &quot;hovering&quot;);
+    }
</ins><span class="cx"> #else
</span><span class="cx">     gtk_widget_path_iter_add_class(path.get(), -1, &quot;scrollbar&quot;);
</span><span class="cx"> #endif
</span><del>-    gtk_widget_path_iter_add_class(path.get(), -1, orientationStyleClass(orientation));
</del><ins>+    gtk_widget_path_iter_add_class(path.get(), -1, orientationStyleClass(scrollbar ? scrollbar-&gt;orientation() : VerticalScrollbar));
</ins><span class="cx">     gtk_style_context_set_path(styleContext.get(), path.get());
</span><span class="cx"> 
</span><span class="cx">     gtk_style_context_get_style(
</span><span class="lines">@@ -222,6 +231,15 @@
</span><span class="cx"> 
</span><span class="cx"> ScrollbarThemeGtk::ScrollbarThemeGtk()
</span><span class="cx"> {
</span><ins>+#if GTK_CHECK_VERSION(3, 19, 2)
+#if USE(COORDINATED_GRAPHICS_THREADED)
+    m_usesOverlayScrollbars = true;
+#else
+    // FIXME: Disable overlay scrollbars by default for now due to bug #153404.
+    // Invert the logic here once bug #153404 is fixed.
+    m_usesOverlayScrollbars = !g_strcmp0(g_getenv(&quot;GTK_OVERLAY_SCROLLING&quot;), &quot;1&quot;);
+#endif
+#endif
</ins><span class="cx">     updateThemeProperties();
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="lines">@@ -245,7 +263,7 @@
</span><span class="cx"> 
</span><span class="cx"> IntRect ScrollbarThemeGtk::thumbRect(Scrollbar&amp; scrollbar, const IntRect&amp; unconstrainedTrackRect)
</span><span class="cx"> {
</span><del>-    GRefPtr&lt;GtkStyleContext&gt; styleContext = getOrCreateStyleContext(scrollbar.orientation());
</del><ins>+    GRefPtr&lt;GtkStyleContext&gt; styleContext = getOrCreateStyleContext(&amp;scrollbar);
</ins><span class="cx">     IntRect trackRect = constrainTrackRectToTrackPieces(scrollbar, unconstrainedTrackRect);
</span><span class="cx">     int thumbPos = thumbPosition(scrollbar);
</span><span class="cx">     if (scrollbar.orientation() == HorizontalScrollbar)
</span><span class="lines">@@ -259,13 +277,13 @@
</span><span class="cx"> {
</span><span class="cx">     GtkBorder margin;
</span><span class="cx">     gtk_style_context_get_margin(context, gtk_style_context_get_state(context), &amp;margin);
</span><del>-    rect.move(margin.left, margin.right);
</del><ins>+    rect.move(margin.left, margin.top);
</ins><span class="cx">     rect.contract(margin.left + margin.right, margin.top + margin.bottom);
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void ScrollbarThemeGtk::paintTrackBackground(GraphicsContext&amp; context, Scrollbar&amp; scrollbar, const IntRect&amp; rect)
</span><span class="cx"> {
</span><del>-    GRefPtr&lt;GtkStyleContext&gt; parentStyleContext = getOrCreateStyleContext(scrollbar.orientation());
</del><ins>+    GRefPtr&lt;GtkStyleContext&gt; parentStyleContext = getOrCreateStyleContext(&amp;scrollbar, StyleContextMode::Paint);
</ins><span class="cx">     // Paint the track background. If the trough-under-steppers property is true, this
</span><span class="cx">     // should be the full size of the scrollbar, but if is false, it should only be the
</span><span class="cx">     // track rect.
</span><span class="lines">@@ -281,14 +299,14 @@
</span><span class="cx"> 
</span><span class="cx"> void ScrollbarThemeGtk::paintScrollbarBackground(GraphicsContext&amp; context, Scrollbar&amp; scrollbar)
</span><span class="cx"> {
</span><del>-    GRefPtr&lt;GtkStyleContext&gt; styleContext = getOrCreateStyleContext(scrollbar.orientation());
</del><ins>+    GRefPtr&lt;GtkStyleContext&gt; styleContext = getOrCreateStyleContext(&amp;scrollbar, StyleContextMode::Paint);
</ins><span class="cx">     gtk_render_frame(styleContext.get(), context.platformContext()-&gt;cr(), scrollbar.x(), scrollbar.y(), scrollbar.width(), scrollbar.height());
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void ScrollbarThemeGtk::paintThumb(GraphicsContext&amp; context, Scrollbar&amp; scrollbar, const IntRect&amp; rect)
</span><span class="cx"> {
</span><span class="cx">     ScrollbarOrientation orientation = scrollbar.orientation();
</span><del>-    GRefPtr&lt;GtkStyleContext&gt; parentStyleContext = getOrCreateStyleContext(orientation);
</del><ins>+    GRefPtr&lt;GtkStyleContext&gt; parentStyleContext = getOrCreateStyleContext(&amp;scrollbar, StyleContextMode::Paint);
</ins><span class="cx">     GRefPtr&lt;GtkStyleContext&gt; troughStyleContext = createChildStyleContext(parentStyleContext.get(), &quot;trough&quot;);
</span><span class="cx">     GRefPtr&lt;GtkStyleContext&gt; styleContext = createChildStyleContext(troughStyleContext.get(), &quot;slider&quot;);
</span><span class="cx"> 
</span><span class="lines">@@ -300,6 +318,14 @@
</span><span class="cx">     gtk_style_context_set_state(styleContext.get(), static_cast&lt;GtkStateFlags&gt;(flags));
</span><span class="cx"> 
</span><span class="cx">     IntRect thumbRect(rect);
</span><ins>+    if (m_usesOverlayScrollbars &amp;&amp; scrollbar.hoveredPart() == NoPart) {
+        // When using overlay scrollbars we always claim the size of the scrollbar when hovered, so when
+        // drawing the indicator we need to adjust the rectangle to its actual size in indicator mode.
+        if (orientation == VerticalScrollbar)
+            thumbRect.move(scrollbar.width() - m_cachedProperties.thumbFatness, 0);
+        else
+            thumbRect.move(0, scrollbar.height() - m_cachedProperties.thumbFatness);
+    }
</ins><span class="cx">     adjustRectAccordingToMargin(styleContext.get(), thumbRect);
</span><span class="cx">     gtk_render_slider(styleContext.get(), context.platformContext()-&gt;cr(), thumbRect.x(), thumbRect.y(), thumbRect.width(), thumbRect.height(),
</span><span class="cx">         orientation == VerticalScrollbar ? GTK_ORIENTATION_VERTICAL : GTK_ORIENTATION_HORIZONTAL);
</span><span class="lines">@@ -308,7 +334,7 @@
</span><span class="cx"> void ScrollbarThemeGtk::paintButton(GraphicsContext&amp; context, Scrollbar&amp; scrollbar, const IntRect&amp; rect, ScrollbarPart part)
</span><span class="cx"> {
</span><span class="cx">     ScrollbarOrientation orientation = scrollbar.orientation();
</span><del>-    GRefPtr&lt;GtkStyleContext&gt; parentStyleContext = getOrCreateStyleContext(orientation);
</del><ins>+    GRefPtr&lt;GtkStyleContext&gt; parentStyleContext = getOrCreateStyleContext(&amp;scrollbar, StyleContextMode::Paint);
</ins><span class="cx">     GRefPtr&lt;GtkStyleContext&gt; styleContext = createChildStyleContext(parentStyleContext.get(), &quot;button&quot;);
</span><span class="cx"> 
</span><span class="cx">     unsigned flags = 0;
</span><span class="lines">@@ -355,8 +381,12 @@
</span><span class="cx">     if (graphicsContext.paintingDisabled())
</span><span class="cx">         return false;
</span><span class="cx"> 
</span><ins>+    double opacity = scrollbar.hoveredPart() == NoPart ? scrollbar.opacity() : 1;
+    if (!opacity)
+        return true;
+
</ins><span class="cx">     // Cache a new GtkStyleContext for the duration of this scope.
</span><del>-    TemporaryChange&lt;GRefPtr&lt;GtkStyleContext&gt;&gt; tempStyleContext(m_cachedStyleContext, getOrCreateStyleContext(scrollbar.orientation()));
</del><ins>+    TemporaryChange&lt;GRefPtr&lt;GtkStyleContext&gt;&gt; tempStyleContext(m_cachedStyleContext, getOrCreateStyleContext(&amp;scrollbar, StyleContextMode::Paint));
</ins><span class="cx"> 
</span><span class="cx">     // Create the ScrollbarControlPartMask based on the damageRect
</span><span class="cx">     ScrollbarControlPartMask scrollMask = NoPart;
</span><span class="lines">@@ -399,6 +429,31 @@
</span><span class="cx">             scrollMask |= ThumbPart;
</span><span class="cx">     }
</span><span class="cx"> 
</span><ins>+    if (m_usesOverlayScrollbars) {
+        // FIXME: Remove this check once 3.20 is released.
+#if GTK_CHECK_VERSION(3, 19, 8)
+        unsigned flags = 0;
+        if (scrollbar.hoveredPart() != NoPart)
+            flags |= GTK_STATE_FLAG_PRELIGHT;
+        if (scrollbar.pressedPart() != NoPart)
+            flags |= GTK_STATE_FLAG_ACTIVE;
+        double styleOpacity;
+        gtk_style_context_set_state(m_cachedStyleContext.get(), static_cast&lt;GtkStateFlags&gt;(flags));
+        gtk_style_context_get(m_cachedStyleContext.get(), gtk_style_context_get_state(m_cachedStyleContext.get()), &quot;opacity&quot;, &amp;styleOpacity, nullptr);
+        opacity *= styleOpacity;
+#else
+        opacity *= scrollbar.hoveredPart() == NoPart ? 0.4 : 0.7;
+#endif
+    }
+    if (!opacity)
+        return true;
+
+    if (opacity != 1) {
+        graphicsContext.save();
+        graphicsContext.clip(damageRect);
+        graphicsContext.beginTransparencyLayer(opacity);
+    }
+
</ins><span class="cx">     ScrollbarControlPartMask allButtons = BackButtonStartPart | BackButtonEndPart | ForwardButtonStartPart | ForwardButtonEndPart;
</span><span class="cx">     if (scrollMask &amp; TrackBGPart || scrollMask &amp; ThumbPart || scrollMask &amp; allButtons)
</span><span class="cx">         paintScrollbarBackground(graphicsContext, scrollbar);
</span><span class="lines">@@ -418,6 +473,11 @@
</span><span class="cx">     if (scrollMask &amp; ThumbPart)
</span><span class="cx">         paintThumb(graphicsContext, scrollbar, currentThumbRect);
</span><span class="cx"> 
</span><ins>+    if (opacity != 1) {
+        graphicsContext.endTransparencyLayer();
+        graphicsContext.restore();
+    }
+
</ins><span class="cx">     return true;
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="lines">@@ -434,7 +494,7 @@
</span><span class="cx"> 
</span><span class="cx"> IntSize ScrollbarThemeGtk::buttonSize(Scrollbar&amp; scrollbar)
</span><span class="cx"> {
</span><del>-    GRefPtr&lt;GtkStyleContext&gt; styleContext = getOrCreateStyleContext(scrollbar.orientation());
</del><ins>+    GRefPtr&lt;GtkStyleContext&gt; styleContext = getOrCreateStyleContext(&amp;scrollbar);
</ins><span class="cx">     if (scrollbar.orientation() == VerticalScrollbar)
</span><span class="cx">         return IntSize(m_cachedProperties.thumbFatness, m_cachedProperties.stepperSize);
</span><span class="cx"> 
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformgtkScrollbarThemeGtkh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/gtk/ScrollbarThemeGtk.h (195809 => 195810)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/gtk/ScrollbarThemeGtk.h        2016-01-29 09:58:02 UTC (rev 195809)
+++ trunk/Source/WebCore/platform/gtk/ScrollbarThemeGtk.h        2016-01-29 10:58:17 UTC (rev 195810)
</span><span class="lines">@@ -61,10 +61,14 @@
</span><span class="cx">     virtual double initialAutoscrollTimerDelay() override { return 0.20; }
</span><span class="cx">     virtual double autoscrollTimerDelay() override { return 0.02; }
</span><span class="cx">     virtual void themeChanged() override;
</span><ins>+    virtual bool usesOverlayScrollbars() const override { return m_usesOverlayScrollbars; }
+    // When using overlay scrollbars, always invalidate the whole scrollbar when entering/leaving.
+    virtual bool invalidateOnMouseEnterExit() override { return m_usesOverlayScrollbars; }
</ins><span class="cx"> 
</span><span class="cx"> private:
</span><span class="cx">     void updateThemeProperties();
</span><del>-    GRefPtr&lt;GtkStyleContext&gt; getOrCreateStyleContext(ScrollbarOrientation = VerticalScrollbar);
</del><ins>+    enum class StyleContextMode { Layout, Paint };
+    GRefPtr&lt;GtkStyleContext&gt; getOrCreateStyleContext(Scrollbar* = nullptr, StyleContextMode = StyleContextMode::Layout);
</ins><span class="cx"> 
</span><span class="cx">     IntSize buttonSize(Scrollbar&amp;);
</span><span class="cx"> 
</span><span class="lines">@@ -83,6 +87,7 @@
</span><span class="cx">     gboolean m_hasForwardButtonEndPart;
</span><span class="cx">     gboolean m_hasBackButtonStartPart;
</span><span class="cx">     gboolean m_hasBackButtonEndPart;
</span><ins>+    bool m_usesOverlayScrollbars { false };
</ins><span class="cx"> #endif // GTK_API_VERSION_2
</span><span class="cx"> };
</span><span class="cx"> 
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmacScrollAnimatorMach"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mac/ScrollAnimatorMac.h (195809 => 195810)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mac/ScrollAnimatorMac.h        2016-01-29 09:58:02 UTC (rev 195809)
+++ trunk/Source/WebCore/platform/mac/ScrollAnimatorMac.h        2016-01-29 10:58:17 UTC (rev 195810)
</span><span class="lines">@@ -95,17 +95,17 @@
</span><span class="cx">     
</span><span class="cx">     virtual void notifyPositionChanged(const FloatSize&amp; delta) override;
</span><span class="cx">     virtual void contentAreaWillPaint() const override;
</span><del>-    virtual void mouseEnteredContentArea() const override;
-    virtual void mouseExitedContentArea() const override;
-    virtual void mouseMovedInContentArea() const override;
</del><ins>+    virtual void mouseEnteredContentArea() override;
+    virtual void mouseExitedContentArea() override;
+    virtual void mouseMovedInContentArea() override;
</ins><span class="cx">     virtual void mouseEnteredScrollbar(Scrollbar*) const override;
</span><span class="cx">     virtual void mouseExitedScrollbar(Scrollbar*) const override;
</span><span class="cx">     virtual void mouseIsDownInScrollbar(Scrollbar*, bool) const override;
</span><span class="cx">     virtual void willStartLiveResize() override;
</span><span class="cx">     virtual void contentsResized() const override;
</span><span class="cx">     virtual void willEndLiveResize() override;
</span><del>-    virtual void contentAreaDidShow() const override;
-    virtual void contentAreaDidHide() const override;
</del><ins>+    virtual void contentAreaDidShow() override;
+    virtual void contentAreaDidHide() override;
</ins><span class="cx">     void didBeginScrollGesture() const;
</span><span class="cx">     void didEndScrollGesture() const;
</span><span class="cx">     void mayBeginScrollGesture() const;
</span></span></pre></div>
<a id="trunkSourceWebCoreplatformmacScrollAnimatorMacmm"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/platform/mac/ScrollAnimatorMac.mm (195809 => 195810)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/platform/mac/ScrollAnimatorMac.mm        2016-01-29 09:58:02 UTC (rev 195809)
+++ trunk/Source/WebCore/platform/mac/ScrollAnimatorMac.mm        2016-01-29 10:58:17 UTC (rev 195810)
</span><span class="lines">@@ -806,7 +806,7 @@
</span><span class="cx">     [m_scrollbarPainterController contentAreaWillDraw];
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-void ScrollAnimatorMac::mouseEnteredContentArea() const
</del><ins>+void ScrollAnimatorMac::mouseEnteredContentArea()
</ins><span class="cx"> {
</span><span class="cx">     if ([m_scrollbarPainterController overlayScrollerStateIsLocked])
</span><span class="cx">         return;
</span><span class="lines">@@ -814,7 +814,7 @@
</span><span class="cx">     [m_scrollbarPainterController mouseEnteredContentArea];
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-void ScrollAnimatorMac::mouseExitedContentArea() const
</del><ins>+void ScrollAnimatorMac::mouseExitedContentArea()
</ins><span class="cx"> {
</span><span class="cx">     if ([m_scrollbarPainterController overlayScrollerStateIsLocked])
</span><span class="cx">         return;
</span><span class="lines">@@ -822,7 +822,7 @@
</span><span class="cx">     [m_scrollbarPainterController mouseExitedContentArea];
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-void ScrollAnimatorMac::mouseMovedInContentArea() const
</del><ins>+void ScrollAnimatorMac::mouseMovedInContentArea()
</ins><span class="cx"> {
</span><span class="cx">     if ([m_scrollbarPainterController overlayScrollerStateIsLocked])
</span><span class="cx">         return;
</span><span class="lines">@@ -898,7 +898,7 @@
</span><span class="cx">     [m_scrollbarPainterController endLiveResize];
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-void ScrollAnimatorMac::contentAreaDidShow() const
</del><ins>+void ScrollAnimatorMac::contentAreaDidShow()
</ins><span class="cx"> {
</span><span class="cx">     if ([m_scrollbarPainterController overlayScrollerStateIsLocked])
</span><span class="cx">         return;
</span><span class="lines">@@ -906,7 +906,7 @@
</span><span class="cx">     [m_scrollbarPainterController windowOrderedIn];
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-void ScrollAnimatorMac::contentAreaDidHide() const
</del><ins>+void ScrollAnimatorMac::contentAreaDidHide()
</ins><span class="cx"> {
</span><span class="cx">     if ([m_scrollbarPainterController overlayScrollerStateIsLocked])
</span><span class="cx">         return;
</span></span></pre>
</div>
</div>

</body>
</html>