@windrun-huaiin/base-ui 3.1.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.
Files changed (123) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +190 -0
  3. package/dist/base-ui.css +3 -0
  4. package/dist/components/index.d.mts +144 -0
  5. package/dist/components/index.d.ts +144 -0
  6. package/dist/components/index.js +1699 -0
  7. package/dist/components/index.js.map +1 -0
  8. package/dist/components/index.mjs +1741 -0
  9. package/dist/components/index.mjs.map +1 -0
  10. package/dist/index.d.mts +47 -0
  11. package/dist/index.d.ts +47 -0
  12. package/dist/index.js +6055 -0
  13. package/dist/index.js.map +1 -0
  14. package/dist/index.mjs +5842 -0
  15. package/dist/index.mjs.map +1 -0
  16. package/dist/lib/index.d.mts +24 -0
  17. package/dist/lib/index.d.ts +24 -0
  18. package/dist/lib/index.js +1324 -0
  19. package/dist/lib/index.js.map +1 -0
  20. package/dist/lib/index.mjs +1372 -0
  21. package/dist/lib/index.mjs.map +1 -0
  22. package/dist/ui/index.d.mts +754 -0
  23. package/dist/ui/index.d.ts +754 -0
  24. package/dist/ui/index.js +5796 -0
  25. package/dist/ui/index.js.map +1 -0
  26. package/dist/ui/index.mjs +5593 -0
  27. package/dist/ui/index.mjs.map +1 -0
  28. package/package.json +120 -0
  29. package/src/assets/bitcoin.tsx +23 -0
  30. package/src/assets/clerk.tsx +23 -0
  31. package/src/assets/css.tsx +21 -0
  32. package/src/assets/csv.tsx +35 -0
  33. package/src/assets/d8.tsx +25 -0
  34. package/src/assets/diff.tsx +23 -0
  35. package/src/assets/dpa.tsx +22 -0
  36. package/src/assets/github.tsx +23 -0
  37. package/src/assets/html.tsx +22 -0
  38. package/src/assets/http.tsx +23 -0
  39. package/src/assets/index.ts +61 -0
  40. package/src/assets/iterm.tsx +23 -0
  41. package/src/assets/java.tsx +23 -0
  42. package/src/assets/json.tsx +23 -0
  43. package/src/assets/last-updated.tsx +23 -0
  44. package/src/assets/log.tsx +28 -0
  45. package/src/assets/mac.tsx +23 -0
  46. package/src/assets/markdown.tsx +24 -0
  47. package/src/assets/mdx.tsx +98 -0
  48. package/src/assets/mermaid.tsx +24 -0
  49. package/src/assets/scheme.tsx +22 -0
  50. package/src/assets/snippets.tsx +23 -0
  51. package/src/assets/sql.tsx +31 -0
  52. package/src/assets/subp.tsx +22 -0
  53. package/src/assets/t3p.tsx +23 -0
  54. package/src/assets/test.tsx +23 -0
  55. package/src/assets/txt.tsx +23 -0
  56. package/src/assets/xml.tsx +23 -0
  57. package/src/assets/yaml.tsx +23 -0
  58. package/src/components/404-page.tsx +106 -0
  59. package/src/components/global-icon.tsx +193 -0
  60. package/src/components/go-to-top.tsx +43 -0
  61. package/src/components/index.ts +10 -0
  62. package/src/components/language-detector.tsx +175 -0
  63. package/src/components/language-switcher.tsx +77 -0
  64. package/src/components/script/google-analytics-script.tsx +56 -0
  65. package/src/components/script/microsoft-clarity-script.tsx +24 -0
  66. package/src/index.ts +4 -0
  67. package/src/lib/icon-context.tsx +57 -0
  68. package/src/lib/index.ts +3 -0
  69. package/src/lib/site-icon.tsx +46 -0
  70. package/src/lib/theme-util.ts +7 -0
  71. package/src/styles/base-ui.css +2 -0
  72. package/src/ui/accordion.tsx +58 -0
  73. package/src/ui/alert-dialog.tsx +141 -0
  74. package/src/ui/alert.tsx +59 -0
  75. package/src/ui/aspect-ratio.tsx +7 -0
  76. package/src/ui/avatar.tsx +50 -0
  77. package/src/ui/badge.tsx +36 -0
  78. package/src/ui/breadcrumb.tsx +115 -0
  79. package/src/ui/button.tsx +76 -0
  80. package/src/ui/calendar.tsx +66 -0
  81. package/src/ui/card.tsx +79 -0
  82. package/src/ui/carousel.tsx +262 -0
  83. package/src/ui/chart.tsx +365 -0
  84. package/src/ui/checkbox.tsx +30 -0
  85. package/src/ui/collapsible.tsx +11 -0
  86. package/src/ui/command.tsx +153 -0
  87. package/src/ui/context-menu.tsx +200 -0
  88. package/src/ui/dialog.tsx +122 -0
  89. package/src/ui/drawer.tsx +118 -0
  90. package/src/ui/dropdown-menu.tsx +200 -0
  91. package/src/ui/form.tsx +178 -0
  92. package/src/ui/hover-card.tsx +29 -0
  93. package/src/ui/index.ts +52 -0
  94. package/src/ui/input-otp.tsx +71 -0
  95. package/src/ui/input.tsx +22 -0
  96. package/src/ui/label.tsx +26 -0
  97. package/src/ui/language-button.tsx +43 -0
  98. package/src/ui/menubar.tsx +236 -0
  99. package/src/ui/navigation-menu.tsx +128 -0
  100. package/src/ui/pagination.tsx +117 -0
  101. package/src/ui/popover.tsx +31 -0
  102. package/src/ui/progress.tsx +28 -0
  103. package/src/ui/radio-group.tsx +44 -0
  104. package/src/ui/resizable.tsx +45 -0
  105. package/src/ui/scroll-area.tsx +48 -0
  106. package/src/ui/select.tsx +160 -0
  107. package/src/ui/separator.tsx +31 -0
  108. package/src/ui/sheet.tsx +140 -0
  109. package/src/ui/sidebar.tsx +763 -0
  110. package/src/ui/skeleton.tsx +15 -0
  111. package/src/ui/slider.tsx +28 -0
  112. package/src/ui/sonner.tsx +31 -0
  113. package/src/ui/switch.tsx +29 -0
  114. package/src/ui/table.tsx +117 -0
  115. package/src/ui/tabs.tsx +55 -0
  116. package/src/ui/textarea.tsx +22 -0
  117. package/src/ui/toast.tsx +129 -0
  118. package/src/ui/toaster.tsx +35 -0
  119. package/src/ui/toggle-group.tsx +61 -0
  120. package/src/ui/toggle.tsx +45 -0
  121. package/src/ui/tooltip.tsx +30 -0
  122. package/src/ui/use-mobile.tsx +19 -0
  123. package/src/ui/use-toast.ts +194 -0
@@ -0,0 +1,98 @@
1
+ import React from 'react';
2
+ import { LucideProps } from 'lucide-react';
3
+ import { themeSvgIconColor } from '@base-ui/lib/theme-util';
4
+
5
+ const MDXIcon = React.forwardRef<SVGSVGElement, LucideProps>(
6
+ ({ color = "currentColor", className, ...props }, ref) => (
7
+ <svg
8
+ ref={ref}
9
+ role="img"
10
+ className={className}
11
+ {...props}
12
+ viewBox="0 0 1024 1024" xmlns="http://www.w3.org/2000/svg"
13
+ >
14
+ <path
15
+ d="M20.48 327.76192a163.84 163.84 0 0 1 163.84-163.84h655.36a163.84 163.84 0 0 1 163.84 163.84v327.68a163.84 163.84 0 0 1-163.84 163.84H184.32a163.84 163.84 0 0 1-163.84-163.84v-327.68z m163.84-81.92a81.92 81.92 0 0 0-81.92 81.92v327.68a81.92 81.92 0 0 0 81.92 81.92h655.36a81.92 81.92 0 0 0 81.92-81.92v-327.68a81.92 81.92 0 0 0-81.92-81.92H184.32z m68.97664 84.00896a40.96 40.96 0 0 1 45.71136 14.336L389.12 464.24064l90.112-120.13568a40.96 40.96 0 0 1 73.728 24.576v245.76a40.96 40.96 0 0 1-81.92 0v-122.88l-49.152 65.536a41.04192 41.04192 0 0 1-65.536 0l-49.152-65.536v122.88a40.96 40.96 0 1 1-81.92 0v-245.76a40.96 40.96 0 0 1 28.01664-38.87104zM757.76 368.76288a40.96 40.96 0 0 0-81.92 0v146.8416l-12.00128-12.00128a40.96 40.96 0 0 0-57.91744 57.91744l81.92 81.92a40.96 40.96 0 0 0 57.91744 0l81.92-81.92a40.96 40.96 0 0 0-57.91744-57.91744l-12.00128 12.00128V368.72192z"
16
+ p-id="7370"
17
+ id="path1"
18
+ style={{
19
+ stroke: "none",
20
+ strokeOpacity: 1,
21
+ fill: themeSvgIconColor,
22
+ fillOpacity: 1,
23
+ strokeWidth: 16,
24
+ strokeDasharray: "none"
25
+ }} />
26
+ <circle
27
+ id="path3"
28
+ cx="719.29987"
29
+ cy="577.29211"
30
+ r="40.298649"
31
+ style={{
32
+ opacity: 1,
33
+ fill: "#FFFFFF",
34
+ fillOpacity: 1,
35
+ stroke: "none",
36
+ strokeWidth: 9.49366,
37
+ strokeDasharray: "none",
38
+ strokeOpacity: 1
39
+ }} />
40
+ <circle
41
+ id="path3-6"
42
+ cx="850.25433"
43
+ cy="310.07559"
44
+ r="40.298649"
45
+ style={{
46
+ fill: themeSvgIconColor,
47
+ fillOpacity: 1,
48
+ stroke: "none",
49
+ strokeWidth: 9.49366,
50
+ strokeDasharray: "none",
51
+ strokeOpacity: 1
52
+ }}/>
53
+ <circle
54
+ id="path3-6-8"
55
+ cx="173.18126"
56
+ cy="310.07559"
57
+ r="40.298649"
58
+ style={{
59
+ fill: themeSvgIconColor,
60
+ fillOpacity: 1,
61
+ stroke: "none",
62
+ strokeWidth: 9.49366,
63
+ strokeDasharray: "none",
64
+ strokeOpacity: 1
65
+ }} />
66
+ <circle
67
+ id="path3-6-8-7"
68
+ cx="850.25433"
69
+ cy="666.45483"
70
+ r="40.298649"
71
+ style={{
72
+ fill: themeSvgIconColor,
73
+ fillOpacity: 1,
74
+ stroke: "none",
75
+ strokeWidth: 9.49366,
76
+ strokeDasharray: "none",
77
+ strokeOpacity: 1
78
+ }} />
79
+ <circle
80
+ id="path3-6-4"
81
+ cx="173.18126"
82
+ cy="669.54193"
83
+ r="40.298649"
84
+ style={{
85
+ fill: themeSvgIconColor,
86
+ fillOpacity: 1,
87
+ stroke: "none",
88
+ strokeWidth: 9.49366,
89
+ strokeDasharray: "none",
90
+ strokeOpacity: 1
91
+ }} />
92
+ </svg>
93
+ )
94
+ );
95
+
96
+ MDXIcon.displayName = "MDX";
97
+
98
+ export default MDXIcon;
@@ -0,0 +1,24 @@
1
+ import React from 'react';
2
+ import { LucideProps } from 'lucide-react';
3
+ import { themeSvgIconColor } from '@base-ui/lib/theme-util';
4
+
5
+ const MermaidIcon = React.forwardRef<SVGSVGElement, LucideProps>(
6
+ // Memmaid need special size for good view
7
+ ({ color = "currentColor", className, ...props }, ref) => (
8
+ <svg
9
+ ref={ref}
10
+ role="img"
11
+ className={className}
12
+ {...props}
13
+ viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg" >
14
+ <path
15
+ d="M23.99 2.115A12.223 12.223 0 0 0 12 10.149 12.223 12.223 0 0 0 .01 2.115a12.23 12.23 0 0 0 5.32 10.604 6.562 6.562 0 0 1 2.845 5.423v3.754h7.65v-3.754a6.561 6.561 0 0 1 2.844-5.423 12.223 12.223 0 0 0 5.32-10.604Z"
16
+ fill="none" stroke={themeSvgIconColor} strokeWidth="2"
17
+ />
18
+ </svg>
19
+ )
20
+ );
21
+
22
+ MermaidIcon.displayName = "Mmd";
23
+
24
+ export default MermaidIcon;
@@ -0,0 +1,22 @@
1
+ import React from 'react';
2
+ import { LucideProps } from 'lucide-react';
3
+ import { themeSvgIconColor } from '@base-ui/lib/theme-util';
4
+
5
+ const SchemeIcon = React.forwardRef<SVGSVGElement, LucideProps>(
6
+ ({ color = "currentColor", className, ...props }, ref) => (
7
+ <svg
8
+ ref={ref}
9
+ role="img"
10
+ className={className}
11
+ {...props}
12
+ viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg">
13
+ <path fill={themeSvgIconColor}
14
+ d="M5.11 21.186 9.887 7.303 8.945 5.11H7.407V2.813h2.296c.483 0 .896.299 1.068.724l6.58 15.353h1.539v2.296h-2.297a1.14 1.14 0 0 1-1.068-.735L11.231 10.45 7.544 21.186z"
15
+ />
16
+ </svg>
17
+ )
18
+ );
19
+
20
+ SchemeIcon.displayName = "Scheme";
21
+
22
+ export default SchemeIcon;
@@ -0,0 +1,23 @@
1
+ import React from 'react';
2
+ import { LucideProps } from 'lucide-react';
3
+ import { themeSvgIconColor } from '@base-ui/lib/theme-util';
4
+
5
+ const SnippetsIcon = React.forwardRef<SVGSVGElement, LucideProps>(
6
+ ({ color = "currentColor", className, ...props }, ref) => (
7
+ <svg
8
+ ref={ref}
9
+ role="img"
10
+ className={className}
11
+ {...props}
12
+ viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg">
13
+ <path
14
+ d="M9.825 17.527a.111.111 0 0 1-.107-.142l3.05-10.837a.111.111 0 0 1 .108-.081H14.2c.074 0 .127.07.107.141l-3.063 10.838a.111.111 0 0 1-.107.08H9.825Zm-2.146-2.732a.11.11 0 0 1-.079-.033l-2.667-2.704a.111.111 0 0 1 0-.156L7.6 9.211a.111.111 0 0 1 .08-.033h1.702c.1 0 .149.12.079.19l-2.534 2.534a.111.111 0 0 0 0 .157l2.535 2.546c.07.07.02.19-.079.19H7.68Zm6.954 0a.111.111 0 0 1-.079-.19l2.525-2.546a.111.111 0 0 0 0-.157l-2.524-2.535a.111.111 0 0 1 .079-.19h1.692c.03 0 .058.013.078.034l2.68 2.69a.111.111 0 0 1 0 .157l-2.68 2.704a.111.111 0 0 1-.078.033h-1.693ZM12 24C5.383 24 0 18.617 0 12S5.383 0 12 0s12 5.383 12 12-5.383 12-12 12Zm0-22.667C6.118 1.333 1.333 6.118 1.333 12S6.118 22.667 12 22.667 22.667 17.882 22.667 12 17.882 1.333 12 1.333Z"
15
+ fill={themeSvgIconColor}
16
+ />
17
+ </svg>
18
+ )
19
+ );
20
+
21
+ SnippetsIcon.displayName = "Snippets";
22
+
23
+ export default SnippetsIcon;
@@ -0,0 +1,31 @@
1
+ import React from 'react';
2
+ import { LucideProps } from 'lucide-react';
3
+ import { themeSvgIconColor } from '@base-ui/lib/theme-util';
4
+
5
+ const SQLIcon = React.forwardRef<SVGSVGElement, LucideProps>(
6
+ ({ color = "currentColor", className, ...props }, ref) => (
7
+ <svg
8
+ ref={ref}
9
+ role="img"
10
+ className={className}
11
+ {...props}
12
+ viewBox="0 0 1024 1024" xmlns="http://www.w3.org/2000/svg">
13
+ <path
14
+ d="M477.12 858.56l14.72-16.64a77.44 77.44 0 0 0 54.08 24c25.6 0 40.96-12.8 40.96-32s-14.08-26.56-32-34.88l-28.48-12.16a52.16 52.16 0 0 1 22.08-101.76 79.36 79.36 0 0 1 57.28 24l-12.8 15.68a64 64 0 0 0-44.48-18.24c-22.08 0-36.48 11.2-36.48 28.8s16.96 25.92 32 32l28.16 12.16A54.08 54.08 0 0 1 611.84 832a58.88 58.88 0 0 1-66.24 55.36 93.76 93.76 0 0 1-68.48-28.8zM810.24 928a96 96 0 0 1-28.16 4.16 74.24 74.24 0 0 1-71.68-46.4c-42.56-4.8-70.4-42.56-70.4-99.84 0-62.4 34.56-100.48 83.52-100.48s83.2 38.08 83.2 100.48c0 56.32-27.52 93.44-68.8 100.8a50.24 50.24 0 0 0 47.68 25.92 68.8 68.8 0 0 0 20.8-2.88z m-87.68-61.44c34.88 0 57.92-32 57.92-81.6s-23.04-79.04-57.92-79.04-58.24 30.08-58.24 79.04 23.04 82.56 58.24 82.56zM848 688.96h24.64V864h85.44v21.12H848zM444.16 377.28c-192 0-387.2-52.8-387.2-153.92s194.56-154.24 387.2-154.24S832 121.92 832 224s-195.52 153.28-387.84 153.28z m0-244.16C234.88 133.12 120.96 192 120.96 224s113.92 89.92 323.2 89.92S768 253.76 768 224s-114.88-90.88-323.84-90.88z"
15
+ p-id="12089" fill={themeSvgIconColor} >
16
+ </path>
17
+ <path
18
+ d="M444.16 554.88c-192 0-387.2-52.8-387.2-154.24a32 32 0 0 1 64 0c0 32 113.92 90.24 323.2 90.24S768 431.36 768 400.64a32 32 0 1 1 64 0c0 101.44-195.52 154.24-387.84 154.24zM444.16 732.48c-192 0-387.2-53.12-387.2-154.24a32 32 0 0 1 64 0c0 32 113.92 90.24 323.2 90.24a32 32 0 1 1 0 64zM444.16 932.16c-192 0-387.2-52.8-387.2-153.92a32 32 0 0 1 64 0c0 30.4 113.92 89.92 323.2 89.92a32 32 0 0 1 0 64z"
19
+ p-id="12090" fill={themeSvgIconColor} >
20
+ </path>
21
+ <path
22
+ d="M800 699.2a32 32 0 0 1-32-32V234.24a32 32 0 0 1 64 0v432.96a32 32 0 0 1-32 32zM88.96 821.12a32 32 0 0 1-32-32V234.24a32 32 0 0 1 64 0v554.88a32 32 0 0 1-32 32z"
23
+ p-id="12091" fill={themeSvgIconColor} >
24
+ </path>
25
+ </svg>
26
+ )
27
+ );
28
+
29
+ SQLIcon.displayName = "SQL";
30
+
31
+ export default SQLIcon;
@@ -0,0 +1,22 @@
1
+ import React from 'react';
2
+ import { LucideProps } from 'lucide-react';
3
+ import { themeSvgIconColor } from '@base-ui/lib/theme-util';
4
+
5
+ const SubPIcon = React.forwardRef<SVGSVGElement, LucideProps>(
6
+ ({ color = "currentColor", className, ...props }, ref) => (
7
+ <svg
8
+ ref={ref}
9
+ role="img"
10
+ className={className}
11
+ {...props}
12
+ viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg">
13
+ <path
14
+ d="M11.999 0a12 12 0 100 24A12 12 0 0012 0zm1.183 5.255h.048c3.273 0 5.247 1.48 5.247 4.103 0 2.727-1.974 4.536-5.295 4.669v-1.742c1.837-.11 2.801-1.061 2.801-2.744 0-1.498-.957-2.442-2.8-2.516zm-1.773.026l.005 11.896c.779.052 1.583.18 2.26.337l-.269 1.324H6.788v-1.324a14.96 14.96 0 012.26-.337V6.993a14.71 14.71 0 01-2.26-.337V5.33h2.26c.64 0 1.469-.028 2.361-.05z"
15
+ fill="none" stroke={themeSvgIconColor} strokeWidth="1.5" />
16
+ </svg>
17
+ )
18
+ );
19
+
20
+ SubPIcon.displayName = "SubP";
21
+
22
+ export default SubPIcon;
@@ -0,0 +1,23 @@
1
+ import React from 'react';
2
+ import { LucideProps } from 'lucide-react';
3
+ import { themeSvgIconColor } from '@base-ui/lib/theme-util';
4
+
5
+ const T3PIcon = React.forwardRef<SVGSVGElement, LucideProps>(
6
+ ({ color = "currentColor", className, ...props }, ref) => (
7
+ <svg
8
+ ref={ref}
9
+ role="img"
10
+ className={className}
11
+ {...props}
12
+ viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg">
13
+ <path
14
+ d="M9.71 2.136a1.43 1.43 0 0 0-2.047 0h-.007a1.48 1.48 0 0 0-.421 1.042c0 .41.161.777.422 1.039l.007.007c.257.264.616.426 1.019.426.404 0 .766-.162 1.027-.426l.003-.007c.261-.262.421-.629.421-1.039 0-.408-.159-.777-.421-1.042H9.71zM8.683 22.295c.404 0 .766-.167 1.027-.429l.003-.008c.261-.261.421-.631.421-1.036 0-.41-.159-.778-.421-1.044H9.71a1.42 1.42 0 0 0-1.027-.432 1.4 1.4 0 0 0-1.02.432h-.007c-.26.266-.422.634-.422 1.044 0 .406.161.775.422 1.036l.007.008c.258.262.617.429 1.02.429zm7.89-4.462c.359-.096.683-.33.882-.684l.027-.052a1.47 1.47 0 0 0 .114-1.067 1.454 1.454 0 0 0-.675-.896l-.021-.014a1.425 1.425 0 0 0-1.078-.132c-.36.091-.684.335-.881.686-.2.349-.241.75-.146 1.119.099.363.33.691.675.896h.002c.346.203.737.239 1.101.144zm-6.405-7.342a2.083 2.083 0 0 0-1.485-.627c-.58 0-1.103.242-1.482.627-.378.385-.612.916-.612 1.507s.233 1.124.612 1.514a2.08 2.08 0 0 0 2.967 0c.379-.39.612-.923.612-1.514s-.233-1.122-.612-1.507zm-.835-2.51c.843.141 1.6.552 2.178 1.144h.004c.092.093.182.196.265.299l1.446-.851a3.176 3.176 0 0 1-.047-1.808 3.149 3.149 0 0 1 1.456-1.926l.025-.016a3.062 3.062 0 0 1 2.345-.306c.77.21 1.465.721 1.898 1.482v.002c.431.757.518 1.626.313 2.408a3.145 3.145 0 0 1-1.456 1.928l-.198.118h-.02a3.095 3.095 0 0 1-2.154.201 3.127 3.127 0 0 1-1.514-.944l-1.444.848a4.162 4.162 0 0 1 0 2.879l1.444.846c.413-.47.939-.789 1.514-.944a3.041 3.041 0 0 1 2.371.319l.048.023v.002a3.17 3.17 0 0 1 1.408 1.906 3.215 3.215 0 0 1-.313 2.405l-.026.053-.003-.005a3.147 3.147 0 0 1-1.867 1.436 3.096 3.096 0 0 1-2.371-.318v-.006a3.156 3.156 0 0 1-1.456-1.927 3.175 3.175 0 0 1 .047-1.805l-1.446-.848a3.905 3.905 0 0 1-.265.294l-.004.005a3.938 3.938 0 0 1-2.178 1.138v1.699a3.09 3.09 0 0 1 1.56.862l.002.004c.565.572.914 1.368.914 2.243 0 .873-.35 1.664-.914 2.239l-.002.009a3.1 3.1 0 0 1-2.21.931 3.1 3.1 0 0 1-2.206-.93h-.002v-.009a3.186 3.186 0 0 1-.916-2.239c0-.875.35-1.672.916-2.243v-.004h.002a3.1 3.1 0 0 1 1.558-.862v-1.699a3.926 3.926 0 0 1-2.176-1.138l-.006-.005a4.098 4.098 0 0 1-1.173-2.874c0-1.122.452-2.136 1.173-2.872h.006a3.947 3.947 0 0 1 2.176-1.144V6.289a3.137 3.137 0 0 1-1.558-.864h-.002v-.004a3.192 3.192 0 0 1-.916-2.243c0-.871.35-1.669.916-2.243l.002-.002A3.084 3.084 0 0 1 8.683 0c.861 0 1.641.355 2.21.932v.002h.002c.565.574.914 1.372.914 2.243 0 .876-.35 1.667-.914 2.243l-.002.005a3.142 3.142 0 0 1-1.56.864v1.692zm8.121-1.129l-.012-.019a1.452 1.452 0 0 0-.87-.668 1.43 1.43 0 0 0-1.103.146h.002c-.347.2-.58.529-.677.896-.095.365-.054.768.146 1.119l.007.009c.2.347.519.579.874.673.357.103.755.059 1.098-.144l.019-.009a1.47 1.47 0 0 0 .657-.885 1.493 1.493 0 0 0-.141-1.118"
15
+ fill={themeSvgIconColor}
16
+ />
17
+ </svg>
18
+ )
19
+ );
20
+
21
+ T3PIcon.displayName = "T3P";
22
+
23
+ export default T3PIcon;
@@ -0,0 +1,23 @@
1
+ import React from 'react';
2
+ import { LucideProps } from 'lucide-react';
3
+ import { themeSvgIconColor } from '@base-ui/lib/theme-util';
4
+
5
+ const TestIcon = React.forwardRef<SVGSVGElement, LucideProps>(
6
+ ({ color = "currentColor", className, ...props }, ref) => (
7
+ <svg
8
+ ref={ref}
9
+ role="img"
10
+ className={className}
11
+ {...props}
12
+ viewBox="0 0 1024 1024" xmlns="http://www.w3.org/2000/svg">
13
+ <path
14
+ d="M640 126.577778c-140.8 0-256 115.2-256 256 0 65.422222 25.6 125.155556 65.422222 170.666666l-91.022222 91.022223-35.555556-35.555556-174.933333 176.355556c-25.6 25.6-25.6 68.266667 0 93.866666 25.6 25.6 68.266667 25.6 93.866667 0l176.355555-176.355555-38.4-38.4 91.022223-91.022222c45.511111 41.244444 105.244444 65.422222 170.666666 65.422222 140.8 0 256-115.2 256-256-1.422222-142.222222-116.622222-256-257.422222-256z m19.911111 462.222222c-41.244444 0-75.377778-34.133333-75.377778-75.377778v-4.266666c0-8.533333 5.688889-14.222222 14.222223-14.222223s14.222222 5.688889 14.222222 14.222223v4.266666c0 25.6 21.333333 46.933333 46.933333 46.933334 8.533333 0 14.222222 5.688889 14.222222 14.222222s-5.688889 14.222222-14.222222 14.222222zM817.777778 341.333333h-58.311111c-2.844444 12.8-7.111111 24.177778-14.222223 35.555556l41.244445 41.244444c5.688889 5.688889 5.688889 14.222222 0 19.911111-2.844444 2.844444-7.111111 4.266667-9.955556 4.266667-2.844444 0-7.111111-1.422222-9.955555-4.266667L725.333333 396.8c-14.222222 9.955556-31.288889 15.644444-49.777777 15.644444-18.488889 0-35.555556-5.688889-49.777778-15.644444l-41.244445 41.244444c-2.844444 2.844444-7.111111 4.266667-9.955555 4.266667-2.844444 0-7.111111-1.422222-9.955556-4.266667-5.688889-5.688889-5.688889-14.222222 0-19.911111l41.244445-41.244444c-7.111111-9.955556-12.8-22.755556-14.222223-35.555556h-58.311111c-8.533333 0-14.222222-5.688889-14.222222-14.222222s5.688889-14.222222 14.222222-14.222222h58.311111c2.844444-12.8 7.111111-24.177778 14.222223-35.555556l-41.244445-41.244444c-5.688889-5.688889-5.688889-14.222222 0-19.911111 5.688889-5.688889 14.222222-5.688889 19.911111 0l41.244445 41.244444c14.222222-9.955556 31.288889-15.644444 49.777778-15.644444 18.488889 0 35.555556 5.688889 49.777777 15.644444l41.244445-41.244444c5.688889-5.688889 14.222222-5.688889 19.911111 0 5.688889 5.688889 5.688889 14.222222 0 19.911111l-41.244445 41.244444c7.111111 9.955556 12.8 22.755556 14.222223 35.555556h58.311111c8.533333 0 14.222222 5.688889 14.222222 14.222222s-5.688889 14.222222-14.222222 14.222222z"
15
+ fill={themeSvgIconColor} p-id="7101">
16
+ </path>
17
+ </svg>
18
+ )
19
+ );
20
+
21
+ TestIcon.displayName = "Test";
22
+
23
+ export default TestIcon;
@@ -0,0 +1,23 @@
1
+ import React from 'react';
2
+ import { LucideProps } from 'lucide-react';
3
+ import { themeSvgIconColor } from '@base-ui/lib/theme-util';
4
+
5
+ const TxtIcon = React.forwardRef<SVGSVGElement, LucideProps>(
6
+ ({ color = "currentColor", className, ...props }, ref) => (
7
+ <svg
8
+ ref={ref}
9
+ role="img"
10
+ className={className}
11
+ {...props}
12
+ viewBox="0 0 1024 1024" xmlns="http://www.w3.org/2000/svg">
13
+ <path
14
+ d="M764.6 791c-35.6 0-77.2-19.2-77.2-73.6 0-21.8 7.8-37.2 25.2-49.6 17-12.2 43-20.8 73.4-24.4 42.8-5 91-7.8 132.2-9.2 0.6 0 1 0.2 1.6 0.4 0.6 0.2 1 0.6 1.4 1 0.4 0.4 0.6 0.8 0.8 1.4 0.2 0.6 0.2 1 0.2 1.6-5.4 102.4-57.2 152.4-157.6 152.4z m42.2-460.6c-84.6-0.6-160.4 48.8-192.8 125.6-0.6 1.4-1 2.8-1.6 4.2-0.4 1.4-0.8 2.8-1 4.2-0.2 1.4-0.6 2.8-0.6 4.4-0.2 1.4-0.2 3-0.2 4.4 0 1.4 0 3 0.2 4.4 0.2 1.4 0.4 3 0.6 4.4 0.2 1.4 0.6 2.8 1 4.2 0.4 1.4 0.8 2.8 1.4 4.2 0.6 1.4 1.2 2.8 1.8 4 0.6 1.4 1.4 2.6 2.2 3.8 0.8 1.2 1.6 2.4 2.6 3.6 1 1.2 1.8 2.2 3 3.2 1 1 2 2 3.2 3 1.2 1 2.2 1.8 3.4 2.6 1.2 0.8 2.4 1.6 3.8 2.4 1.2 0.8 2.6 1.4 4 2 1.4 0.6 2.8 1 4.2 1.6l4.2 1.2c1.4 0.4 2.8 0.6 4.4 0.6 1.4 0.2 3 0.2 4.4 0.2 1.4 0 3 0 4.4-0.2 1.4-0.2 3-0.4 4.4-0.6 1.4-0.2 2.8-0.6 4.2-1 1.4-0.4 2.8-0.8 4.2-1.4 1.4-0.6 2.6-1.2 4-1.8 1.2-0.6 2.6-1.4 3.8-2.2 1.2-0.8 2.4-1.6 3.6-2.6 1.2-1 2.2-2 3.2-3s2-2.2 3-3.2c1-1.2 1.8-2.4 2.6-3.6 0.8-1.2 1.6-2.4 2.2-3.8 0.8-1.2 1.4-2.6 2-4 18-42.8 60.4-70.4 108.2-70.8 65.6-0.4 118.6 54.2 118.6 120.4 0 0.4 0 0.8-0.2 1.2-0.2 0.4-0.4 0.6-0.6 1-0.2 0.2-0.6 0.6-1 0.6-0.4 0.2-0.8 0.2-1.2 0.2-44.4 1.2-97.2 4.2-144.4 9.8-111 13.2-177.4 74.2-177.4 163.4 0 47.4 17.8 90 50 120 30.2 28.2 71.6 43.6 116.4 43.6 63 0 117-16.4 158.2-47.6h0.2c0 1.4 0 3 0.2 4.4 0.2 1.4 0.4 3 0.6 4.4 0.2 1.4 0.6 2.8 1 4.2 0.4 1.4 1 2.8 1.4 4.2 0.6 1.4 1.2 2.8 1.8 4 0.6 1.4 1.4 2.6 2.2 3.8 0.8 1.2 1.6 2.4 2.6 3.6 1 1.2 1.8 2.2 3 3.2 1 1 2.2 2 3.2 3 1.2 1 2.2 1.8 3.6 2.6 1.2 0.8 2.4 1.6 3.8 2.2 1.2 0.8 2.6 1.4 4 2 1.4 0.6 2.8 1 4.2 1.6 1.4 0.4 2.8 0.8 4.2 1 1.4 0.2 2.8 0.6 4.4 0.6 1.4 0.2 3 0.2 4.4 0.2 1.4 0 3 0 4.4-0.2 1.4-0.2 3-0.4 4.4-0.6 1.4-0.2 2.8-0.6 4.2-1 1.4-0.4 2.8-1 4.2-1.4 1.4-0.6 2.6-1.2 4-1.8 1.2-0.6 2.6-1.4 3.8-2.2 1.2-0.8 2.4-1.6 3.6-2.6 1.2-1 2.2-2 3.2-3s2-2.2 3-3.2c1-1.2 1.8-2.4 2.6-3.6 0.8-1.2 1.6-2.4 2.2-3.8 0.6-1.2 1.4-2.6 1.8-4 0.6-1.4 1-2.8 1.4-4.2 0.4-1.4 0.8-2.8 1-4.2 0.2-1.4 0.6-3 0.6-4.4 0.2-1.4 0.2-3 0.2-4.4V541.2c-0.4-115-91.8-210-205.8-210.8zM210.2 554l88-236.6c0.2-0.8 0.8-1.4 1.4-2 0.6-0.4 1.4-0.8 2.4-0.8 0.8 0 1.6 0.2 2.4 0.8 0.6 0.4 1.2 1.2 1.4 2l88 236.8c0.2 0.4 0.2 0.6 0.2 1v1c0 0.4-0.2 0.6-0.2 1-0.2 0.4-0.2 0.6-0.4 0.8-0.2 0.2-0.4 0.6-0.6 0.8-0.2 0.2-0.6 0.4-0.8 0.6-0.2 0.2-0.6 0.2-1 0.4-0.4 0-0.6 0.2-1 0.2h-176c-0.4 0-0.6 0-1-0.2-0.4 0-0.6-0.2-1-0.4-0.2-0.2-0.6-0.4-0.8-0.6-0.2-0.2-0.4-0.4-0.6-0.8-0.2-0.2-0.4-0.6-0.4-0.8-0.2-0.4-0.2-0.6-0.2-1v-1c0-0.4 0-0.8 0.2-1.2z m377 264L343.8 163.2c-0.8-2.2-1.8-4.2-2.8-6.2-1.2-2-2.4-3.8-3.8-5.6-1.4-1.8-3-3.4-4.6-5-1.6-1.6-3.4-3-5.2-4.2-1.8-1.2-3.8-2.4-5.8-3.4s-4.2-1.8-6.2-2.6c-2.2-0.6-4.4-1.2-6.6-1.6-2.2-0.4-4.4-0.6-6.8-0.6-2.2 0-4.6 0.2-6.8 0.6-2.2 0.4-4.4 0.8-6.6 1.6-2.2 0.6-4.2 1.6-6.2 2.6s-4 2.2-5.8 3.4c-1.8 1.2-3.6 2.8-5.2 4.2-1.6 1.6-3.2 3.2-4.6 5-1.4 1.8-2.6 3.6-3.8 5.6-1.2 2-2 4-2.8 6.2L16.6 818c-0.4 1.4-1 2.8-1.2 4.2-0.4 1.4-0.6 2.8-0.8 4.4-0.2 1.4-0.4 3-0.4 4.4v4.4c0 1.4 0.2 3 0.4 4.4 0.2 1.4 0.4 2.8 0.8 4.4l1.2 4.2c0.4 1.4 1 2.8 1.6 4 0.6 1.4 1.2 2.6 2 3.8l2.4 3.6c0.8 1.2 1.8 2.4 2.8 3.4 1 1 2 2.2 3 3.2s2.2 2 3.4 2.8c1.2 0.8 2.4 1.8 3.6 2.4 1.2 0.8 2.6 1.4 3.8 2.2 1.4 0.6 2.6 1.2 4 1.8 1.4 0.6 2.8 1 4.2 1.4 1.4 0.4 2.8 0.6 4.2 1 1.4 0.2 2.8 0.4 4.4 0.6 1.4 0 3 0.2 4.4 0 1.4 0 2.8-0.2 4.4-0.4 1.4-0.2 2.8-0.4 4.2-0.8l4.2-1.2c1.4-0.4 2.8-1 4-1.6 1.4-0.6 2.6-1.2 3.8-2l3.6-2.4c1.2-0.8 2.4-1.8 3.4-2.8 1-1 2.2-2 3.2-3s2-2.2 2.8-3.4c0.8-1.2 1.8-2.4 2.6-3.6 0.8-1.2 1.4-2.6 2.2-3.8 0.6-1.4 1.2-2.6 1.8-4L174 652.2c0.2-0.8 0.8-1.4 1.4-2 0.6-0.4 1.4-0.8 2.4-0.8h249c0.8 0 1.6 0.2 2.4 0.8 0.6 0.4 1.2 1.2 1.4 2l73.4 197.4c0.6 1.4 1.2 2.8 1.8 4 0.6 1.4 1.4 2.6 2.2 3.8 0.8 1.2 1.6 2.4 2.6 3.6 0.8 1.2 1.8 2.2 2.8 3.4 1 1 2 2 3.2 3s2.2 1.8 3.4 2.8l3.6 2.4c1.2 0.8 2.6 1.4 3.8 2 1.4 0.6 2.6 1.2 4 1.6l4.2 1.2c1.4 0.4 2.8 0.6 4.2 0.8 1.4 0.2 2.8 0.4 4.4 0.4h4.4c1.4 0 2.8-0.2 4.4-0.6s2.8-0.6 4.2-1c1.4-0.4 2.8-0.8 4.2-1.4 1.4-0.6 2.6-1 4-1.8 1.4-0.6 2.6-1.4 3.8-2.2l3.6-2.4c1.2-0.8 2.2-1.8 3.4-2.8 1-1 2-2 3-3.2 1-1 1.8-2.2 2.8-3.4l2.4-3.6c0.8-1.2 1.4-2.6 2-3.8 0.6-1.4 1.2-2.6 1.6-4l1.2-4.2c0.4-1.4 0.6-2.8 0.8-4.4 0.2-1.4 0.4-3 0.4-4.4v-4.4c0-1.4-0.2-3-0.4-4.4-0.2-1.4-0.6-2.8-0.8-4.4-1-1.4-1.4-2.8-2-4.2z"
15
+ fill={themeSvgIconColor} p-id="18326">
16
+ </path>
17
+ </svg>
18
+ )
19
+ );
20
+
21
+ TxtIcon.displayName = "Txt";
22
+
23
+ export default TxtIcon;
@@ -0,0 +1,23 @@
1
+ import React from 'react';
2
+ import { LucideProps } from 'lucide-react';
3
+ import { themeSvgIconColor } from '@base-ui/lib/theme-util';
4
+
5
+ const XMLIcon = React.forwardRef<SVGSVGElement, LucideProps>(
6
+ ({ color = "currentColor", className, ...props }, ref) => (
7
+ <svg
8
+ ref={ref}
9
+ role="img"
10
+ className={className}
11
+ {...props}
12
+ viewBox="0 0 1024 1024" xmlns="http://www.w3.org/2000/svg">
13
+ <path
14
+ d="M354.40128 0c-87.04 0-157.44 70.55872-157.44 157.59872v275.68128H78.72c-21.6576 0-39.36256 17.69984-39.36256 39.36256v236.31872c0 21.6576 17.69984 39.35744 39.36256 39.35744h118.24128v118.08256c0 87.04 70.4 157.59872 157.44 157.59872h472.63744c87.04 0 157.59872-70.55872 157.59872-157.59872V315.0336c0-41.74848-38.9888-81.93024-107.52-149.27872l-29.11744-29.12256L818.87744 107.52C751.5392 38.9888 711.39328 0 669.59872 0H354.4064z m0 78.72h287.20128c28.35456 7.0912 27.99616 42.1376 27.99616 76.8v120.16128c0 21.6576 17.69984 39.35744 39.36256 39.35744h118.07744c39.38816 0 78.87872-0.0256 78.87872 39.36256v512c0 43.32032-35.55328 78.87872-78.87872 78.87872H354.4064c-43.32544 0-78.72-35.5584-78.72-78.87872v-118.08256h393.91744c21.66272 0 39.36256-17.69472 39.36256-39.35744V472.64256c0-21.66272-17.69984-39.36256-39.36256-39.36256H275.68128V157.59872c0-43.32032 35.39456-78.87872 78.72-78.87872zM145.12128 507.36128h23.99744l39.36256 67.2 40.32-67.2h23.04l-50.88256 83.51744 54.72256 92.16h-24.96l-43.20256-75.83744-43.19744 75.83744h-23.04l54.71744-92.16-50.87744-83.51744z m154.55744 0h32.64l49.92 143.03744h0.96256l48.95744-143.03744h33.60256v175.67744h-22.08256v-106.55744c0-10.88 0.32256-26.56256 0.96256-47.04256h-0.96256l-52.79744 153.6h-19.2l-52.80256-153.6h-0.95744c1.28 22.4 1.92 38.72256 1.92 48.96256v104.63744H299.6736V507.36128z m214.08256 0h22.07744v155.52h69.12v20.15744h-91.19744V507.36128z"
15
+ p-id="9479" fill={themeSvgIconColor}>
16
+ </path>
17
+ </svg>
18
+ )
19
+ );
20
+
21
+ XMLIcon.displayName = "XML";
22
+
23
+ export default XMLIcon;
@@ -0,0 +1,23 @@
1
+ import React from 'react';
2
+ import { LucideProps } from 'lucide-react';
3
+ import { themeSvgIconColor } from '@base-ui/lib/theme-util';
4
+
5
+ const YamlIcon = React.forwardRef<SVGSVGElement, LucideProps>(
6
+ ({ color = "currentColor", className, ...props }, ref) => (
7
+ <svg
8
+ ref={ref}
9
+ role="img"
10
+ className={className}
11
+ {...props}
12
+ viewBox="0 0 1024 1024" xmlns="http://www.w3.org/2000/svg">
13
+ <path
14
+ d="M354.401 0c-87.04 0-157.44 70.559-157.44 157.599V433.28H78.72c-21.658 0-39.363 17.7-39.363 39.363V708.96c0 21.658 17.7 39.358 39.363 39.358h118.241V866.4c0 87.04 70.4 157.599 157.44 157.599H827.04c87.04 0 157.598-70.559 157.598-157.599V315.034c0-41.749-38.988-81.93-107.52-149.28L848 136.633l-29.123-29.112C751.54 38.989 711.393 0 669.6 0H354.406z m0 78.72h287.202c28.354 7.091 27.996 42.138 27.996 76.8v120.161c0 21.658 17.7 39.358 39.362 39.358H827.04c39.388 0 78.878-0.026 78.878 39.362v512c0 43.32-35.553 78.879-78.878 78.879H354.406c-43.325 0-78.72-35.558-78.72-78.879V748.32h393.918c21.663 0 39.362-17.695 39.362-39.358V472.643c0-21.663-17.7-39.363-39.362-39.363H275.68V157.599c0-43.32 35.395-78.879 78.72-78.879z m-93.127 427.679h20.162l65.28 176.64h-23.04l-19.2-54.718h-65.28l-19.2 54.718h-23.04l64.318-176.64z m-181.438 0.962h23.998l40.32 89.278 41.282-89.278h23.998l-53.76 107.52v68.158h-22.078v-67.2L79.836 507.36z m290.878 0h32.64l49.92 143.038h0.962l48.958-143.038h33.602V683.04h-22.082V576.48c0-10.88 0.322-26.562 0.962-47.042h-0.962l-52.798 153.6h-19.2l-52.802-153.6h-0.958c1.28 22.4 1.92 38.722 1.92 48.962V683.04h-20.162V507.36z m214.082 0h22.078v155.52h69.12v20.158h-91.188V507.36z m-312.96 23.04c-1.92 8.96-4.802 18.238-8.642 27.838l-17.28 50.882h51.84l-18.238-50.882c-3.84-10.88-6.4-20.158-7.68-27.838z"
15
+ p-id="10866" fill={themeSvgIconColor}>
16
+ </path>
17
+ </svg>
18
+ )
19
+ );
20
+
21
+ YamlIcon.displayName = "Yaml";
22
+
23
+ export default YamlIcon;
@@ -0,0 +1,106 @@
1
+ "use client";
2
+
3
+ import { NotFoundIcon } from "@base-ui/components/global-icon";
4
+ import { SiteIcon } from "@base-ui/lib/site-icon";
5
+ import { useEffect, useState } from "react";
6
+
7
+ export function NotFoundPage() {
8
+ const [glitchText, setGlitchText] = useState("404");
9
+
10
+ // glitch effect
11
+ useEffect(() => {
12
+ const glitchChars = ["4", "0", "4", "?", "#", "!", "*", "&", "%", "$"];
13
+
14
+ const interval = setInterval(() => {
15
+ // 80% probability to display "404", 20% probability to display random characters
16
+ if (Math.random() < 0.5) {
17
+ setGlitchText("404");
18
+ } else {
19
+ const randomChars = Array.from(
20
+ { length: 3 },
21
+ () => glitchChars[Math.floor(Math.random() * glitchChars.length)]
22
+ ).join("");
23
+ setGlitchText(randomChars);
24
+ }
25
+ }, 600); // every 1.5 seconds
26
+
27
+ return () => clearInterval(interval);
28
+ }, []);
29
+
30
+ return (
31
+ <div className="flex flex-col items-center justify-center min-h-[75vh] w-full px-4 py-8">
32
+ {/* main content area */}
33
+ <div className="text-center space-y-8 max-w-2xl">
34
+ {/* 404 number - glitch effect */}
35
+ <div className="relative flex justify-center">
36
+ <h1
37
+ className="text-8xl md:text-9xl font-bold bg-gradient-to-r from-purple-600 via-pink-500 to-purple-700 bg-clip-text text-transparent select-none"
38
+ style={{
39
+ fontFamily: "Montserrat, monospace",
40
+ textShadow: "0 0 30px rgba(172, 98, 253, 0.3)",
41
+ letterSpacing: "0.1em",
42
+ }}
43
+ >
44
+ {glitchText}
45
+ </h1>
46
+ {/* scan line effect */}
47
+ <div className="absolute inset-0 pointer-events-none">
48
+ <div className="h-full w-full bg-gradient-to-b from-transparent via-purple-500/10 to-transparent animate-pulse" />
49
+ </div>
50
+ </div>
51
+
52
+ {/* error message */}
53
+ <div className="space-y-4">
54
+ <h2 className="text-2xl md:text-3xl font-semibold text-foreground">
55
+ Page Not Found
56
+ </h2>
57
+ <p className="text-lg text-muted-foreground max-w-md mx-auto leading-relaxed">
58
+ The page you&#39;re looking for doesn&#39;t exist
59
+ </p>
60
+ </div>
61
+
62
+ {/* decorative elements */}
63
+ <div className="flex justify-center items-center gap-8 pt-8 opacity-60">
64
+ <div className="flex items-center gap-2 text-sm text-muted-foreground">
65
+ <SiteIcon />
66
+ <span>Woops!</span>
67
+ </div>
68
+ <div className="w-1 h-1 bg-purple-500 rounded-full animate-ping" />
69
+ <div className="flex items-center gap-2 text-sm text-muted-foreground">
70
+ <NotFoundIcon />
71
+ <span>Error Code: 404</span>
72
+ </div>
73
+ </div>
74
+ </div>
75
+
76
+ {/* background decoration */}
77
+ <div className="fixed inset-0 pointer-events-none overflow-hidden -z-10">
78
+ {/* grid background */}
79
+ <div
80
+ className="absolute inset-0 opacity-[0.02] dark:opacity-[0.05]"
81
+ style={{
82
+ backgroundImage: `
83
+ linear-gradient(rgba(172, 98, 253, 0.1) 1px, transparent 1px),
84
+ linear-gradient(90deg, rgba(172, 98, 253, 0.1) 1px, transparent 1px)
85
+ `,
86
+ backgroundSize: "50px 50px",
87
+ }}
88
+ />
89
+
90
+ {/* floating particles */}
91
+ {Array.from({ length: 6 }).map((_, i) => (
92
+ <div
93
+ key={i}
94
+ className="absolute w-2 h-2 bg-purple-500/20 rounded-full animate-bounce"
95
+ style={{
96
+ left: `${20 + i * 15}%`,
97
+ top: `${30 + (i % 3) * 20}%`,
98
+ animationDelay: `${i * 0.5}s`,
99
+ animationDuration: `${2 + i * 0.3}s`,
100
+ }}
101
+ />
102
+ ))}
103
+ </div>
104
+ </div>
105
+ );
106
+ }
@@ -0,0 +1,193 @@
1
+ /*
2
+ * For the icon used in the project, unified management is required
3
+ * 1. Strictly control the number of icons introduced to reduce the project package size and use them as needed
4
+ * 2. Unify the style customization, and keep the icon style consistent within the project
5
+ * 3. Mainly support the introduction of icons in mdx files, and report errors in advance
6
+ */
7
+
8
+ import { BUILTIN_ICON_COMPONENTS } from '@base-ui/assets';
9
+ import { themeIconColor, themeSvgIconSize } from '@base-ui/lib/theme-util';
10
+
11
+ import * as limitedIconsModule from '@lib/limited-lucide-icons';
12
+ import { type LucideProps } from 'lucide-react';
13
+ import React from 'react';
14
+
15
+
16
+ // Type for styled Lucide icon components (accepts LucideProps)
17
+ type StyledLucideIconComponent = (props: LucideProps) => React.ReactElement;
18
+
19
+ // Union type for all icon components (both Lucide and built-in)
20
+ type IconComponent = StyledLucideIconComponent | React.ComponentType<LucideProps>;
21
+
22
+ // Style Lucide icons with global color
23
+ const tempStyledLimitedIcons: Partial<Record<keyof typeof limitedIconsModule, StyledLucideIconComponent>> = {};
24
+
25
+ for (const iconNameKey in limitedIconsModule) {
26
+ if (Object.prototype.hasOwnProperty.call(limitedIconsModule, iconNameKey)) {
27
+ const iconName = iconNameKey as keyof typeof limitedIconsModule;
28
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
29
+ const OriginalIconComponent = limitedIconsModule[iconName] as any;
30
+
31
+ if (typeof OriginalIconComponent === 'function' ||
32
+ (typeof OriginalIconComponent === 'object' &&
33
+ OriginalIconComponent !== null &&
34
+ OriginalIconComponent.$$typeof === Symbol.for('react.forward_ref'))) {
35
+ const ComponentToRender = OriginalIconComponent as React.ComponentType<LucideProps>;
36
+
37
+ const StyledIcon = (props: LucideProps): React.ReactElement => {
38
+ const originalClassName = props.className || '';
39
+ // Check if user provided a text color class, if so, don't use global color
40
+ const hasTextColor = /\btext-\w+(-\d+)?\b/.test(originalClassName);
41
+ // Check if user provided size/dimension classes
42
+ const hasSizeClass = /\b(size-\d+|w-\d+|h-\d+)\b/.test(originalClassName);
43
+
44
+ const newClassName = hasTextColor
45
+ ? originalClassName
46
+ : `${themeIconColor} ${originalClassName}`.trim();
47
+
48
+ // If user provided size classes in className, don't use default size
49
+ // Otherwise, use inline styles to ensure size precedence over external CSS
50
+ const finalProps = hasSizeClass
51
+ ? { ...props, className: newClassName, size: undefined }
52
+ : {
53
+ ...props,
54
+ className: newClassName,
55
+ style: {
56
+ width: props.size || themeSvgIconSize,
57
+ height: props.size || themeSvgIconSize,
58
+ ...props.style
59
+ }
60
+ };
61
+
62
+ return <ComponentToRender {...finalProps} />;
63
+ };
64
+ StyledIcon.displayName = `Styled(${iconName})`;
65
+ tempStyledLimitedIcons[iconName] = StyledIcon;
66
+ } else {
67
+ console.warn(`[global-icon.tsx] Skipped styling for "${iconName}" as it is not a function, undefined, or not a recognized React component type. Value:`, OriginalIconComponent);
68
+ }
69
+ }
70
+ }
71
+
72
+ const styledLimitedIconsPart = tempStyledLimitedIcons as {
73
+ [K in keyof typeof limitedIconsModule]: StyledLucideIconComponent;
74
+ };
75
+
76
+ // Wrap built-in SVG components with the same className handling logic
77
+ const tempWrappedBuiltinIcons: Partial<Record<keyof typeof BUILTIN_ICON_COMPONENTS, StyledLucideIconComponent>> = {};
78
+ for (const [iconName, IconComponent] of Object.entries(BUILTIN_ICON_COMPONENTS)) {
79
+ const WrappedIcon = (props: LucideProps): React.ReactElement => {
80
+ const originalClassName = props.className || '';
81
+ // Check if user provided a text color class, if so, don't use global color
82
+ const hasTextColor = /\btext-\w+(-\d+)?\b/.test(originalClassName);
83
+ // Check if user provided size/dimension classes
84
+ const hasSizeClass = /\b(size-\d+|w-\d+|h-\d+)\b/.test(originalClassName);
85
+
86
+ const newClassName = hasTextColor
87
+ ? originalClassName
88
+ : `${themeIconColor} ${originalClassName}`.trim();
89
+
90
+ // If user provided size classes in className, don't use default size
91
+ // Otherwise, use inline styles to ensure size precedence over external CSS
92
+ const finalProps = hasSizeClass
93
+ ? { ...props, className: newClassName, size: undefined }
94
+ : {
95
+ ...props,
96
+ className: newClassName,
97
+ style: {
98
+ width: props.size || themeSvgIconSize,
99
+ height: props.size || themeSvgIconSize,
100
+ ...props.style
101
+ }
102
+ };
103
+
104
+ return <IconComponent {...finalProps} />;
105
+ };
106
+ WrappedIcon.displayName = `Wrapped(${iconName})`;
107
+ tempWrappedBuiltinIcons[iconName as keyof typeof BUILTIN_ICON_COMPONENTS] = WrappedIcon;
108
+ }
109
+
110
+ const wrappedBuiltinIconsPart = tempWrappedBuiltinIcons as {
111
+ [K in keyof typeof BUILTIN_ICON_COMPONENTS]: StyledLucideIconComponent;
112
+ };
113
+
114
+ // All icons should be imported from here, and icons will occupy the project package size, so it is best to design and plan in advance
115
+ export const globalLucideIcons = {
116
+ ...styledLimitedIconsPart,
117
+ ...wrappedBuiltinIconsPart, // Spread all wrapped built-in icon components
118
+ };
119
+
120
+ // Default fallback icon - centralized configuration
121
+ // Use a safe fallback that we know exists in both Lucide and custom icons
122
+ const DEFAULT_FALLBACK_ICON = 'BTC' as keyof typeof globalLucideIcons;
123
+
124
+ /**
125
+ * use iconKey to load icon safely
126
+ * @param iconKey translation or configuration
127
+ * @param createElement whether to return a React element instead of component
128
+ */
129
+ export function getGlobalIcon(
130
+ iconKey: string | undefined
131
+ ): IconComponent;
132
+ export function getGlobalIcon(
133
+ iconKey: string | undefined,
134
+ createElement: true
135
+ ): React.ReactElement | undefined;
136
+ export function getGlobalIcon(
137
+ iconKey: string | undefined,
138
+ createElement?: boolean
139
+ ): IconComponent | React.ReactElement | undefined {
140
+ // Handle undefined iconKey case (for getIconElement compatibility)
141
+ if (!iconKey) {
142
+ if (createElement) {
143
+ return undefined;
144
+ }
145
+ return globalLucideIcons[DEFAULT_FALLBACK_ICON] as IconComponent;
146
+ }
147
+
148
+ const Icon = globalLucideIcons[iconKey as keyof typeof globalLucideIcons];
149
+ if (!Icon) {
150
+ if (process.env.NODE_ENV !== 'production') {
151
+ // only show in dev|test
152
+ // eslint-disable-next-line no-console
153
+ console.warn(
154
+ `[global-icon] iconKey "${iconKey}" is not defined in globalIcons, will use default "${String(DEFAULT_FALLBACK_ICON)}" icon, please check!`
155
+ );
156
+ }
157
+ const FallbackIcon = globalLucideIcons[DEFAULT_FALLBACK_ICON];
158
+ if (createElement) {
159
+ return React.createElement(FallbackIcon as React.ComponentType<any>);
160
+ }
161
+ return FallbackIcon as IconComponent;
162
+ }
163
+
164
+ if (createElement) {
165
+ return React.createElement(Icon as React.ComponentType<any>);
166
+ }
167
+ return Icon as IconComponent;
168
+ }
169
+
170
+ /**
171
+ * Get icon element (for fumadocs source compatibility)
172
+ * This is a wrapper around getGlobalIcon for backwards compatibility
173
+ * @param icon icon key from frontmatter
174
+ */
175
+ export function getIconElement(
176
+ icon: string | undefined,
177
+ ): React.ReactElement | undefined {
178
+ // Note: defaultIconKey parameter is kept for backwards compatibility but ignored
179
+ // The function now uses the centralized DEFAULT_FALLBACK_ICON
180
+ return getGlobalIcon(icon, true);
181
+ }
182
+
183
+ // Define the default site icon as a functional component (for export)
184
+ export const DefaultSiteIcon = () => (
185
+ <globalLucideIcons.Zap className={`h-8 w-8 rounded-full p-1 shadow-lg ring-0.5 border border-purple-500 ring-purple-500/20 ${themeIconColor}`} />
186
+ );
187
+
188
+ // Note: SiteIcon is available from @base-ui/lib/site-icon as a separate client component
189
+
190
+ // Define 404 not found icon as a functional component (fixed, no configuration)
191
+ export const NotFoundIcon = () => (
192
+ <globalLucideIcons.SquareTerminal className={`h-8 w-8 rounded-full p-1 shadow-lg ring-0.5 border border-purple-500 ring-purple-500/20 ${themeIconColor}`} />
193
+ );