@otmc/ui 0.1.2 → 0.1.3

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/dist/index.js CHANGED
@@ -100,8 +100,174 @@ function Footer({
100
100
  ] });
101
101
  }
102
102
 
103
+ // src/components/ThemeMenu.tsx
104
+ import {
105
+ ActionIcon as ActionIcon2,
106
+ Menu,
107
+ Tooltip as Tooltip2
108
+ } from "@mantine/core";
109
+ import { Sun, Moon, Monitor, Clock } from "lucide-react";
110
+
111
+ // src/contexts/ThemeProvider.tsx
112
+ import { createContext, useContext, useEffect, useState } from "react";
113
+ import {
114
+ useMantineColorScheme
115
+ } from "@mantine/core";
116
+ import { jsx as jsx2 } from "react/jsx-runtime";
117
+ var ThemeContext = createContext(null);
118
+ var useTheme = () => {
119
+ const ctx = useContext(ThemeContext);
120
+ if (!ctx) {
121
+ throw new Error("useTheme must be used inside ThemeProvider");
122
+ }
123
+ return ctx;
124
+ };
125
+ var resolveColorScheme = (colorScheme) => {
126
+ if (colorScheme === "auto") {
127
+ return window.matchMedia("(prefers-color-scheme: dark)").matches ? "dark" : "light";
128
+ }
129
+ return colorScheme;
130
+ };
131
+ var resolveTimeBasedTheme = (settings) => {
132
+ const now = /* @__PURE__ */ new Date();
133
+ const minutes = now.getHours() * 60 + now.getMinutes();
134
+ const [lh, lm] = settings.lightStartTime.split(":").map(Number);
135
+ const [dh, dm] = settings.darkStartTime.split(":").map(Number);
136
+ const light = lh * 60 + lm;
137
+ const dark = dh * 60 + dm;
138
+ return light < dark ? minutes >= light && minutes < dark ? "light" : "dark" : minutes >= light || minutes < dark ? "light" : "dark";
139
+ };
140
+ var resolveAutoScheme = () => window.matchMedia("(prefers-color-scheme: dark)").matches ? "dark" : "light";
141
+ var ThemeProvider = ({
142
+ children,
143
+ defaultTheme = "auto",
144
+ defaultTimeBasedSettings = {
145
+ lightStartTime: "07:00",
146
+ darkStartTime: "19:00"
147
+ },
148
+ storagePrefix = ""
149
+ }) => {
150
+ const themeStorageKey = `${storagePrefix}theme`;
151
+ const timeStorageKey = `${storagePrefix}time-theme`;
152
+ const { colorScheme, setColorScheme } = useMantineColorScheme();
153
+ const [theme, setThemeState] = useState(
154
+ () => localStorage.getItem(themeStorageKey) ?? defaultTheme
155
+ );
156
+ const [timeBasedSettings, setTimeBasedSettings] = useState(
157
+ () => JSON.parse(localStorage.getItem(timeStorageKey) || "null") ?? defaultTimeBasedSettings
158
+ );
159
+ const handleSetTimeBasedSettings = (settings) => {
160
+ setTimeBasedSettings(settings);
161
+ localStorage.setItem(timeStorageKey, JSON.stringify(settings));
162
+ if (theme === "time-based") {
163
+ applyTheme("time-based");
164
+ }
165
+ };
166
+ const applyTheme = (mode) => {
167
+ let scheme;
168
+ switch (mode) {
169
+ case "light":
170
+ case "dark":
171
+ case "auto":
172
+ scheme = mode;
173
+ break;
174
+ case "time-based":
175
+ scheme = resolveTimeBasedTheme(timeBasedSettings);
176
+ break;
177
+ default:
178
+ scheme = "auto";
179
+ }
180
+ setColorScheme(scheme);
181
+ };
182
+ useEffect(() => {
183
+ applyTheme(theme);
184
+ }, [theme, timeBasedSettings]);
185
+ const setTheme = (mode) => {
186
+ setThemeState(mode);
187
+ localStorage.setItem(themeStorageKey, mode);
188
+ applyTheme(mode);
189
+ };
190
+ const toggleTheme = () => {
191
+ setTheme(colorScheme === "dark" ? "light" : "dark");
192
+ };
193
+ const currentTheme = theme === "time-based" ? resolveTimeBasedTheme(timeBasedSettings) : colorScheme === "auto" ? resolveAutoScheme() : colorScheme;
194
+ return /* @__PURE__ */ jsx2(
195
+ ThemeContext.Provider,
196
+ {
197
+ value: {
198
+ theme,
199
+ currentTheme,
200
+ setTheme,
201
+ toggleTheme,
202
+ timeBasedSettings,
203
+ setTimeBasedSettings: handleSetTimeBasedSettings
204
+ },
205
+ children
206
+ }
207
+ );
208
+ };
209
+
210
+ // src/components/ThemeMenu.tsx
211
+ import { jsx as jsx3, jsxs as jsxs2 } from "react/jsx-runtime";
212
+ var DEFAULT_LABELS = {
213
+ tooltip: "Ch\u1EBF \u0111\u1ED9 giao di\u1EC7n",
214
+ title: "Ch\u1EBF \u0111\u1ED9 giao di\u1EC7n",
215
+ light: "S\xE1ng",
216
+ dark: "T\u1ED1i",
217
+ auto: "Theo h\u1EC7 th\u1ED1ng",
218
+ timeBased: "Theo th\u1EDDi gian"
219
+ };
220
+ var MODE_ICONS = {
221
+ light: /* @__PURE__ */ jsx3(Sun, { size: 16 }),
222
+ dark: /* @__PURE__ */ jsx3(Moon, { size: 16 }),
223
+ auto: /* @__PURE__ */ jsx3(Monitor, { size: 16 }),
224
+ "time-based": /* @__PURE__ */ jsx3(Clock, { size: 16 })
225
+ };
226
+ function ThemeMenu({
227
+ modes = ["light", "dark", "auto", "time-based"],
228
+ labels = {},
229
+ iconSize = 20,
230
+ size = "lg",
231
+ menuProps = {}
232
+ }) {
233
+ const { theme, currentTheme, setTheme } = useTheme();
234
+ const text = { ...DEFAULT_LABELS, ...labels };
235
+ const isDark = currentTheme === "dark";
236
+ const activeColor = isDark ? "yellow.8" : "blue.8";
237
+ const triggerIcon = theme === "light" ? /* @__PURE__ */ jsx3(Sun, { size: iconSize, strokeWidth: 2 }) : theme === "dark" ? /* @__PURE__ */ jsx3(Moon, { size: iconSize, strokeWidth: 2 }) : theme === "auto" ? /* @__PURE__ */ jsx3(Monitor, { size: iconSize, strokeWidth: 2 }) : /* @__PURE__ */ jsx3(Clock, { size: iconSize, strokeWidth: 2 });
238
+ return /* @__PURE__ */ jsxs2(Menu, { shadow: "md", width: 200, position: "bottom-end", ...menuProps, children: [
239
+ /* @__PURE__ */ jsx3(Menu.Target, { children: /* @__PURE__ */ jsx3(Tooltip2, { label: text.tooltip, position: "bottom", withArrow: true, children: /* @__PURE__ */ jsx3(
240
+ ActionIcon2,
241
+ {
242
+ variant: "subtle",
243
+ color: activeColor,
244
+ size,
245
+ radius: "lg",
246
+ style: {
247
+ boxShadow: isDark ? "0 0 15px rgba(250, 176, 5, 0.2)" : "0 0 15px rgba(34, 139, 230, 0.2)"
248
+ },
249
+ children: triggerIcon
250
+ }
251
+ ) }) }),
252
+ /* @__PURE__ */ jsxs2(Menu.Dropdown, { style: { borderRadius: "11px" }, children: [
253
+ /* @__PURE__ */ jsx3(Menu.Label, { children: text.title }),
254
+ modes.map((mode) => /* @__PURE__ */ jsx3(
255
+ Menu.Item,
256
+ {
257
+ leftSection: MODE_ICONS[mode],
258
+ onClick: () => setTheme(mode),
259
+ color: theme === mode ? activeColor : void 0,
260
+ fw: theme === mode ? 700 : 400,
261
+ children: text[mode === "time-based" ? "timeBased" : mode]
262
+ },
263
+ mode
264
+ ))
265
+ ] })
266
+ ] });
267
+ }
268
+
103
269
  // src/modals/Information.tsx
