mediawiki.action.view.redirect: Explicitly scroll to element in hash
authorjdlrobson <jdlrobson@gmail.com>
Mon, 14 Dec 2015 23:52:39 +0000 (15:52 -0800)
committerTimo Tijhof <krinklemail@gmail.com>
Fri, 18 Dec 2015 00:28:02 +0000 (16:28 -0800)
Specification of replaceState doesn't state whether the browser should scroll to the element
matching the fragment [1]. It only determines how to alter the history stack.
(The fact it doesn't impact UI is sometimes a desired behaviour [2)]

As a result force a scroll to the element. Harmless if element is already present.

[1] http://www.w3.org/TR/2011/WD-html5-20110113/history.html#the-history-interface
[2] http://lea.verou.me/2011/05/change-url-hash-without-page-jump/

Bug: T110501
Change-Id: I7440f7a6a6dd20d984da1834007d581324fb96f4

resources/src/mediawiki.action/mediawiki.action.view.redirect.js

index e66d8f6..29a5a79 100644 (file)
@@ -9,7 +9,7 @@
        var profile = $.client.profile(),
                canonical = mw.config.get( 'wgInternalRedirectTargetUrl' ),
                fragment = null,
-               shouldChangeFragment, index;
+               node, shouldChangeFragment, index;
 
        index = canonical.indexOf( '#' );
        if ( index !== -1 ) {
                        canonical += location.hash;
                }
 
-               // This will also cause the browser to scroll to given fragment
+               // Note that this will update the hash in a modern browser, retaining back behaviour
                history.replaceState( /*data=*/ history.state, /*title=*/ document.title, /*url=*/ canonical );
-
-               // â€¦except for IE 10 and 11. Prod it with a location.hash change.
-               if ( shouldChangeFragment && profile.name === 'msie' && profile.versionNumber >= 10 ) {
-                       location.hash = fragment;
+               if ( shouldChangeFragment ) {
+                       // Specification for history.replaceState() doesn't require browser to scroll,
+                       // so scroll to be sure (see also T110501). Support for IE9 and IE10.
+                       node = document.getElementById( fragment.slice( 1 ) );
+                       if ( node ) {
+                               node.scrollIntoView();
+                       }
                }
 
        } else if ( shouldChangeFragment ) {