|
3 | 3 | // This is a script, and not included directly in the page, to control the total size of the book.
|
4 | 4 | // The TOC contains an entry for each page, so if each page includes a copy of the TOC,
|
5 | 5 | // the total size of the page becomes O(n**2).
|
6 |
| -var sidebarScrollbox = document.querySelector("#sidebar .sidebar-scrollbox"); |
7 |
| -sidebarScrollbox.innerHTML = '{{#toc}}{{/toc}}'; |
8 |
| -(function() { |
9 |
| - let current_page = document.location.href.toString(); |
10 |
| - if (current_page.endsWith("/")) { |
11 |
| - current_page += "index.html"; |
| 6 | +class MDBookSidebarScrollbox extends HTMLElement { |
| 7 | + constructor() { |
| 8 | + super(); |
12 | 9 | }
|
13 |
| - var links = sidebarScrollbox.querySelectorAll("a"); |
14 |
| - var l = links.length; |
15 |
| - for (var i = 0; i < l; ++i) { |
16 |
| - var link = links[i]; |
17 |
| - var href = link.getAttribute("href"); |
18 |
| - if (href && !href.startsWith("#") && !/^(?:[a-z+]+:)?\/\//.test(href)) { |
19 |
| - link.href = path_to_root + href; |
| 10 | + connectedCallback() { |
| 11 | + this.innerHTML = '{{#toc}}{{/toc}}'; |
| 12 | + // Set the current, active page, and reveal it if it's hidden |
| 13 | + let current_page = document.location.href.toString(); |
| 14 | + if (current_page.endsWith("/")) { |
| 15 | + current_page += "index.html"; |
20 | 16 | }
|
21 |
| - // The "index" page is supposed to alias the first chapter in the book. |
22 |
| - if (link.href === current_page || (i === 0 && path_to_root === "" && current_page.endsWith("/index.html"))) { |
23 |
| - link.classList.add("active"); |
24 |
| - var parent = link.parentElement; |
25 |
| - while (parent) { |
26 |
| - if (parent.tagName === "LI" && parent.previousElementSibling) { |
27 |
| - if (parent.previousElementSibling.classList.contains("chapter-item")) { |
28 |
| - parent.previousElementSibling.classList.add("expanded"); |
| 17 | + var links = Array.prototype.slice.call(this.querySelectorAll("a")); |
| 18 | + var l = links.length; |
| 19 | + for (var i = 0; i < l; ++i) { |
| 20 | + var link = links[i]; |
| 21 | + var href = link.getAttribute("href"); |
| 22 | + if (href && !href.startsWith("#") && !/^(?:[a-z+]+:)?\/\//.test(href)) { |
| 23 | + link.href = path_to_root + href; |
| 24 | + } |
| 25 | + // The "index" page is supposed to alias the first chapter in the book. |
| 26 | + if (link.href === current_page || (i === 0 && path_to_root === "" && current_page.endsWith("/index.html"))) { |
| 27 | + link.classList.add("active"); |
| 28 | + var parent = link.parentElement; |
| 29 | + if (parent && parent.classList.contains("chapter-item")) { |
| 30 | + parent.classList.add("expanded"); |
| 31 | + } |
| 32 | + while (parent) { |
| 33 | + if (parent.tagName === "LI" && parent.previousElementSibling) { |
| 34 | + if (parent.previousElementSibling.classList.contains("chapter-item")) { |
| 35 | + parent.previousElementSibling.classList.add("expanded"); |
| 36 | + } |
29 | 37 | }
|
| 38 | + parent = parent.parentElement; |
30 | 39 | }
|
31 |
| - parent = parent.parentElement; |
32 | 40 | }
|
33 | 41 | }
|
34 |
| - } |
35 |
| -})(); |
36 |
| - |
37 |
| -// Track and set sidebar scroll position |
38 |
| -sidebarScrollbox.addEventListener('click', function(e) { |
39 |
| - if (e.target.tagName === 'A') { |
40 |
| - sessionStorage.setItem('sidebar-scroll', sidebarScrollbox.scrollTop); |
41 |
| - } |
42 |
| -}, { passive: true }); |
43 |
| -var sidebarScrollTop = sessionStorage.getItem('sidebar-scroll'); |
44 |
| -sessionStorage.removeItem('sidebar-scroll'); |
45 |
| -if (sidebarScrollTop) { |
46 |
| - // preserve sidebar scroll position when navigating via links within sidebar |
47 |
| - sidebarScrollbox.scrollTop = sidebarScrollTop; |
48 |
| -} else { |
49 |
| - // scroll sidebar to current active section when navigating via "next/previous chapter" buttons |
50 |
| - var activeSection = document.querySelector('#sidebar .active'); |
51 |
| - if (activeSection) { |
52 |
| - activeSection.scrollIntoView({ block: 'center' }); |
| 42 | + // Track and set sidebar scroll position |
| 43 | + this.addEventListener('click', function(e) { |
| 44 | + if (e.target.tagName === 'A') { |
| 45 | + sessionStorage.setItem('sidebar-scroll', this.scrollTop); |
| 46 | + } |
| 47 | + }, { passive: true }); |
| 48 | + var sidebarScrollTop = sessionStorage.getItem('sidebar-scroll'); |
| 49 | + sessionStorage.removeItem('sidebar-scroll'); |
| 50 | + if (sidebarScrollTop) { |
| 51 | + // preserve sidebar scroll position when navigating via links within sidebar |
| 52 | + this.scrollTop = sidebarScrollTop; |
| 53 | + } else { |
| 54 | + // scroll sidebar to current active section when navigating via "next/previous chapter" buttons |
| 55 | + var activeSection = document.querySelector('#sidebar .active'); |
| 56 | + if (activeSection) { |
| 57 | + activeSection.scrollIntoView({ block: 'center' }); |
| 58 | + } |
| 59 | + } |
| 60 | + // Toggle buttons |
| 61 | + var sidebarAnchorToggles = document.querySelectorAll('#sidebar a.toggle'); |
| 62 | + function toggleSection(ev) { |
| 63 | + ev.currentTarget.parentElement.classList.toggle('expanded'); |
| 64 | + } |
| 65 | + Array.from(sidebarAnchorToggles).forEach(function (el) { |
| 66 | + el.addEventListener('click', toggleSection); |
| 67 | + }); |
53 | 68 | }
|
54 | 69 | }
|
| 70 | +window.customElements.define("mdbook-sidebar-scrollbox", MDBookSidebarScrollbox); |
0 commit comments