104
- import { useState } from "react";
270
+ import { useState as useState2 } from "react";
105
271
  import {
106
272
  Modal,
107
273
  Stack as Stack2,
@@ -113,8 +279,8 @@ import {
113
279
  ThemeIcon,
114
280
  SimpleGrid,
115
281
  Paper,
116
- ActionIcon as ActionIcon2,
117
- Tooltip as Tooltip2,
282
+ ActionIcon as ActionIcon3,
283
+ Tooltip as Tooltip3,
118
284
  useComputedColorScheme
119
285
  } from "@mantine/core";
120
286
  import {
@@ -268,10 +434,10 @@ function formatHumanDate(date, options) {
268
434
  }
269
435
 
270
436
  // src/modals/Information.tsx
271
- import { jsx as jsx2, jsxs as jsxs2 } from "react/jsx-runtime";
272
- var DEFAULT_TITLE = /* @__PURE__ */ jsxs2(Group2, { gap: "xs", wrap: "nowrap", children: [
273
- /* @__PURE__ */ jsx2(IconCpu, { size: 20 }),
274
- /* @__PURE__ */ jsx2("span", { children: "System Information" })
437
+ import { jsx as jsx4, jsxs as jsxs3 } from "react/jsx-runtime";
438
+ var DEFAULT_TITLE = /* @__PURE__ */ jsxs3(Group2, { gap: "xs", wrap: "nowrap", children: [
439
+ /* @__PURE__ */ jsx4(IconCpu, { size: 20 }),
440
+ /* @__PURE__ */ jsx4("span", { children: "System Information" })
275
441
  ] });
276
442
  function InformationContent({ info }) {
277
443
  const colorScheme = useComputedColorScheme();
@@ -279,46 +445,46 @@ function InformationContent({ info }) {
279
445
  const versionType = info.versionType ?? DEFAULT_VERSION_TYPE;
280
446
  const cards = [
281
447
  {
282
- icon: /* @__PURE__ */ jsx2(IconUser, { size: 18 }),
448
+ icon: /* @__PURE__ */ jsx4(IconUser, { size: 18 }),
283
449
  label: "Author",
284
450
  value: author,
285
451
  color: "blue"
286
452
  },
287
453
  {
288
- icon: /* @__PURE__ */ jsx2(IconLicense, { size: 18 }),
454
+ icon: /* @__PURE__ */ jsx4(IconLicense, { size: 18 }),
289
455
  label: "License",
290
456
  value: info.license ?? DEFAULT_LICENSE,
291
457
  color: "orange"
292
458
  },
293
459
  {
294
- icon: /* @__PURE__ */ jsx2(IconMapPin, { size: 18 }),
460
+ icon: /* @__PURE__ */ jsx4(IconMapPin, { size: 18 }),
295
461
  label: "Location",
296
462
  value: info.location ?? DEFAULT_LOCATION,
297
463
  color: "teal"
298
464
  },
299
465
  {
300
- icon: /* @__PURE__ */ jsx2(IconTag, { size: 18 }),
466
+ icon: /* @__PURE__ */ jsx4(IconTag, { size: 18 }),
301
467
  label: "Version Type",
302
468
  value: versionType,
303
469
  color: "red"
304
470
  },
305
471
  {
306
- icon: /* @__PURE__ */ jsx2(IconCalendar, { size: 18 }),
472
+ icon: /* @__PURE__ */ jsx4(IconCalendar, { size: 18 }),
307
473
  label: "Build Time",
308
474
  value: info.buildTime !== void 0 ? formatAbsoluteAndRelativeTime(info.buildTime) : UNKNOWN,
309
475
  color: "green"
310
476
  },
311
477
  ...info.metadata ?? []
312
478
  ];
313
- return /* @__PURE__ */ jsxs2(Stack2, { gap: "lg", children: [
314
- /* @__PURE__ */ jsxs2(Stack2, { gap: "xs", align: "center", children: [
479
+ return /* @__PURE__ */ jsxs3(Stack2, { gap: "lg", children: [
480
+ /* @__PURE__ */ jsxs3(Stack2, { gap: "xs", align: "center", children: [
315
481
  info.logo,
316
- /* @__PURE__ */ jsxs2(Stack2, { gap: 2, align: "center", children: [
317
- /* @__PURE__ */ jsx2(Title, { order: 2, children: info.name }),
318
- info.tagline && /* @__PURE__ */ jsx2(Text2, { size: "sm", c: "dimmed", w: 600, ta: "center", children: info.tagline })
482
+ /* @__PURE__ */ jsxs3(Stack2, { gap: 2, align: "center", children: [
483
+ /* @__PURE__ */ jsx4(Title, { order: 2, children: info.name }),
484
+ info.tagline && /* @__PURE__ */ jsx4(Text2, { size: "sm", c: "dimmed", w: 600, ta: "center", children: info.tagline })
319
485
  ] }),
320
- /* @__PURE__ */ jsxs2(Group2, { gap: "xs", children: [
321
- info.version && /* @__PURE__ */ jsxs2(
486
+ /* @__PURE__ */ jsxs3(Group2, { gap: "xs", children: [
487
+ info.version && /* @__PURE__ */ jsxs3(
322
488
  Badge,
323
489
  {
324
490
  size: "lg",
@@ -333,7 +499,7 @@ function InformationContent({ info }) {
333
499
  ]
334
500
  }
335
501
  ),
336
- /* @__PURE__ */ jsxs2(
502
+ /* @__PURE__ */ jsxs3(
337
503
  Badge,
338
504
  {
339
505
  size: "lg",
@@ -350,39 +516,39 @@ function InformationContent({ info }) {
350
516
  )
351
517
  ] })
352
518
  ] }),
353
- /* @__PURE__ */ jsx2(Divider, { label: "System Information", labelPosition: "center" }),
354
- /* @__PURE__ */ jsxs2(SimpleGrid, { cols: { base: 1, sm: 2 }, children: [
355
- cards.map((card) => /* @__PURE__ */ jsx2(
519
+ /* @__PURE__ */ jsx4(Divider, { label: "System Information", labelPosition: "center" }),
520
+ /* @__PURE__ */ jsxs3(SimpleGrid, { cols: { base: 1, sm: 2 }, children: [
521
+ cards.map((card) => /* @__PURE__ */ jsx4(
356
522
  InfoCard,
357
523
  {
358
- icon: card.icon ?? /* @__PURE__ */ jsx2(IconAward, { size: 18 }),
524
+ icon: card.icon ?? /* @__PURE__ */ jsx4(IconAward, { size: 18 }),
359
525
  label: card.label,
360
526
  value: card.value,
361
527
  color: card.color ?? "gray"
362
528
  },
363
529
  card.label
364
530
  )),
365
- /* @__PURE__ */ jsx2(
531
+ /* @__PURE__ */ jsx4(
366
532
  Paper,
367
533
  {
368
534
  withBorder: true,
369
535
  p: "sm",
370
536
  radius: "18px",
371
537
  bg: colorScheme === "dark" ? "gray.9" : "gray.0",
372
- children: /* @__PURE__ */ jsxs2(Group2, { justify: "space-between", wrap: "nowrap", children: [
373
- /* @__PURE__ */ jsxs2(Group2, { gap: "sm", flex: 1, children: [
374
- /* @__PURE__ */ jsx2(ThemeIcon, { variant: "light", color: "yellow", size: "lg", radius: "14px", children: /* @__PURE__ */ jsx2(IconHash, { size: 18 }) }),
375
- /* @__PURE__ */ jsxs2(Stack2, { gap: 2, children: [
376
- /* @__PURE__ */ jsx2(Text2, { size: "xs", c: "dimmed", fw: 700, tt: "uppercase", children: "Build ID" }),
377
- /* @__PURE__ */ jsx2(Text2, { size: "sm", fw: 500, truncate: true, children: info.buildId ?? UNKNOWN })
538
+ children: /* @__PURE__ */ jsxs3(Group2, { justify: "space-between", wrap: "nowrap", children: [
539
+ /* @__PURE__ */ jsxs3(Group2, { gap: "sm", flex: 1, children: [
540
+ /* @__PURE__ */ jsx4(ThemeIcon, { variant: "light", color: "yellow", size: "lg", radius: "14px", children: /* @__PURE__ */ jsx4(IconHash, { size: 18 }) }),
541
+ /* @__PURE__ */ jsxs3(Stack2, { gap: 2, children: [
542
+ /* @__PURE__ */ jsx4(Text2, { size: "xs", c: "dimmed", fw: 700, tt: "uppercase", children: "Build ID" }),
543
+ /* @__PURE__ */ jsx4(Text2, { size: "sm", fw: 500, truncate: true, children: info.buildId ?? UNKNOWN })
378
544
  ] })
379
545
  ] }),
380
- info.buildId && /* @__PURE__ */ jsx2(CopyBuildIdButton, { buildId: info.buildId })
546
+ info.buildId && /* @__PURE__ */ jsx4(CopyBuildIdButton, { buildId: info.buildId })
381
547
  ] })
382
548
  }
383
549
  )
384
550
  ] }),
385
- /* @__PURE__ */ jsx2(
551
+ /* @__PURE__ */ jsx4(
386
552
  Footer,
387
553
  {
388
554
  copyright: info.copyright,
@@ -399,7 +565,7 @@ function InformationModal({
399
565
  info,
400
566
  title = DEFAULT_TITLE
401
567
  }) {
402
- return /* @__PURE__ */ jsx2(
568
+ return /* @__PURE__ */ jsx4(
403
569
  Modal,
404
570
  {
405
571
  opened,
@@ -419,12 +585,12 @@ function InformationModal({
419
585
  }
420
586
  },
421
587
  title,
422
- children: /* @__PURE__ */ jsx2(InformationContent, { info })
588
+ children: /* @__PURE__ */ jsx4(InformationContent, { info })
423
589
  }
424
590
  );
425
591
  }
426
592
  function CopyBuildIdButton({ buildId }) {
427
- const [copied, setCopied] = useState(false);
593
+ const [copied, setCopied] = useState2(false);
428
594
  const handleCopy = async () => {
429
595
  const success = await copyToClipboard(buildId);
430
596
  if (success) {
@@ -432,13 +598,13 @@ function CopyBuildIdButton({ buildId }) {
432
598
  setTimeout(() => setCopied(false), 2e3);
433
599
  }
434
600
  };
435
- return /* @__PURE__ */ jsx2(Tooltip2, { label: copied ? "Copied!" : "Copy ID", withArrow: true, children: /* @__PURE__ */ jsx2(
436
- ActionIcon2,
601
+ return /* @__PURE__ */ jsx4(Tooltip3, { label: copied ? "Copied!" : "Copy ID", withArrow: true, children: /* @__PURE__ */ jsx4(
602
+ ActionIcon3,
437
603
  {
438
604
  variant: "subtle",
439
605
  color: copied ? "teal" : "gray",
440
606
  onClick: handleCopy,
441
- children: copied ? /* @__PURE__ */ jsx2(IconCheck, { size: 16 }) : /* @__PURE__ */ jsx2(IconCopy, { size: 16 })
607
+ children: copied ? /* @__PURE__ */ jsx4(IconCheck, { size: 16 }) : /* @__PURE__ */ jsx4(IconCopy, { size: 16 })
442
608
  }
443
609
  ) });
444
610
  }
@@ -449,14 +615,115 @@ function InfoCard({
449
615
  color
450
616
  }) {
451
617
  const colorScheme = useComputedColorScheme();
452
- return /* @__PURE__ */ jsx2(Paper, { withBorder: true, p: "md", radius: "18px", h: "100%", bg: colorScheme === "dark" ? "gray.9" : "gray.0", children: /* @__PURE__ */ jsxs2(Group2, { gap: "sm", align: "flex-start", children: [
453
- /* @__PURE__ */ jsx2(ThemeIcon, { color, variant: "light", size: "lg", radius: "14px", children: icon }),
454
- /* @__PURE__ */ jsxs2(Stack2, { gap: 2, flex: 1, children: [
455
- /* @__PURE__ */ jsx2(Text2, { size: "xs", c: "dimmed", fw: 700, tt: "uppercase", children: label }),
456
- /* @__PURE__ */ jsx2(Text2, { size: "sm", fw: 500, lineClamp: 1, children: value })
618
+ return /* @__PURE__ */ jsx4(Paper, { withBorder: true, p: "md", radius: "18px", h: "100%", bg: colorScheme === "dark" ? "gray.9" : "gray.0", children: /* @__PURE__ */ jsxs3(Group2, { gap: "sm", align: "flex-start", children: [
619
+ /* @__PURE__ */ jsx4(ThemeIcon, { color, variant: "light", size: "lg", radius: "14px", children: icon }),
620
+ /* @__PURE__ */ jsxs3(Stack2, { gap: 2, flex: 1, children: [
621
+ /* @__PURE__ */ jsx4(Text2, { size: "xs", c: "dimmed", fw: 700, tt: "uppercase", children: label }),
622
+ /* @__PURE__ */ jsx4(Text2, { size: "sm", fw: 500, lineClamp: 1, children: value })
457
623
  ] })
458
624
  ] }) });
459
625
  }
626
+
627
+ // src/pages/NotFound.tsx
628
+ import {
629
+ Box,
630
+ Button,
631
+ Container,
632
+ Group as Group3,
633
+ Paper as Paper2,
634
+ Text as Text3,
635
+ Title as Title2,
636
+ Code,
637
+ Badge as Badge2
638
+ } from "@mantine/core";
639
+ import {
640
+ IconArrowLeft,
641
+ IconHome,
642
+ IconSearch,
643
+ IconFileOff
644
+ } from "@tabler/icons-react";
645
+ import { jsx as jsx5, jsxs as jsxs4 } from "react/jsx-runtime";
646
+ function NotFound({
647
+ path,
648
+ onSearchClick,
649
+ onHomeClick
650
+ }) {
651
+ const currentPath = path || (typeof window !== "undefined" ? window.location.pathname : "/404");
652
+ return /* @__PURE__ */ jsx5(
653
+ Box,
654
+ {
655
+ style: {
656
+ minHeight: "100vh",
657
+ display: "flex",
658
+ alignItems: "center",
659
+ background: "radial-gradient(circle at top left, rgba(34, 139, 230, 0.15), transparent 45%), radial-gradient(circle at bottom right, rgba(34, 211, 238, 0.12), transparent 45%), var(--mantine-color-body)"
660
+ },
661
+ children: /* @__PURE__ */ jsx5(Container, { size: "xl", py: 80, children: /* @__PURE__ */ jsxs4(Paper2, { radius: "xl", p: 48, withBorder: true, style: { borderColor: "var(--mantine-color-default-border)", textAlign: "center" }, children: [
662
+ /* @__PURE__ */ jsx5(
663
+ Box,
664
+ {
665
+ mx: "auto",
666
+ mb: "xl",
667
+ w: 96,
668
+ h: 96,
669
+ style: {
670
+ borderRadius: "50%",
671
+ display: "flex",
672
+ alignItems: "center",
673
+ justifyContent: "center",
674
+ background: "linear-gradient(135deg, var(--mantine-color-blue-6), var(--mantine-color-cyan-6))",
675
+ boxShadow: "0 12px 32px rgba(34, 139, 230, 0.35)"
676
+ },
677
+ children: /* @__PURE__ */ jsx5(IconFileOff, { size: 44, stroke: 1.5, color: "white" })
678
+ }
679
+ ),
680
+ /* @__PURE__ */ jsx5(
681
+ Text3,
682
+ {
683
+ fz: { base: 72, sm: 100 },
684
+ fw: 900,
685
+ lh: 1,
686
+ variant: "gradient",
687
+ gradient: { from: "blue.7", to: "cyan.5", deg: 45 },
688
+ children: "404"
689
+ }
690
+ ),
691
+ /* @__PURE__ */ jsx5(Badge2, { variant: "light", color: "blue", size: "lg", mb: "xs", children: "NOT FOUND" }),
692
+ /* @__PURE__ */ jsx5(Title2, { order: 2, mt: "sm", mb: "xs", children: "Trang kh\xF4ng t\u1ED3n t\u1EA1i" }),
693
+ /* @__PURE__ */ jsx5(Text3, { c: "dimmed", size: "sm", maw: 440, mx: "auto", children: "Trang ho\u1EB7c \u0111\u01B0\u1EDDng d\u1EABn b\u1EA1n truy c\u1EADp kh\xF4ng t\u1ED3n t\u1EA1i ho\u1EB7c \u0111\xE3 \u0111\u01B0\u1EE3c di chuy\u1EC3n. Vui l\xF2ng ki\u1EC3m tra l\u1EA1i \u0111\u01B0\u1EDDng d\u1EABn ho\u1EB7c quay v\u1EC1 trang ch\u1EE7." }),
694
+ /* @__PURE__ */ jsx5(Box, { mt: "lg", children: /* @__PURE__ */ jsx5(Code, { color: "blue", variant: "light", px: "md", py: 6, children: currentPath }) }),
695
+ /* @__PURE__ */ jsxs4(Group3, { gap: "sm", mt: "xl", justify: "center", children: [
696
+ /* @__PURE__ */ jsx5(
697
+ Button,
698
+ {
699
+ variant: "light",
700
+ leftSection: /* @__PURE__ */ jsx5(IconArrowLeft, { size: 16 }),
701
+ onClick: () => window.history.back(),
702
+ children: "Quay l\u1EA1i"
703
+ }
704
+ ),
705
+ onSearchClick && /* @__PURE__ */ jsx5(
706
+ Button,
707
+ {
708
+ variant: "outline",
709
+ leftSection: /* @__PURE__ */ jsx5(IconSearch, { size: 16 }),
710
+ onClick: onSearchClick,
711
+ children: "T\xECm Docs"
712
+ }
713
+ ),
714
+ /* @__PURE__ */ jsx5(
715
+ Button,
716
+ {
717
+ leftSection: /* @__PURE__ */ jsx5(IconHome, { size: 16 }),
718
+ onClick: onHomeClick || (() => window.location.href = "/"),
719
+ children: "Trang ch\u1EE7"
720
+ }
721
+ )
722
+ ] })
723
+ ] }) })
724
+ }
725
+ );
726
+ }
460
727
  export {
461
728
  DEFAULT_AUTHOR,
462
729
  DEFAULT_AUTHOR_HREF,
@@ -467,6 +734,9 @@ export {
467
734
  Footer,
468
735
  InformationContent,
469
736
  InformationModal,
737
+ NotFound,
738
+ ThemeMenu,
739
+ ThemeProvider,
470
740
  UNKNOWN,
471
741
  calculateRemainingTime,
472
742
  copyToClipboard,
@@ -475,6 +745,8 @@ export {
475
745
  formatHumanDate,
476
746
  formatRelativeTime,
477
747
  normalizeDate,
478
- pad
748
+ pad,
749
+ resolveColorScheme,
750
+ useTheme
479
751
  };
480
752
  //# sourceMappingURL=index.js.map