mirror of
https://github.com/eliasstepanik/strudel-docker.git
synced 2026-01-21 10:38:37 +00:00
basic style for toc + further cleanup
This commit is contained in:
parent
bc7a84e462
commit
7efaff4f6f
@ -12,3 +12,5 @@ tailwind.config.js
|
|||||||
vite.config.js
|
vite.config.js
|
||||||
/**/dist/**/*
|
/**/dist/**/*
|
||||||
!**/*.mjs
|
!**/*.mjs
|
||||||
|
**/*.tsx
|
||||||
|
**/*.ts
|
||||||
|
|||||||
@ -1,40 +0,0 @@
|
|||||||
---
|
|
||||||
type Props = {
|
|
||||||
size: number;
|
|
||||||
};
|
|
||||||
const { size } = Astro.props as Props;
|
|
||||||
---
|
|
||||||
|
|
||||||
<svg
|
|
||||||
class="logo"
|
|
||||||
width={size}
|
|
||||||
height={size}
|
|
||||||
viewBox="0 0 256 256"
|
|
||||||
fill="none"
|
|
||||||
xmlns="http://www.w3.org/2000/svg"
|
|
||||||
>
|
|
||||||
<style>
|
|
||||||
#flame {
|
|
||||||
fill: var(--theme-text-accent);
|
|
||||||
}
|
|
||||||
|
|
||||||
#a {
|
|
||||||
fill: var(--theme-text-accent);
|
|
||||||
}
|
|
||||||
</style>
|
|
||||||
<title>Logo</title>
|
|
||||||
<path
|
|
||||||
id="a"
|
|
||||||
fill-rule="evenodd"
|
|
||||||
clip-rule="evenodd"
|
|
||||||
d="M163.008 18.929c1.944 2.413 2.935 5.67 4.917 12.181l43.309 142.27a180.277 180.277 0 00-51.778-17.53l-28.198-95.29a3.67 3.67 0 00-7.042.01l-27.857 95.232a180.225 180.225 0 00-52.01 17.557l43.52-142.281c1.99-6.502 2.983-9.752 4.927-12.16a15.999 15.999 0 016.484-4.798c2.872-1.154 6.271-1.154 13.07-1.154h31.085c6.807 0 10.211 0 13.086 1.157a16.004 16.004 0 016.487 4.806z"
|
|
||||||
>
|
|
||||||
</path>
|
|
||||||
<path
|
|
||||||
id="flame"
|
|
||||||
fill-rule="evenodd"
|
|
||||||
clip-rule="evenodd"
|
|
||||||
d="M168.19 180.151c-7.139 6.105-21.39 10.268-37.804 10.268-20.147 0-37.033-6.272-41.513-14.707-1.602 4.835-1.961 10.367-1.961 13.902 0 0-1.056 17.355 11.015 29.426 0-6.268 5.081-11.349 11.349-11.349 10.743 0 10.731 9.373 10.721 16.977v.679c0 11.542 7.054 21.436 17.086 25.606a23.27 23.27 0 01-2.339-10.2c0-11.008 6.463-15.107 13.974-19.87 5.976-3.79 12.616-8.001 17.192-16.449a31.024 31.024 0 003.743-14.82c0-3.299-.513-6.479-1.463-9.463z"
|
|
||||||
>
|
|
||||||
</path>
|
|
||||||
</svg>
|
|
||||||
@ -1,149 +0,0 @@
|
|||||||
---
|
|
||||||
// import { getLanguageFromURL, KNOWN_LANGUAGE_CODES } from '../../languages';
|
|
||||||
import * as CONFIG from '../../config';
|
|
||||||
// import AstroLogo from './AstroLogo.astro';
|
|
||||||
import SkipToContent from './SkipToContent.astro';
|
|
||||||
import SidebarToggle from './SidebarToggle';
|
|
||||||
// import LanguageSelect from './LanguageSelect';
|
|
||||||
import Search from './Search';
|
|
||||||
|
|
||||||
type Props = {
|
|
||||||
currentPage: string;
|
|
||||||
};
|
|
||||||
|
|
||||||
const { currentPage } = Astro.props as Props;
|
|
||||||
// const lang = getLanguageFromURL(currentPage);
|
|
||||||
---
|
|
||||||
|
|
||||||
<header>
|
|
||||||
<SkipToContent />
|
|
||||||
<nav class="nav-wrapper" title="Top Navigation">
|
|
||||||
<div class="menu-toggle">
|
|
||||||
<SidebarToggle client:idle />
|
|
||||||
</div>
|
|
||||||
<div class="logo flex" style="overflow:visible">
|
|
||||||
<a href="/">
|
|
||||||
<div>🌀</div>
|
|
||||||
<h1>{CONFIG.SITE.title ?? 'Documentation'}</h1>
|
|
||||||
</a>
|
|
||||||
</div>
|
|
||||||
<div style="flex-grow: 1;"></div>
|
|
||||||
{/* KNOWN_LANGUAGE_CODES.length > 1 && <LanguageSelect lang={lang} client:idle /> */}
|
|
||||||
<div class="search-item">
|
|
||||||
<Search client:idle />
|
|
||||||
</div>
|
|
||||||
</nav>
|
|
||||||
</header>
|
|
||||||
|
|
||||||
<style>
|
|
||||||
header {
|
|
||||||
z-index: 11;
|
|
||||||
height: var(--theme-navbar-height);
|
|
||||||
width: 100%;
|
|
||||||
background-color: var(--theme-navbar-bg);
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
overflow: hidden;
|
|
||||||
position: sticky;
|
|
||||||
top: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.logo {
|
|
||||||
flex: 1;
|
|
||||||
display: flex;
|
|
||||||
overflow: hidden;
|
|
||||||
width: 30px;
|
|
||||||
font-size: 2rem;
|
|
||||||
flex-shrink: 0;
|
|
||||||
font-weight: 600;
|
|
||||||
line-height: 1;
|
|
||||||
color: hsla(var(--color-base-white), 100%, 1);
|
|
||||||
gap: 0.25em;
|
|
||||||
z-index: -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
.logo a {
|
|
||||||
display: flex;
|
|
||||||
padding: 0.5em 0.25em;
|
|
||||||
margin: -0.5em -0.25em;
|
|
||||||
text-decoration: none;
|
|
||||||
font-weight: bold;
|
|
||||||
}
|
|
||||||
|
|
||||||
.logo a {
|
|
||||||
transition: color 100ms ease-out;
|
|
||||||
color: var(--theme-text);
|
|
||||||
}
|
|
||||||
|
|
||||||
.logo a:hover,
|
|
||||||
.logo a:focus {
|
|
||||||
color: var(--theme-text-accent);
|
|
||||||
}
|
|
||||||
|
|
||||||
.logo h1 {
|
|
||||||
display: none;
|
|
||||||
font: inherit;
|
|
||||||
color: inherit;
|
|
||||||
margin: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.nav-wrapper {
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: flex-end;
|
|
||||||
gap: 1em;
|
|
||||||
width: 100%;
|
|
||||||
max-width: 82em;
|
|
||||||
padding: 0 1rem;
|
|
||||||
}
|
|
||||||
|
|
||||||
@media (min-width: 50em) {
|
|
||||||
header {
|
|
||||||
position: static;
|
|
||||||
padding: 2rem 0rem;
|
|
||||||
}
|
|
||||||
|
|
||||||
.logo {
|
|
||||||
width: auto;
|
|
||||||
margin: 0;
|
|
||||||
z-index: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.logo h1 {
|
|
||||||
display: initial;
|
|
||||||
}
|
|
||||||
|
|
||||||
.menu-toggle {
|
|
||||||
display: none;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/** Style Algolia */
|
|
||||||
:root {
|
|
||||||
--docsearch-primary-color: var(--theme-accent);
|
|
||||||
--docsearch-logo-color: var(--theme-text);
|
|
||||||
}
|
|
||||||
|
|
||||||
.search-item {
|
|
||||||
display: none;
|
|
||||||
position: relative;
|
|
||||||
z-index: 10;
|
|
||||||
flex-grow: 1;
|
|
||||||
padding-right: 0.7rem;
|
|
||||||
display: flex;
|
|
||||||
max-width: 200px;
|
|
||||||
}
|
|
||||||
|
|
||||||
@media (min-width: 50em) {
|
|
||||||
.search-item {
|
|
||||||
max-width: 400px;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
</style>
|
|
||||||
|
|
||||||
<style is:global>
|
|
||||||
.search-item > * {
|
|
||||||
flex-grow: 1;
|
|
||||||
}
|
|
||||||
</style>
|
|
||||||
@ -2,7 +2,6 @@
|
|||||||
// import { getLanguageFromURL, KNOWN_LANGUAGE_CODES } from '../../languages';
|
// import { getLanguageFromURL, KNOWN_LANGUAGE_CODES } from '../../languages';
|
||||||
import * as CONFIG from '../../config';
|
import * as CONFIG from '../../config';
|
||||||
// import AstroLogo from './AstroLogo.astro';
|
// import AstroLogo from './AstroLogo.astro';
|
||||||
import SkipToContent from './SkipToContent.astro';
|
|
||||||
import SidebarToggle from './SidebarToggle';
|
import SidebarToggle from './SidebarToggle';
|
||||||
// import LanguageSelect from './LanguageSelect';
|
// import LanguageSelect from './LanguageSelect';
|
||||||
import Search from './Search';
|
import Search from './Search';
|
||||||
@ -15,7 +14,6 @@ const { currentPage } = Astro.props as Props;
|
|||||||
// const lang = getLanguageFromURL(currentPage);
|
// const lang = getLanguageFromURL(currentPage);
|
||||||
---
|
---
|
||||||
|
|
||||||
<SkipToContent />
|
|
||||||
<nav class="flex justify-between py-2" title="Top Navigation">
|
<nav class="flex justify-between py-2" title="Top Navigation">
|
||||||
<!-- <div class="menu-toggle">
|
<!-- <div class="menu-toggle">
|
||||||
<SidebarToggle client:idle />
|
<SidebarToggle client:idle />
|
||||||
@ -29,7 +27,7 @@ const { currentPage } = Astro.props as Props;
|
|||||||
<div style="flex-grow: 1;"></div>
|
<div style="flex-grow: 1;"></div>
|
||||||
{/* KNOWN_LANGUAGE_CODES.length > 1 && <LanguageSelect lang={lang} client:idle /> */}
|
{/* KNOWN_LANGUAGE_CODES.length > 1 && <LanguageSelect lang={lang} client:idle /> */}
|
||||||
<div class="search-item h-10">
|
<div class="search-item h-10">
|
||||||
<Search client:idle />
|
<!-- <Search client:idle /> -->
|
||||||
</div>
|
</div>
|
||||||
</nav>
|
</nav>
|
||||||
|
|
||||||
|
|||||||
@ -26,7 +26,7 @@ export default function Search() {
|
|||||||
}, [setIsOpen]);
|
}, [setIsOpen]);
|
||||||
|
|
||||||
const onInput = useCallback(
|
const onInput = useCallback(
|
||||||
(e) => {
|
(e: any) => {
|
||||||
setIsOpen(true);
|
setIsOpen(true);
|
||||||
setInitialQuery(e.key);
|
setInitialQuery(e.key);
|
||||||
},
|
},
|
||||||
|
|||||||
@ -3,42 +3,37 @@ import type { FunctionalComponent } from 'preact';
|
|||||||
import { useState, useEffect } from 'preact/hooks';
|
import { useState, useEffect } from 'preact/hooks';
|
||||||
|
|
||||||
const MenuToggle: FunctionalComponent = () => {
|
const MenuToggle: FunctionalComponent = () => {
|
||||||
const [sidebarShown, setSidebarShown] = useState(false);
|
const [sidebarShown, setSidebarShown] = useState(false);
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
const body = document.querySelector('body')!;
|
const body = document.querySelector('body')!;
|
||||||
if (sidebarShown) {
|
if (sidebarShown) {
|
||||||
body.classList.add('mobile-sidebar-toggle');
|
body.classList.add('mobile-sidebar-toggle');
|
||||||
} else {
|
} else {
|
||||||
body.classList.remove('mobile-sidebar-toggle');
|
body.classList.remove('mobile-sidebar-toggle');
|
||||||
}
|
}
|
||||||
}, [sidebarShown]);
|
}, [sidebarShown]);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<button
|
<button
|
||||||
type="button"
|
type="button"
|
||||||
aria-pressed={sidebarShown ? 'true' : 'false'}
|
aria-pressed={sidebarShown ? 'true' : 'false'}
|
||||||
id="menu-toggle"
|
id="menu-toggle"
|
||||||
onClick={() => setSidebarShown(!sidebarShown)}
|
onClick={() => setSidebarShown(!sidebarShown)}
|
||||||
>
|
>
|
||||||
<svg
|
<svg
|
||||||
xmlns="http://www.w3.org/2000/svg"
|
xmlns="http://www.w3.org/2000/svg"
|
||||||
width="1em"
|
width="1em"
|
||||||
height="1em"
|
height="1em"
|
||||||
fill="none"
|
fill="none"
|
||||||
viewBox="0 0 24 24"
|
viewBox="0 0 24 24"
|
||||||
stroke="currentColor"
|
stroke="currentColor"
|
||||||
>
|
>
|
||||||
<path
|
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M4 6h16M4 12h16M4 18h16" />
|
||||||
stroke-linecap="round"
|
</svg>
|
||||||
stroke-linejoin="round"
|
<span className="sr-only">Toggle sidebar</span>
|
||||||
stroke-width="2"
|
</button>
|
||||||
d="M4 6h16M4 12h16M4 18h16"
|
);
|
||||||
/>
|
|
||||||
</svg>
|
|
||||||
<span className="sr-only">Toggle sidebar</span>
|
|
||||||
</button>
|
|
||||||
);
|
|
||||||
};
|
};
|
||||||
|
|
||||||
export default MenuToggle;
|
export default MenuToggle;
|
||||||
|
|||||||
@ -1,26 +0,0 @@
|
|||||||
---
|
|
||||||
type Props = {};
|
|
||||||
---
|
|
||||||
|
|
||||||
<a href="#article" class="sr-only focus:not-sr-only skiplink"><span>Skip to Content</span></a>
|
|
||||||
|
|
||||||
<style>
|
|
||||||
.skiplink,
|
|
||||||
.skiplink:focus,
|
|
||||||
.skiplink:focus-visible {
|
|
||||||
position: absolute;
|
|
||||||
padding: 0.25em;
|
|
||||||
font-size: larger;
|
|
||||||
top: 0;
|
|
||||||
left: 0;
|
|
||||||
right: 0;
|
|
||||||
z-index: 9;
|
|
||||||
display: block;
|
|
||||||
text-align: center;
|
|
||||||
background-color: var(--theme-text-accent);
|
|
||||||
color: var(--theme-bg);
|
|
||||||
border-radius: 0.25em;
|
|
||||||
outline: var(--theme-bg) solid 1px;
|
|
||||||
outline-offset: 0;
|
|
||||||
}
|
|
||||||
</style>
|
|
||||||
@ -4,31 +4,14 @@ import MoreMenu from './MoreMenu.astro';
|
|||||||
import type { MarkdownHeading } from 'astro';
|
import type { MarkdownHeading } from 'astro';
|
||||||
|
|
||||||
type Props = {
|
type Props = {
|
||||||
headings: MarkdownHeading[];
|
headings: MarkdownHeading[];
|
||||||
githubEditUrl: string;
|
githubEditUrl: string;
|
||||||
};
|
};
|
||||||
|
|
||||||
const { headings, githubEditUrl } = Astro.props as Props;
|
const { headings, githubEditUrl } = Astro.props as Props;
|
||||||
---
|
---
|
||||||
|
|
||||||
<nav class="sidebar-nav" aria-labelledby="grid-right">
|
<nav aria-labelledby="grid-right">
|
||||||
<div class="sidebar-nav-inner">
|
<TableOfContents client:media="(min-width: 50em)" headings={headings} />
|
||||||
<TableOfContents client:media="(min-width: 50em)" headings={headings} />
|
<MoreMenu editHref={githubEditUrl} />
|
||||||
<MoreMenu editHref={githubEditUrl} />
|
|
||||||
</div>
|
|
||||||
</nav>
|
</nav>
|
||||||
|
|
||||||
<style>
|
|
||||||
.sidebar-nav {
|
|
||||||
width: 100%;
|
|
||||||
position: sticky;
|
|
||||||
top: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.sidebar-nav-inner {
|
|
||||||
height: 100%;
|
|
||||||
padding: 0;
|
|
||||||
padding-top: var(--doc-padding);
|
|
||||||
overflow: auto;
|
|
||||||
}
|
|
||||||
</style>
|
|
||||||
|
|||||||
@ -4,90 +4,85 @@ import type { FunctionalComponent } from 'preact';
|
|||||||
import { useState, useEffect, useRef } from 'preact/hooks';
|
import { useState, useEffect, useRef } from 'preact/hooks';
|
||||||
|
|
||||||
type ItemOffsets = {
|
type ItemOffsets = {
|
||||||
id: string;
|
id: string;
|
||||||
topOffset: number;
|
topOffset: number;
|
||||||
};
|
};
|
||||||
|
|
||||||
const TableOfContents: FunctionalComponent<{ headings: MarkdownHeading[] }> = ({
|
const TableOfContents: FunctionalComponent<{ headings: MarkdownHeading[] }> = ({ headings = [] }) => {
|
||||||
headings = [],
|
const toc = useRef<any>();
|
||||||
}) => {
|
const onThisPageID = 'on-this-page-heading';
|
||||||
const toc = useRef<HTMLUListElement>();
|
const itemOffsets = useRef<ItemOffsets[]>([]);
|
||||||
const onThisPageID = 'on-this-page-heading';
|
const [currentID, setCurrentID] = useState('overview');
|
||||||
const itemOffsets = useRef<ItemOffsets[]>([]);
|
useEffect(() => {
|
||||||
const [currentID, setCurrentID] = useState('overview');
|
const getItemOffsets = () => {
|
||||||
useEffect(() => {
|
const titles = document.querySelectorAll('article :is(h1, h2, h3, h4)');
|
||||||
const getItemOffsets = () => {
|
itemOffsets.current = Array.from(titles).map((title) => ({
|
||||||
const titles = document.querySelectorAll('article :is(h1, h2, h3, h4)');
|
id: title.id,
|
||||||
itemOffsets.current = Array.from(titles).map((title) => ({
|
topOffset: title.getBoundingClientRect().top + window.scrollY,
|
||||||
id: title.id,
|
}));
|
||||||
topOffset: title.getBoundingClientRect().top + window.scrollY,
|
};
|
||||||
}));
|
|
||||||
};
|
|
||||||
|
|
||||||
getItemOffsets();
|
getItemOffsets();
|
||||||
window.addEventListener('resize', getItemOffsets);
|
window.addEventListener('resize', getItemOffsets);
|
||||||
|
|
||||||
return () => {
|
return () => {
|
||||||
window.removeEventListener('resize', getItemOffsets);
|
window.removeEventListener('resize', getItemOffsets);
|
||||||
};
|
};
|
||||||
}, []);
|
}, []);
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (!toc.current) return;
|
if (!toc.current) return;
|
||||||
|
|
||||||
const setCurrent: IntersectionObserverCallback = (entries) => {
|
const setCurrent: IntersectionObserverCallback = (entries) => {
|
||||||
for (const entry of entries) {
|
for (const entry of entries) {
|
||||||
if (entry.isIntersecting) {
|
if (entry.isIntersecting) {
|
||||||
const { id } = entry.target;
|
const { id } = entry.target;
|
||||||
if (id === onThisPageID) continue;
|
if (id === onThisPageID) continue;
|
||||||
setCurrentID(entry.target.id);
|
setCurrentID(entry.target.id);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
const observerOptions: IntersectionObserverInit = {
|
const observerOptions: IntersectionObserverInit = {
|
||||||
// Negative top margin accounts for `scroll-margin`.
|
// Negative top margin accounts for `scroll-margin`.
|
||||||
// Negative bottom margin means heading needs to be towards top of viewport to trigger intersection.
|
// Negative bottom margin means heading needs to be towards top of viewport to trigger intersection.
|
||||||
rootMargin: '-100px 0% -66%',
|
rootMargin: '-100px 0% -66%',
|
||||||
threshold: 1,
|
threshold: 1,
|
||||||
};
|
};
|
||||||
|
|
||||||
const headingsObserver = new IntersectionObserver(setCurrent, observerOptions);
|
const headingsObserver = new IntersectionObserver(setCurrent, observerOptions);
|
||||||
|
|
||||||
// Observe all the headings in the main page content.
|
// Observe all the headings in the main page content.
|
||||||
document.querySelectorAll('article :is(h1,h2,h3)').forEach((h) => headingsObserver.observe(h));
|
document.querySelectorAll('article :is(h1,h2,h3)').forEach((h) => headingsObserver.observe(h));
|
||||||
|
|
||||||
// Stop observing when the component is unmounted.
|
// Stop observing when the component is unmounted.
|
||||||
return () => headingsObserver.disconnect();
|
return () => headingsObserver.disconnect();
|
||||||
}, [toc.current]);
|
}, [toc.current]);
|
||||||
|
|
||||||
const onLinkClick = (e) => {
|
const onLinkClick = (e: any) => {
|
||||||
setCurrentID(e.target.getAttribute('href').replace('#', ''));
|
setCurrentID(e.target.getAttribute('href').replace('#', ''));
|
||||||
};
|
};
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<h2 id={onThisPageID} className="heading">
|
<ul ref={toc}>
|
||||||
On this page
|
{headings
|
||||||
</h2>
|
.filter(({ depth }) => depth > 0 && depth < 4)
|
||||||
<ul ref={toc}>
|
.map((heading) => (
|
||||||
{headings
|
<li
|
||||||
.filter(({ depth }) => depth > 1 && depth < 4)
|
className={`border-l-4 border-slate-900 ${['pl-4', 'pl-8', 'pl-12'][heading.depth - 1]} ${
|
||||||
.map((heading) => (
|
currentID === heading.slug ? 'bg-slate-900' : ''
|
||||||
<li
|
}`.trim()}
|
||||||
className={`header-link depth-${heading.depth} ${
|
>
|
||||||
currentID === heading.slug ? 'current-header-link' : ''
|
<a href={`#${heading.slug}`} onClick={onLinkClick}>
|
||||||
}`.trim()}
|
{unescape(heading.text)}
|
||||||
>
|
</a>
|
||||||
<a href={`#${heading.slug}`} onClick={onLinkClick}>
|
</li>
|
||||||
{unescape(heading.text)}
|
))}
|
||||||
</a>
|
</ul>
|
||||||
</li>
|
</>
|
||||||
))}
|
);
|
||||||
</ul>
|
|
||||||
</>
|
|
||||||
);
|
|
||||||
};
|
};
|
||||||
|
|
||||||
export default TableOfContents;
|
export default TableOfContents;
|
||||||
|
|||||||
@ -1,136 +0,0 @@
|
|||||||
---
|
|
||||||
import HeadCommon from '../components/HeadCommon.astro';
|
|
||||||
import HeadSEO from '../components/HeadSEO.astro';
|
|
||||||
import Header from '../components/Header/Header.astro';
|
|
||||||
import PageContent from '../components/PageContent/PageContent.astro';
|
|
||||||
import LeftSidebar from '../components/LeftSidebar/LeftSidebar.astro';
|
|
||||||
import RightSidebar from '../components/RightSidebar/RightSidebar.astro';
|
|
||||||
import * as CONFIG from '../config';
|
|
||||||
import type { MarkdownHeading } from 'astro';
|
|
||||||
import Footer from '../components/Footer/Footer.astro';
|
|
||||||
|
|
||||||
type Props = {
|
|
||||||
frontmatter: CONFIG.Frontmatter;
|
|
||||||
headings: MarkdownHeading[];
|
|
||||||
};
|
|
||||||
|
|
||||||
const { frontmatter, headings } = Astro.props as Props;
|
|
||||||
const canonicalURL = new URL(Astro.url.pathname, Astro.site);
|
|
||||||
const currentPage = Astro.url.pathname;
|
|
||||||
const currentFile = `src/pages${currentPage.replace(/\/$/, '')}.md`;
|
|
||||||
const githubEditUrl = `${CONFIG.GITHUB_EDIT_URL}/${currentFile}`;
|
|
||||||
---
|
|
||||||
|
|
||||||
<html dir={frontmatter.dir ?? 'ltr'} lang={frontmatter.lang ?? 'en-us'} class="initial">
|
|
||||||
<head>
|
|
||||||
<HeadCommon />
|
|
||||||
<HeadSEO frontmatter={frontmatter} canonicalUrl={canonicalURL} />
|
|
||||||
<title>
|
|
||||||
{frontmatter.title ? `${frontmatter.title} 🚀 ${CONFIG.SITE.title}` : CONFIG.SITE.title}
|
|
||||||
</title>
|
|
||||||
<style>
|
|
||||||
body {
|
|
||||||
width: 100%;
|
|
||||||
display: grid;
|
|
||||||
grid-template-rows: var(--theme-navbar-height) 1fr;
|
|
||||||
--gutter: 0.5rem;
|
|
||||||
--doc-padding: 2rem;
|
|
||||||
}
|
|
||||||
|
|
||||||
.layout {
|
|
||||||
display: grid;
|
|
||||||
grid-auto-flow: column;
|
|
||||||
grid-template-columns: minmax(var(--gutter), 1fr) minmax(0, var(--max-width)) minmax(var(--gutter), 1fr);
|
|
||||||
overflow-x: hidden;
|
|
||||||
}
|
|
||||||
|
|
||||||
.grid-sidebar {
|
|
||||||
height: 100vh;
|
|
||||||
position: sticky;
|
|
||||||
top: 0;
|
|
||||||
padding: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
#grid-left {
|
|
||||||
position: fixed;
|
|
||||||
background-color: var(--theme-bg);
|
|
||||||
z-index: 10;
|
|
||||||
display: none;
|
|
||||||
}
|
|
||||||
|
|
||||||
#grid-main {
|
|
||||||
padding: var(--doc-padding) var(--gutter);
|
|
||||||
grid-column: 2;
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
height: 100%;
|
|
||||||
}
|
|
||||||
|
|
||||||
#grid-right {
|
|
||||||
display: none;
|
|
||||||
}
|
|
||||||
|
|
||||||
@media (min-width: 50em) {
|
|
||||||
.layout {
|
|
||||||
overflow: initial;
|
|
||||||
grid-template-columns: 20rem minmax(0, var(--max-width));
|
|
||||||
gap: 1em;
|
|
||||||
}
|
|
||||||
|
|
||||||
#grid-left {
|
|
||||||
display: flex;
|
|
||||||
padding-left: 2rem;
|
|
||||||
position: sticky;
|
|
||||||
grid-column: 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@media (min-width: 72em) {
|
|
||||||
.layout {
|
|
||||||
grid-template-columns: 20rem minmax(0, var(--max-width)) 18rem;
|
|
||||||
padding-left: 0;
|
|
||||||
padding-right: 0;
|
|
||||||
margin: 0 auto;
|
|
||||||
}
|
|
||||||
|
|
||||||
#grid-right {
|
|
||||||
grid-column: 3;
|
|
||||||
display: flex;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
</style>
|
|
||||||
<style is:global>
|
|
||||||
.layout > * {
|
|
||||||
width: 100%;
|
|
||||||
height: 100%;
|
|
||||||
}
|
|
||||||
|
|
||||||
.mobile-sidebar-toggle {
|
|
||||||
overflow: hidden;
|
|
||||||
}
|
|
||||||
|
|
||||||
.mobile-sidebar-toggle #grid-left {
|
|
||||||
display: block;
|
|
||||||
top: 2rem;
|
|
||||||
}
|
|
||||||
</style>
|
|
||||||
</head>
|
|
||||||
|
|
||||||
<body>
|
|
||||||
<Header currentPage={currentPage} />
|
|
||||||
<main class="layout">
|
|
||||||
<!-- <aside id="grid-left" class="grid-sidebar" title="Site Navigation">
|
|
||||||
<LeftSidebar currentPage={currentPage} />
|
|
||||||
</aside> -->
|
|
||||||
<div id="grid-main">
|
|
||||||
<PageContent frontmatter={frontmatter} headings={headings} githubEditUrl={githubEditUrl}>
|
|
||||||
<slot />
|
|
||||||
</PageContent>
|
|
||||||
</div>
|
|
||||||
<aside id="grid-right" class="grid-sidebar" title="Table of Contents">
|
|
||||||
<RightSidebar headings={headings} githubEditUrl={githubEditUrl} />
|
|
||||||
</aside>
|
|
||||||
</main>
|
|
||||||
<Footer path={currentFile} />
|
|
||||||
</body>
|
|
||||||
</html>
|
|
||||||
@ -5,3 +5,4 @@
|
|||||||
</script>
|
</script>
|
||||||
|
|
||||||
<h1>Hello</h1>
|
<h1>Hello</h1>
|
||||||
|
<a href="/tutorial">Tutorial</a>
|
||||||
@ -0,0 +1,4 @@
|
|||||||
|
|
||||||
|
.cm-gutters {
|
||||||
|
display: none !important;
|
||||||
|
}
|
||||||
Loading…
x
Reference in New Issue
Block a user