Skip to content

Commit

Permalink
fix(docs): theme selector
Browse files Browse the repository at this point in the history
  • Loading branch information
jer3m01 committed Mar 1, 2024
1 parent 3b53e11 commit 2dfeb71
Show file tree
Hide file tree
Showing 2 changed files with 31 additions and 51 deletions.
42 changes: 13 additions & 29 deletions apps/docs/src/components/table-of-contents.tsx
Original file line number Diff line number Diff line change
@@ -1,14 +1,6 @@
import { cache, createAsync, useLocation } from "@solidjs/router";
import { clsx } from "clsx";
import {
Accessor,
For,
Suspense,
createEffect,
createSignal,
on,
onCleanup,
} from "solid-js";
import { Accessor, For, Suspense, createEffect, createSignal, on, onCleanup } from "solid-js";
import { isServer } from "solid-js/web";
import { mods } from "../app";

Expand Down Expand Up @@ -36,9 +28,7 @@ function getHeadingsFromToc(tableOfContents: TocItem[]) {
}

function useCurrentSection(tableOfContents: Accessor<TocItem[] | undefined>) {
const [currentSection, setCurrentSection] = createSignal(
tableOfContents()?.[0]?.slug,
);
const [currentSection, setCurrentSection] = createSignal(tableOfContents()?.[0]?.slug);

createEffect(() => {
const toc = tableOfContents();
Expand Down Expand Up @@ -96,18 +86,14 @@ function updateHeadings(setter: Setter<TocItem[]>) {
return;
}

console.log("update");

setter(
[
...document
.getElementsByTagName("article")[0]
.querySelectorAll("h1, h2, h3, h4, h5, h6"),
].map((element) => ({
depth: Number(element.tagName.substr(1)),
text: element.textContent!,
slug: element.id,
})),
[...document.getElementsByTagName("article")[0].querySelectorAll("h1, h2, h3, h4, h5, h6")].map(
element => ({
depth: Number(element.tagName.substr(1)),
text: element.textContent!,
slug: element.id,
}),
),
);
}

Expand All @@ -121,7 +107,7 @@ export function TableOfContents() {
createEffect(
on(
() => path.pathname,
(pathname) => {
pathname => {
if (isServer) return;

updateHeadings(setToc);
Expand All @@ -134,12 +120,10 @@ export function TableOfContents() {
createEffect(
on(
() => currentSection(),
(currentSection) => {
currentSection => {
if (isServer) return;

const element = document.querySelector(
`a[data-toc-slug="${currentSection}"]`,
);
const element = document.querySelector(`a[data-toc-slug="${currentSection}"]`);

element?.scrollIntoView({
behavior: "smooth",
Expand All @@ -161,7 +145,7 @@ export function TableOfContents() {
</h2>
<ol class="mt-3 text-sm">
<For each={toc()}>
{(section) => (
{section => (
<li>
<h3>
<a
Expand Down
40 changes: 18 additions & 22 deletions apps/docs/src/components/theme-selector.tsx
Original file line number Diff line number Diff line change
@@ -1,54 +1,59 @@
import { ConfigColorMode, Select, useColorMode } from "@kobalte/core";
import { JSX } from "solid-js";
import { Dynamic } from "solid-js/web";
import { JSX, onMount, createSignal } from "solid-js";

import { DesktopIcon, MoonIcon, SunIcon } from "./icons";

interface ThemeOption {
value: ConfigColorMode;
label: string;
icon: () => JSX.Element;
icon: (clazz: string) => JSX.Element;
}

const THEME_OPTIONS: ThemeOption[] = [
{
value: "light",
label: "Light",
icon: () => <SunIcon class="h-4 w-4" />,
icon: (clazz: string) => <SunIcon class={clazz} />,
},
{
value: "dark",
label: "Dark",
icon: () => <MoonIcon class="h-4 w-4" />,
icon: (clazz: string) => <MoonIcon class={clazz} />,
},
{
value: "system",
label: "System",
icon: () => <DesktopIcon class="h-4 w-4" />,
icon: (clazz: string) => <DesktopIcon class={clazz} />,
},
];

export function ThemeSelector() {
const { colorMode, setColorMode } = useColorMode();
const [selectedTheme, setSelectedTheme] = createSignal<ThemeOption>();

onMount(() => {
setSelectedTheme(THEME_OPTIONS.find(option => option.value === colorMode()));
});

return (
<Select.Root<ThemeOption>
options={THEME_OPTIONS}
optionValue="value"
optionTextValue="label"
defaultValue={THEME_OPTIONS.find(
(option) => option.value === colorMode(),
)}
onChange={(option) => setColorMode(option.value)}
value={selectedTheme() ?? THEME_OPTIONS[0]}
onChange={option => {
setSelectedTheme(option);
setColorMode(option.value);
}}
gutter={8}
sameWidth={false}
placement="bottom"
itemComponent={(props) => (
itemComponent={props => (
<Select.Item
item={props.item}
class="flex items-center space-x-2 px-3 py-1 text-sm outline-none ui-selected:text-sky-700 ui-highlighted:bg-zinc-100 transition-colors cursor-default dark:ui-selected:text-sky-400 dark:ui-highlighted:bg-zinc-700"
>
{props.item.rawValue.icon()}
{props.item.rawValue.icon("h-4 w-4")}
<Select.ItemLabel>{props.item.rawValue.label}</Select.ItemLabel>
</Select.Item>
)}
Expand All @@ -57,16 +62,7 @@ export function ThemeSelector() {
aria-label="toggle color mode"
class="flex p-2.5 rounded-md cursor-pointer items-center justify-center transition text-zinc-700 hover:text-zinc-800 hover:bg-zinc-100 dark:text-zinc-300 dark:hover:text-zinc-200 dark:hover:bg-zinc-800"
>
<Select.Value<ThemeOption>>
{({ selectedOptions }) => (
<Dynamic
component={
selectedOptions()[0].value === "dark" ? MoonIcon : SunIcon
}
class="h-5 w-5"
/>
)}
</Select.Value>
<Select.Value<ThemeOption>>{state => state.selectedOption().icon("h-5 w-5")}</Select.Value>
</Select.Trigger>
<Select.Portal>
<Select.Content class="bg-white border border-zinc-300 rounded shadow-md py-1 z-50 dark:text-zinc-300 dark:bg-zinc-800 dark:border-none dark:shadow-none">
Expand Down

0 comments on commit 2dfeb71

Please sign in to comment.