@fumadocs/base-ui 16.5.4 → 16.6.0
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.
- package/css/generated/shared.css +45 -8
- package/dist/components/dialog/search.d.ts +4 -3
- package/dist/components/dialog/search.d.ts.map +1 -1
- package/dist/components/dialog/search.js +117 -38
- package/dist/components/dialog/search.js.map +1 -1
- package/dist/layouts/home/client.d.ts +1 -1
- package/dist/style.css +54 -33
- package/package.json +7 -3
package/css/generated/shared.css
CHANGED
|
@@ -39,6 +39,7 @@
|
|
|
39
39
|
@source inline("-translate-y-1/2");
|
|
40
40
|
@source inline("@container");
|
|
41
41
|
@source inline("@defaultValue");
|
|
42
|
+
@source inline("@deprecated");
|
|
42
43
|
@source inline("@example");
|
|
43
44
|
@source inline("@keyframes");
|
|
44
45
|
@source inline("@max-lg:col-span-full");
|
|
@@ -70,6 +71,7 @@
|
|
|
70
71
|
@source inline("all");
|
|
71
72
|
@source inline("allowClear");
|
|
72
73
|
@source inline("allowCopy");
|
|
74
|
+
@source inline("allowDangerousHtml");
|
|
73
75
|
@source inline("allowing");
|
|
74
76
|
@source inline("always");
|
|
75
77
|
@source inline("an");
|
|
@@ -124,12 +126,14 @@
|
|
|
124
126
|
@source inline("bg-transparent");
|
|
125
127
|
@source inline("black");
|
|
126
128
|
@source inline("block");
|
|
129
|
+
@source inline("blocks");
|
|
127
130
|
@source inline("body");
|
|
128
131
|
@source inline("boolean");
|
|
129
132
|
@source inline("border");
|
|
130
133
|
@source inline("border-b");
|
|
131
134
|
@source inline("border-fd-foreground/10");
|
|
132
135
|
@source inline("border-l");
|
|
136
|
+
@source inline("border-none");
|
|
133
137
|
@source inline("border-s");
|
|
134
138
|
@source inline("border-t");
|
|
135
139
|
@source inline("border-transparent");
|
|
@@ -187,13 +191,13 @@
|
|
|
187
191
|
@source inline("container");
|
|
188
192
|
@source inline("containerRef");
|
|
189
193
|
@source inline("content");
|
|
190
|
-
@source inline("contentWithHighlights");
|
|
191
194
|
@source inline("context");
|
|
192
195
|
@source inline("controlled/uncontrolled");
|
|
193
196
|
@source inline("copy");
|
|
194
197
|
@source inline("core");
|
|
195
198
|
@source inline("counterSet");
|
|
196
199
|
@source inline("createContext");
|
|
200
|
+
@source inline("createMarkdownRenderer");
|
|
197
201
|
@source inline("createRelativeLink");
|
|
198
202
|
@source inline("css");
|
|
199
203
|
@source inline("ctx");
|
|
@@ -209,16 +213,12 @@
|
|
|
209
213
|
@source inline("data-[active=true]:text-fd-primary");
|
|
210
214
|
@source inline("data-[active]:border-fd-primary");
|
|
211
215
|
@source inline("data-[active]:text-fd-primary");
|
|
212
|
-
@source inline("data-[closed]:animate-fd-dialog-out");
|
|
213
|
-
@source inline("data-[closed]:animate-fd-fade-out");
|
|
214
216
|
@source inline("data-[closed]:animate-fd-popover-out");
|
|
215
217
|
@source inline("data-[ending-style]:data-[activation-direction=left]:translate-x-1/2");
|
|
216
218
|
@source inline("data-[ending-style]:data-[activation-direction=right]:-translate-x-1/2");
|
|
217
219
|
@source inline("data-[ending-style]:h-0");
|
|
218
220
|
@source inline("data-[ending-style]:opacity-0");
|
|
219
221
|
@source inline("data-[inactive]:hidden");
|
|
220
|
-
@source inline("data-[open]:animate-fd-dialog-in");
|
|
221
|
-
@source inline("data-[open]:animate-fd-fade-in");
|
|
222
222
|
@source inline("data-[open]:animate-fd-popover-in");
|
|
223
223
|
@source inline("data-[starting-style]:data-[activation-direction=left]:-translate-x-1/2");
|
|
224
224
|
@source inline("data-[starting-style]:data-[activation-direction=right]:translate-x-1/2");
|
|
@@ -229,18 +229,22 @@
|
|
|
229
229
|
@source inline("data-card");
|
|
230
230
|
@source inline("data-checked");
|
|
231
231
|
@source inline("data-checked:text-fd-accent-foreground");
|
|
232
|
+
@source inline("data-closed:animate-fd-dialog-out");
|
|
233
|
+
@source inline("data-closed:animate-fd-fade-out");
|
|
232
234
|
@source inline("data-collapsed");
|
|
233
235
|
@source inline("data-empty");
|
|
234
236
|
@source inline("data-hidden");
|
|
235
237
|
@source inline("data-icon");
|
|
236
238
|
@source inline("data-line-numbers");
|
|
237
239
|
@source inline("data-line-numbers-start");
|
|
240
|
+
@source inline("data-open:animate-fd-fade-in");
|
|
238
241
|
@source inline("data-open:bg-fd-accent");
|
|
239
242
|
@source inline("data-open:text-fd-accent-foreground");
|
|
240
243
|
@source inline("data-search");
|
|
241
244
|
@source inline("data-search-full");
|
|
242
245
|
@source inline("data-state");
|
|
243
246
|
@source inline("data-theme-toggle");
|
|
247
|
+
@source inline("dataopen:animate-fd-dialog-in");
|
|
244
248
|
@source inline("date");
|
|
245
249
|
@source inline("debounced");
|
|
246
250
|
@source inline("decimal");
|
|
@@ -277,6 +281,7 @@
|
|
|
277
281
|
@source inline("displayed");
|
|
278
282
|
@source inline("div");
|
|
279
283
|
@source inline("divide-fd-border");
|
|
284
|
+
@source inline("divide-x");
|
|
280
285
|
@source inline("divide-y");
|
|
281
286
|
@source inline("docsLayoutCtx");
|
|
282
287
|
@source inline("documented");
|
|
@@ -350,6 +355,7 @@
|
|
|
350
355
|
@source inline("formattedValue");
|
|
351
356
|
@source inline("forwardRef");
|
|
352
357
|
@source inline("found");
|
|
358
|
+
@source inline("fragment");
|
|
353
359
|
@source inline("framework");
|
|
354
360
|
@source inline("free");
|
|
355
361
|
@source inline("from");
|
|
@@ -404,9 +410,11 @@
|
|
|
404
410
|
@source inline("h4");
|
|
405
411
|
@source inline("h5");
|
|
406
412
|
@source inline("h6");
|
|
413
|
+
@source inline("handle");
|
|
407
414
|
@source inline("happens");
|
|
408
415
|
@source inline("has-focus-visible:bg-fd-accent");
|
|
409
416
|
@source inline("hash");
|
|
417
|
+
@source inline("hast");
|
|
410
418
|
@source inline("have");
|
|
411
419
|
@source inline("headers");
|
|
412
420
|
@source inline("heading");
|
|
@@ -414,7 +422,7 @@
|
|
|
414
422
|
@source inline("hence");
|
|
415
423
|
@source inline("here");
|
|
416
424
|
@source inline("hidden");
|
|
417
|
-
@source inline("
|
|
425
|
+
@source inline("highlight");
|
|
418
426
|
@source inline("hooks");
|
|
419
427
|
@source inline("horizontal");
|
|
420
428
|
@source inline("hotKey");
|
|
@@ -441,11 +449,11 @@
|
|
|
441
449
|
@source inline("img");
|
|
442
450
|
@source inline("import");
|
|
443
451
|
@source inline("in");
|
|
452
|
+
@source inline("inPre");
|
|
444
453
|
@source inline("inTab");
|
|
445
454
|
@source inline("index");
|
|
446
455
|
@source inline("infinite");
|
|
447
456
|
@source inline("info");
|
|
448
|
-
@source inline("inline");
|
|
449
457
|
@source inline("inline-flex");
|
|
450
458
|
@source inline("input");
|
|
451
459
|
@source inline("inputType");
|
|
@@ -523,12 +531,15 @@
|
|
|
523
531
|
@source inline("make");
|
|
524
532
|
@source inline("mapped");
|
|
525
533
|
@source inline("marginBottom");
|
|
534
|
+
@source inline("mark");
|
|
526
535
|
@source inline("marked");
|
|
527
536
|
@source inline("mask-[linear-gradient(to_bottom,transparent,white_16px,white_calc(100%-16px),transparent)]");
|
|
537
|
+
@source inline("mask-[linear-gradient(to_bottom,white,white_30px,transparent_80px)]");
|
|
528
538
|
@source inline("maskComposite");
|
|
529
539
|
@source inline("maskImage");
|
|
530
540
|
@source inline("matching");
|
|
531
541
|
@source inline("max-h-(--available-height)");
|
|
542
|
+
@source inline("max-h-20");
|
|
532
543
|
@source inline("max-h-[460px]");
|
|
533
544
|
@source inline("max-h-[600px]");
|
|
534
545
|
@source inline("max-md:bg-fd-secondary");
|
|
@@ -537,6 +548,7 @@
|
|
|
537
548
|
@source inline("max-md:rounded-md");
|
|
538
549
|
@source inline("max-w-[1400px]");
|
|
539
550
|
@source inline("max-w-[98vw]");
|
|
551
|
+
@source inline("max-w-full");
|
|
540
552
|
@source inline("max-w-screen-sm");
|
|
541
553
|
@source inline("max-width");
|
|
542
554
|
@source inline("mb-1");
|
|
@@ -546,6 +558,8 @@
|
|
|
546
558
|
@source inline("md:mb-auto");
|
|
547
559
|
@source inline("md:size-5");
|
|
548
560
|
@source inline("md:top-[calc(50%-250px)]");
|
|
561
|
+
@source inline("mdComponents");
|
|
562
|
+
@source inline("mdRenderer");
|
|
549
563
|
@source inline("me-1");
|
|
550
564
|
@source inline("me-2");
|
|
551
565
|
@source inline("me-auto");
|
|
@@ -571,6 +585,7 @@
|
|
|
571
585
|
@source inline("mx-auto");
|
|
572
586
|
@source inline("my-0");
|
|
573
587
|
@source inline("my-0!");
|
|
588
|
+
@source inline("my-0.5");
|
|
574
589
|
@source inline("my-4");
|
|
575
590
|
@source inline("my-6");
|
|
576
591
|
@source inline("my-auto");
|
|
@@ -603,6 +618,7 @@
|
|
|
603
618
|
@source inline("not");
|
|
604
619
|
@source inline("not-last:mb-2");
|
|
605
620
|
@source inline("not-prose");
|
|
621
|
+
@source inline("now");
|
|
606
622
|
@source inline("null");
|
|
607
623
|
@source inline("num");
|
|
608
624
|
@source inline("number");
|
|
@@ -624,13 +640,17 @@
|
|
|
624
640
|
@source inline("onKey");
|
|
625
641
|
@source inline("onKeyDown");
|
|
626
642
|
@source inline("onOpenChange");
|
|
643
|
+
@source inline("onOpenChangeCallback");
|
|
627
644
|
@source inline("onPointerEnter");
|
|
628
645
|
@source inline("onPointerLeave");
|
|
629
646
|
@source inline("onPointerMove");
|
|
630
647
|
@source inline("onPrint");
|
|
631
648
|
@source inline("onSearchChange");
|
|
649
|
+
@source inline("onSearchChangeCallback");
|
|
632
650
|
@source inline("onSelect");
|
|
651
|
+
@source inline("onSelectCallback");
|
|
633
652
|
@source inline("onTagChange");
|
|
653
|
+
@source inline("onTagChangeCallback");
|
|
634
654
|
@source inline("onValueChange");
|
|
635
655
|
@source inline("one");
|
|
636
656
|
@source inline("only");
|
|
@@ -660,6 +680,7 @@
|
|
|
660
680
|
@source inline("owner");
|
|
661
681
|
@source inline("p");
|
|
662
682
|
@source inline("p-0");
|
|
683
|
+
@source inline("p-0.5");
|
|
663
684
|
@source inline("p-1");
|
|
664
685
|
@source inline("p-1.5");
|
|
665
686
|
@source inline("p-2");
|
|
@@ -714,11 +735,14 @@
|
|
|
714
735
|
@source inline("pt-0");
|
|
715
736
|
@source inline("pure");
|
|
716
737
|
@source inline("px");
|
|
738
|
+
@source inline("px-0.5");
|
|
739
|
+
@source inline("px-1");
|
|
717
740
|
@source inline("px-1.5");
|
|
718
741
|
@source inline("px-2");
|
|
719
742
|
@source inline("px-2.5");
|
|
720
743
|
@source inline("px-3");
|
|
721
744
|
@source inline("px-4");
|
|
745
|
+
@source inline("px-px");
|
|
722
746
|
@source inline("py-0.5");
|
|
723
747
|
@source inline("py-1");
|
|
724
748
|
@source inline("py-1.5");
|
|
@@ -744,11 +768,17 @@
|
|
|
744
768
|
@source inline("refs");
|
|
745
769
|
@source inline("region");
|
|
746
770
|
@source inline("registering");
|
|
771
|
+
@source inline("rehype-raw");
|
|
772
|
+
@source inline("rehypeCustomElements");
|
|
773
|
+
@source inline("rehypePlugins");
|
|
774
|
+
@source inline("rehypeRaw");
|
|
747
775
|
@source inline("rel");
|
|
748
776
|
@source inline("relative");
|
|
777
|
+
@source inline("remarkRehypeOptions");
|
|
749
778
|
@source inline("remove");
|
|
750
779
|
@source inline("render");
|
|
751
780
|
@source inline("renderHighlights");
|
|
781
|
+
@source inline("renderMarkdown");
|
|
752
782
|
@source inline("repo");
|
|
753
783
|
@source inline("repository");
|
|
754
784
|
@source inline("required");
|
|
@@ -851,6 +881,7 @@
|
|
|
851
881
|
@source inline("stars");
|
|
852
882
|
@source inline("start-0");
|
|
853
883
|
@source inline("start-3");
|
|
884
|
+
@source inline("start-6");
|
|
854
885
|
@source inline("state");
|
|
855
886
|
@source inline("static");
|
|
856
887
|
@source inline("sticky");
|
|
@@ -859,6 +890,7 @@
|
|
|
859
890
|
@source inline("stroke-fd-foreground/10");
|
|
860
891
|
@source inline("stroke-width");
|
|
861
892
|
@source inline("strokeWidth");
|
|
893
|
+
@source inline("strong");
|
|
862
894
|
@source inline("style");
|
|
863
895
|
@source inline("styles");
|
|
864
896
|
@source inline("success");
|
|
@@ -877,6 +909,7 @@
|
|
|
877
909
|
@source inline("tabs");
|
|
878
910
|
@source inline("tabsRef");
|
|
879
911
|
@source inline("tag");
|
|
912
|
+
@source inline("tagName");
|
|
880
913
|
@source inline("tags");
|
|
881
914
|
@source inline("tailwind-merge");
|
|
882
915
|
@source inline("target");
|
|
@@ -926,6 +959,7 @@
|
|
|
926
959
|
@source inline("top-1.5");
|
|
927
960
|
@source inline("top-1/2");
|
|
928
961
|
@source inline("top-2");
|
|
962
|
+
@source inline("top-2.5");
|
|
929
963
|
@source inline("top-4");
|
|
930
964
|
@source inline("touch");
|
|
931
965
|
@source inline("trailing");
|
|
@@ -950,6 +984,8 @@
|
|
|
950
984
|
@source inline("under");
|
|
951
985
|
@source inline("underline");
|
|
952
986
|
@source inline("underlying");
|
|
987
|
+
@source inline("unified");
|
|
988
|
+
@source inline("unist-util-visit");
|
|
953
989
|
@source inline("unknown");
|
|
954
990
|
@source inline("unmounted");
|
|
955
991
|
@source inline("updateAnchor");
|
|
@@ -978,12 +1014,12 @@
|
|
|
978
1014
|
@source inline("useTheme");
|
|
979
1015
|
@source inline("useTreeContext");
|
|
980
1016
|
@source inline("useTreePath");
|
|
981
|
-
@source inline("used");
|
|
982
1017
|
@source inline("useful");
|
|
983
1018
|
@source inline("user");
|
|
984
1019
|
@source inline("users");
|
|
985
1020
|
@source inline("using");
|
|
986
1021
|
@source inline("usually");
|
|
1022
|
+
@source inline("v");
|
|
987
1023
|
@source inline("v17");
|
|
988
1024
|
@source inline("value");
|
|
989
1025
|
@source inline("valueToIdMap");
|
|
@@ -996,6 +1032,7 @@
|
|
|
996
1032
|
@source inline("viewRef");
|
|
997
1033
|
@source inline("viewport");
|
|
998
1034
|
@source inline("viewportProps");
|
|
1035
|
+
@source inline("visit");
|
|
999
1036
|
@source inline("void");
|
|
1000
1037
|
@source inline("w");
|
|
1001
1038
|
@source inline("w-(--anchor-width)");
|
|
@@ -69,10 +69,12 @@ declare function SearchDialogListItem({
|
|
|
69
69
|
item,
|
|
70
70
|
className,
|
|
71
71
|
children,
|
|
72
|
-
|
|
72
|
+
renderMarkdown,
|
|
73
|
+
renderHighlights: _,
|
|
73
74
|
...props
|
|
74
75
|
}: ComponentProps<'button'> & {
|
|
75
|
-
|
|
76
|
+
renderMarkdown?: (v: string) => ReactNode; /** @deprecated highlight blocks is now wrapped in `<mark />`, use `renderMarkdown` to handle instead. */
|
|
77
|
+
renderHighlights?: (blocks: HighlightedText<ReactNode>[]) => ReactNode;
|
|
76
78
|
item: SearchItemType;
|
|
77
79
|
}): react_jsx_runtime0.JSX.Element;
|
|
78
80
|
declare function SearchDialogIcon(props: ComponentProps<'svg'>): react_jsx_runtime0.JSX.Element;
|
|
@@ -94,7 +96,6 @@ declare function TagsListItem({
|
|
|
94
96
|
}: ComponentProps<'button'> & {
|
|
95
97
|
value: string;
|
|
96
98
|
}): react_jsx_runtime0.JSX.Element;
|
|
97
|
-
declare function renderHighlights(highlights: HighlightedText<ReactNode>[]): ReactNode;
|
|
98
99
|
declare function useSearch(): {
|
|
99
100
|
open: boolean;
|
|
100
101
|
onOpenChange: (open: boolean) => void;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"search.d.ts","names":[],"sources":["../../../src/components/dialog/search.tsx"],"mappings":";;;;;;;
|
|
1
|
+
{"version":3,"file":"search.d.ts","names":[],"sources":["../../../src/components/dialog/search.tsx"],"mappings":";;;;;;;KAgCY,cAAA,IACP,iBAAA;EACC,QAAA;AAAA;EAGA,EAAA;EACA,IAAA;EACA,IAAA,EAAM,SAAA;EACN,QAAA;AAAA;AAAA,UAMW,iBAAA,SAA0B,WAAA;EACzC,MAAA;EACA,cAAA,GAAiB,CAAA;EACjB,QAAA,IAAY,IAAA,EAAM,cAAA;EAClB,SAAA;EAEA,QAAA,EAAU,SAAA;AAAA;AAAA,iBAkHI,YAAA,CAAA;EACd,IAAA;EACA,YAAA;EACA,MAAA;EACA,cAAA;EACA,SAAA;EACA,QAAA,EAAU,YAAA;EACV;AAAA,GACC,iBAAA,GAAiB,kBAAA,CAAA,GAAA,CAAA,OAAA;AAAA,iBA0CJ,kBAAA,CAAmB,KAAA,EAAO,cAAA,UAAqB,kBAAA,CAAA,GAAA,CAAA,OAAA;AAAA,iBAI/C,iBAAA,CAAkB,KAAA,EAAO,cAAA,YAAuB,kBAAA,CAAA,GAAA,CAAA,OAAA;AAAA,iBAehD,iBAAA,CAAA;EACd,QAAA;EACA,SAAA;EAAA,GACG;AAAA,GACF,cAAA,aAAwB,kBAAA,CAAA,GAAA,CAAA,OAAA;AAAA,iBAsBX,kBAAA,CAAmB,KAAA,EAAO,cAAA,UAAqB,kBAAA,CAAA,GAAA,CAAA,OAAA;AAAA,iBAI/C,mBAAA,CAAA;EACd,SAAA;EAAA,GACG;AAAA,GACF,cAAA,QAAsB,MAAA,CAAO,QAAA,IAAS,kBAAA,CAAA,GAAA,CAAA,OAAA;AAAA,iBAczB,mBAAA,CAAA;EACd,QAAA;EACA,SAAA;EAAA,GACG;AAAA,GACF,cAAA,QAAsB,MAAA,CAAO,KAAA,IAAM,kBAAA,CAAA,GAAA,CAAA,OAAA;AAAA,iBAuBtB,gBAAA,CAAA;EACd,KAAA;EACA,KAAA;EAKA,IAAA;EAAA,GACG;AAAA,GACF,IAAA,CAAK,cAAA;EACN,KAAA,EAAO,cAAA;EAhRP;;;EAoRA,KAAA,SAAc,SAAA;EAlRI;;;EAsRlB,IAAA,IAAQ,KAAA;IAAS,IAAA,EAAM,cAAA;IAAgB,OAAA;EAAA,MAA0B,SAAA;AAAA,IAClE,kBAAA,CAAA,GAAA,CAAA,OAAA;AAAA,iBAuFe,oBAAA,CAAA;EACd,IAAA;EACA,SAAA;EACA,QAAA;EACA,cAAA;EACA,gBAAA,EAAkB,CAAA;EAAA,GACf;AAAA,GACF,cAAA;EACD,cAAA,IAAkB,CAAA,aAAc,SAAA,EAhQhC;EAkQA,gBAAA,IAAoB,MAAA,EAAQ,eAAA,CAAgB,SAAA,QAAiB,SAAA;EAC7D,IAAA,EAAM,cAAA;AAAA,IACP,kBAAA,CAAA,GAAA,CAAA,OAAA;AAAA,iBAoEe,gBAAA,CAAiB,KAAA,EAAO,cAAA,UAAqB,kBAAA,CAAA,GAAA,CAAA,OAAA;AAAA,UAe5C,aAAA,SAAsB,cAAA;EACrC,GAAA;EACA,WAAA,GAAc,GAAA;EACd,UAAA;AAAA;AAAA,iBAac,QAAA,CAAA;EAAW,GAAA;EAAK,WAAA;EAAa,UAAA;EAAA,GAAuB;AAAA,GAAS,aAAA,GAAa,kBAAA,CAAA,GAAA,CAAA,OAAA;AAAA,iBAqB1E,YAAA,CAAA;EACd,KAAA;EACA,SAAA;EAAA,GACG;AAAA,GACF,cAAA;EACD,KAAA;AAAA,IACD,kBAAA,CAAA,GAAA,CAAA,OAAA;AAAA,iBAkBe,SAAA,CAAA;;iBAlgBC,IAAA;;mBAEE,CAAA;aACN,IAAA,EAAM,cAAA;;;iBAqgBH,WAAA,CAAA;;kBA1fE,KAAA;;;iBAggBF,aAAA,CAAA;;cArgBF,CAAA;AAAA"}
|
|
@@ -11,35 +11,123 @@ import { cva } from "class-variance-authority";
|
|
|
11
11
|
import { useOnChange } from "fumadocs-core/utils/use-on-change";
|
|
12
12
|
import scrollIntoView from "scroll-into-view-if-needed";
|
|
13
13
|
import { Dialog } from "@base-ui/react/dialog";
|
|
14
|
+
import { createMarkdownRenderer } from "fumadocs-core/content/md";
|
|
15
|
+
import rehypeRaw from "rehype-raw";
|
|
16
|
+
import { visit } from "unist-util-visit";
|
|
14
17
|
|
|
15
18
|
//#region src/components/dialog/search.tsx
|
|
16
|
-
const
|
|
19
|
+
const RootContext = createContext(null);
|
|
17
20
|
const ListContext = createContext(null);
|
|
18
21
|
const TagsListContext = createContext(null);
|
|
22
|
+
const PreContext = createContext(false);
|
|
23
|
+
const mdRenderer = createMarkdownRenderer({
|
|
24
|
+
remarkRehypeOptions: { allowDangerousHtml: true },
|
|
25
|
+
rehypePlugins: [rehypeRaw, rehypeCustomElements]
|
|
26
|
+
});
|
|
27
|
+
const mdComponents = {
|
|
28
|
+
mark(props) {
|
|
29
|
+
return /* @__PURE__ */ jsx("span", {
|
|
30
|
+
...props,
|
|
31
|
+
className: "text-fd-primary underline"
|
|
32
|
+
});
|
|
33
|
+
},
|
|
34
|
+
a: "span",
|
|
35
|
+
p(props) {
|
|
36
|
+
return /* @__PURE__ */ jsx("p", {
|
|
37
|
+
...props,
|
|
38
|
+
className: "min-w-0"
|
|
39
|
+
});
|
|
40
|
+
},
|
|
41
|
+
strong(props) {
|
|
42
|
+
return /* @__PURE__ */ jsx("strong", {
|
|
43
|
+
...props,
|
|
44
|
+
className: "text-fd-accent-foreground font-medium"
|
|
45
|
+
});
|
|
46
|
+
},
|
|
47
|
+
code(props) {
|
|
48
|
+
if (use(PreContext)) return /* @__PURE__ */ jsx("code", {
|
|
49
|
+
...props,
|
|
50
|
+
className: "mask-[linear-gradient(to_bottom,white,white_30px,transparent_80px)]"
|
|
51
|
+
});
|
|
52
|
+
return /* @__PURE__ */ jsx("code", {
|
|
53
|
+
...props,
|
|
54
|
+
className: "border rounded-md px-px bg-fd-secondary text-fd-secondary-foreground"
|
|
55
|
+
});
|
|
56
|
+
},
|
|
57
|
+
custom({ _tagName = "fragment", children, ...rest }) {
|
|
58
|
+
return /* @__PURE__ */ jsxs("span", {
|
|
59
|
+
className: "inline-flex max-w-full items-center border p-0.5 rounded-md bg-fd-card text-fd-card-foreground divide-x divide-fd-border",
|
|
60
|
+
children: [
|
|
61
|
+
/* @__PURE__ */ jsx("code", {
|
|
62
|
+
className: "rounded-sm px-0.5 me-1 bg-fd-primary font-medium text-xs text-fd-primary-foreground border-none",
|
|
63
|
+
children: _tagName
|
|
64
|
+
}),
|
|
65
|
+
Object.entries(rest).map(([k, v]) => {
|
|
66
|
+
if (typeof v !== "string") return;
|
|
67
|
+
return /* @__PURE__ */ jsxs("code", {
|
|
68
|
+
className: "truncate text-xs text-fd-muted-foreground px-1",
|
|
69
|
+
children: [/* @__PURE__ */ jsxs("span", {
|
|
70
|
+
className: "text-fd-card-foreground",
|
|
71
|
+
children: [k, ": "]
|
|
72
|
+
}), v]
|
|
73
|
+
}, k);
|
|
74
|
+
}),
|
|
75
|
+
children && /* @__PURE__ */ jsx("span", {
|
|
76
|
+
className: "ps-1",
|
|
77
|
+
children
|
|
78
|
+
})
|
|
79
|
+
]
|
|
80
|
+
});
|
|
81
|
+
},
|
|
82
|
+
pre(props) {
|
|
83
|
+
return /* @__PURE__ */ jsx("pre", {
|
|
84
|
+
...props,
|
|
85
|
+
className: cn("flex flex-col border rounded-md my-0.5 p-2 bg-fd-secondary text-fd-secondary-foreground max-h-20 overflow-hidden", props.className),
|
|
86
|
+
children: /* @__PURE__ */ jsx(PreContext, {
|
|
87
|
+
value: true,
|
|
88
|
+
children: props.children
|
|
89
|
+
})
|
|
90
|
+
});
|
|
91
|
+
}
|
|
92
|
+
};
|
|
93
|
+
function rehypeCustomElements() {
|
|
94
|
+
return (tree) => {
|
|
95
|
+
visit(tree, (node) => {
|
|
96
|
+
if (node.type === "element" && document.createElement(node.tagName) instanceof HTMLUnknownElement) {
|
|
97
|
+
node.properties._tagName = node.tagName;
|
|
98
|
+
node.tagName = "custom";
|
|
99
|
+
}
|
|
100
|
+
});
|
|
101
|
+
};
|
|
102
|
+
}
|
|
19
103
|
function SearchDialog({ open, onOpenChange, search, onSearchChange, isLoading = false, onSelect: onSelectProp, children }) {
|
|
20
104
|
const router = useRouter();
|
|
21
|
-
const
|
|
105
|
+
const onOpenChangeCallback = useRef(onOpenChange);
|
|
106
|
+
onOpenChangeCallback.current = onOpenChange;
|
|
107
|
+
const onSearchChangeCallback = useRef(onSearchChange);
|
|
108
|
+
onSearchChangeCallback.current = onSearchChange;
|
|
109
|
+
const onSelect = (item) => {
|
|
22
110
|
if (item.type === "action") item.onSelect();
|
|
23
111
|
else if (item.external) window.open(item.url, "_blank")?.focus();
|
|
24
112
|
else router.push(item.url);
|
|
25
113
|
onOpenChange(false);
|
|
26
114
|
onSelectProp?.(item);
|
|
27
|
-
}
|
|
115
|
+
};
|
|
116
|
+
const onSelectCallback = useRef(onSelect);
|
|
117
|
+
onSelectCallback.current = onSelect;
|
|
28
118
|
return /* @__PURE__ */ jsx(Dialog.Root, {
|
|
29
119
|
open,
|
|
30
120
|
onOpenChange,
|
|
31
|
-
children: /* @__PURE__ */ jsx(
|
|
121
|
+
children: /* @__PURE__ */ jsx(RootContext, {
|
|
32
122
|
value: useMemo(() => ({
|
|
33
123
|
open,
|
|
34
|
-
onOpenChange,
|
|
35
124
|
search,
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
125
|
+
isLoading,
|
|
126
|
+
onOpenChange: (v) => onOpenChangeCallback.current(v),
|
|
127
|
+
onSearchChange: (v) => onSearchChangeCallback.current(v),
|
|
128
|
+
onSelect: (v) => onSelectCallback.current(v)
|
|
39
129
|
}), [
|
|
40
130
|
isLoading,
|
|
41
|
-
onOpenChange,
|
|
42
|
-
onSearchChange,
|
|
43
131
|
open,
|
|
44
132
|
search
|
|
45
133
|
]),
|
|
@@ -87,7 +175,7 @@ function SearchDialogFooter(props) {
|
|
|
87
175
|
function SearchDialogOverlay({ className, ...props }) {
|
|
88
176
|
return /* @__PURE__ */ jsx(Dialog.Backdrop, {
|
|
89
177
|
...props,
|
|
90
|
-
className: (s) => cn("fixed inset-0 z-50 backdrop-blur-xs bg-fd-overlay data-
|
|
178
|
+
className: (s) => cn("fixed inset-0 z-50 backdrop-blur-xs bg-fd-overlay data-open:animate-fd-fade-in data-closed:animate-fd-fade-out", typeof className === "function" ? className(s) : className)
|
|
91
179
|
});
|
|
92
180
|
}
|
|
93
181
|
function SearchDialogContent({ children, className, ...props }) {
|
|
@@ -95,7 +183,7 @@ function SearchDialogContent({ children, className, ...props }) {
|
|
|
95
183
|
return /* @__PURE__ */ jsx(Dialog.Portal, { children: /* @__PURE__ */ jsxs(Dialog.Popup, {
|
|
96
184
|
"aria-describedby": void 0,
|
|
97
185
|
...props,
|
|
98
|
-
className: (s) => cn("fixed left-1/2 top-4 md:top-[calc(50%-250px)] z-50 w-[calc(100%-1rem)] max-w-screen-sm -translate-x-1/2 rounded-xl border bg-fd-popover text-fd-popover-foreground shadow-2xl shadow-black/50 overflow-hidden data-
|
|
186
|
+
className: (s) => cn("fixed left-1/2 top-4 md:top-[calc(50%-250px)] z-50 w-[calc(100%-1rem)] max-w-screen-sm -translate-x-1/2 rounded-xl border bg-fd-popover text-fd-popover-foreground shadow-2xl shadow-black/50 overflow-hidden data-closed:animate-fd-dialog-out dataopen:animate-fd-dialog-in", "*:border-b *:has-[+:last-child[data-empty=true]]:border-b-0 *:data-[empty=true]:border-b-0 *:last:border-b-0", typeof className === "function" ? className(s) : className),
|
|
99
187
|
children: [/* @__PURE__ */ jsx(Dialog.Title, {
|
|
100
188
|
className: "hidden",
|
|
101
189
|
children: text.search
|
|
@@ -150,7 +238,7 @@ function SearchDialogList({ items = null, Empty = () => /* @__PURE__ */ jsx("div
|
|
|
150
238
|
className: cn("overflow-hidden h-(--fd-animated-height) transition-[height]", props.className),
|
|
151
239
|
children: /* @__PURE__ */ jsx("div", {
|
|
152
240
|
className: cn("w-full flex flex-col overflow-y-auto max-h-[460px] p-1", !items && "hidden"),
|
|
153
|
-
children: /* @__PURE__ */ jsxs(ListContext
|
|
241
|
+
children: /* @__PURE__ */ jsxs(ListContext, {
|
|
154
242
|
value: useMemo(() => ({
|
|
155
243
|
active,
|
|
156
244
|
setActive
|
|
@@ -163,7 +251,10 @@ function SearchDialogList({ items = null, Empty = () => /* @__PURE__ */ jsx("div
|
|
|
163
251
|
})
|
|
164
252
|
});
|
|
165
253
|
}
|
|
166
|
-
function SearchDialogListItem({ item, className, children,
|
|
254
|
+
function SearchDialogListItem({ item, className, children, renderMarkdown = (s) => /* @__PURE__ */ jsx(mdRenderer.Markdown, {
|
|
255
|
+
components: mdComponents,
|
|
256
|
+
children: s
|
|
257
|
+
}), renderHighlights: _, ...props }) {
|
|
167
258
|
const { active: activeId, setActive } = useSearchList();
|
|
168
259
|
const active = item.id === activeId;
|
|
169
260
|
if (item.type === "action") children ??= item.node;
|
|
@@ -176,9 +267,10 @@ function SearchDialogListItem({ item, className, children, renderHighlights: ren
|
|
|
176
267
|
role: "none",
|
|
177
268
|
className: "absolute start-3 inset-y-0 w-px bg-fd-border"
|
|
178
269
|
}),
|
|
179
|
-
/* @__PURE__ */
|
|
180
|
-
|
|
181
|
-
|
|
270
|
+
item.type === "heading" && /* @__PURE__ */ jsx(Hash, { className: "absolute start-6 top-2.5 size-4 text-fd-muted-foreground" }),
|
|
271
|
+
/* @__PURE__ */ jsx("div", {
|
|
272
|
+
className: cn("min-w-0", item.type === "text" && "ps-4", item.type === "heading" && "ps-8", item.type === "page" || item.type === "heading" ? "font-medium" : "text-fd-popover-foreground/80"),
|
|
273
|
+
children: typeof item.content === "string" ? renderMarkdown(item.content) : item.content
|
|
182
274
|
})
|
|
183
275
|
] });
|
|
184
276
|
return /* @__PURE__ */ jsx("button", {
|
|
@@ -191,7 +283,7 @@ function SearchDialogListItem({ item, className, children, renderHighlights: ren
|
|
|
191
283
|
});
|
|
192
284
|
}, [active]),
|
|
193
285
|
"aria-selected": active,
|
|
194
|
-
className: cn("relative select-none px-2.5 py-2 text-start text-sm rounded-lg", active && "bg-fd-accent text-fd-accent-foreground", className),
|
|
286
|
+
className: cn("relative select-none shrink-0 px-2.5 py-2 text-start text-sm overflow-hidden rounded-lg", active && "bg-fd-accent text-fd-accent-foreground", className),
|
|
195
287
|
onPointerMove: () => setActive(item.id),
|
|
196
288
|
...props,
|
|
197
289
|
children
|
|
@@ -206,19 +298,17 @@ function SearchDialogIcon(props) {
|
|
|
206
298
|
}
|
|
207
299
|
const itemVariants = cva("rounded-md border px-2 py-0.5 text-xs font-medium text-fd-muted-foreground transition-colors", { variants: { active: { true: "bg-fd-accent text-fd-accent-foreground" } } });
|
|
208
300
|
function TagsList({ tag, onTagChange, allowClear = false, ...props }) {
|
|
301
|
+
const onTagChangeCallback = useRef(onTagChange);
|
|
302
|
+
onTagChangeCallback.current = onTagChange;
|
|
209
303
|
return /* @__PURE__ */ jsx("div", {
|
|
210
304
|
...props,
|
|
211
305
|
className: cn("flex items-center gap-1 flex-wrap", props.className),
|
|
212
|
-
children: /* @__PURE__ */ jsx(TagsListContext
|
|
306
|
+
children: /* @__PURE__ */ jsx(TagsListContext, {
|
|
213
307
|
value: useMemo(() => ({
|
|
214
308
|
value: tag,
|
|
215
|
-
onValueChange:
|
|
309
|
+
onValueChange: (v) => onTagChangeCallback.current(v),
|
|
216
310
|
allowClear
|
|
217
|
-
}), [
|
|
218
|
-
allowClear,
|
|
219
|
-
onTagChange,
|
|
220
|
-
tag
|
|
221
|
-
]),
|
|
311
|
+
}), [allowClear, tag]),
|
|
222
312
|
children: props.children
|
|
223
313
|
})
|
|
224
314
|
});
|
|
@@ -233,25 +323,14 @@ function TagsListItem({ value, className, ...props }) {
|
|
|
233
323
|
active: selected,
|
|
234
324
|
className
|
|
235
325
|
})),
|
|
236
|
-
onClick: () =>
|
|
237
|
-
onValueChange(selected && allowClear ? void 0 : value);
|
|
238
|
-
},
|
|
326
|
+
onClick: () => onValueChange(selected && allowClear ? void 0 : value),
|
|
239
327
|
tabIndex: -1,
|
|
240
328
|
...props,
|
|
241
329
|
children: props.children
|
|
242
330
|
});
|
|
243
331
|
}
|
|
244
|
-
function renderHighlights(highlights) {
|
|
245
|
-
return highlights.map((node, i) => {
|
|
246
|
-
if (node.styles?.highlight) return /* @__PURE__ */ jsx("span", {
|
|
247
|
-
className: "text-fd-primary underline",
|
|
248
|
-
children: node.content
|
|
249
|
-
}, i);
|
|
250
|
-
return /* @__PURE__ */ jsx(Fragment, { children: node.content }, i);
|
|
251
|
-
});
|
|
252
|
-
}
|
|
253
332
|
function useSearch() {
|
|
254
|
-
const ctx = use(
|
|
333
|
+
const ctx = use(RootContext);
|
|
255
334
|
if (!ctx) throw new Error("Missing <SearchDialog />");
|
|
256
335
|
return ctx;
|
|
257
336
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"search.js","names":["SearchIcon"],"sources":["../../../src/components/dialog/search.tsx"],"sourcesContent":["'use client';\n\nimport { ChevronRight, Hash, Search as SearchIcon } from 'lucide-react';\nimport {\n type ComponentProps,\n createContext,\n Fragment,\n type ReactNode,\n use,\n useCallback,\n useEffect,\n useEffectEvent,\n useMemo,\n useRef,\n useState,\n} from 'react';\nimport { I18nLabel, useI18n } from '@/contexts/i18n';\nimport { cn } from '@/utils/cn';\nimport { Dialog } from '@base-ui/react/dialog';\nimport type { HighlightedText, ReactSortedResult as BaseResultType } from 'fumadocs-core/search';\nimport { cva } from 'class-variance-authority';\nimport { useRouter } from 'fumadocs-core/framework';\nimport type { SharedProps } from '@/contexts/search';\nimport { useOnChange } from 'fumadocs-core/utils/use-on-change';\nimport scrollIntoView from 'scroll-into-view-if-needed';\nimport { buttonVariants } from '@/components/ui/button';\n\nexport type SearchItemType =\n | (BaseResultType & {\n external?: boolean;\n })\n | {\n id: string;\n type: 'action';\n node: ReactNode;\n onSelect: () => void;\n };\n\n// needed for backward compatible since some previous guides referenced it\nexport type { SharedProps };\n\nexport interface SearchDialogProps extends SharedProps {\n search: string;\n onSearchChange: (v: string) => void;\n onSelect?: (item: SearchItemType) => void;\n isLoading?: boolean;\n\n children: ReactNode;\n}\n\nconst Context = createContext<{\n open: boolean;\n onOpenChange: (open: boolean) => void;\n search: string;\n onSearchChange: (v: string) => void;\n onSelect: (item: SearchItemType) => void;\n isLoading: boolean;\n} | null>(null);\n\nconst ListContext = createContext<{\n active: string | null;\n setActive: (v: string | null) => void;\n} | null>(null);\n\nconst TagsListContext = createContext<{\n value?: string;\n onValueChange: (value: string | undefined) => void;\n allowClear: boolean;\n} | null>(null);\n\nexport function SearchDialog({\n open,\n onOpenChange,\n search,\n onSearchChange,\n isLoading = false,\n onSelect: onSelectProp,\n children,\n}: SearchDialogProps) {\n const router = useRouter();\n const onSelect = useEffectEvent((item: SearchItemType) => {\n if (item.type === 'action') {\n item.onSelect();\n } else if (item.external) {\n window.open(item.url, '_blank')?.focus();\n } else {\n router.push(item.url);\n }\n\n onOpenChange(false);\n onSelectProp?.(item);\n });\n\n return (\n <Dialog.Root open={open} onOpenChange={onOpenChange}>\n <Context.Provider\n value={useMemo(\n () => ({\n open,\n onOpenChange,\n search,\n onSearchChange,\n // eslint-disable-next-line react-hooks/rules-of-hooks -- used in child components\n onSelect,\n isLoading,\n }),\n [isLoading, onOpenChange, onSearchChange, open, search],\n )}\n >\n {children}\n </Context.Provider>\n </Dialog.Root>\n );\n}\n\nexport function SearchDialogHeader(props: ComponentProps<'div'>) {\n return <div {...props} className={cn('flex flex-row items-center gap-2 p-3', props.className)} />;\n}\n\nexport function SearchDialogInput(props: ComponentProps<'input'>) {\n const { text } = useI18n();\n const { search, onSearchChange } = useSearch();\n\n return (\n <input\n {...props}\n value={search}\n onChange={(e) => onSearchChange(e.target.value)}\n placeholder={text.search}\n className=\"w-0 flex-1 bg-transparent text-lg placeholder:text-fd-muted-foreground focus-visible:outline-none\"\n />\n );\n}\n\nexport function SearchDialogClose({\n children = 'ESC',\n className,\n ...props\n}: ComponentProps<'button'>) {\n const { onOpenChange } = useSearch();\n\n return (\n <button\n type=\"button\"\n onClick={() => onOpenChange(false)}\n className={cn(\n buttonVariants({\n color: 'outline',\n size: 'sm',\n className: 'font-mono text-fd-muted-foreground',\n }),\n className,\n )}\n {...props}\n >\n {children}\n </button>\n );\n}\n\nexport function SearchDialogFooter(props: ComponentProps<'div'>) {\n return <div {...props} className={cn('bg-fd-secondary/50 p-3 empty:hidden', props.className)} />;\n}\n\nexport function SearchDialogOverlay({\n className,\n ...props\n}: ComponentProps<typeof Dialog.Backdrop>) {\n return (\n <Dialog.Backdrop\n {...props}\n className={(s) =>\n cn(\n 'fixed inset-0 z-50 backdrop-blur-xs bg-fd-overlay data-[open]:animate-fd-fade-in data-[closed]:animate-fd-fade-out',\n typeof className === 'function' ? className(s) : className,\n )\n }\n />\n );\n}\n\nexport function SearchDialogContent({\n children,\n className,\n ...props\n}: ComponentProps<typeof Dialog.Popup>) {\n const { text } = useI18n();\n\n return (\n <Dialog.Portal>\n <Dialog.Popup\n aria-describedby={undefined}\n {...props}\n className={(s) =>\n cn(\n 'fixed left-1/2 top-4 md:top-[calc(50%-250px)] z-50 w-[calc(100%-1rem)] max-w-screen-sm -translate-x-1/2 rounded-xl border bg-fd-popover text-fd-popover-foreground shadow-2xl shadow-black/50 overflow-hidden data-[closed]:animate-fd-dialog-out data-[open]:animate-fd-dialog-in',\n '*:border-b *:has-[+:last-child[data-empty=true]]:border-b-0 *:data-[empty=true]:border-b-0 *:last:border-b-0',\n typeof className === 'function' ? className(s) : className,\n )\n }\n >\n <Dialog.Title className=\"hidden\">{text.search}</Dialog.Title>\n {children}\n </Dialog.Popup>\n </Dialog.Portal>\n );\n}\n\nexport function SearchDialogList({\n items = null,\n Empty = () => (\n <div className=\"py-12 text-center text-sm text-fd-muted-foreground\">\n <I18nLabel label=\"searchNoResult\" />\n </div>\n ),\n Item = (props) => <SearchDialogListItem {...props} />,\n ...props\n}: Omit<ComponentProps<'div'>, 'children'> & {\n items: SearchItemType[] | null | undefined;\n /**\n * Renderer for empty list UI\n */\n Empty?: () => ReactNode;\n /**\n * Renderer for items\n */\n Item?: (props: { item: SearchItemType; onClick: () => void }) => ReactNode;\n}) {\n const ref = useRef<HTMLDivElement>(null);\n const { onSelect } = useSearch();\n const [active, setActive] = useState<string | null>(() =>\n items && items.length > 0 ? items[0].id : null,\n );\n\n const onKey = useEffectEvent((e: KeyboardEvent) => {\n if (!items || e.isComposing) return;\n\n if (e.key === 'ArrowDown' || e.key == 'ArrowUp') {\n let idx = items.findIndex((item) => item.id === active);\n if (idx === -1) idx = 0;\n else if (e.key === 'ArrowDown') idx++;\n else idx--;\n\n setActive(items.at(idx % items.length)?.id ?? null);\n e.preventDefault();\n }\n\n if (e.key === 'Enter') {\n const selected = items.find((item) => item.id === active);\n\n if (selected) onSelect(selected);\n e.preventDefault();\n }\n });\n\n useEffect(() => {\n const element = ref.current;\n if (!element) return;\n\n const observer = new ResizeObserver(() => {\n const viewport = element.firstElementChild!;\n\n element.style.setProperty('--fd-animated-height', `${viewport.clientHeight}px`);\n });\n\n const viewport = element.firstElementChild;\n if (viewport) observer.observe(viewport);\n\n window.addEventListener('keydown', onKey);\n return () => {\n observer.disconnect();\n window.removeEventListener('keydown', onKey);\n };\n }, []);\n\n useOnChange(items, () => {\n if (items && items.length > 0) {\n setActive(items[0].id);\n }\n });\n\n return (\n <div\n {...props}\n ref={ref}\n data-empty={items === null}\n className={cn(\n 'overflow-hidden h-(--fd-animated-height) transition-[height]',\n props.className,\n )}\n >\n <div\n className={cn('w-full flex flex-col overflow-y-auto max-h-[460px] p-1', !items && 'hidden')}\n >\n <ListContext.Provider\n value={useMemo(\n () => ({\n active,\n setActive,\n }),\n [active],\n )}\n >\n {items?.length === 0 && Empty()}\n\n {items?.map((item) => (\n <Fragment key={item.id}>{Item({ item, onClick: () => onSelect(item) })}</Fragment>\n ))}\n </ListContext.Provider>\n </div>\n </div>\n );\n}\n\nexport function SearchDialogListItem({\n item,\n className,\n children,\n renderHighlights: render = renderHighlights,\n ...props\n}: ComponentProps<'button'> & {\n renderHighlights?: typeof renderHighlights;\n item: SearchItemType;\n}) {\n const { active: activeId, setActive } = useSearchList();\n const active = item.id === activeId;\n\n if (item.type === 'action') {\n children ??= item.node;\n } else {\n children ??= (\n <>\n <div className=\"inline-flex items-center text-fd-muted-foreground text-xs empty:hidden\">\n {item.breadcrumbs?.map((item, i) => (\n <Fragment key={i}>\n {i > 0 && <ChevronRight className=\"size-4 rtl:rotate-180\" />}\n {item}\n </Fragment>\n ))}\n </div>\n\n {item.type !== 'page' && (\n <div role=\"none\" className=\"absolute start-3 inset-y-0 w-px bg-fd-border\" />\n )}\n <p\n className={cn(\n 'min-w-0 truncate',\n item.type !== 'page' && 'ps-4',\n item.type === 'page' || item.type === 'heading'\n ? 'font-medium'\n : 'text-fd-popover-foreground/80',\n )}\n >\n {item.type === 'heading' && (\n <Hash className=\"inline me-1 size-4 text-fd-muted-foreground\" />\n )}\n {item.contentWithHighlights ? render(item.contentWithHighlights) : item.content}\n </p>\n </>\n );\n }\n\n return (\n <button\n type=\"button\"\n ref={useCallback(\n (element: HTMLButtonElement | null) => {\n if (active && element) {\n scrollIntoView(element, {\n scrollMode: 'if-needed',\n block: 'nearest',\n boundary: element.parentElement,\n });\n }\n },\n [active],\n )}\n aria-selected={active}\n className={cn(\n 'relative select-none px-2.5 py-2 text-start text-sm rounded-lg',\n active && 'bg-fd-accent text-fd-accent-foreground',\n className,\n )}\n onPointerMove={() => setActive(item.id)}\n {...props}\n >\n {children}\n </button>\n );\n}\n\nexport function SearchDialogIcon(props: ComponentProps<'svg'>) {\n const { isLoading } = useSearch();\n\n return (\n <SearchIcon\n {...props}\n className={cn(\n 'size-5 text-fd-muted-foreground',\n isLoading && 'animate-pulse duration-400',\n props.className,\n )}\n />\n );\n}\n\nexport interface TagsListProps extends ComponentProps<'div'> {\n tag?: string;\n onTagChange: (tag: string | undefined) => void;\n allowClear?: boolean;\n}\n\nconst itemVariants = cva(\n 'rounded-md border px-2 py-0.5 text-xs font-medium text-fd-muted-foreground transition-colors',\n {\n variants: {\n active: {\n true: 'bg-fd-accent text-fd-accent-foreground',\n },\n },\n },\n);\n\nexport function TagsList({ tag, onTagChange, allowClear = false, ...props }: TagsListProps) {\n return (\n <div {...props} className={cn('flex items-center gap-1 flex-wrap', props.className)}>\n <TagsListContext.Provider\n value={useMemo(\n () => ({\n value: tag,\n onValueChange: onTagChange,\n allowClear,\n }),\n [allowClear, onTagChange, tag],\n )}\n >\n {props.children}\n </TagsListContext.Provider>\n </div>\n );\n}\n\nexport function TagsListItem({\n value,\n className,\n ...props\n}: ComponentProps<'button'> & {\n value: string;\n}) {\n const { onValueChange, value: selectedValue, allowClear } = useTagsList();\n const selected = value === selectedValue;\n\n return (\n <button\n type=\"button\"\n data-active={selected}\n className={cn(itemVariants({ active: selected, className }))}\n onClick={() => {\n onValueChange(selected && allowClear ? undefined : value);\n }}\n tabIndex={-1}\n {...props}\n >\n {props.children}\n </button>\n );\n}\n\nfunction renderHighlights(highlights: HighlightedText<ReactNode>[]): ReactNode {\n return highlights.map((node, i) => {\n if (node.styles?.highlight) {\n return (\n <span key={i} className=\"text-fd-primary underline\">\n {node.content}\n </span>\n );\n }\n\n return <Fragment key={i}>{node.content}</Fragment>;\n });\n}\n\nexport function useSearch() {\n const ctx = use(Context);\n if (!ctx) throw new Error('Missing <SearchDialog />');\n return ctx;\n}\n\nexport function useTagsList() {\n const ctx = use(TagsListContext);\n if (!ctx) throw new Error('Missing <TagsList />');\n return ctx;\n}\n\nexport function useSearchList() {\n const ctx = use(ListContext);\n if (!ctx) throw new Error('Missing <SearchDialogList />');\n return ctx;\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"search.js","names":["SearchIcon"],"sources":["../../../src/components/dialog/search.tsx"],"sourcesContent":["'use client';\n\nimport { ChevronRight, Hash, Search as SearchIcon } from 'lucide-react';\nimport {\n type ComponentProps,\n createContext,\n Fragment,\n type ReactNode,\n use,\n useCallback,\n useEffect,\n useEffectEvent,\n useMemo,\n useRef,\n useState,\n} from 'react';\nimport { I18nLabel, useI18n } from '@/contexts/i18n';\nimport { cn } from '@/utils/cn';\nimport { Dialog } from '@base-ui/react/dialog';\nimport type { HighlightedText, ReactSortedResult as BaseResultType } from 'fumadocs-core/search';\nimport { cva } from 'class-variance-authority';\nimport { useRouter } from 'fumadocs-core/framework';\nimport type { SharedProps } from '@/contexts/search';\nimport { useOnChange } from 'fumadocs-core/utils/use-on-change';\nimport scrollIntoView from 'scroll-into-view-if-needed';\nimport { buttonVariants } from '@/components/ui/button';\nimport { createMarkdownRenderer } from 'fumadocs-core/content/md';\nimport rehypeRaw from 'rehype-raw';\nimport { visit } from 'unist-util-visit';\nimport type { Transformer } from 'unified';\nimport type { Root } from 'hast';\n\nexport type SearchItemType =\n | (BaseResultType & {\n external?: boolean;\n })\n | {\n id: string;\n type: 'action';\n node: ReactNode;\n onSelect: () => void;\n };\n\n// needed for backward compatible since some previous guides referenced it\nexport type { SharedProps };\n\nexport interface SearchDialogProps extends SharedProps {\n search: string;\n onSearchChange: (v: string) => void;\n onSelect?: (item: SearchItemType) => void;\n isLoading?: boolean;\n\n children: ReactNode;\n}\n\nconst RootContext = createContext<{\n open: boolean;\n onOpenChange: (open: boolean) => void;\n search: string;\n onSearchChange: (v: string) => void;\n onSelect: (item: SearchItemType) => void;\n isLoading: boolean;\n} | null>(null);\n\nconst ListContext = createContext<{\n active: string | null;\n setActive: (v: string | null) => void;\n} | null>(null);\n\nconst TagsListContext = createContext<{\n value?: string;\n onValueChange: (value: string | undefined) => void;\n allowClear: boolean;\n} | null>(null);\n\nconst PreContext = createContext(false);\n\nconst mdRenderer = createMarkdownRenderer({\n remarkRehypeOptions: {\n allowDangerousHtml: true,\n },\n rehypePlugins: [rehypeRaw, rehypeCustomElements],\n});\n\nconst mdComponents = {\n mark(props: ComponentProps<'mark'>) {\n return <span {...props} className=\"text-fd-primary underline\" />;\n },\n a: 'span',\n p(props: ComponentProps<'p'>) {\n return <p {...props} className=\"min-w-0\" />;\n },\n strong(props: ComponentProps<'strong'>) {\n return <strong {...props} className=\"text-fd-accent-foreground font-medium\" />;\n },\n code(props: ComponentProps<'pre'>) {\n // eslint-disable-next-line react-hooks/rules-of-hooks -- this is a component\n const inPre = use(PreContext);\n if (inPre)\n return (\n <code\n {...props}\n className=\"mask-[linear-gradient(to_bottom,white,white_30px,transparent_80px)]\"\n />\n );\n\n return (\n <code\n {...props}\n className=\"border rounded-md px-px bg-fd-secondary text-fd-secondary-foreground\"\n />\n );\n },\n custom({\n _tagName = 'fragment',\n children,\n ...rest\n }: Record<string, unknown> & { _tagName: string; children: ReactNode }) {\n return (\n <span className=\"inline-flex max-w-full items-center border p-0.5 rounded-md bg-fd-card text-fd-card-foreground divide-x divide-fd-border\">\n <code className=\"rounded-sm px-0.5 me-1 bg-fd-primary font-medium text-xs text-fd-primary-foreground border-none\">\n {_tagName}\n </code>\n {Object.entries(rest).map(([k, v]) => {\n if (typeof v !== 'string') return;\n\n return (\n <code key={k} className=\"truncate text-xs text-fd-muted-foreground px-1\">\n <span className=\"text-fd-card-foreground\">{k}: </span>\n {v}\n </code>\n );\n })}\n {children && <span className=\"ps-1\">{children}</span>}\n </span>\n );\n },\n pre(props: ComponentProps<'pre'>) {\n return (\n <pre\n {...props}\n className={cn(\n 'flex flex-col border rounded-md my-0.5 p-2 bg-fd-secondary text-fd-secondary-foreground max-h-20 overflow-hidden',\n props.className,\n )}\n >\n <PreContext value={true}>{props.children}</PreContext>\n </pre>\n );\n },\n};\n\nfunction rehypeCustomElements(): Transformer<Root, Root> {\n return (tree) => {\n visit(tree, (node) => {\n if (\n node.type === 'element' &&\n document.createElement(node.tagName) instanceof HTMLUnknownElement\n ) {\n node.properties._tagName = node.tagName;\n node.tagName = 'custom';\n }\n });\n };\n}\n\nexport function SearchDialog({\n open,\n onOpenChange,\n search,\n onSearchChange,\n isLoading = false,\n onSelect: onSelectProp,\n children,\n}: SearchDialogProps) {\n const router = useRouter();\n const onOpenChangeCallback = useRef(onOpenChange);\n onOpenChangeCallback.current = onOpenChange;\n const onSearchChangeCallback = useRef(onSearchChange);\n onSearchChangeCallback.current = onSearchChange;\n const onSelect = (item: SearchItemType) => {\n if (item.type === 'action') {\n item.onSelect();\n } else if (item.external) {\n window.open(item.url, '_blank')?.focus();\n } else {\n router.push(item.url);\n }\n\n onOpenChange(false);\n onSelectProp?.(item);\n };\n const onSelectCallback = useRef(onSelect);\n onSelectCallback.current = onSelect;\n\n return (\n <Dialog.Root open={open} onOpenChange={onOpenChange}>\n <RootContext\n value={useMemo(\n () => ({\n open,\n search,\n isLoading,\n onOpenChange: (v) => onOpenChangeCallback.current(v),\n onSearchChange: (v) => onSearchChangeCallback.current(v),\n onSelect: (v) => onSelectCallback.current(v),\n }),\n [isLoading, open, search],\n )}\n >\n {children}\n </RootContext>\n </Dialog.Root>\n );\n}\n\nexport function SearchDialogHeader(props: ComponentProps<'div'>) {\n return <div {...props} className={cn('flex flex-row items-center gap-2 p-3', props.className)} />;\n}\n\nexport function SearchDialogInput(props: ComponentProps<'input'>) {\n const { text } = useI18n();\n const { search, onSearchChange } = useSearch();\n\n return (\n <input\n {...props}\n value={search}\n onChange={(e) => onSearchChange(e.target.value)}\n placeholder={text.search}\n className=\"w-0 flex-1 bg-transparent text-lg placeholder:text-fd-muted-foreground focus-visible:outline-none\"\n />\n );\n}\n\nexport function SearchDialogClose({\n children = 'ESC',\n className,\n ...props\n}: ComponentProps<'button'>) {\n const { onOpenChange } = useSearch();\n\n return (\n <button\n type=\"button\"\n onClick={() => onOpenChange(false)}\n className={cn(\n buttonVariants({\n color: 'outline',\n size: 'sm',\n className: 'font-mono text-fd-muted-foreground',\n }),\n className,\n )}\n {...props}\n >\n {children}\n </button>\n );\n}\n\nexport function SearchDialogFooter(props: ComponentProps<'div'>) {\n return <div {...props} className={cn('bg-fd-secondary/50 p-3 empty:hidden', props.className)} />;\n}\n\nexport function SearchDialogOverlay({\n className,\n ...props\n}: ComponentProps<typeof Dialog.Backdrop>) {\n return (\n <Dialog.Backdrop\n {...props}\n className={(s) =>\n cn(\n 'fixed inset-0 z-50 backdrop-blur-xs bg-fd-overlay data-open:animate-fd-fade-in data-closed:animate-fd-fade-out',\n typeof className === 'function' ? className(s) : className,\n )\n }\n />\n );\n}\n\nexport function SearchDialogContent({\n children,\n className,\n ...props\n}: ComponentProps<typeof Dialog.Popup>) {\n const { text } = useI18n();\n\n return (\n <Dialog.Portal>\n <Dialog.Popup\n aria-describedby={undefined}\n {...props}\n className={(s) =>\n cn(\n 'fixed left-1/2 top-4 md:top-[calc(50%-250px)] z-50 w-[calc(100%-1rem)] max-w-screen-sm -translate-x-1/2 rounded-xl border bg-fd-popover text-fd-popover-foreground shadow-2xl shadow-black/50 overflow-hidden data-closed:animate-fd-dialog-out dataopen:animate-fd-dialog-in',\n '*:border-b *:has-[+:last-child[data-empty=true]]:border-b-0 *:data-[empty=true]:border-b-0 *:last:border-b-0',\n typeof className === 'function' ? className(s) : className,\n )\n }\n >\n <Dialog.Title className=\"hidden\">{text.search}</Dialog.Title>\n {children}\n </Dialog.Popup>\n </Dialog.Portal>\n );\n}\n\nexport function SearchDialogList({\n items = null,\n Empty = () => (\n <div className=\"py-12 text-center text-sm text-fd-muted-foreground\">\n <I18nLabel label=\"searchNoResult\" />\n </div>\n ),\n Item = (props) => <SearchDialogListItem {...props} />,\n ...props\n}: Omit<ComponentProps<'div'>, 'children'> & {\n items: SearchItemType[] | null | undefined;\n /**\n * Renderer for empty list UI\n */\n Empty?: () => ReactNode;\n /**\n * Renderer for items\n */\n Item?: (props: { item: SearchItemType; onClick: () => void }) => ReactNode;\n}) {\n const ref = useRef<HTMLDivElement>(null);\n const { onSelect } = useSearch();\n const [active, setActive] = useState<string | null>(() =>\n items && items.length > 0 ? items[0].id : null,\n );\n\n const onKey = useEffectEvent((e: KeyboardEvent) => {\n if (!items || e.isComposing) return;\n\n if (e.key === 'ArrowDown' || e.key == 'ArrowUp') {\n let idx = items.findIndex((item) => item.id === active);\n if (idx === -1) idx = 0;\n else if (e.key === 'ArrowDown') idx++;\n else idx--;\n\n setActive(items.at(idx % items.length)?.id ?? null);\n e.preventDefault();\n }\n\n if (e.key === 'Enter') {\n const selected = items.find((item) => item.id === active);\n\n if (selected) onSelect(selected);\n e.preventDefault();\n }\n });\n\n useEffect(() => {\n const element = ref.current;\n if (!element) return;\n\n const observer = new ResizeObserver(() => {\n const viewport = element.firstElementChild!;\n\n element.style.setProperty('--fd-animated-height', `${viewport.clientHeight}px`);\n });\n\n const viewport = element.firstElementChild;\n if (viewport) observer.observe(viewport);\n\n window.addEventListener('keydown', onKey);\n return () => {\n observer.disconnect();\n window.removeEventListener('keydown', onKey);\n };\n }, []);\n\n useOnChange(items, () => {\n if (items && items.length > 0) {\n setActive(items[0].id);\n }\n });\n\n return (\n <div\n {...props}\n ref={ref}\n data-empty={items === null}\n className={cn(\n 'overflow-hidden h-(--fd-animated-height) transition-[height]',\n props.className,\n )}\n >\n <div\n className={cn('w-full flex flex-col overflow-y-auto max-h-[460px] p-1', !items && 'hidden')}\n >\n <ListContext\n value={useMemo(\n () => ({\n active,\n setActive,\n }),\n [active],\n )}\n >\n {items?.length === 0 && Empty()}\n\n {items?.map((item) => (\n <Fragment key={item.id}>{Item({ item, onClick: () => onSelect(item) })}</Fragment>\n ))}\n </ListContext>\n </div>\n </div>\n );\n}\n\nexport function SearchDialogListItem({\n item,\n className,\n children,\n renderMarkdown = (s) => <mdRenderer.Markdown components={mdComponents}>{s}</mdRenderer.Markdown>,\n renderHighlights: _,\n ...props\n}: ComponentProps<'button'> & {\n renderMarkdown?: (v: string) => ReactNode;\n /** @deprecated highlight blocks is now wrapped in `<mark />`, use `renderMarkdown` to handle instead. */\n renderHighlights?: (blocks: HighlightedText<ReactNode>[]) => ReactNode;\n item: SearchItemType;\n}) {\n const { active: activeId, setActive } = useSearchList();\n const active = item.id === activeId;\n\n if (item.type === 'action') {\n children ??= item.node;\n } else {\n children ??= (\n <>\n <div className=\"inline-flex items-center text-fd-muted-foreground text-xs empty:hidden\">\n {item.breadcrumbs?.map((item, i) => (\n <Fragment key={i}>\n {i > 0 && <ChevronRight className=\"size-4 rtl:rotate-180\" />}\n {item}\n </Fragment>\n ))}\n </div>\n\n {item.type !== 'page' && (\n <div role=\"none\" className=\"absolute start-3 inset-y-0 w-px bg-fd-border\" />\n )}\n {item.type === 'heading' && (\n <Hash className=\"absolute start-6 top-2.5 size-4 text-fd-muted-foreground\" />\n )}\n <div\n className={cn(\n 'min-w-0',\n item.type === 'text' && 'ps-4',\n item.type === 'heading' && 'ps-8',\n item.type === 'page' || item.type === 'heading'\n ? 'font-medium'\n : 'text-fd-popover-foreground/80',\n )}\n >\n {typeof item.content === 'string' ? renderMarkdown(item.content) : item.content}\n </div>\n </>\n );\n }\n\n return (\n <button\n type=\"button\"\n ref={useCallback(\n (element: HTMLButtonElement | null) => {\n if (active && element) {\n scrollIntoView(element, {\n scrollMode: 'if-needed',\n block: 'nearest',\n boundary: element.parentElement,\n });\n }\n },\n [active],\n )}\n aria-selected={active}\n className={cn(\n 'relative select-none shrink-0 px-2.5 py-2 text-start text-sm overflow-hidden rounded-lg',\n active && 'bg-fd-accent text-fd-accent-foreground',\n className,\n )}\n onPointerMove={() => setActive(item.id)}\n {...props}\n >\n {children}\n </button>\n );\n}\nexport function SearchDialogIcon(props: ComponentProps<'svg'>) {\n const { isLoading } = useSearch();\n\n return (\n <SearchIcon\n {...props}\n className={cn(\n 'size-5 text-fd-muted-foreground',\n isLoading && 'animate-pulse duration-400',\n props.className,\n )}\n />\n );\n}\n\nexport interface TagsListProps extends ComponentProps<'div'> {\n tag?: string;\n onTagChange: (tag: string | undefined) => void;\n allowClear?: boolean;\n}\n\nconst itemVariants = cva(\n 'rounded-md border px-2 py-0.5 text-xs font-medium text-fd-muted-foreground transition-colors',\n {\n variants: {\n active: {\n true: 'bg-fd-accent text-fd-accent-foreground',\n },\n },\n },\n);\nexport function TagsList({ tag, onTagChange, allowClear = false, ...props }: TagsListProps) {\n const onTagChangeCallback = useRef(onTagChange);\n onTagChangeCallback.current = onTagChange;\n return (\n <div {...props} className={cn('flex items-center gap-1 flex-wrap', props.className)}>\n <TagsListContext\n value={useMemo(\n () => ({\n value: tag,\n onValueChange: (v) => onTagChangeCallback.current(v),\n allowClear,\n }),\n [allowClear, tag],\n )}\n >\n {props.children}\n </TagsListContext>\n </div>\n );\n}\n\nexport function TagsListItem({\n value,\n className,\n ...props\n}: ComponentProps<'button'> & {\n value: string;\n}) {\n const { onValueChange, value: selectedValue, allowClear } = useTagsList();\n const selected = value === selectedValue;\n\n return (\n <button\n type=\"button\"\n data-active={selected}\n className={cn(itemVariants({ active: selected, className }))}\n onClick={() => onValueChange(selected && allowClear ? undefined : value)}\n tabIndex={-1}\n {...props}\n >\n {props.children}\n </button>\n );\n}\n\nexport function useSearch() {\n const ctx = use(RootContext);\n if (!ctx) throw new Error('Missing <SearchDialog />');\n return ctx;\n}\n\nexport function useTagsList() {\n const ctx = use(TagsListContext);\n if (!ctx) throw new Error('Missing <TagsList />');\n return ctx;\n}\n\nexport function useSearchList() {\n const ctx = use(ListContext);\n if (!ctx) throw new Error('Missing <SearchDialogList />');\n return ctx;\n}\n"],"mappings":"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"}
|
|
@@ -4,7 +4,7 @@ import * as class_variance_authority_types0 from "class-variance-authority/types
|
|
|
4
4
|
|
|
5
5
|
//#region src/layouts/home/client.d.ts
|
|
6
6
|
declare const navItemVariants: (props?: ({
|
|
7
|
-
variant?: "
|
|
7
|
+
variant?: "button" | "main" | "icon" | null | undefined;
|
|
8
8
|
} & class_variance_authority_types0.ClassProp) | undefined) => string;
|
|
9
9
|
declare function Header({
|
|
10
10
|
nav,
|
package/dist/style.css
CHANGED
|
@@ -66,7 +66,6 @@
|
|
|
66
66
|
--color-fd-diff-add-symbol: rgb(10, 200, 100);
|
|
67
67
|
--animate-fd-fade-in: fd-fade-in 300ms ease;
|
|
68
68
|
--animate-fd-fade-out: fd-fade-out 300ms ease;
|
|
69
|
-
--animate-fd-dialog-in: fd-dialog-in 300ms cubic-bezier(0.16, 1, 0.3, 1);
|
|
70
69
|
--animate-fd-dialog-out: fd-dialog-out 300ms cubic-bezier(0.16, 1, 0.3, 1);
|
|
71
70
|
--animate-fd-popover-in: fd-popover-in 100ms ease;
|
|
72
71
|
--animate-fd-popover-out: fd-popover-out 100ms ease;
|
|
@@ -300,6 +299,9 @@
|
|
|
300
299
|
.start-4 {
|
|
301
300
|
inset-inline-start: calc(var(--spacing) * 4);
|
|
302
301
|
}
|
|
302
|
+
.start-6 {
|
|
303
|
+
inset-inline-start: calc(var(--spacing) * 6);
|
|
304
|
+
}
|
|
303
305
|
.end-0 {
|
|
304
306
|
inset-inline-end: calc(var(--spacing) * 0);
|
|
305
307
|
}
|
|
@@ -333,6 +335,9 @@
|
|
|
333
335
|
.top-2 {
|
|
334
336
|
top: calc(var(--spacing) * 2);
|
|
335
337
|
}
|
|
338
|
+
.top-2\.5 {
|
|
339
|
+
top: calc(var(--spacing) * 2.5);
|
|
340
|
+
}
|
|
336
341
|
.top-4 {
|
|
337
342
|
top: calc(var(--spacing) * 4);
|
|
338
343
|
}
|
|
@@ -414,6 +419,9 @@
|
|
|
414
419
|
.my-0\! {
|
|
415
420
|
margin-block: calc(var(--spacing) * 0) !important;
|
|
416
421
|
}
|
|
422
|
+
.my-0\.5 {
|
|
423
|
+
margin-block: calc(var(--spacing) * 0.5);
|
|
424
|
+
}
|
|
417
425
|
.my-4 {
|
|
418
426
|
margin-block: calc(var(--spacing) * 4);
|
|
419
427
|
}
|
|
@@ -886,9 +894,6 @@
|
|
|
886
894
|
.hidden {
|
|
887
895
|
display: none;
|
|
888
896
|
}
|
|
889
|
-
.inline {
|
|
890
|
-
display: inline;
|
|
891
|
-
}
|
|
892
897
|
.inline-flex {
|
|
893
898
|
display: inline-flex;
|
|
894
899
|
}
|
|
@@ -987,6 +992,9 @@
|
|
|
987
992
|
.max-h-\(--available-height\) {
|
|
988
993
|
max-height: var(--available-height);
|
|
989
994
|
}
|
|
995
|
+
.max-h-20 {
|
|
996
|
+
max-height: calc(var(--spacing) * 20);
|
|
997
|
+
}
|
|
990
998
|
.max-h-\[50vh\] {
|
|
991
999
|
max-height: 50vh;
|
|
992
1000
|
}
|
|
@@ -1083,6 +1091,9 @@
|
|
|
1083
1091
|
.max-w-\[1400px\] {
|
|
1084
1092
|
max-width: 1400px;
|
|
1085
1093
|
}
|
|
1094
|
+
.max-w-full {
|
|
1095
|
+
max-width: 100%;
|
|
1096
|
+
}
|
|
1086
1097
|
.max-w-screen-sm {
|
|
1087
1098
|
max-width: var(--breakpoint-sm);
|
|
1088
1099
|
}
|
|
@@ -1237,6 +1248,14 @@
|
|
|
1237
1248
|
.gap-y-4 {
|
|
1238
1249
|
row-gap: calc(var(--spacing) * 4);
|
|
1239
1250
|
}
|
|
1251
|
+
.divide-x {
|
|
1252
|
+
:where(& > :not(:last-child)) {
|
|
1253
|
+
--tw-divide-x-reverse: 0;
|
|
1254
|
+
border-inline-style: var(--tw-border-style);
|
|
1255
|
+
border-inline-start-width: calc(1px * var(--tw-divide-x-reverse));
|
|
1256
|
+
border-inline-end-width: calc(1px * calc(1 - var(--tw-divide-x-reverse)));
|
|
1257
|
+
}
|
|
1258
|
+
}
|
|
1240
1259
|
.divide-y {
|
|
1241
1260
|
:where(& > :not(:last-child)) {
|
|
1242
1261
|
--tw-divide-y-reverse: 0;
|
|
@@ -1341,6 +1360,10 @@
|
|
|
1341
1360
|
border-left-style: var(--tw-border-style);
|
|
1342
1361
|
border-left-width: 1px;
|
|
1343
1362
|
}
|
|
1363
|
+
.border-none {
|
|
1364
|
+
--tw-border-style: none;
|
|
1365
|
+
border-style: none;
|
|
1366
|
+
}
|
|
1344
1367
|
.border-fd-foreground\/10 {
|
|
1345
1368
|
border-color: color-mix(in srgb, hsl(0, 0%, 3.9%) 10%, transparent);
|
|
1346
1369
|
@supports (color: color-mix(in lab, red, red)) {
|
|
@@ -1440,6 +1463,9 @@
|
|
|
1440
1463
|
.mask-\[linear-gradient\(to_bottom\,transparent\,white_calc\(var\(--spacing\)\*14\)\,white_calc\(100\%-var\(--spacing\)\*14\)\,transparent\)\] {
|
|
1441
1464
|
mask-image: linear-gradient(to bottom,transparent,white calc(var(--spacing) * 14),white calc(100% - var(--spacing) * 14),transparent);
|
|
1442
1465
|
}
|
|
1466
|
+
.mask-\[linear-gradient\(to_bottom\,white\,white_30px\,transparent_80px\)\] {
|
|
1467
|
+
mask-image: linear-gradient(to bottom,white,white 30px,transparent 80px);
|
|
1468
|
+
}
|
|
1443
1469
|
.fill-\(--callout-color\) {
|
|
1444
1470
|
fill: var(--callout-color);
|
|
1445
1471
|
}
|
|
@@ -1500,6 +1526,9 @@
|
|
|
1500
1526
|
.px-6 {
|
|
1501
1527
|
padding-inline: calc(var(--spacing) * 6);
|
|
1502
1528
|
}
|
|
1529
|
+
.px-px {
|
|
1530
|
+
padding-inline: 1px;
|
|
1531
|
+
}
|
|
1503
1532
|
.py-0 {
|
|
1504
1533
|
padding-block: calc(var(--spacing) * 0);
|
|
1505
1534
|
}
|
|
@@ -2224,6 +2253,16 @@
|
|
|
2224
2253
|
color: var(--color-fd-accent-foreground);
|
|
2225
2254
|
}
|
|
2226
2255
|
}
|
|
2256
|
+
.data-closed\:animate-fd-dialog-out {
|
|
2257
|
+
&[data-closed] {
|
|
2258
|
+
animation: var(--animate-fd-dialog-out);
|
|
2259
|
+
}
|
|
2260
|
+
}
|
|
2261
|
+
.data-closed\:animate-fd-fade-out {
|
|
2262
|
+
&[data-closed] {
|
|
2263
|
+
animation: var(--animate-fd-fade-out);
|
|
2264
|
+
}
|
|
2265
|
+
}
|
|
2227
2266
|
.data-ending-style\:scale-90 {
|
|
2228
2267
|
&[data-ending-style] {
|
|
2229
2268
|
--tw-scale-x: 90%;
|
|
@@ -2248,6 +2287,11 @@
|
|
|
2248
2287
|
transition-property: none;
|
|
2249
2288
|
}
|
|
2250
2289
|
}
|
|
2290
|
+
.data-open\:animate-fd-fade-in {
|
|
2291
|
+
&[data-open] {
|
|
2292
|
+
animation: var(--animate-fd-fade-in);
|
|
2293
|
+
}
|
|
2294
|
+
}
|
|
2251
2295
|
.data-open\:bg-fd-accent {
|
|
2252
2296
|
&[data-open] {
|
|
2253
2297
|
background-color: var(--color-fd-accent);
|
|
@@ -2364,16 +2408,6 @@
|
|
|
2364
2408
|
}
|
|
2365
2409
|
}
|
|
2366
2410
|
}
|
|
2367
|
-
.data-\[closed\]\:animate-fd-dialog-out {
|
|
2368
|
-
&[data-closed] {
|
|
2369
|
-
animation: var(--animate-fd-dialog-out);
|
|
2370
|
-
}
|
|
2371
|
-
}
|
|
2372
|
-
.data-\[closed\]\:animate-fd-fade-out {
|
|
2373
|
-
&[data-closed] {
|
|
2374
|
-
animation: var(--animate-fd-fade-out);
|
|
2375
|
-
}
|
|
2376
|
-
}
|
|
2377
2411
|
.data-\[closed\]\:animate-fd-popover-out {
|
|
2378
2412
|
&[data-closed] {
|
|
2379
2413
|
animation: var(--animate-fd-popover-out);
|
|
@@ -2423,16 +2457,6 @@
|
|
|
2423
2457
|
display: none;
|
|
2424
2458
|
}
|
|
2425
2459
|
}
|
|
2426
|
-
.data-\[open\]\:animate-fd-dialog-in {
|
|
2427
|
-
&[data-open] {
|
|
2428
|
-
animation: var(--animate-fd-dialog-in);
|
|
2429
|
-
}
|
|
2430
|
-
}
|
|
2431
|
-
.data-\[open\]\:animate-fd-fade-in {
|
|
2432
|
-
&[data-open] {
|
|
2433
|
-
animation: var(--animate-fd-fade-in);
|
|
2434
|
-
}
|
|
2435
|
-
}
|
|
2436
2460
|
.data-\[open\]\:animate-fd-popover-in {
|
|
2437
2461
|
&[data-open] {
|
|
2438
2462
|
animation: var(--animate-fd-popover-in);
|
|
@@ -2991,6 +3015,11 @@
|
|
|
2991
3015
|
syntax: "*";
|
|
2992
3016
|
inherits: false;
|
|
2993
3017
|
}
|
|
3018
|
+
@property --tw-divide-x-reverse {
|
|
3019
|
+
syntax: "*";
|
|
3020
|
+
inherits: false;
|
|
3021
|
+
initial-value: 0;
|
|
3022
|
+
}
|
|
2994
3023
|
@property --tw-divide-y-reverse {
|
|
2995
3024
|
syntax: "*";
|
|
2996
3025
|
inherits: false;
|
|
@@ -3206,15 +3235,6 @@
|
|
|
3206
3235
|
transform: translateX(var(--fd-sidebar-drawer-offset));
|
|
3207
3236
|
}
|
|
3208
3237
|
}
|
|
3209
|
-
@keyframes fd-dialog-in {
|
|
3210
|
-
from {
|
|
3211
|
-
transform: scale(1.06);
|
|
3212
|
-
opacity: 0;
|
|
3213
|
-
}
|
|
3214
|
-
to {
|
|
3215
|
-
transform: scale(1);
|
|
3216
|
-
}
|
|
3217
|
-
}
|
|
3218
3238
|
@keyframes fd-dialog-out {
|
|
3219
3239
|
from {
|
|
3220
3240
|
transform: scale(1);
|
|
@@ -3264,6 +3284,7 @@
|
|
|
3264
3284
|
--tw-rotate-z: initial;
|
|
3265
3285
|
--tw-skew-x: initial;
|
|
3266
3286
|
--tw-skew-y: initial;
|
|
3287
|
+
--tw-divide-x-reverse: 0;
|
|
3267
3288
|
--tw-divide-y-reverse: 0;
|
|
3268
3289
|
--tw-leading: initial;
|
|
3269
3290
|
--tw-font-weight: initial;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@fumadocs/base-ui",
|
|
3
|
-
"version": "16.
|
|
3
|
+
"version": "16.6.0",
|
|
4
4
|
"description": "The Base UI version of Fumadocs UI",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"Docs",
|
|
@@ -101,20 +101,24 @@
|
|
|
101
101
|
"next-themes": "^0.4.6",
|
|
102
102
|
"react-medium-image-zoom": "^5.4.0",
|
|
103
103
|
"react-remove-scroll": "^2.7.2",
|
|
104
|
+
"rehype-raw": "^7.0.0",
|
|
104
105
|
"scroll-into-view-if-needed": "^3.1.0",
|
|
105
106
|
"tailwind-merge": "^3.4.0",
|
|
107
|
+
"unist-util-visit": "^5.1.0",
|
|
106
108
|
"@fumadocs/tailwind": "0.0.2"
|
|
107
109
|
},
|
|
108
110
|
"devDependencies": {
|
|
109
111
|
"@tailwindcss/cli": "^4.1.18",
|
|
112
|
+
"@types/hast": "^3.0.4",
|
|
110
113
|
"@types/node": "^25.2.1",
|
|
111
114
|
"@types/react": "^19.2.13",
|
|
112
115
|
"@types/react-dom": "^19.2.3",
|
|
113
116
|
"tailwindcss": "^4.1.18",
|
|
114
117
|
"tsdown": "^0.20.3",
|
|
118
|
+
"unified": "^11.0.5",
|
|
115
119
|
"@fumadocs/cli": "1.2.4",
|
|
116
120
|
"eslint-config-custom": "0.0.0",
|
|
117
|
-
"fumadocs-core": "16.
|
|
121
|
+
"fumadocs-core": "16.6.0",
|
|
118
122
|
"tsconfig": "0.0.0"
|
|
119
123
|
},
|
|
120
124
|
"peerDependencies": {
|
|
@@ -123,7 +127,7 @@
|
|
|
123
127
|
"react": "^19.2.0",
|
|
124
128
|
"react-dom": "^19.2.0",
|
|
125
129
|
"tailwindcss": "^4.0.0",
|
|
126
|
-
"fumadocs-core": "16.
|
|
130
|
+
"fumadocs-core": "16.6.0"
|
|
127
131
|
},
|
|
128
132
|
"peerDependenciesMeta": {
|
|
129
133
|
"next": {
|