Aff table of contents if the toc variable is truthy
This commit is contained in:
parent
915b6a6b05
commit
c8fc0803e3
|
@ -0,0 +1,68 @@
|
||||||
|
/* Article Table of Contents */
|
||||||
|
.toc {
|
||||||
|
background-color: var(--clr-quote-bg);
|
||||||
|
max-width: max-content;
|
||||||
|
padding: 1rem 1.3rem 0.3rem 1.3rem;
|
||||||
|
margin-top: 1rem;
|
||||||
|
outline: 1px solid var(--clr-title-border);
|
||||||
|
position: relative;
|
||||||
|
border-radius: 0.4rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.toc-heading {
|
||||||
|
font-size: 1.1rem;
|
||||||
|
font-weight: 700;
|
||||||
|
margin-bottom: 0.5rem;
|
||||||
|
margin-right: 2rem;
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
|
||||||
|
.toc ol {
|
||||||
|
border-top: 1px solid var(--clr-title-border);
|
||||||
|
padding: 0.8em 0 0 1em;
|
||||||
|
line-height: 1.8;
|
||||||
|
}
|
||||||
|
|
||||||
|
.toc ol ul {
|
||||||
|
list-style-type: disc;
|
||||||
|
line-height: 1.5;
|
||||||
|
padding-left: 1em;
|
||||||
|
}
|
||||||
|
|
||||||
|
.toc a {
|
||||||
|
font-size: 1.1rem;
|
||||||
|
padding-left: 0.4rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.toc ul a {
|
||||||
|
padding: 0;
|
||||||
|
font-size: 1rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Sidebar Table of Contents */
|
||||||
|
.sidebar__toc {
|
||||||
|
position: sticky;
|
||||||
|
top: 4rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.sidebar__toc-title {
|
||||||
|
font-size: 1.3rem;
|
||||||
|
font-weight: bold;
|
||||||
|
}
|
||||||
|
|
||||||
|
.sidebar__toc ol {
|
||||||
|
list-style: none;
|
||||||
|
margin-left: 0;
|
||||||
|
padding-left: 0;
|
||||||
|
font-size: 1rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.sidebar__toc ol li {
|
||||||
|
margin-bottom: 0.5em;
|
||||||
|
}
|
||||||
|
|
||||||
|
.sidebar__toc ol ul {
|
||||||
|
padding-top: 0.5em;
|
||||||
|
padding-left: 1.25rem;
|
||||||
|
list-style-type: disc;
|
||||||
|
}
|
|
@ -0,0 +1,68 @@
|
||||||
|
/* Article Table of Contents */
|
||||||
|
.toc {
|
||||||
|
background-color: var(--clr-quote-bg);
|
||||||
|
max-width: max-content;
|
||||||
|
padding: 1rem 1.3rem 0.3rem 1.3rem;
|
||||||
|
margin-top: 1rem;
|
||||||
|
outline: 1px solid var(--clr-title-border);
|
||||||
|
position: relative;
|
||||||
|
border-radius: 0.4rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.toc-heading {
|
||||||
|
font-size: 1.1rem;
|
||||||
|
font-weight: 700;
|
||||||
|
margin-bottom: 0.5rem;
|
||||||
|
margin-right: 2rem;
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
|
||||||
|
.toc ol {
|
||||||
|
border-top: 1px solid var(--clr-title-border);
|
||||||
|
padding: 0.8em 0 0 1em;
|
||||||
|
line-height: 1.8;
|
||||||
|
}
|
||||||
|
|
||||||
|
.toc ol ul {
|
||||||
|
list-style-type: disc;
|
||||||
|
line-height: 1.5;
|
||||||
|
padding-left: 1em;
|
||||||
|
}
|
||||||
|
|
||||||
|
.toc a {
|
||||||
|
font-size: 1.1rem;
|
||||||
|
padding-left: 0.4rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.toc ul a {
|
||||||
|
padding: 0;
|
||||||
|
font-size: 1rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Sidebar Table of Contents */
|
||||||
|
.sidebar__toc {
|
||||||
|
position: sticky;
|
||||||
|
top: 4rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.sidebar__toc-title {
|
||||||
|
font-size: 1.3rem;
|
||||||
|
font-weight: bold;
|
||||||
|
}
|
||||||
|
|
||||||
|
.sidebar__toc ol {
|
||||||
|
list-style: none;
|
||||||
|
margin-left: 0;
|
||||||
|
padding-left: 0;
|
||||||
|
font-size: 1rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.sidebar__toc ol li {
|
||||||
|
margin-bottom: 0.5em;
|
||||||
|
}
|
||||||
|
|
||||||
|
.sidebar__toc ol ul {
|
||||||
|
padding-top: 0.5em;
|
||||||
|
padding-left: 1.25rem;
|
||||||
|
list-style-type: disc;
|
||||||
|
}
|
|
@ -0,0 +1,76 @@
|
||||||
|
// Auto generate table of contents
|
||||||
|
// Code based on https://techindetail.com/table-of-contents-javascript/
|
||||||
|
window.addEventListener('DOMContentLoaded', (event) => {
|
||||||
|
const article = document.querySelector("article");
|
||||||
|
const headings = article.querySelectorAll("h2, h3");
|
||||||
|
const toc = document.querySelector(".toc");
|
||||||
|
const tocSidebar = document.querySelector(".sidebar__toc");
|
||||||
|
const leftSidebar = document.querySelector('.left-sidebar');
|
||||||
|
const totalHeadings = headings.length;
|
||||||
|
let tocOl = document.createElement("ol");
|
||||||
|
let tocFragment = new DocumentFragment();
|
||||||
|
let mainLi = null;
|
||||||
|
let subUl = null;
|
||||||
|
let subLi = null;
|
||||||
|
let isSibling = false;
|
||||||
|
|
||||||
|
if (totalHeadings > 1) {
|
||||||
|
for (let element of headings) {
|
||||||
|
let anchor = document.createElement("a");
|
||||||
|
let anchorText = element.innerText;
|
||||||
|
anchor.innerText = anchorText;
|
||||||
|
let elementId = anchorText.replaceAll(" ", "-").toLowerCase();
|
||||||
|
anchor.href = "#" + elementId;
|
||||||
|
element.id = elementId;
|
||||||
|
let level = element.nodeName;
|
||||||
|
|
||||||
|
if ("H3" === level) {
|
||||||
|
if (mainLi) {
|
||||||
|
subLi = document.createElement("li");
|
||||||
|
subLi.appendChild(anchor);
|
||||||
|
|
||||||
|
if (isSibling === false) {
|
||||||
|
subUl = document.createElement("ul");
|
||||||
|
}
|
||||||
|
subUl.appendChild(subLi);
|
||||||
|
mainLi.appendChild(subUl);
|
||||||
|
|
||||||
|
isSibling = true;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
mainLi = document.createElement("li");
|
||||||
|
mainLi.appendChild(anchor);
|
||||||
|
tocFragment.appendChild(mainLi);
|
||||||
|
isSibling = false;
|
||||||
|
subUl = null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
tocOl.append(tocFragment);
|
||||||
|
toc.append(tocOl);
|
||||||
|
|
||||||
|
const tocClone = tocOl.cloneNode(true);
|
||||||
|
if (tocSidebar) {
|
||||||
|
tocSidebar.appendChild(tocClone);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
toc.classList.add('hidden');
|
||||||
|
leftSidebar.classList.add('hidden');
|
||||||
|
}
|
||||||
|
|
||||||
|
// Close article ToC accordion and the left sidebar for small screen sizes
|
||||||
|
if (window.innerWidth < 480) {
|
||||||
|
toc.removeAttribute("open");
|
||||||
|
leftSidebar.classList.add("hidden");
|
||||||
|
} else {
|
||||||
|
toc.setAttribute("open", true);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Remove the stickiness of the sidebar ToC if it is larger than screen height
|
||||||
|
function preventSidebarOverflow() {
|
||||||
|
if (document.documentElement.clientHeight < tocSidebar.offsetHeight + 50) {
|
||||||
|
tocSidebar.style.marginTop = "0";
|
||||||
|
tocSidebar.style.position = "static";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
preventSidebarOverflow();
|
||||||
|
});
|
|
@ -14,6 +14,7 @@
|
||||||
|
|
||||||
|
|
||||||
<link rel="stylesheet" href="/assets/css/main.css">
|
<link rel="stylesheet" href="/assets/css/main.css">
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
@ -25,6 +26,7 @@
|
||||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Sans:ital,wght@0,100..900;1,100..900&display=swap" rel="stylesheet">
|
<link href="https://fonts.googleapis.com/css2?family=Noto+Sans:ital,wght@0,100..900;1,100..900&display=swap" rel="stylesheet">
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
<link rel="apple-touch-icon" sizes="180x180" href="/assets/favicon/apple-touch-icon.png">
|
<link rel="apple-touch-icon" sizes="180x180" href="/assets/favicon/apple-touch-icon.png">
|
||||||
<link rel="icon" type="image/png" sizes="32x32" href="/assets/favicon/favicon-32x32.png">
|
<link rel="icon" type="image/png" sizes="32x32" href="/assets/favicon/favicon-32x32.png">
|
||||||
<link rel="icon" type="image/png" sizes="16x16" href="/assets/favicon/favicon-16x16.png">
|
<link rel="icon" type="image/png" sizes="16x16" href="/assets/favicon/favicon-16x16.png">
|
||||||
|
@ -33,6 +35,7 @@
|
||||||
|
|
||||||
<script src="/assets/js/navbar.js" defer></script>
|
<script src="/assets/js/navbar.js" defer></script>
|
||||||
<script src="/assets/js/events.js" defer></script>
|
<script src="/assets/js/events.js" defer></script>
|
||||||
|
|
||||||
|
|
||||||
<title>Home | Leilukin's Hub</title>
|
<title>Home | Leilukin's Hub</title>
|
||||||
</head>
|
</head>
|
||||||
|
|
|
@ -14,10 +14,14 @@
|
||||||
|
|
||||||
{# CSS #}
|
{# CSS #}
|
||||||
<link rel="stylesheet" href="{{'/assets/css/main.css' | url | safe}}">
|
<link rel="stylesheet" href="{{'/assets/css/main.css' | url | safe}}">
|
||||||
|
{% if toc %}
|
||||||
|
<link rel="stylesheet" href="{{'/assets/css/toc.css' | url | safe}}">
|
||||||
|
{% endif %}
|
||||||
|
|
||||||
{# CDNs #}
|
{# CDNs #}
|
||||||
{% include "components/cdn.njk" %}
|
{% include "components/cdn.njk" %}
|
||||||
|
|
||||||
|
{# Favicon #}
|
||||||
<link rel="apple-touch-icon" sizes="180x180" href="/assets/favicon/apple-touch-icon.png">
|
<link rel="apple-touch-icon" sizes="180x180" href="/assets/favicon/apple-touch-icon.png">
|
||||||
<link rel="icon" type="image/png" sizes="32x32" href="/assets/favicon/favicon-32x32.png">
|
<link rel="icon" type="image/png" sizes="32x32" href="/assets/favicon/favicon-32x32.png">
|
||||||
<link rel="icon" type="image/png" sizes="16x16" href="/assets/favicon/favicon-16x16.png">
|
<link rel="icon" type="image/png" sizes="16x16" href="/assets/favicon/favicon-16x16.png">
|
||||||
|
@ -26,6 +30,7 @@
|
||||||
{# JavaScript #}
|
{# JavaScript #}
|
||||||
<script src="/assets/js/navbar.js" defer></script>
|
<script src="/assets/js/navbar.js" defer></script>
|
||||||
<script src="/assets/js/events.js" defer></script>
|
<script src="/assets/js/events.js" defer></script>
|
||||||
|
{% if toc %} <script src="/assets/js/toc.js" defer></script> {% endif %}
|
||||||
|
|
||||||
<title>{{ title }} | Leilukin's Hub</title>
|
<title>{{ title }} | Leilukin's Hub</title>
|
||||||
</head>
|
</head>
|
||||||
|
|
|
@ -0,0 +1,68 @@
|
||||||
|
/* Article Table of Contents */
|
||||||
|
.toc {
|
||||||
|
background-color: var(--clr-quote-bg);
|
||||||
|
max-width: max-content;
|
||||||
|
padding: 1rem 1.3rem 0.3rem 1.3rem;
|
||||||
|
margin-top: 1rem;
|
||||||
|
outline: 1px solid var(--clr-title-border);
|
||||||
|
position: relative;
|
||||||
|
border-radius: 0.4rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.toc-heading {
|
||||||
|
font-size: 1.1rem;
|
||||||
|
font-weight: 700;
|
||||||
|
margin-bottom: 0.5rem;
|
||||||
|
margin-right: 2rem;
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
|
||||||
|
.toc ol {
|
||||||
|
border-top: 1px solid var(--clr-title-border);
|
||||||
|
padding: 0.8em 0 0 1em;
|
||||||
|
line-height: 1.8;
|
||||||
|
}
|
||||||
|
|
||||||
|
.toc ol ul {
|
||||||
|
list-style-type: disc;
|
||||||
|
line-height: 1.5;
|
||||||
|
padding-left: 1em;
|
||||||
|
}
|
||||||
|
|
||||||
|
.toc a {
|
||||||
|
font-size: 1.1rem;
|
||||||
|
padding-left: 0.4rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.toc ul a {
|
||||||
|
padding: 0;
|
||||||
|
font-size: 1rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Sidebar Table of Contents */
|
||||||
|
.sidebar__toc {
|
||||||
|
position: sticky;
|
||||||
|
top: 4rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.sidebar__toc-title {
|
||||||
|
font-size: 1.3rem;
|
||||||
|
font-weight: bold;
|
||||||
|
}
|
||||||
|
|
||||||
|
.sidebar__toc ol {
|
||||||
|
list-style: none;
|
||||||
|
margin-left: 0;
|
||||||
|
padding-left: 0;
|
||||||
|
font-size: 1rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.sidebar__toc ol li {
|
||||||
|
margin-bottom: 0.5em;
|
||||||
|
}
|
||||||
|
|
||||||
|
.sidebar__toc ol ul {
|
||||||
|
padding-top: 0.5em;
|
||||||
|
padding-left: 1.25rem;
|
||||||
|
list-style-type: disc;
|
||||||
|
}
|
|
@ -0,0 +1,76 @@
|
||||||
|
// Auto generate table of contents
|
||||||
|
// Code based on https://techindetail.com/table-of-contents-javascript/
|
||||||
|
window.addEventListener('DOMContentLoaded', (event) => {
|
||||||
|
const article = document.querySelector("article");
|
||||||
|
const headings = article.querySelectorAll("h2, h3");
|
||||||
|
const toc = document.querySelector(".toc");
|
||||||
|
const tocSidebar = document.querySelector(".sidebar__toc");
|
||||||
|
const leftSidebar = document.querySelector('.left-sidebar');
|
||||||
|
const totalHeadings = headings.length;
|
||||||
|
let tocOl = document.createElement("ol");
|
||||||
|
let tocFragment = new DocumentFragment();
|
||||||
|
let mainLi = null;
|
||||||
|
let subUl = null;
|
||||||
|
let subLi = null;
|
||||||
|
let isSibling = false;
|
||||||
|
|
||||||
|
if (totalHeadings > 1) {
|
||||||
|
for (let element of headings) {
|
||||||
|
let anchor = document.createElement("a");
|
||||||
|
let anchorText = element.innerText;
|
||||||
|
anchor.innerText = anchorText;
|
||||||
|
let elementId = anchorText.replaceAll(" ", "-").toLowerCase();
|
||||||
|
anchor.href = "#" + elementId;
|
||||||
|
element.id = elementId;
|
||||||
|
let level = element.nodeName;
|
||||||
|
|
||||||
|
if ("H3" === level) {
|
||||||
|
if (mainLi) {
|
||||||
|
subLi = document.createElement("li");
|
||||||
|
subLi.appendChild(anchor);
|
||||||
|
|
||||||
|
if (isSibling === false) {
|
||||||
|
subUl = document.createElement("ul");
|
||||||
|
}
|
||||||
|
subUl.appendChild(subLi);
|
||||||
|
mainLi.appendChild(subUl);
|
||||||
|
|
||||||
|
isSibling = true;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
mainLi = document.createElement("li");
|
||||||
|
mainLi.appendChild(anchor);
|
||||||
|
tocFragment.appendChild(mainLi);
|
||||||
|
isSibling = false;
|
||||||
|
subUl = null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
tocOl.append(tocFragment);
|
||||||
|
toc.append(tocOl);
|
||||||
|
|
||||||
|
const tocClone = tocOl.cloneNode(true);
|
||||||
|
if (tocSidebar) {
|
||||||
|
tocSidebar.appendChild(tocClone);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
toc.classList.add('hidden');
|
||||||
|
leftSidebar.classList.add('hidden');
|
||||||
|
}
|
||||||
|
|
||||||
|
// Close article ToC accordion and the left sidebar for small screen sizes
|
||||||
|
if (window.innerWidth < 480) {
|
||||||
|
toc.removeAttribute("open");
|
||||||
|
leftSidebar.classList.add("hidden");
|
||||||
|
} else {
|
||||||
|
toc.setAttribute("open", true);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Remove the stickiness of the sidebar ToC if it is larger than screen height
|
||||||
|
function preventSidebarOverflow() {
|
||||||
|
if (document.documentElement.clientHeight < tocSidebar.offsetHeight + 50) {
|
||||||
|
tocSidebar.style.marginTop = "0";
|
||||||
|
tocSidebar.style.position = "static";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
preventSidebarOverflow();
|
||||||
|
});
|
Loading…
Reference in New Issue