mirror of
https://github.com/alrayyes/wiki.git
synced 2025-05-31 03:11:01 +00:00
modern toc tweaks
This commit is contained in:
parent
9d2024b11c
commit
917d5791ac
17 changed files with 318 additions and 58 deletions
quartz/components
|
@ -1,3 +1,4 @@
|
|||
// @ts-ignore
|
||||
import clipboardScript from './scripts/clipboard.inline'
|
||||
import clipboardStyle from './styles/clipboard.scss'
|
||||
import { QuartzComponentConstructor, QuartzComponentProps } from "./types"
|
||||
|
|
|
@ -1,38 +1,65 @@
|
|||
import { QuartzComponentConstructor, QuartzComponentProps } from "./types"
|
||||
import style from "./styles/toc.scss"
|
||||
|
||||
import legacyStyle from "./styles/legacyToc.scss"
|
||||
import modernStyle from "./styles/toc.scss"
|
||||
|
||||
interface Options {
|
||||
layout: 'modern' | 'quartz-3'
|
||||
layout: 'modern' | 'legacy'
|
||||
}
|
||||
|
||||
const defaultOptions: Options = {
|
||||
layout: 'quartz-3'
|
||||
layout: 'modern'
|
||||
}
|
||||
|
||||
export default ((opts?: Partial<Options>) => {
|
||||
const layout = opts?.layout ?? defaultOptions.layout
|
||||
if (layout === "modern") {
|
||||
return function() {
|
||||
return null // TODO (make this look like nextra)
|
||||
}
|
||||
} else {
|
||||
function TableOfContents({ fileData }: QuartzComponentProps) {
|
||||
if (!fileData.toc) {
|
||||
return null
|
||||
}
|
||||
|
||||
return <details class="toc" open>
|
||||
<summary><h3>Table of Contents</h3></summary>
|
||||
<ul>
|
||||
{fileData.toc.map(tocEntry => <li key={tocEntry.slug} class={`depth-${tocEntry.depth}`}>
|
||||
<a href={`#${tocEntry.slug}`}>{tocEntry.text}</a>
|
||||
</li>)}
|
||||
</ul>
|
||||
</details>
|
||||
function TableOfContents({ fileData }: QuartzComponentProps) {
|
||||
if (!fileData.toc) {
|
||||
return null
|
||||
}
|
||||
|
||||
TableOfContents.css = style
|
||||
return TableOfContents
|
||||
return <details class="toc" open>
|
||||
<summary><h3>Table of Contents</h3></summary>
|
||||
<ul>
|
||||
{fileData.toc.map(tocEntry => <li key={tocEntry.slug} class={`depth-${tocEntry.depth}`}>
|
||||
<a href={`#${tocEntry.slug}`} data-for={tocEntry.slug}>{tocEntry.text}</a>
|
||||
</li>)}
|
||||
</ul>
|
||||
</details>
|
||||
}
|
||||
|
||||
TableOfContents.css = layout === "modern" ? modernStyle : legacyStyle
|
||||
|
||||
if (layout === "modern") {
|
||||
TableOfContents.afterDOMLoaded = `
|
||||
const bufferPx = 150
|
||||
const observer = new IntersectionObserver(entries => {
|
||||
for (const entry of entries) {
|
||||
const slug = entry.target.id
|
||||
const tocEntryElement = document.querySelector(\`a[data-for="$\{slug\}"]\`)
|
||||
const windowHeight = entry.rootBounds?.height
|
||||
if (windowHeight && tocEntryElement) {
|
||||
if (entry.boundingClientRect.y < windowHeight) {
|
||||
tocEntryElement.classList.add("in-view")
|
||||
} else {
|
||||
tocEntryElement.classList.remove("in-view")
|
||||
}
|
||||
}
|
||||
}
|
||||
})
|
||||
|
||||
function init() {
|
||||
const headers = document.querySelectorAll("h1[id], h2[id], h3[id], h4[id], h5[id], h6[id]")
|
||||
headers.forEach(header => observer.observe(header))
|
||||
}
|
||||
|
||||
init()
|
||||
|
||||
document.addEventListener("spa_nav", (e) => {
|
||||
observer.disconnect()
|
||||
init()
|
||||
})
|
||||
`
|
||||
}
|
||||
|
||||
return TableOfContents
|
||||
}) satisfies QuartzComponentConstructor
|
||||
|
|
|
@ -1,6 +1,3 @@
|
|||
const description = "Initialize copy for codeblocks"
|
||||
export default description
|
||||
|
||||
const svgCopy =
|
||||
'<svg aria-hidden="true" height="16" viewBox="0 0 16 16" version="1.1" width="16" data-view-component="true"><path fill-rule="evenodd" d="M0 6.75C0 5.784.784 5 1.75 5h1.5a.75.75 0 010 1.5h-1.5a.25.25 0 00-.25.25v7.5c0 .138.112.25.25.25h7.5a.25.25 0 00.25-.25v-1.5a.75.75 0 011.5 0v1.5A1.75 1.75 0 019.25 16h-7.5A1.75 1.75 0 010 14.25v-7.5z"></path><path fill-rule="evenodd" d="M5 1.75C5 .784 5.784 0 6.75 0h7.5C15.216 0 16 .784 16 1.75v7.5A1.75 1.75 0 0114.25 11h-7.5A1.75 1.75 0 015 9.25v-7.5zm1.75-.25a.25.25 0 00-.25.25v7.5c0 .138.112.25.25.25h7.5a.25.25 0 00.25-.25v-7.5a.25.25 0 00-.25-.25h-7.5z"></path></svg>'
|
||||
const svgCheck =
|
||||
|
|
|
@ -29,6 +29,11 @@ const getOpts = ({ target }: Event): { url: URL, scroll?: boolean } | undefined
|
|||
return { url: new URL(href), scroll: 'routerNoscroll' in a.dataset ? false : undefined }
|
||||
}
|
||||
|
||||
function notifyNav(slug: string) {
|
||||
const event = new CustomEvent("spa_nav", { detail: { slug } })
|
||||
document.dispatchEvent(event)
|
||||
}
|
||||
|
||||
let p: DOMParser
|
||||
async function navigate(url: URL, isBack: boolean = false) {
|
||||
p = p || new DOMParser()
|
||||
|
@ -64,9 +69,7 @@ async function navigate(url: URL, isBack: boolean = false) {
|
|||
const elementsToAdd = html.head.querySelectorAll(':not([spa-preserve])')
|
||||
elementsToAdd.forEach(el => document.head.appendChild(el))
|
||||
|
||||
if (!document.activeElement?.closest('[data-persist]')) {
|
||||
document.body.focus()
|
||||
}
|
||||
notifyNav(document.body.dataset.slug!)
|
||||
delete announcer.dataset.persist
|
||||
}
|
||||
|
||||
|
|
27
quartz/components/styles/legacyToc.scss
Normal file
27
quartz/components/styles/legacyToc.scss
Normal file
|
@ -0,0 +1,27 @@
|
|||
details.toc {
|
||||
& summary {
|
||||
cursor: pointer;
|
||||
|
||||
&::marker {
|
||||
color: var(--dark);
|
||||
}
|
||||
|
||||
& > * {
|
||||
padding-left: 0.25rem;
|
||||
display: inline-block;
|
||||
margin: 0;
|
||||
}
|
||||
}
|
||||
|
||||
& ul {
|
||||
list-style: none;
|
||||
margin: 0.5rem 1.25rem;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
@for $i from 1 through 6 {
|
||||
& .depth-#{$i} {
|
||||
padding-left: calc(1rem * #{$i});
|
||||
}
|
||||
}
|
||||
}
|
|
@ -2,24 +2,36 @@ details.toc {
|
|||
& summary {
|
||||
cursor: pointer;
|
||||
|
||||
&::marker {
|
||||
color: var(--dark);
|
||||
list-style: none;
|
||||
&::marker, &::-webkit-details-marker {
|
||||
display: none;
|
||||
}
|
||||
|
||||
& > * {
|
||||
padding-left: 0.25rem;
|
||||
display: inline-block;
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
& > h3 {
|
||||
font-size: 1rem;
|
||||
}
|
||||
}
|
||||
|
||||
& ul {
|
||||
list-style: none;
|
||||
margin: 0.5rem 1.25rem;
|
||||
margin: 0.5rem 0;
|
||||
padding: 0;
|
||||
& > li > a {
|
||||
color: var(--dark);
|
||||
opacity: 0.35;
|
||||
transition: 0.5s ease opacity;
|
||||
&.in-view {
|
||||
opacity: 0.75;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@for $i from 1 through 6 {
|
||||
@for $i from 0 through 6 {
|
||||
& .depth-#{$i} {
|
||||
padding-left: calc(1rem * #{$i});
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue