@fumadocs/base-ui 16.7.0 → 16.7.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (33) hide show
  1. package/css/generated/docs.css +1 -3
  2. package/css/generated/notebook.css +1 -3
  3. package/css/generated/shared.css +2 -1
  4. package/dist/components/accordion.js +2 -2
  5. package/dist/components/dialog/search.js +2 -2
  6. package/dist/components/files.js +3 -3
  7. package/dist/components/heading.js +2 -2
  8. package/dist/components/sidebar/tabs/dropdown.js +1 -1
  9. package/dist/components/toc/index.d.ts +3 -2
  10. package/dist/components/toc/index.js +3 -2
  11. package/dist/layouts/docs/client.js +1 -1
  12. package/dist/layouts/docs/page/client.d.ts +6 -6
  13. package/dist/layouts/docs/page/client.js +10 -10
  14. package/dist/layouts/docs/page/slots/breadcrumb.js +2 -1
  15. package/dist/layouts/docs/page/slots/toc.d.ts +29 -1
  16. package/dist/layouts/docs/page/slots/toc.js +137 -4
  17. package/dist/layouts/docs/slots/container.js +1 -1
  18. package/dist/layouts/docs/slots/sidebar.js +7 -7
  19. package/dist/layouts/home/slots/header.js +1 -1
  20. package/dist/layouts/notebook/client.js +1 -1
  21. package/dist/layouts/notebook/page/client.d.ts +6 -6
  22. package/dist/layouts/notebook/page/client.js +10 -10
  23. package/dist/layouts/notebook/page/slots/toc.d.ts +29 -1
  24. package/dist/layouts/notebook/page/slots/toc.js +136 -4
  25. package/dist/layouts/notebook/slots/sidebar.js +5 -5
  26. package/dist/layouts/shared/client.d.ts +2 -2
  27. package/dist/layouts/shared/index.d.ts +3 -3
  28. package/dist/layouts/shared/slots/search-trigger.d.ts +3 -3
  29. package/package.json +4 -6
  30. package/dist/layouts/docs/page/slots/toc-popover.d.ts +0 -31
  31. package/dist/layouts/docs/page/slots/toc-popover.js +0 -141
  32. package/dist/layouts/notebook/page/slots/toc-popover.d.ts +0 -31
  33. package/dist/layouts/notebook/page/slots/toc-popover.js +0 -141
@@ -328,6 +328,7 @@
328
328
  @source inline("pe-4");
329
329
  @source inline("placeholder");
330
330
  @source inline("pointer-events-none");
331
+ @source inline("popover");
331
332
  @source inline("prefetch");
332
333
  @source inline("previous");
333
334
  @source inline("previousPage");
@@ -428,7 +429,6 @@
428
429
  @source inline("tocPopoverEnabled");
429
430
  @source inline("tocPopoverProps");
430
431
  @source inline("tocProps");
431
- @source inline("tocProvider");
432
432
  @source inline("top");
433
433
  @source inline("top-(--fd-docs-row-1)");
434
434
  @source inline("top-(--fd-docs-row-2)");
@@ -456,7 +456,6 @@
456
456
  @source inline("unlisted");
457
457
  @source inline("url");
458
458
  @source inline("use");
459
- @source inline("useActiveAnchor");
460
459
  @source inline("useDocsLayout");
461
460
  @source inline("useDocsPage");
462
461
  @source inline("useFooterItems");
@@ -468,7 +467,6 @@
468
467
  @source inline("useRef");
469
468
  @source inline("useSidebar");
470
469
  @source inline("useState");
471
- @source inline("useTOCItems");
472
470
  @source inline("useTreeContext");
473
471
  @source inline("useTreePath");
474
472
  @source inline("value");
@@ -357,6 +357,7 @@
357
357
  @source inline("placeholder");
358
358
  @source inline("pointer-events-none");
359
359
  @source inline("pointerType");
360
+ @source inline("popover");
360
361
  @source inline("prefetch");
361
362
  @source inline("previous");
362
363
  @source inline("previousPage");
@@ -462,7 +463,6 @@
462
463
  @source inline("tocPopoverEnabled");
463
464
  @source inline("tocPopoverProps");
464
465
  @source inline("tocProps");
465
- @source inline("tocProvider");
466
466
  @source inline("top");
467
467
  @source inline("top-(--fd-docs-row-1)");
468
468
  @source inline("top-(--fd-docs-row-2)");
@@ -491,7 +491,6 @@
491
491
  @source inline("unlisted");
492
492
  @source inline("url");
493
493
  @source inline("use");
494
- @source inline("useActiveAnchor");
495
494
  @source inline("useDocsPage");
496
495
  @source inline("useFooterItems");
497
496
  @source inline("useI18n");
@@ -502,7 +501,6 @@
502
501
  @source inline("useProvider");
503
502
  @source inline("useRef");
504
503
  @source inline("useSidebar");
505
- @source inline("useTOCItems");
506
504
  @source inline("useTreePath");
507
505
  @source inline("value");
508
506
  @source inline("variant");
@@ -129,7 +129,6 @@
129
129
  @source inline("bg-fd-secondary/50");
130
130
  @source inline("bg-transparent");
131
131
  @source inline("bind");
132
- @source inline("binded");
133
132
  @source inline("black");
134
133
  @source inline("block");
135
134
  @source inline("blocks");
@@ -146,6 +145,7 @@
146
145
  @source inline("bottom");
147
146
  @source inline("bottom-0");
148
147
  @source inline("bottom-1.5");
148
+ @source inline("bound");
149
149
  @source inline("boundary");
150
150
  @source inline("breaking");
151
151
  @source inline("button");
@@ -1054,6 +1054,7 @@
1054
1054
  @source inline("urls");
1055
1055
  @source inline("usage");
1056
1056
  @source inline("use");
1057
+ @source inline("useActiveAnchors");
1057
1058
  @source inline("useCopyButton");
1058
1059
  @source inline("useDocsSearch");
1059
1060
  @source inline("useI18n");
@@ -6,7 +6,7 @@ import { mergeRefs } from "../utils/merge-refs.js";
6
6
  import { Accordion as Accordion$1, AccordionContent, AccordionHeader, AccordionItem, AccordionTrigger } from "./ui/accordion.js";
7
7
  import { useEffect, useRef, useState } from "react";
8
8
  import { jsx, jsxs } from "react/jsx-runtime";
9
- import { Check, Link } from "lucide-react";
9
+ import { Check, LinkIcon } from "lucide-react";
10
10
  //#region src/components/accordion.tsx
11
11
  function Accordions({ ref, className, defaultValue, ...props }) {
12
12
  const rootRef = useRef(null);
@@ -60,7 +60,7 @@ function CopyButton({ id }) {
60
60
  className: "text-fd-muted-foreground me-2"
61
61
  })),
62
62
  onClick,
63
- children: checked ? /* @__PURE__ */ jsx(Check, { className: "size-3.5" }) : /* @__PURE__ */ jsx(Link, { className: "size-3.5" })
63
+ children: checked ? /* @__PURE__ */ jsx(Check, { className: "size-3.5" }) : /* @__PURE__ */ jsx(LinkIcon, { className: "size-3.5" })
64
64
  });
65
65
  }
66
66
  //#endregion
@@ -5,7 +5,7 @@ import { buttonVariants } from "../ui/button.js";
5
5
  import { Fragment, createContext, use, useCallback, useEffect, useEffectEvent, useMemo, useRef, useState } from "react";
6
6
  import { useRouter } from "fumadocs-core/framework";
7
7
  import { Fragment as Fragment$1, jsx, jsxs } from "react/jsx-runtime";
8
- import { ChevronRight, Hash, Search } from "lucide-react";
8
+ import { ChevronRight, Hash, SearchIcon } from "lucide-react";
9
9
  import { cva } from "class-variance-authority";
10
10
  import { useOnChange } from "fumadocs-core/utils/use-on-change";
11
11
  import scrollIntoView from "scroll-into-view-if-needed";
@@ -291,7 +291,7 @@ function SearchDialogListItem({ item, className, children, renderMarkdown = (s)
291
291
  }
292
292
  function SearchDialogIcon(props) {
293
293
  const { isLoading } = useSearch();
294
- return /* @__PURE__ */ jsx(Search, {
294
+ return /* @__PURE__ */ jsx(SearchIcon, {
295
295
  ...props,
296
296
  className: cn("size-5 text-fd-muted-foreground", isLoading && "animate-pulse duration-400", props.className)
297
297
  });
@@ -3,7 +3,7 @@ import { cn } from "../utils/cn.js";
3
3
  import { Collapsible, CollapsibleContent, CollapsibleTrigger } from "./ui/collapsible.js";
4
4
  import { useState } from "react";
5
5
  import { jsx, jsxs } from "react/jsx-runtime";
6
- import { File as File$1, Folder as Folder$1, FolderOpen } from "lucide-react";
6
+ import { FileIcon, FolderIcon, FolderOpen } from "lucide-react";
7
7
  import { cva } from "class-variance-authority";
8
8
  //#region src/components/files.tsx
9
9
  const itemVariants = cva("flex flex-row items-center gap-2 rounded-md px-2 py-1.5 text-sm hover:bg-fd-accent hover:text-fd-accent-foreground [&_svg]:size-4");
@@ -14,7 +14,7 @@ function Files({ className, ...props }) {
14
14
  children: props.children
15
15
  });
16
16
  }
17
- function File({ name, icon = /* @__PURE__ */ jsx(File$1, {}), className, ...rest }) {
17
+ function File({ name, icon = /* @__PURE__ */ jsx(FileIcon, {}), className, ...rest }) {
18
18
  return /* @__PURE__ */ jsxs("div", {
19
19
  className: cn(itemVariants({ className })),
20
20
  ...rest,
@@ -29,7 +29,7 @@ function Folder({ name, defaultOpen = false, ...props }) {
29
29
  ...props,
30
30
  children: [/* @__PURE__ */ jsxs(CollapsibleTrigger, {
31
31
  className: cn(itemVariants({ className: "w-full" })),
32
- children: [open ? /* @__PURE__ */ jsx(FolderOpen, {}) : /* @__PURE__ */ jsx(Folder$1, {}), name]
32
+ children: [open ? /* @__PURE__ */ jsx(FolderOpen, {}) : /* @__PURE__ */ jsx(FolderIcon, {}), name]
33
33
  }), /* @__PURE__ */ jsx(CollapsibleContent, { children: /* @__PURE__ */ jsx("div", {
34
34
  className: "ms-2 flex flex-col border-l ps-2",
35
35
  children: props.children
@@ -1,6 +1,6 @@
1
1
  import { cn } from "../utils/cn.js";
2
2
  import { jsx, jsxs } from "react/jsx-runtime";
3
- import { Link } from "lucide-react";
3
+ import { LinkIcon } from "lucide-react";
4
4
  //#region src/components/heading.tsx
5
5
  function Heading({ as, className, ...props }) {
6
6
  const As = as ?? "h1";
@@ -16,7 +16,7 @@ function Heading({ as, className, ...props }) {
16
16
  href: `#${props.id}`,
17
17
  className: "peer",
18
18
  children: props.children
19
- }), /* @__PURE__ */ jsx(Link, {
19
+ }), /* @__PURE__ */ jsx(LinkIcon, {
20
20
  "aria-hidden": true,
21
21
  className: "size-3.5 shrink-0 text-fd-muted-foreground opacity-0 transition-opacity peer-hover:opacity-100"
22
22
  })]
@@ -1,8 +1,8 @@
1
1
  "use client";
2
2
  import { cn } from "../../../utils/cn.js";
3
- import { useSidebar } from "../base.js";
4
3
  import { Popover, PopoverContent, PopoverTrigger } from "../../ui/popover.js";
5
4
  import { isLayoutTabActive } from "../../../layouts/shared/index.js";
5
+ import { useSidebar } from "../base.js";
6
6
  import { useMemo, useState } from "react";
7
7
  import { usePathname } from "fumadocs-core/framework";
8
8
  import { Fragment as Fragment$1, jsx, jsxs } from "react/jsx-runtime";
@@ -4,7 +4,8 @@ import * as Primitive from "fumadocs-core/toc";
4
4
 
5
5
  //#region src/components/toc/index.d.ts
6
6
  declare function useTOCItems(): Primitive.TOCItemType[];
7
- type TOCProviderProps = ComponentProps<typeof Primitive.AnchorProvider>;
7
+ type TOCProviderProps = Primitive.AnchorProviderProps;
8
+ declare const useActiveAnchor: typeof Primitive.useActiveAnchor, useActiveAnchors: typeof Primitive.useActiveAnchors;
8
9
  declare function TOCProvider({
9
10
  toc,
10
11
  children,
@@ -23,4 +24,4 @@ declare function TocThumb({
23
24
  ...props
24
25
  }: ComponentProps<'div'> & RefProps): react_jsx_runtime0.JSX.Element;
25
26
  //#endregion
26
- export { TOCProvider, TOCProviderProps, TOCScrollArea, TocThumb, useTOCItems };
27
+ export { TOCProvider, TOCProviderProps, TOCScrollArea, TocThumb, useActiveAnchor, useActiveAnchors, useTOCItems };
@@ -10,6 +10,7 @@ const TOCContext = createContext([]);
10
10
  function useTOCItems() {
11
11
  return use(TOCContext);
12
12
  }
13
+ const { useActiveAnchor, useActiveAnchors } = Primitive;
13
14
  function TOCProvider({ toc, children, ...props }) {
14
15
  return /* @__PURE__ */ jsx(TOCContext, {
15
16
  value: toc,
@@ -34,7 +35,7 @@ function TOCScrollArea({ ref, className, ...props }) {
34
35
  }
35
36
  function TocThumb({ containerRef, ...props }) {
36
37
  const thumbRef = useRef(null);
37
- const active = Primitive.useActiveAnchors();
38
+ const active = useActiveAnchors();
38
39
  function update(info) {
39
40
  const element = thumbRef.current;
40
41
  if (!element) return;
@@ -75,4 +76,4 @@ function calc(container, active) {
75
76
  return [upper, lower - upper];
76
77
  }
77
78
  //#endregion
78
- export { TOCProvider, TOCScrollArea, TocThumb, useTOCItems };
79
+ export { TOCProvider, TOCScrollArea, TocThumb, useActiveAnchor, useActiveAnchors, useTOCItems };
@@ -1,9 +1,9 @@
1
1
  "use client";
2
2
  import { cn } from "../../utils/cn.js";
3
3
  import { TreeContextProvider } from "../../contexts/tree.js";
4
- import { useIsScrollTop } from "../../utils/use-is-scroll-top.js";
5
4
  import { baseSlots } from "../shared/client.js";
6
5
  import { isLayoutTabActive, useLinkItems } from "../shared/index.js";
6
+ import { useIsScrollTop } from "../../utils/use-is-scroll-top.js";
7
7
  import { Sidebar, SidebarProvider, SidebarTrigger, useSidebar } from "./slots/sidebar.js";
8
8
  import { Header } from "./slots/header.js";
9
9
  import { Container } from "./slots/container.js";
@@ -1,6 +1,4 @@
1
- import { TOCProviderProps } from "../../../components/toc/index.js";
2
- import { TOCProps } from "./slots/toc.js";
3
- import { TOCPopoverProps } from "./slots/toc-popover.js";
1
+ import { TOCPopoverProps, TOCProps, TOCProviderProps } from "./slots/toc.js";
4
2
  import { FooterProps } from "./slots/footer.js";
5
3
  import { BreadcrumbProps } from "./slots/breadcrumb.js";
6
4
  import { ComponentProps, FC, ReactNode } from "react";
@@ -51,10 +49,12 @@ interface TableOfContentPopoverOptions extends TOCPopoverProps {
51
49
  component?: ReactNode;
52
50
  }
53
51
  interface DocsPageSlots {
54
- toc?: FC<TOCProps>;
52
+ toc?: {
53
+ provider: FC<TOCProviderProps>;
54
+ main?: FC<TOCProps>;
55
+ popover?: FC<TOCPopoverProps>;
56
+ };
55
57
  container?: FC<ComponentProps<'article'>>;
56
- tocPopover?: FC<TOCPopoverProps>;
57
- tocProvider?: FC<TOCProviderProps>;
58
58
  footer?: FC<FooterProps>;
59
59
  breadcrumb?: FC<BreadcrumbProps>;
60
60
  }
@@ -1,9 +1,7 @@
1
1
  "use client";
2
2
  import { useI18n } from "../../../contexts/i18n.js";
3
3
  import { cn } from "../../../utils/cn.js";
4
- import { TOCProvider } from "../../../components/toc/index.js";
5
- import { TOC } from "./slots/toc.js";
6
- import { TOCPopover } from "./slots/toc-popover.js";
4
+ import { TOC, TOCPopover, TOCProvider } from "./slots/toc.js";
7
5
  import { Footer } from "./slots/footer.js";
8
6
  import { Breadcrumb } from "./slots/breadcrumb.js";
9
7
  import { Container } from "./slots/container.js";
@@ -16,19 +14,21 @@ function useDocsPage() {
16
14
  if (!context) throw new Error("Please use page components under <DocsPage /> (`fumadocs-ui/layouts/docs/page`).");
17
15
  return context;
18
16
  }
19
- function DocsPage({ tableOfContent: { enabled: tocEnabled, single = false, ...tocProps } = {}, tableOfContentPopover: { enabled: tocPopoverEnabled, ...tocPopoverProps } = {}, footer = {}, breadcrumb = {}, full = false, toc = [], slots: defaultSlots = {}, children, ...containerProps }) {
17
+ function DocsPage({ tableOfContent: { enabled: tocEnabled, single, ...tocProps } = {}, tableOfContentPopover: { enabled: tocPopoverEnabled, ...tocPopoverProps } = {}, footer = {}, breadcrumb = {}, full = false, toc = [], slots: defaultSlots = {}, children, ...containerProps }) {
20
18
  tocEnabled ??= Boolean(!full && (toc.length > 0 || tocProps.footer || tocProps.header));
21
19
  tocPopoverEnabled ??= Boolean(toc.length > 0 || tocPopoverProps.header || tocPopoverProps.footer);
22
20
  const slots = {
23
21
  breadcrumb: breadcrumb.enabled !== false ? defaultSlots.breadcrumb ?? InlineBreadcrumb : void 0,
24
22
  footer: footer.enabled !== false ? defaultSlots.footer ?? InlineFooter : void 0,
25
- toc: tocEnabled ? defaultSlots.toc ?? InlineTOC : void 0,
26
- tocPopover: tocPopoverEnabled ? defaultSlots.tocPopover ?? InlineTOCPopover : void 0,
27
- tocProvider: defaultSlots.tocProvider ?? TOCProvider,
23
+ toc: defaultSlots.toc ?? {
24
+ provider: TOCProvider,
25
+ main: tocEnabled ? InlineTOC : void 0,
26
+ popover: tocPopoverEnabled ? InlineTOCPopover : void 0
27
+ },
28
28
  container: defaultSlots.container ?? Container
29
29
  };
30
30
  let content = /* @__PURE__ */ jsxs(Fragment$1, { children: [
31
- slots.tocPopover && /* @__PURE__ */ jsx(slots.tocPopover, {}),
31
+ slots.toc?.popover && /* @__PURE__ */ jsx(slots.toc.popover, {}),
32
32
  slots.container && /* @__PURE__ */ jsxs(slots.container, {
33
33
  ...containerProps,
34
34
  children: [
@@ -37,9 +37,9 @@ function DocsPage({ tableOfContent: { enabled: tocEnabled, single = false, ...to
37
37
  slots.footer && /* @__PURE__ */ jsx(slots.footer, {})
38
38
  ]
39
39
  }),
40
- slots.toc && /* @__PURE__ */ jsx(slots.toc, {})
40
+ slots.toc?.main && /* @__PURE__ */ jsx(slots.toc.main, {})
41
41
  ] });
42
- if (slots.tocProvider) content = /* @__PURE__ */ jsx(slots.tocProvider, {
42
+ if (slots.toc) content = /* @__PURE__ */ jsx(slots.toc.provider, {
43
43
  single,
44
44
  toc: tocEnabled || tocPopoverEnabled ? toc : [],
45
45
  children: content
@@ -2,7 +2,8 @@ import { cn } from "../../../../utils/cn.js";
2
2
  import { useTreeContext, useTreePath } from "../../../../contexts/tree.js";
3
3
  import { Fragment, useMemo } from "react";
4
4
  import { jsx, jsxs } from "react/jsx-runtime";
5
- import { ChevronRight, Link } from "lucide-react";
5
+ import Link from "fumadocs-core/link";
6
+ import { ChevronRight } from "lucide-react";
6
7
  import { getBreadcrumbItemsFromPath } from "fumadocs-core/breadcrumb";
7
8
  //#region src/layouts/docs/page/slots/breadcrumb.tsx
8
9
  function Breadcrumb({ includeRoot, includeSeparator, includePage, ...props }) {
@@ -1,7 +1,10 @@
1
+ import { TOCProviderProps as TOCProviderProps$1 } from "../../../../components/toc/index.js";
1
2
  import { ComponentProps, ReactNode } from "react";
2
3
  import * as react_jsx_runtime0 from "react/jsx-runtime";
3
4
 
4
5
  //#region src/layouts/docs/page/slots/toc.d.ts
6
+ type TOCProviderProps = TOCProviderProps$1;
7
+ declare function TOCProvider(props: TOCProviderProps): react_jsx_runtime0.JSX.Element;
5
8
  interface TOCProps {
6
9
  container?: ComponentProps<'div'>;
7
10
  /**
@@ -23,5 +26,30 @@ declare function TOC({
23
26
  footer,
24
27
  style
25
28
  }: TOCProps): react_jsx_runtime0.JSX.Element;
29
+ interface TOCPopoverProps {
30
+ container?: ComponentProps<'div'>;
31
+ trigger?: ComponentProps<'button'>;
32
+ content?: ComponentProps<'div'>;
33
+ /**
34
+ * Custom content in TOC container, before the main TOC
35
+ */
36
+ header?: ReactNode;
37
+ /**
38
+ * Custom content in TOC container, after the main TOC
39
+ */
40
+ footer?: ReactNode;
41
+ /**
42
+ * @defaultValue 'normal'
43
+ */
44
+ style?: 'normal' | 'clerk';
45
+ }
46
+ declare function TOCPopover({
47
+ container,
48
+ trigger,
49
+ content,
50
+ header,
51
+ footer,
52
+ style
53
+ }: TOCPopoverProps): react_jsx_runtime0.JSX.Element;
26
54
  //#endregion
27
- export { TOC, TOCProps };
55
+ export { TOC, TOCPopover, TOCPopoverProps, TOCProps, TOCProvider, TOCProviderProps };
@@ -1,12 +1,20 @@
1
1
  "use client";
2
- import { I18nLabel } from "../../../../contexts/i18n.js";
2
+ import { I18nLabel, useI18n } from "../../../../contexts/i18n.js";
3
3
  import { cn } from "../../../../utils/cn.js";
4
- import { TOCScrollArea } from "../../../../components/toc/index.js";
4
+ import { TOCProvider as TOCProvider$1, TOCScrollArea, useActiveAnchor, useTOCItems } from "../../../../components/toc/index.js";
5
5
  import { TOCItems } from "../../../../components/toc/default.js";
6
6
  import { TOCItems as TOCItems$1 } from "../../../../components/toc/clerk.js";
7
+ import { useTreePath } from "../../../../contexts/tree.js";
8
+ import { Collapsible, CollapsibleContent, CollapsibleTrigger } from "../../../../components/ui/collapsible.js";
9
+ import { useDocsLayout } from "../../client.js";
10
+ import "../../index.js";
11
+ import { createContext, use, useEffect, useEffectEvent, useMemo, useRef, useState } from "react";
7
12
  import { jsx, jsxs } from "react/jsx-runtime";
8
- import { Text } from "lucide-react";
13
+ import { ChevronDown, Text } from "lucide-react";
9
14
  //#region src/layouts/docs/page/slots/toc.tsx
15
+ function TOCProvider(props) {
16
+ return /* @__PURE__ */ jsx(TOCProvider$1, { ...props });
17
+ }
10
18
  function TOC({ container, header, footer, style }) {
11
19
  return /* @__PURE__ */ jsxs("div", {
12
20
  id: "nd-toc",
@@ -24,5 +32,130 @@ function TOC({ container, header, footer, style }) {
24
32
  ]
25
33
  });
26
34
  }
35
+ const TocPopoverContext = createContext(null);
36
+ function TOCPopover({ container, trigger, content, header, footer, style }) {
37
+ return /* @__PURE__ */ jsxs(PageTOCPopover, {
38
+ ...container,
39
+ children: [/* @__PURE__ */ jsx(PageTOCPopoverTrigger, { ...trigger }), /* @__PURE__ */ jsxs(PageTOCPopoverContent, {
40
+ ...content,
41
+ children: [
42
+ header,
43
+ /* @__PURE__ */ jsx(TOCScrollArea, { children: style === "clerk" ? /* @__PURE__ */ jsx(TOCItems$1, {}) : /* @__PURE__ */ jsx(TOCItems, {}) }),
44
+ footer
45
+ ]
46
+ })]
47
+ });
48
+ }
49
+ function PageTOCPopover({ className, children, ...rest }) {
50
+ const ref = useRef(null);
51
+ const [open, setOpen] = useState(false);
52
+ const { isNavTransparent } = useDocsLayout();
53
+ const onClick = useEffectEvent((e) => {
54
+ if (!open) return;
55
+ if (ref.current && !ref.current.contains(e.target)) setOpen(false);
56
+ });
57
+ useEffect(() => {
58
+ window.addEventListener("click", onClick);
59
+ return () => {
60
+ window.removeEventListener("click", onClick);
61
+ };
62
+ }, []);
63
+ return /* @__PURE__ */ jsx(TocPopoverContext, {
64
+ value: useMemo(() => ({
65
+ open,
66
+ setOpen
67
+ }), [setOpen, open]),
68
+ children: /* @__PURE__ */ jsx(Collapsible, {
69
+ open,
70
+ onOpenChange: setOpen,
71
+ "data-toc-popover": "",
72
+ className: cn("sticky top-(--fd-docs-row-2) z-10 [grid-area:toc-popover] h-(--fd-toc-popover-height) xl:hidden max-xl:layout:[--fd-toc-popover-height:--spacing(10)]", className),
73
+ ...rest,
74
+ children: /* @__PURE__ */ jsx("header", {
75
+ ref,
76
+ className: cn("border-b backdrop-blur-sm transition-colors", (!isNavTransparent || open) && "bg-fd-background/80", open && "shadow-lg"),
77
+ children
78
+ })
79
+ })
80
+ });
81
+ }
82
+ function PageTOCPopoverTrigger({ className, ...props }) {
83
+ const { text } = useI18n();
84
+ const { open } = use(TocPopoverContext);
85
+ const items = useTOCItems();
86
+ const active = useActiveAnchor();
87
+ const selected = useMemo(() => items.findIndex((item) => active === item.url.slice(1)), [items, active]);
88
+ const path = useTreePath().at(-1);
89
+ const showItem = selected !== -1 && !open;
90
+ return /* @__PURE__ */ jsxs(CollapsibleTrigger, {
91
+ className: cn("flex w-full h-10 items-center text-sm text-fd-muted-foreground gap-2.5 px-4 py-2.5 text-start focus-visible:outline-none [&_svg]:size-4 md:px-6", className),
92
+ "data-toc-popover-trigger": "",
93
+ ...props,
94
+ children: [
95
+ /* @__PURE__ */ jsx(ProgressCircle, {
96
+ value: (selected + 1) / Math.max(1, items.length),
97
+ max: 1,
98
+ className: cn("shrink-0", open && "text-fd-primary")
99
+ }),
100
+ /* @__PURE__ */ jsxs("span", {
101
+ className: "grid flex-1 *:my-auto *:row-start-1 *:col-start-1",
102
+ children: [/* @__PURE__ */ jsx("span", {
103
+ className: cn("truncate transition-[opacity,translate,color]", open && "text-fd-foreground", showItem && "opacity-0 -translate-y-full pointer-events-none"),
104
+ children: path?.name ?? text.toc
105
+ }), /* @__PURE__ */ jsx("span", {
106
+ className: cn("truncate transition-[opacity,translate]", !showItem && "opacity-0 translate-y-full pointer-events-none"),
107
+ children: items[selected]?.title
108
+ })]
109
+ }),
110
+ /* @__PURE__ */ jsx(ChevronDown, { className: cn("shrink-0 transition-transform mx-0.5", open && "rotate-180") })
111
+ ]
112
+ });
113
+ }
114
+ function clamp(input, min, max) {
115
+ if (input < min) return min;
116
+ if (input > max) return max;
117
+ return input;
118
+ }
119
+ function ProgressCircle({ value, strokeWidth = 2, size = 24, min = 0, max = 100, ...restSvgProps }) {
120
+ const normalizedValue = clamp(value, min, max);
121
+ const radius = (size - strokeWidth) / 2;
122
+ const circumference = 2 * Math.PI * radius;
123
+ const progress = normalizedValue / max * circumference;
124
+ const circleProps = {
125
+ cx: size / 2,
126
+ cy: size / 2,
127
+ r: radius,
128
+ fill: "none",
129
+ strokeWidth
130
+ };
131
+ return /* @__PURE__ */ jsxs("svg", {
132
+ role: "progressbar",
133
+ viewBox: `0 0 ${size} ${size}`,
134
+ "aria-valuenow": normalizedValue,
135
+ "aria-valuemin": min,
136
+ "aria-valuemax": max,
137
+ ...restSvgProps,
138
+ children: [/* @__PURE__ */ jsx("circle", {
139
+ ...circleProps,
140
+ className: "stroke-current/25"
141
+ }), /* @__PURE__ */ jsx("circle", {
142
+ ...circleProps,
143
+ stroke: "currentColor",
144
+ strokeDasharray: circumference,
145
+ strokeDashoffset: circumference - progress,
146
+ strokeLinecap: "round",
147
+ transform: `rotate(-90 ${size / 2} ${size / 2})`,
148
+ className: "transition-all"
149
+ })]
150
+ });
151
+ }
152
+ function PageTOCPopoverContent(props) {
153
+ return /* @__PURE__ */ jsx(CollapsibleContent, {
154
+ "data-toc-popover-content": "",
155
+ ...props,
156
+ className: cn("flex flex-col px-4 max-h-[50vh] md:px-6", props.className),
157
+ children: props.children
158
+ });
159
+ }
27
160
  //#endregion
28
- export { TOC };
161
+ export { TOC, TOCPopover, TOCProvider };
@@ -1,6 +1,6 @@
1
1
  import { cn } from "../../../utils/cn.js";
2
- import "../index.js";
3
2
  import { useDocsLayout } from "../client.js";
3
+ import "../index.js";
4
4
  import { jsx } from "react/jsx-runtime";
5
5
  //#region src/layouts/docs/slots/container.tsx
6
6
  function Container(props) {
@@ -2,20 +2,20 @@
2
2
  import { cn } from "../../../utils/cn.js";
3
3
  import { buttonVariants } from "../../../components/ui/button.js";
4
4
  import { mergeRefs } from "../../../utils/merge-refs.js";
5
- import { ScrollArea, ScrollViewport } from "../../../components/ui/scroll-area.js";
6
- import { SidebarCollapseTrigger as SidebarCollapseTrigger$1, SidebarContent as SidebarContent$1, SidebarDrawerContent, SidebarDrawerOverlay, SidebarFolder as SidebarFolder$1, SidebarFolderContent as SidebarFolderContent$1, SidebarFolderLink as SidebarFolderLink$1, SidebarFolderTrigger as SidebarFolderTrigger$1, SidebarItem as SidebarItem$1, SidebarProvider as SidebarProvider$1, SidebarSeparator as SidebarSeparator$1, SidebarTrigger as SidebarTrigger$1, base_exports, useFolder, useFolderDepth } from "../../../components/sidebar/base.js";
7
- import { createPageTreeRenderer } from "../../../components/sidebar/page-tree.js";
8
5
  import { Popover, PopoverContent, PopoverTrigger } from "../../../components/ui/popover.js";
9
6
  import { SearchTrigger } from "../../shared/slots/search-trigger.js";
10
7
  import { LinkItem } from "../../shared/client.js";
11
8
  import { isLayoutTabActive } from "../../shared/index.js";
9
+ import { ScrollArea, ScrollViewport } from "../../../components/ui/scroll-area.js";
10
+ import { SidebarCollapseTrigger as SidebarCollapseTrigger$1, SidebarContent as SidebarContent$1, SidebarDrawerContent, SidebarDrawerOverlay, SidebarFolder as SidebarFolder$1, SidebarFolderContent as SidebarFolderContent$1, SidebarFolderLink as SidebarFolderLink$1, SidebarFolderTrigger as SidebarFolderTrigger$1, SidebarItem as SidebarItem$1, SidebarProvider as SidebarProvider$1, SidebarSeparator as SidebarSeparator$1, SidebarTrigger as SidebarTrigger$1, base_exports, useFolder, useFolderDepth } from "../../../components/sidebar/base.js";
11
+ import { createPageTreeRenderer } from "../../../components/sidebar/page-tree.js";
12
12
  import { createLinkItemRenderer } from "../../../components/sidebar/link-item.js";
13
13
  import { useDocsLayout } from "../client.js";
14
14
  import { useMemo, useRef, useState } from "react";
15
15
  import { usePathname } from "fumadocs-core/framework";
16
16
  import { Fragment as Fragment$1, jsx, jsxs } from "react/jsx-runtime";
17
17
  import Link from "fumadocs-core/link";
18
- import { Check, ChevronsUpDown, Languages, Sidebar as Sidebar$1 } from "lucide-react";
18
+ import { Check, ChevronsUpDown, Languages, SidebarIcon } from "lucide-react";
19
19
  import { cva } from "class-variance-authority";
20
20
  //#region src/layouts/docs/slots/sidebar.tsx
21
21
  const itemVariants = cva("relative flex flex-row items-center gap-2 rounded-lg p-2 text-start text-fd-muted-foreground wrap-anywhere [&_svg]:size-4 [&_svg]:shrink-0", { variants: {
@@ -53,7 +53,7 @@ function Sidebar({ footer, banner, collapsible = true, components, ...rest }) {
53
53
  size: "icon-sm",
54
54
  className: "mb-auto text-fd-muted-foreground"
55
55
  })),
56
- children: /* @__PURE__ */ jsx(Sidebar$1, {})
56
+ children: /* @__PURE__ */ jsx(SidebarIcon, {})
57
57
  })
58
58
  ]
59
59
  }),
@@ -111,7 +111,7 @@ function Sidebar({ footer, banner, collapsible = true, components, ...rest }) {
111
111
  size: "icon-sm",
112
112
  className: "p-2"
113
113
  })),
114
- children: /* @__PURE__ */ jsx(Sidebar$1, {})
114
+ children: /* @__PURE__ */ jsx(SidebarIcon, {})
115
115
  })
116
116
  ]
117
117
  }),
@@ -174,7 +174,7 @@ function SidebarContent({ ref: refProp, className, children, ...props }) {
174
174
  size: "icon-sm",
175
175
  className: "rounded-lg"
176
176
  })),
177
- children: /* @__PURE__ */ jsx(Sidebar$1, {})
177
+ children: /* @__PURE__ */ jsx(SidebarIcon, {})
178
178
  }), /* @__PURE__ */ jsx(SearchTrigger, {
179
179
  className: "rounded-lg",
180
180
  hideIfDisabled: true
@@ -1,9 +1,9 @@
1
1
  "use client";
2
2
  import { cn } from "../../../utils/cn.js";
3
3
  import { buttonVariants } from "../../../components/ui/button.js";
4
- import { useIsScrollTop } from "../../../utils/use-is-scroll-top.js";
5
4
  import { LinkItem } from "../../shared/client.js";
6
5
  import "../../shared/index.js";
6
+ import { useIsScrollTop } from "../../../utils/use-is-scroll-top.js";
7
7
  import { NavigationMenu as NavigationMenuRoot, NavigationMenuContent, NavigationMenuItem, NavigationMenuLink, NavigationMenuList, NavigationMenuTrigger, NavigationMenuViewport } from "../../../components/ui/navigation-menu.js";
8
8
  import { useHomeLayout } from "../index.js";
9
9
  import { Fragment, useState } from "react";
@@ -1,8 +1,8 @@
1
1
  "use client";
2
2
  import { TreeContextProvider } from "../../contexts/tree.js";
3
- import { useIsScrollTop } from "../../utils/use-is-scroll-top.js";
4
3
  import { baseSlots } from "../shared/client.js";
5
4
  import { useLinkItems } from "../shared/index.js";
5
+ import { useIsScrollTop } from "../../utils/use-is-scroll-top.js";
6
6
  import { Container } from "./slots/container.js";
7
7
  import { Sidebar, SidebarCollapseTrigger, SidebarProvider, SidebarTrigger, useSidebar } from "./slots/sidebar.js";
8
8
  import { Header } from "./slots/header.js";
@@ -1,6 +1,4 @@
1
- import { TOCProviderProps } from "../../../components/toc/index.js";
2
- import { TOCProps } from "./slots/toc.js";
3
- import { TOCPopoverProps } from "./slots/toc-popover.js";
1
+ import { TOCPopoverProps, TOCProps, TOCProviderProps } from "./slots/toc.js";
4
2
  import { FooterProps } from "./slots/footer.js";
5
3
  import { BreadcrumbProps } from "./slots/breadcrumb.js";
6
4
  import { ComponentProps, FC, ReactNode } from "react";
@@ -9,10 +7,12 @@ import { TOCItemType } from "fumadocs-core/toc";
9
7
 
10
8
  //#region src/layouts/notebook/page/client.d.ts
11
9
  interface DocsPageSlots {
12
- toc?: FC<TOCProps>;
10
+ toc?: {
11
+ provider: FC<TOCProviderProps>;
12
+ main?: FC<TOCProps>;
13
+ popover?: FC<TOCPopoverProps>;
14
+ };
13
15
  container?: FC<ComponentProps<'article'>>;
14
- tocPopover?: FC<TOCPopoverProps>;
15
- tocProvider?: FC<TOCProviderProps>;
16
16
  footer?: FC<FooterProps>;
17
17
  breadcrumb?: FC<BreadcrumbProps>;
18
18
  }