mirror of
https://github.com/eliasstepanik/strudel-docker.git
synced 2026-01-11 05:38:34 +00:00
remove preact
This commit is contained in:
parent
0fcec0a0ca
commit
c0b0ea4493
110
pnpm-lock.yaml
generated
110
pnpm-lock.yaml
generated
@ -474,9 +474,6 @@ importers:
|
||||
'@astrojs/mdx':
|
||||
specifier: ^0.13.0
|
||||
version: 0.13.0(rollup@3.12.0)
|
||||
'@astrojs/preact':
|
||||
specifier: ^1.2.0
|
||||
version: 1.2.0(preact@10.11.3)
|
||||
'@astrojs/react':
|
||||
specifier: ^1.2.2
|
||||
version: 1.2.2(@types/react-dom@18.0.10)(@types/react@18.0.27)(react-dom@18.2.0)(react@18.2.0)
|
||||
@ -573,9 +570,6 @@ importers:
|
||||
nanostores:
|
||||
specifier: ^0.8.1
|
||||
version: 0.8.1
|
||||
preact:
|
||||
specifier: ^10.7.3
|
||||
version: 10.11.3
|
||||
react:
|
||||
specifier: ^18.2.0
|
||||
version: 18.2.0
|
||||
@ -831,22 +825,6 @@ packages:
|
||||
uvu: 0.5.6
|
||||
vfile-message: 3.1.3
|
||||
|
||||
/@astrojs/preact@1.2.0(preact@10.11.3):
|
||||
resolution: {integrity: sha512-Vm8rkBIE3cNlxhFoUO2Rsv5RxSP7x7Oi9J6qz8+91lwAIjdm6oyDOrrBmdGqsONJ1MqnjPG4EPmIZJGuFtz2SQ==}
|
||||
engines: {node: ^14.18.0 || >=16.12.0}
|
||||
peerDependencies:
|
||||
preact: ^10.6.5
|
||||
dependencies:
|
||||
'@babel/core': 7.20.12
|
||||
'@babel/plugin-transform-react-jsx': 7.20.13(@babel/core@7.20.12)
|
||||
'@preact/signals': 1.1.3(preact@10.11.3)
|
||||
babel-plugin-module-resolver: 4.1.0
|
||||
preact: 10.11.3
|
||||
preact-render-to-string: 5.2.6(preact@10.11.3)
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
dev: false
|
||||
|
||||
/@astrojs/prism@1.0.2:
|
||||
resolution: {integrity: sha512-o3cUVoAuALDqdN5puNlsN2eO4Yi1kDh68YO8V7o6U4Ts+J/mMayzlJ7JsgYAmob0xrf/XnADVgu8khfMv/w3uA==}
|
||||
engines: {node: ^14.18.0 || >=16.12.0}
|
||||
@ -2974,19 +2952,6 @@ packages:
|
||||
/@polka/url@1.0.0-next.21:
|
||||
resolution: {integrity: sha512-a5Sab1C4/icpTZVzZc5Ghpz88yQtGOyNqYXcZgOssB2uuAr+wF/MvN6bgtW32q7HHrvBki+BsZ0OuNv6EV3K9g==}
|
||||
|
||||
/@preact/signals-core@1.2.3:
|
||||
resolution: {integrity: sha512-Kui4p7PMcEQevBgsTO0JBo3gyQ88Q3qzEvsVCuSp11t0JcN4DmGCTJcGRVSCq7Bn7lGxJBO+57jNSzDoDJ+QmA==}
|
||||
dev: false
|
||||
|
||||
/@preact/signals@1.1.3(preact@10.11.3):
|
||||
resolution: {integrity: sha512-N09DuAVvc90bBZVRwD+aFhtGyHAmJLhS3IFoawO/bYJRcil4k83nBOchpCEoS0s5+BXBpahgp0Mjf+IOqP57Og==}
|
||||
peerDependencies:
|
||||
preact: 10.x
|
||||
dependencies:
|
||||
'@preact/signals-core': 1.2.3
|
||||
preact: 10.11.3
|
||||
dev: false
|
||||
|
||||
/@proload/core@0.3.3:
|
||||
resolution: {integrity: sha512-7dAFWsIK84C90AMl24+N/ProHKm4iw0akcnoKjRvbfHifJZBLhaDsDus1QJmhG12lXj4e/uB/8mB/0aduCW+NQ==}
|
||||
dependencies:
|
||||
@ -4501,17 +4466,6 @@ packages:
|
||||
- debug
|
||||
dev: true
|
||||
|
||||
/babel-plugin-module-resolver@4.1.0:
|
||||
resolution: {integrity: sha512-MlX10UDheRr3lb3P0WcaIdtCSRlxdQsB1sBqL7W0raF070bGl1HQQq5K3T2vf2XAYie+ww+5AKC/WrkjRO2knA==}
|
||||
engines: {node: '>= 8.0.0'}
|
||||
dependencies:
|
||||
find-babel-config: 1.2.0
|
||||
glob: 7.2.3
|
||||
pkg-up: 3.1.0
|
||||
reselect: 4.1.7
|
||||
resolve: 1.22.1
|
||||
dev: false
|
||||
|
||||
/babel-plugin-polyfill-corejs2@0.3.3(@babel/core@7.20.12):
|
||||
resolution: {integrity: sha512-8hOdmFYFSZhqg2C/JgLUQ+t52o5nirNwaWM2B9LWteozwIvM14VSwdsCAUET10qT+kmySAlseadmfeeSWFCy+Q==}
|
||||
peerDependencies:
|
||||
@ -6525,14 +6479,6 @@ packages:
|
||||
dependencies:
|
||||
to-regex-range: 5.0.1
|
||||
|
||||
/find-babel-config@1.2.0:
|
||||
resolution: {integrity: sha512-jB2CHJeqy6a820ssiqwrKMeyC6nNdmrcgkKWJWmpoxpE8RKciYJXCcXRq1h2AzCo5I5BJeN2tkGEO3hLTuePRA==}
|
||||
engines: {node: '>=4.0.0'}
|
||||
dependencies:
|
||||
json5: 0.5.1
|
||||
path-exists: 3.0.0
|
||||
dev: false
|
||||
|
||||
/find-cache-dir@3.3.2:
|
||||
resolution: {integrity: sha512-wXZV5emFEjrridIgED11OoUKLxiYjAcqot/NJdAkOhlJ+vGzwhOAfcG5OX1jP+S0PcjEn8bdMJv+g2jwQ3Onig==}
|
||||
engines: {node: '>=8'}
|
||||
@ -6556,13 +6502,6 @@ packages:
|
||||
locate-path: 2.0.0
|
||||
dev: true
|
||||
|
||||
/find-up@3.0.0:
|
||||
resolution: {integrity: sha512-1yD6RmLI1XBfxugvORwlck6f75tYL+iR0jqwsOrOxMZyGYqUuDhJ0l4AXdO1iX/FTs9cBAMEk1gWSEx1kSbylg==}
|
||||
engines: {node: '>=6'}
|
||||
dependencies:
|
||||
locate-path: 3.0.0
|
||||
dev: false
|
||||
|
||||
/find-up@4.1.0:
|
||||
resolution: {integrity: sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw==}
|
||||
engines: {node: '>=8'}
|
||||
@ -7962,11 +7901,6 @@ packages:
|
||||
/json-stringify-safe@5.0.1:
|
||||
resolution: {integrity: sha512-ZClg6AaYvamvYEE82d3Iyd3vSSIjQ+odgjaTzRuO3s7toCdFKczob2i0zCh7JE8kWn17yvAWhUVxvqGwUalsRA==}
|
||||
|
||||
/json5@0.5.1:
|
||||
resolution: {integrity: sha512-4xrs1aW+6N5DalkqSVA8fxh458CXvR99WU8WLKmq4v8eWAL86Xo3BVqyd3SkA9wEVjCMqyvvRRkshAdOnBp5rw==}
|
||||
hasBin: true
|
||||
dev: false
|
||||
|
||||
/json5@1.0.2:
|
||||
resolution: {integrity: sha512-g1MWMLBiz8FKi1e4w0UyVL3w+iJceWAFBAaBnnGKOpNa5f8TLktkbre1+s6oICydWAm+HRUGTmI+//xv2hvXYA==}
|
||||
hasBin: true
|
||||
@ -8239,14 +8173,6 @@ packages:
|
||||
path-exists: 3.0.0
|
||||
dev: true
|
||||
|
||||
/locate-path@3.0.0:
|
||||
resolution: {integrity: sha512-7AO748wWnIhNqAuaty2ZWHkQHRSNfPVIsPIfwEOWO22AmaoVrWavlOcMR5nzTLNYvp36X220/maaRsrec1G65A==}
|
||||
engines: {node: '>=6'}
|
||||
dependencies:
|
||||
p-locate: 3.0.0
|
||||
path-exists: 3.0.0
|
||||
dev: false
|
||||
|
||||
/locate-path@5.0.0:
|
||||
resolution: {integrity: sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==}
|
||||
engines: {node: '>=8'}
|
||||
@ -9786,13 +9712,6 @@ packages:
|
||||
p-limit: 1.3.0
|
||||
dev: true
|
||||
|
||||
/p-locate@3.0.0:
|
||||
resolution: {integrity: sha512-x+12w/To+4GFfgJhBEpiDcLozRJGegY+Ei7/z0tSLkMmxGZNybVMSfWj9aJn8Z5Fc7dBUNJOOVgPv2H7IwulSQ==}
|
||||
engines: {node: '>=6'}
|
||||
dependencies:
|
||||
p-limit: 2.3.0
|
||||
dev: false
|
||||
|
||||
/p-locate@4.1.0:
|
||||
resolution: {integrity: sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A==}
|
||||
engines: {node: '>=8'}
|
||||
@ -9962,6 +9881,7 @@ packages:
|
||||
/path-exists@3.0.0:
|
||||
resolution: {integrity: sha512-bpC7GYwiDYQ4wYLe+FA8lhRjhQCMcQGuSgGGqDkg/QerRWw9CmGRT0iSOVRSZJ29NMLZgIzqaljJ63oaL4NIJQ==}
|
||||
engines: {node: '>=4'}
|
||||
dev: true
|
||||
|
||||
/path-exists@4.0.0:
|
||||
resolution: {integrity: sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==}
|
||||
@ -10086,13 +10006,6 @@ packages:
|
||||
mlly: 1.2.0
|
||||
pathe: 1.1.0
|
||||
|
||||
/pkg-up@3.1.0:
|
||||
resolution: {integrity: sha512-nDywThFk1i4BQK4twPQ6TA4RT8bDY96yeuCVBWL3ePARCiEKDRSrNGbFIgUJpLp+XeIR65v8ra7WuJOFUBtkMA==}
|
||||
engines: {node: '>=8'}
|
||||
dependencies:
|
||||
find-up: 3.0.0
|
||||
dev: false
|
||||
|
||||
/pkg@5.8.0:
|
||||
resolution: {integrity: sha512-8h9PUDYFi+LOMLbIyGRdP21g08mAtHidSpofSrf8LWhxUWGHymaRzcopEGiynB5EhQmZUKM6PQ9kCImV2TpdjQ==}
|
||||
hasBin: true
|
||||
@ -10204,19 +10117,6 @@ packages:
|
||||
picocolors: 1.0.0
|
||||
source-map-js: 1.0.2
|
||||
|
||||
/preact-render-to-string@5.2.6(preact@10.11.3):
|
||||
resolution: {integrity: sha512-JyhErpYOvBV1hEPwIxc/fHWXPfnEGdRKxc8gFdAZ7XV4tlzyzG847XAyEZqoDnynP88akM4eaHcSOzNcLWFguw==}
|
||||
peerDependencies:
|
||||
preact: '>=10'
|
||||
dependencies:
|
||||
preact: 10.11.3
|
||||
pretty-format: 3.8.0
|
||||
dev: false
|
||||
|
||||
/preact@10.11.3:
|
||||
resolution: {integrity: sha512-eY93IVpod/zG3uMF22Unl8h9KkrcKIRs2EGar8hwLZZDU1lkjph303V9HZBwufh2s736U6VXuhD109LYqPoffg==}
|
||||
dev: false
|
||||
|
||||
/prebuild-install@6.1.4:
|
||||
resolution: {integrity: sha512-Z4vpywnK1lBg+zdPCVCsKq0xO66eEV9rWo2zrROGGiRS4JtueBOdlB1FnY8lcy7JsUud/Q3ijUxyWN26Ika0vQ==}
|
||||
engines: {node: '>=6'}
|
||||
@ -10308,10 +10208,6 @@ packages:
|
||||
ansi-styles: 5.2.0
|
||||
react-is: 17.0.2
|
||||
|
||||
/pretty-format@3.8.0:
|
||||
resolution: {integrity: sha512-WuxUnVtlWL1OfZFQFuqvnvs6MiAGk9UNsBostyBOB0Is9wb5uRESevA6rnl/rkksXaGX3GzZhPup5d6Vp1nFew==}
|
||||
dev: false
|
||||
|
||||
/prismjs@1.29.0:
|
||||
resolution: {integrity: sha512-Kx/1w86q/epKcmte75LNrEoT+lX8pBpavuAbvJWRXar7Hz8jrtF+e3vY751p0R8H9HdArwaCTNDDzHg/ScJK1Q==}
|
||||
engines: {node: '>=6'}
|
||||
@ -10837,10 +10733,6 @@ packages:
|
||||
lodash: 4.17.21
|
||||
dev: true
|
||||
|
||||
/reselect@4.1.7:
|
||||
resolution: {integrity: sha512-Zu1xbUt3/OPwsXL46hvOOoQrap2azE7ZQbokq61BQfiXvhewsKDwhMeZjTX9sX0nvw1t/U5Audyn1I9P/m9z0A==}
|
||||
dev: false
|
||||
|
||||
/resolve-cwd@3.0.0:
|
||||
resolution: {integrity: sha512-OrZaX2Mb+rJCpH/6CpSqt9xFVpN++x01XnN2ie9g6P5/3xelLAkXWVADpdz1IHD/KFfEXyE6V0U01OQ3UO2rEg==}
|
||||
engines: {node: '>=8'}
|
||||
|
||||
@ -1,5 +1,4 @@
|
||||
import { defineConfig } from 'astro/config';
|
||||
import preact from '@astrojs/preact';
|
||||
import react from '@astrojs/react';
|
||||
import mdx from '@astrojs/mdx';
|
||||
|
||||
@ -47,9 +46,6 @@ const options = {
|
||||
// https://astro.build/config
|
||||
export default defineConfig({
|
||||
integrations: [
|
||||
// Enable Preact to support Preact JSX components.
|
||||
preact(),
|
||||
// Enable React for the Algolia search component.
|
||||
react(),
|
||||
mdx(options),
|
||||
tailwind(),
|
||||
|
||||
@ -14,7 +14,6 @@
|
||||
"dependencies": {
|
||||
"@algolia/client-search": "^4.13.1",
|
||||
"@astrojs/mdx": "^0.13.0",
|
||||
"@astrojs/preact": "^1.2.0",
|
||||
"@astrojs/react": "^1.2.2",
|
||||
"@astrojs/tailwind": "^2.1.3",
|
||||
"@docsearch/css": "^3.1.0",
|
||||
@ -47,7 +46,6 @@
|
||||
"fraction.js": "^4.2.0",
|
||||
"nanoid": "^4.0.0",
|
||||
"nanostores": "^0.8.1",
|
||||
"preact": "^10.7.3",
|
||||
"react": "^18.2.0",
|
||||
"react-dom": "^18.2.0",
|
||||
"rehype-autolink-headings": "^6.1.1",
|
||||
|
||||
@ -2,7 +2,6 @@
|
||||
// import { getLanguageFromURL, KNOWN_LANGUAGE_CODES } from '../../languages';
|
||||
import * as CONFIG from '../../config';
|
||||
// import AstroLogo from './AstroLogo.astro';
|
||||
import SidebarToggle from './SidebarToggle';
|
||||
// import LanguageSelect from './LanguageSelect';
|
||||
import Search from './Search';
|
||||
import CommandLineIcon from '@heroicons/react/20/solid/CommandLineIcon';
|
||||
@ -23,9 +22,6 @@ const sidebar = SIDEBAR[langCode];
|
||||
class="flex justify-between py-2 px-4 items-center h-14 max-h-14 bg-lineHighlight text-foreground"
|
||||
title="Top Navigation"
|
||||
>
|
||||
<!-- <div class="menu-toggle">
|
||||
<SidebarToggle client:idle />
|
||||
</div> -->
|
||||
<div class="flex overflow-visible items-center grow" style="overflow:visible">
|
||||
<a href="/" class="flex items-center text-2xl space-x-2">
|
||||
<h1 class="font-bold flex space-x-2 items-baseline text-xl">
|
||||
|
||||
@ -1,39 +0,0 @@
|
||||
/** @jsxImportSource preact */
|
||||
import type { FunctionalComponent } from 'preact';
|
||||
import { useState, useEffect } from 'preact/hooks';
|
||||
|
||||
const MenuToggle: FunctionalComponent = () => {
|
||||
const [sidebarShown, setSidebarShown] = useState(false);
|
||||
|
||||
useEffect(() => {
|
||||
const body = document.querySelector('body')!;
|
||||
if (sidebarShown) {
|
||||
body.classList.add('mobile-sidebar-toggle');
|
||||
} else {
|
||||
body.classList.remove('mobile-sidebar-toggle');
|
||||
}
|
||||
}, [sidebarShown]);
|
||||
|
||||
return (
|
||||
<button
|
||||
type="button"
|
||||
aria-pressed={sidebarShown ? 'true' : 'false'}
|
||||
id="menu-toggle"
|
||||
onClick={() => setSidebarShown(!sidebarShown)}
|
||||
>
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="1em"
|
||||
height="1em"
|
||||
fill="none"
|
||||
viewBox="0 0 24 24"
|
||||
stroke="currentColor"
|
||||
>
|
||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M4 6h16M4 12h16M4 18h16" />
|
||||
</svg>
|
||||
<span className="sr-only">Toggle sidebar</span>
|
||||
</button>
|
||||
);
|
||||
};
|
||||
|
||||
export default MenuToggle;
|
||||
@ -18,10 +18,6 @@ const currentPage = Astro.url.pathname;
|
||||
<article id="article" class="content">
|
||||
<section class="main-section">
|
||||
<!-- TODO: add dropdown toc on mobile -->
|
||||
<!-- <nav class="block sm:hidden mb-8">
|
||||
<span>On this Page:</span>
|
||||
<TableOfContents client:media="(max-width: 50em)" headings={headings} currentPage={currentPage} />
|
||||
</nav> -->
|
||||
<div class="prose dark:prose-invert max-w-full pb-8">
|
||||
<slot />
|
||||
</div>
|
||||
|
||||
@ -1,5 +1,4 @@
|
||||
---
|
||||
import ThemeToggleButton from './ThemeToggleButton';
|
||||
import * as CONFIG from '../../config';
|
||||
|
||||
type Props = {
|
||||
@ -64,6 +63,3 @@ const showMoreSection = CONFIG.COMMUNITY_INVITE_URL;
|
||||
)
|
||||
}
|
||||
</ul>
|
||||
<div style="margin: 2rem 0; text-align: center;">
|
||||
<!-- <ThemeToggleButton client:visible /> -->
|
||||
</div>
|
||||
|
||||
@ -1,17 +1,14 @@
|
||||
import { unescape } from 'html-escaper';
|
||||
import type { MarkdownHeading } from 'astro';
|
||||
import type { FunctionalComponent } from 'preact';
|
||||
import { useState, useEffect, useRef } from 'preact/hooks';
|
||||
import type { FC } from 'react';
|
||||
import { useState, useEffect, useRef } from 'react';
|
||||
|
||||
type ItemOffsets = {
|
||||
id: string;
|
||||
topOffset: number;
|
||||
};
|
||||
|
||||
const TableOfContents: FunctionalComponent<{ headings: MarkdownHeading[]; currentPage: string }> = ({
|
||||
headings = [],
|
||||
currentPage,
|
||||
}) => {
|
||||
const TableOfContents: FC<{ headings: MarkdownHeading[]; currentPage: string }> = ({ headings = [], currentPage }) => {
|
||||
const toc = useRef<any>();
|
||||
const onThisPageID = 'on-this-page-heading';
|
||||
const itemOffsets = useRef<ItemOffsets[]>([]);
|
||||
@ -73,8 +70,8 @@ const TableOfContents: FunctionalComponent<{ headings: MarkdownHeading[]; curren
|
||||
<ul ref={toc}>
|
||||
{headings
|
||||
.filter(({ depth }) => depth >= minDepth && depth < 4)
|
||||
.map((heading) => (
|
||||
<li className={`w-full`}>
|
||||
.map((heading, i) => (
|
||||
<li className={`w-full`} key={i}>
|
||||
<a
|
||||
href={`${currentPage}#${heading.slug}`}
|
||||
onClick={onLinkClick}
|
||||
|
||||
@ -1,37 +0,0 @@
|
||||
.theme-toggle {
|
||||
display: inline-flex;
|
||||
align-items: center;
|
||||
gap: 0.25em;
|
||||
padding: 0.33em 0.67em;
|
||||
border-radius: 99em;
|
||||
background-color: var(--theme-code-inline-bg);
|
||||
}
|
||||
|
||||
.theme-toggle > label:focus-within {
|
||||
outline: 2px solid transparent;
|
||||
box-shadow: 0 0 0 0.08em var(--theme-accent), 0 0 0 0.12em white;
|
||||
}
|
||||
|
||||
.theme-toggle > label {
|
||||
color: var(--theme-code-inline-text);
|
||||
position: relative;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
opacity: 0.5;
|
||||
}
|
||||
|
||||
.theme-toggle .checked {
|
||||
color: var(--theme-accent);
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
input[name='theme-toggle'] {
|
||||
position: absolute;
|
||||
opacity: 0;
|
||||
top: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
z-index: -1;
|
||||
}
|
||||
@ -1,70 +0,0 @@
|
||||
import type { FunctionalComponent } from 'preact';
|
||||
import { useState, useEffect } from 'preact/hooks';
|
||||
import './ThemeToggleButton.css';
|
||||
|
||||
const themes = ['light', 'dark'];
|
||||
|
||||
const icons = [
|
||||
<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 20 20" fill="currentColor">
|
||||
<path
|
||||
fillRule="evenodd"
|
||||
d="M10 2a1 1 0 011 1v1a1 1 0 11-2 0V3a1 1 0 011-1zm4 8a4 4 0 11-8 0 4 4 0 018 0zm-.464 4.95l.707.707a1 1 0 001.414-1.414l-.707-.707a1 1 0 00-1.414 1.414zm2.12-10.607a1 1 0 010 1.414l-.706.707a1 1 0 11-1.414-1.414l.707-.707a1 1 0 011.414 0zM17 11a1 1 0 100-2h-1a1 1 0 100 2h1zm-7 4a1 1 0 011 1v1a1 1 0 11-2 0v-1a1 1 0 011-1zM5.05 6.464A1 1 0 106.465 5.05l-.708-.707a1 1 0 00-1.414 1.414l.707.707zm1.414 8.486l-.707.707a1 1 0 01-1.414-1.414l.707-.707a1 1 0 011.414 1.414zM4 11a1 1 0 100-2H3a1 1 0 000 2h1z"
|
||||
clipRule="evenodd"
|
||||
/>
|
||||
</svg>,
|
||||
<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 20 20" fill="currentColor">
|
||||
<path d="M17.293 13.293A8 8 0 016.707 2.707a8.001 8.001 0 1010.586 10.586z" />
|
||||
</svg>,
|
||||
];
|
||||
|
||||
const ThemeToggle: FunctionalComponent = () => {
|
||||
const [theme, setTheme] = useState(() => {
|
||||
if (import.meta.env.SSR) {
|
||||
return undefined;
|
||||
}
|
||||
if (typeof localStorage !== undefined && localStorage.getItem('theme')) {
|
||||
return localStorage.getItem('theme');
|
||||
}
|
||||
if (window.matchMedia('(prefers-color-scheme: dark)').matches) {
|
||||
return 'dark';
|
||||
}
|
||||
return 'light';
|
||||
});
|
||||
|
||||
useEffect(() => {
|
||||
const root = document.documentElement;
|
||||
if (theme === 'light') {
|
||||
root.classList.remove('theme-dark');
|
||||
} else {
|
||||
root.classList.add('theme-dark');
|
||||
}
|
||||
}, [theme]);
|
||||
|
||||
return (
|
||||
<div className="theme-toggle">
|
||||
{themes.map((t, i) => {
|
||||
const icon = icons[i];
|
||||
const checked = t === theme;
|
||||
return (
|
||||
<label className={checked ? ' checked' : ''}>
|
||||
{icon}
|
||||
<input
|
||||
type="radio"
|
||||
name="theme-toggle"
|
||||
checked={checked}
|
||||
value={t}
|
||||
title={`Use ${t} theme`}
|
||||
aria-label={`Use ${t} theme`}
|
||||
onChange={() => {
|
||||
localStorage.setItem('theme', t);
|
||||
setTheme(t);
|
||||
}}
|
||||
/>
|
||||
</label>
|
||||
);
|
||||
})}
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
export default ThemeToggle;
|
||||
Loading…
x
Reference in New Issue
Block a user