mediawiki-skins-Citizen/resources/skins.citizen.scripts.toc/skins.citizen.scripts.toc.js

91 lines
2.1 KiB
JavaScript
Raw Normal View History

2019-08-15 17:40:13 +00:00
/*
* Citizen - ToC JS
* https://starcitizen.tools
*
* Smooth scroll fallback and Scrollspy
*/
2020-06-17 03:16:45 +00:00
/**
* Implement smooth scroll when an item in table of content is clicked.
*
2020-06-17 03:16:45 +00:00
* @constructor
*/
2020-02-15 22:52:32 +00:00
function SmoothScroll() {
2020-02-15 23:01:01 +00:00
var navLinks, eventListener, link;
2020-02-16 00:20:20 +00:00
if ( !( 'scrollBehavior' in document.documentElement.style ) ) {
navLinks = document.querySelectorAll( '#toc a' );
eventListener = function clickHandler( e ) {
2020-02-15 23:01:01 +00:00
e.preventDefault();
2020-02-16 00:20:20 +00:00
e.target.scrollIntoView( {
behavior: 'smooth'
} );
2020-02-15 23:01:01 +00:00
};
2019-12-25 23:24:31 +00:00
2020-02-16 00:20:20 +00:00
for ( link in navLinks ) {
if ( Object.prototype.hasOwnProperty.call( navLinks, link ) ) {
navLinks[ link ].addEventListener( 'click', eventListener );
2020-02-15 22:56:29 +00:00
}
}
}
2020-02-15 22:55:31 +00:00
}
2019-08-15 17:40:13 +00:00
2020-06-17 03:16:45 +00:00
/**
* Add active HTML class to items in table of content based on user viewport.
*
2020-06-17 03:16:45 +00:00
* @constructor
*/
2020-02-15 22:52:32 +00:00
function ScrollSpy() {
2020-02-16 00:20:20 +00:00
var sections = document.querySelectorAll( '.mw-headline' );
window.addEventListener( 'scroll', function () {
2020-02-15 23:05:56 +00:00
var scrollPos = document.documentElement.scrollTop || document.body.scrollTop,
2020-02-15 23:12:09 +00:00
section, id, node, active;
2019-08-15 17:40:13 +00:00
2020-02-16 00:20:20 +00:00
for ( section in sections ) {
2020-02-15 23:01:01 +00:00
if (
2020-02-16 00:20:20 +00:00
Object.prototype.hasOwnProperty.call( sections, section ) &&
sections[ section ].offsetTop <= scrollPos
2020-02-15 23:01:01 +00:00
) {
2020-02-16 00:20:20 +00:00
id = mw.util.escapeIdForAttribute( sections[ section ].id );
node = document.querySelector( "a[href='#" + id + "']" ).parentNode;
active = document.querySelector( '.active' );
if ( active !== null ) {
active.classList.remove( 'active' );
2020-02-15 22:56:29 +00:00
}
2020-02-16 00:20:20 +00:00
if ( node !== null ) {
node.classList.add( 'active' );
2020-02-15 22:56:29 +00:00
}
}
}
2020-02-16 00:20:20 +00:00
} );
2020-02-15 22:55:31 +00:00
}
2020-06-17 03:16:45 +00:00
/**
* Run SmoothScroll() and ScrollSpy() when table of content is present.
*
2020-06-17 03:16:45 +00:00
* @constructor
*/
2020-02-15 22:52:32 +00:00
function CheckToC() {
2020-02-16 00:20:20 +00:00
if ( document.getElementById( 'toc' ) ) {
2020-02-15 22:56:29 +00:00
SmoothScroll();
ScrollSpy();
}
2020-02-15 22:55:31 +00:00
}
2020-08-12 16:37:43 +00:00
function main() {
if ( document.readyState !== 'loading' ) {
CheckToC();
} else if ( document.addEventListener ) {
// All modern browsers to register DOMContentLoaded
document.addEventListener( 'DOMContentLoaded', CheckToC );
} else {
// Old IE browsers
document.attachEvent( 'onreadystatechange', function () {
if ( document.readyState === 'complete' ) {
CheckToC();
}
} );
}
2020-02-16 00:20:20 +00:00
}
2020-08-12 16:37:43 +00:00
main();