@tooee/themes 0.1.19 → 0.1.21

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.
@@ -0,0 +1,17 @@
1
+ interface CloseButtonProps {
2
+ /** Called when the button is clicked (left mouse button). */
3
+ onClose: () => void;
4
+ /** Glyph to render (default "✕"). */
5
+ glyph?: string;
6
+ /** Foreground colour (defaults to theme.textMuted). */
7
+ color?: string;
8
+ }
9
+ /**
10
+ * Reusable clickable close control for overlays.
11
+ *
12
+ * Renders a small themed glyph that calls `onClose` on left-click. Purely
13
+ * additive — overlays keep their existing Escape / cancel keyboard paths.
14
+ */
15
+ export declare function CloseButton({ onClose, glyph, color }: CloseButtonProps): import("react").ReactNode;
16
+ export {};
17
+ //# sourceMappingURL=CloseButton.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"CloseButton.d.ts","sourceRoot":"","sources":["../src/CloseButton.tsx"],"names":[],"mappings":"AAIA,UAAU,gBAAgB;IACxB,6DAA6D;IAC7D,OAAO,EAAE,MAAM,IAAI,CAAA;IACnB,qCAAqC;IACrC,KAAK,CAAC,EAAE,MAAM,CAAA;IACd,uDAAuD;IACvD,KAAK,CAAC,EAAE,MAAM,CAAA;CACf;AAED;;;;;GAKG;AACH,wBAAgB,WAAW,CAAC,EAAE,OAAO,EAAE,KAAW,EAAE,KAAK,EAAE,EAAE,gBAAgB,6BAmB5E"}
@@ -0,0 +1,22 @@
1
+ import { jsx as _jsx } from "@opentui/react/jsx-runtime";
2
+ import { useCallback } from "react";
3
+ import { useTheme } from "./context.js";
4
+ /**
5
+ * Reusable clickable close control for overlays.
6
+ *
7
+ * Renders a small themed glyph that calls `onClose` on left-click. Purely
8
+ * additive — overlays keep their existing Escape / cancel keyboard paths.
9
+ */
10
+ export function CloseButton({ onClose, glyph = "✕", color }) {
11
+ const { theme } = useTheme();
12
+ const handleMouseDown = useCallback((event) => {
13
+ // Left button only; let other buttons bubble.
14
+ if (event.button !== 0)
15
+ return;
16
+ event.preventDefault();
17
+ event.stopPropagation();
18
+ onClose();
19
+ }, [onClose]);
20
+ return (_jsx("box", { flexShrink: 0, paddingLeft: 1, onMouseDown: handleMouseDown, children: _jsx("text", { content: glyph, fg: color ?? theme.textMuted }) }));
21
+ }
22
+ //# sourceMappingURL=CloseButton.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"CloseButton.js","sourceRoot":"","sources":["../src/CloseButton.tsx"],"names":[],"mappings":";AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,OAAO,CAAA;AAEnC,OAAO,EAAE,QAAQ,EAAE,MAAM,cAAc,CAAA;AAWvC;;;;;GAKG;AACH,MAAM,UAAU,WAAW,CAAC,EAAE,OAAO,EAAE,KAAK,GAAG,GAAG,EAAE,KAAK,EAAoB;IAC3E,MAAM,EAAE,KAAK,EAAE,GAAG,QAAQ,EAAE,CAAA;IAE5B,MAAM,eAAe,GAAG,WAAW,CACjC,CAAC,KAAiB,EAAE,EAAE;QACpB,8CAA8C;QAC9C,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC;YAAE,OAAM;QAC9B,KAAK,CAAC,cAAc,EAAE,CAAA;QACtB,KAAK,CAAC,eAAe,EAAE,CAAA;QACvB,OAAO,EAAE,CAAA;IACX,CAAC,EACD,CAAC,OAAO,CAAC,CACV,CAAA;IAED,OAAO,CACL,cAAK,UAAU,EAAE,CAAC,EAAE,WAAW,EAAE,CAAC,EAAE,WAAW,EAAE,eAAe,YAC9D,eAAM,OAAO,EAAE,KAAK,EAAE,EAAE,EAAE,KAAK,IAAI,KAAK,CAAC,SAAS,GAAI,GAClD,CACP,CAAA;AACH,CAAC"}
@@ -1 +1 @@
1
- {"version":3,"file":"ThemePicker.d.ts","sourceRoot":"","sources":["../src/ThemePicker.tsx"],"names":[],"mappings":"AAKA,MAAM,WAAW,gBAAgB;IAC/B,EAAE,EAAE,MAAM,CAAA;IACV,KAAK,EAAE,MAAM,CAAA;CACd;AAED,UAAU,gBAAgB;IACxB,OAAO,EAAE,gBAAgB,EAAE,CAAA;IAC3B,YAAY,EAAE,MAAM,CAAA;IACpB,QAAQ,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAA;IAChC,OAAO,EAAE,MAAM,IAAI,CAAA;IACnB,UAAU,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAA;CACnC;AAED,wBAAgB,WAAW,CAAC,EAC1B,OAAO,EACP,YAAY,EACZ,QAAQ,EACR,OAAO,EACP,UAAU,GACX,EAAE,gBAAgB,6BAqHlB"}
1
+ {"version":3,"file":"ThemePicker.d.ts","sourceRoot":"","sources":["../src/ThemePicker.tsx"],"names":[],"mappings":"AAMA,MAAM,WAAW,gBAAgB;IAC/B,EAAE,EAAE,MAAM,CAAA;IACV,KAAK,EAAE,MAAM,CAAA;CACd;AAED,UAAU,gBAAgB;IACxB,OAAO,EAAE,gBAAgB,EAAE,CAAA;IAC3B,YAAY,EAAE,MAAM,CAAA;IACpB,QAAQ,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAA;IAChC,OAAO,EAAE,MAAM,IAAI,CAAA;IACnB,UAAU,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAA;CACnC;AAED,wBAAgB,WAAW,CAAC,EAC1B,OAAO,EACP,YAAY,EACZ,QAAQ,EACR,OAAO,EACP,UAAU,GACX,EAAE,gBAAgB,6BAuJlB"}
@@ -1,8 +1,9 @@
1
1
  import { jsx as _jsx, jsxs as _jsxs } from "@opentui/react/jsx-runtime";
2
2
  import { useState, useMemo, useCallback } from "react";
3
- import { useKeyboard } from "@opentui/react";
3
+ import { useCommand } from "@tooee/commands";
4
4
  import { fuzzyMatch } from "@tooee/fuzzy";
5
5
  import { useTheme } from "./context.js";
6
+ import { CloseButton } from "./CloseButton.js";
6
7
  export function ThemePicker({ entries, currentTheme, onSelect, onClose, onNavigate, }) {
7
8
  const { theme } = useTheme();
8
9
  const [filter, setFilter] = useState("");
@@ -35,25 +36,45 @@ export function ThemePicker({ entries, currentTheme, onSelect, onClose, onNaviga
35
36
  onNavigate(item.id);
36
37
  }
37
38
  }, [filtered, onNavigate]);
38
- useKeyboard((key) => {
39
- if (key.name === "escape") {
40
- key.preventDefault();
41
- onClose();
42
- }
43
- else if (key.name === "return") {
44
- key.preventDefault();
45
- handleSelect();
46
- }
47
- else if (key.name === "up") {
48
- key.preventDefault();
49
- navigateTo(Math.max(0, activeIndex - 1));
50
- }
51
- else if (key.name === "down") {
52
- key.preventDefault();
53
- navigateTo(Math.min(filtered.length - 1, activeIndex + 1));
54
- }
39
+ const moveUp = useCallback(() => {
40
+ navigateTo(Math.max(0, activeIndex - 1));
41
+ }, [activeIndex, navigateTo]);
42
+ const moveDown = useCallback(() => {
43
+ navigateTo(Math.min(filtered.length - 1, activeIndex + 1));
44
+ }, [activeIndex, filtered.length, navigateTo]);
45
+ useCommand({
46
+ id: "theme-picker:close",
47
+ title: "Close theme picker",
48
+ hotkey: "Escape",
49
+ modes: ["insert", "cursor"],
50
+ hidden: true,
51
+ handler: onClose,
52
+ });
53
+ useCommand({
54
+ id: "theme-picker:select",
55
+ title: "Select theme",
56
+ hotkey: "Enter",
57
+ modes: ["insert", "cursor"],
58
+ hidden: true,
59
+ handler: handleSelect,
60
+ });
61
+ useCommand({
62
+ id: "theme-picker:move-up",
63
+ title: "Move up",
64
+ hotkey: "up",
65
+ modes: ["insert", "cursor"],
66
+ hidden: true,
67
+ handler: moveUp,
68
+ });
69
+ useCommand({
70
+ id: "theme-picker:move-down",
71
+ title: "Move down",
72
+ hotkey: "down",
73
+ modes: ["insert", "cursor"],
74
+ hidden: true,
75
+ handler: moveDown,
55
76
  });
56
- return (_jsxs("box", { position: "absolute", left: "20%", right: "20%", top: 2, maxHeight: "60%", flexDirection: "column", backgroundColor: theme.backgroundPanel, border: true, borderColor: theme.border, children: [_jsxs("box", { flexDirection: "row", paddingLeft: 1, paddingRight: 1, height: 1, children: [_jsx("text", { content: "\uD83C\uDFA8 ", fg: theme.accent }), _jsx("input", { focused: true, placeholder: "Filter themes...", onInput: (value) => {
77
+ return (_jsxs("box", { position: "absolute", left: "20%", right: "20%", top: 2, maxHeight: "60%", flexDirection: "column", backgroundColor: theme.backgroundPanel, border: true, borderColor: theme.border, children: [_jsxs("box", { flexDirection: "row", paddingLeft: 1, paddingRight: 1, height: 1, children: [_jsx("text", { content: "\uD83C\uDFA8 ", fg: theme.accent }), _jsx("input", { focused: true, placeholder: "Filter themes...", onSubmit: handleSelect, onInput: (value) => {
57
78
  setFilter(value);
58
79
  setActiveIndex(0);
59
80
  // Preview first match
@@ -72,6 +93,13 @@ export function ThemePicker({ entries, currentTheme, onSelect, onClose, onNaviga
72
93
  if (results.length > 0)
73
94
  onNavigate(results[0].entry.id);
74
95
  }
75
- }, backgroundColor: "transparent", focusedBackgroundColor: "transparent", textColor: theme.text, placeholderColor: theme.textMuted, cursorColor: theme.accent, style: { flexGrow: 1 } }), _jsx("text", { content: ` ${filtered.length}`, fg: theme.textMuted })] }), _jsx("box", { height: 1, width: "100%", backgroundColor: theme.border }), _jsx("scrollbox", { focused: false, style: { flexGrow: 1 }, children: filtered.map((entry, i) => (_jsx("box", { flexDirection: "row", paddingLeft: 1, paddingRight: 1, height: 1, backgroundColor: i === activeIndex ? theme.backgroundElement : undefined, children: _jsx("text", { content: entry.title, fg: theme.text, style: { flexGrow: 1 } }) }, entry.id))) })] }));
96
+ }, backgroundColor: "transparent", focusedBackgroundColor: "transparent", textColor: theme.text, placeholderColor: theme.textMuted, cursorColor: theme.accent, style: { flexGrow: 1 } }), _jsx("text", { content: ` ${filtered.length}`, fg: theme.textMuted }), _jsx(CloseButton, { onClose: onClose })] }), _jsx("box", { height: 1, width: "100%", backgroundColor: theme.border }), _jsx("scrollbox", { focused: false, style: { flexGrow: 1 }, children: filtered.map((entry, i) => (_jsx("box", { flexDirection: "row", paddingLeft: 1, paddingRight: 1, height: 1, backgroundColor: i === activeIndex ? theme.backgroundElement : undefined, onMouseDown: (event) => {
97
+ // Left-click applies the theme — same code path as Enter.
98
+ if (event.button !== 0)
99
+ return;
100
+ event.preventDefault();
101
+ event.stopPropagation();
102
+ onSelect(entry.id);
103
+ }, children: _jsx("text", { content: entry.title, fg: theme.text, style: { flexGrow: 1 } }) }, entry.id))) })] }));
76
104
  }
77
105
  //# sourceMappingURL=ThemePicker.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"ThemePicker.js","sourceRoot":"","sources":["../src/ThemePicker.tsx"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"ThemePicker.js","sourceRoot":"","sources":["../src/ThemePicker.tsx"],"names":[],"mappings":"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"}
package/dist/index.d.ts CHANGED
@@ -7,4 +7,5 @@ export { ThemeProvider, ThemeSwitcherProvider, useTheme, useThemeSwitcher } from
7
7
  export type { ThemeProviderProps, ThemeSwitcherProviderProps } from "./context.js";
8
8
  export { ThemePicker } from "./ThemePicker.js";
9
9
  export type { ThemePickerEntry } from "./ThemePicker.js";
10
+ export { CloseButton } from "./CloseButton.js";
10
11
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,YAAY,CAAA;AACzC,YAAY,EAAE,SAAS,EAAE,aAAa,EAAE,MAAM,YAAY,CAAA;AAE1D,OAAO,EAAE,gBAAgB,EAAE,MAAM,mBAAmB,CAAA;AAEpD,OAAO,EAAE,UAAU,EAAE,aAAa,EAAE,YAAY,EAAE,MAAM,aAAa,CAAA;AACrE,YAAY,EAAE,KAAK,EAAE,MAAM,aAAa,CAAA;AAExC,OAAO,EAAE,aAAa,EAAE,qBAAqB,EAAE,QAAQ,EAAE,gBAAgB,EAAE,MAAM,cAAc,CAAA;AAC/F,YAAY,EAAE,kBAAkB,EAAE,0BAA0B,EAAE,MAAM,cAAc,CAAA;AAElF,OAAO,EAAE,WAAW,EAAE,MAAM,kBAAkB,CAAA;AAC9C,YAAY,EAAE,gBAAgB,EAAE,MAAM,kBAAkB,CAAA"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,YAAY,CAAA;AACzC,YAAY,EAAE,SAAS,EAAE,aAAa,EAAE,MAAM,YAAY,CAAA;AAE1D,OAAO,EAAE,gBAAgB,EAAE,MAAM,mBAAmB,CAAA;AAEpD,OAAO,EAAE,UAAU,EAAE,aAAa,EAAE,YAAY,EAAE,MAAM,aAAa,CAAA;AACrE,YAAY,EAAE,KAAK,EAAE,MAAM,aAAa,CAAA;AAExC,OAAO,EAAE,aAAa,EAAE,qBAAqB,EAAE,QAAQ,EAAE,gBAAgB,EAAE,MAAM,cAAc,CAAA;AAC/F,YAAY,EAAE,kBAAkB,EAAE,0BAA0B,EAAE,MAAM,cAAc,CAAA;AAElF,OAAO,EAAE,WAAW,EAAE,MAAM,kBAAkB,CAAA;AAC9C,YAAY,EAAE,gBAAgB,EAAE,MAAM,kBAAkB,CAAA;AAExD,OAAO,EAAE,WAAW,EAAE,MAAM,kBAAkB,CAAA"}
package/dist/index.js CHANGED
@@ -3,4 +3,5 @@ export { buildSyntaxStyle } from "./syntax-rules.js";
3
3
  export { loadThemes, getThemeNames, defaultTheme } from "./loader.js";
4
4
  export { ThemeProvider, ThemeSwitcherProvider, useTheme, useThemeSwitcher } from "./context.js";
5
5
  export { ThemePicker } from "./ThemePicker.js";
6
+ export { CloseButton } from "./CloseButton.js";
6
7
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,YAAY,CAAA;AAGzC,OAAO,EAAE,gBAAgB,EAAE,MAAM,mBAAmB,CAAA;AAEpD,OAAO,EAAE,UAAU,EAAE,aAAa,EAAE,YAAY,EAAE,MAAM,aAAa,CAAA;AAGrE,OAAO,EAAE,aAAa,EAAE,qBAAqB,EAAE,QAAQ,EAAE,gBAAgB,EAAE,MAAM,cAAc,CAAA;AAG/F,OAAO,EAAE,WAAW,EAAE,MAAM,kBAAkB,CAAA"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,YAAY,CAAA;AAGzC,OAAO,EAAE,gBAAgB,EAAE,MAAM,mBAAmB,CAAA;AAEpD,OAAO,EAAE,UAAU,EAAE,aAAa,EAAE,YAAY,EAAE,MAAM,aAAa,CAAA;AAGrE,OAAO,EAAE,aAAa,EAAE,qBAAqB,EAAE,QAAQ,EAAE,gBAAgB,EAAE,MAAM,cAAc,CAAA;AAG/F,OAAO,EAAE,WAAW,EAAE,MAAM,kBAAkB,CAAA;AAG9C,OAAO,EAAE,WAAW,EAAE,MAAM,kBAAkB,CAAA"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@tooee/themes",
3
- "version": "0.1.19",
3
+ "version": "0.1.21",
4
4
  "description": "Theme management with 34 bundled themes for Tooee",
5
5
  "keywords": [
6
6
  "cli",
@@ -37,8 +37,9 @@
37
37
  "typecheck": "tsc --noEmit"
38
38
  },
39
39
  "dependencies": {
40
- "@tooee/config": "0.1.19",
41
- "@tooee/fuzzy": "0.1.19"
40
+ "@tooee/commands": "0.1.21",
41
+ "@tooee/config": "0.1.21",
42
+ "@tooee/fuzzy": "0.1.21"
42
43
  },
43
44
  "devDependencies": {
44
45
  "@opentui/core": "^0.2.15",
@@ -0,0 +1,39 @@
1
+ import { useCallback } from "react"
2
+ import type { MouseEvent } from "@opentui/core"
3
+ import { useTheme } from "./context.js"
4
+
5
+ interface CloseButtonProps {
6
+ /** Called when the button is clicked (left mouse button). */
7
+ onClose: () => void
8
+ /** Glyph to render (default "✕"). */
9
+ glyph?: string
10
+ /** Foreground colour (defaults to theme.textMuted). */
11
+ color?: string
12
+ }
13
+
14
+ /**
15
+ * Reusable clickable close control for overlays.
16
+ *
17
+ * Renders a small themed glyph that calls `onClose` on left-click. Purely
18
+ * additive — overlays keep their existing Escape / cancel keyboard paths.
19
+ */
20
+ export function CloseButton({ onClose, glyph = "✕", color }: CloseButtonProps) {
21
+ const { theme } = useTheme()
22
+
23
+ const handleMouseDown = useCallback(
24
+ (event: MouseEvent) => {
25
+ // Left button only; let other buttons bubble.
26
+ if (event.button !== 0) return
27
+ event.preventDefault()
28
+ event.stopPropagation()
29
+ onClose()
30
+ },
31
+ [onClose],
32
+ )
33
+
34
+ return (
35
+ <box flexShrink={0} paddingLeft={1} onMouseDown={handleMouseDown}>
36
+ <text content={glyph} fg={color ?? theme.textMuted} />
37
+ </box>
38
+ )
39
+ }
@@ -1,7 +1,8 @@
1
1
  import { useState, useMemo, useCallback } from "react"
2
- import { useKeyboard } from "@opentui/react"
2
+ import { useCommand } from "@tooee/commands"
3
3
  import { fuzzyMatch } from "@tooee/fuzzy"
4
4
  import { useTheme } from "./context.js"
5
+ import { CloseButton } from "./CloseButton.js"
5
6
 
6
7
  export interface ThemePickerEntry {
7
8
  id: string
@@ -59,20 +60,45 @@ export function ThemePicker({
59
60
  [filtered, onNavigate],
60
61
  )
61
62
 
62
- useKeyboard((key) => {
63
- if (key.name === "escape") {
64
- key.preventDefault()
65
- onClose()
66
- } else if (key.name === "return") {
67
- key.preventDefault()
68
- handleSelect()
69
- } else if (key.name === "up") {
70
- key.preventDefault()
71
- navigateTo(Math.max(0, activeIndex - 1))
72
- } else if (key.name === "down") {
73
- key.preventDefault()
74
- navigateTo(Math.min(filtered.length - 1, activeIndex + 1))
75
- }
63
+ const moveUp = useCallback(() => {
64
+ navigateTo(Math.max(0, activeIndex - 1))
65
+ }, [activeIndex, navigateTo])
66
+
67
+ const moveDown = useCallback(() => {
68
+ navigateTo(Math.min(filtered.length - 1, activeIndex + 1))
69
+ }, [activeIndex, filtered.length, navigateTo])
70
+
71
+ useCommand({
72
+ id: "theme-picker:close",
73
+ title: "Close theme picker",
74
+ hotkey: "Escape",
75
+ modes: ["insert", "cursor"],
76
+ hidden: true,
77
+ handler: onClose,
78
+ })
79
+ useCommand({
80
+ id: "theme-picker:select",
81
+ title: "Select theme",
82
+ hotkey: "Enter",
83
+ modes: ["insert", "cursor"],
84
+ hidden: true,
85
+ handler: handleSelect,
86
+ })
87
+ useCommand({
88
+ id: "theme-picker:move-up",
89
+ title: "Move up",
90
+ hotkey: "up",
91
+ modes: ["insert", "cursor"],
92
+ hidden: true,
93
+ handler: moveUp,
94
+ })
95
+ useCommand({
96
+ id: "theme-picker:move-down",
97
+ title: "Move down",
98
+ hotkey: "down",
99
+ modes: ["insert", "cursor"],
100
+ hidden: true,
101
+ handler: moveDown,
76
102
  })
77
103
 
78
104
  return (
@@ -93,6 +119,7 @@ export function ThemePicker({
93
119
  <input
94
120
  focused
95
121
  placeholder="Filter themes..."
122
+ onSubmit={handleSelect}
96
123
  onInput={(value: string) => {
97
124
  setFilter(value)
98
125
  setActiveIndex(0)
@@ -117,6 +144,7 @@ export function ThemePicker({
117
144
  style={{ flexGrow: 1 }}
118
145
  />
119
146
  <text content={` ${filtered.length}`} fg={theme.textMuted} />
147
+ <CloseButton onClose={onClose} />
120
148
  </box>
121
149
 
122
150
  {/* Separator */}
@@ -132,6 +160,13 @@ export function ThemePicker({
132
160
  paddingRight={1}
133
161
  height={1}
134
162
  backgroundColor={i === activeIndex ? theme.backgroundElement : undefined}
163
+ onMouseDown={(event) => {
164
+ // Left-click applies the theme — same code path as Enter.
165
+ if (event.button !== 0) return
166
+ event.preventDefault()
167
+ event.stopPropagation()
168
+ onSelect(entry.id)
169
+ }}
135
170
  >
136
171
  <text content={entry.title} fg={theme.text} style={{ flexGrow: 1 }} />
137
172
  </box>
package/src/index.ts CHANGED
@@ -11,3 +11,5 @@ export type { ThemeProviderProps, ThemeSwitcherProviderProps } from "./context.j
11
11
 
12
12
  export { ThemePicker } from "./ThemePicker.js"
13
13
  export type { ThemePickerEntry } from "./ThemePicker.js"
14
+
15
+ export { CloseButton } from "./CloseButton.js"