giggles 0.3.14 → 0.3.16
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/README.md +15 -28
- package/dist/index.js +3 -3
- package/dist/markdown/index.js +18 -1
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -4,10 +4,25 @@
|
|
|
4
4
|
|
|
5
5
|
# giggles
|
|
6
6
|
|
|
7
|
+

|
|
8
|
+
|
|
7
9
|
giggles is a batteries-included react framework for building terminal apps. built on ink, it handles focus, input routing, screen navigation, and theming out of the box so you can skip the plumbing and build.
|
|
8
10
|
|
|
9
11
|
inspired by the [charmbracelet](https://github.com/charmbracelet) ecosystem, it comes with a rich set of UI components, hooks for focus and navigation management, and terminal utilities for things like running shell commands.
|
|
10
12
|
|
|
13
|
+
## features
|
|
14
|
+
|
|
15
|
+
- no `useInput` hooks scattered across your app — focus, input routing, and keyboard navigation are handled for you
|
|
16
|
+
- navigate between views with a simple API; the previously focused component is restored when you return
|
|
17
|
+
- a full set of hooks and components — `useFocus`, `FocusGroup`, `FocusTrap`, `useNavigation`, and more — for building any interaction pattern without reimplementing the plumbing
|
|
18
|
+
- built-in keybinding registry so your app can always show users what keys do what, in the current context — context-aware and accessible via a hook
|
|
19
|
+
- a component library covering most TUI use cases, from text inputs and autocomplete to virtual lists for large datasets — with sensible defaults and render props for full customization
|
|
20
|
+
- render markdown in the terminal, with full formatting and syntax-highlighted code block and diff support
|
|
21
|
+
- hand off terminal control to external programs like `vim` or `less` and reclaim it cleanly when they exit (similar to `tea.ExecProcess` from charmbracelet/bubbletea)
|
|
22
|
+
- a consistent look out of the box, customizable from a single theme object
|
|
23
|
+
|
|
24
|
+
## your first TUI
|
|
25
|
+
|
|
11
26
|
to get started, run
|
|
12
27
|
|
|
13
28
|
```bash
|
|
@@ -15,31 +30,3 @@ npx create-giggles-app
|
|
|
15
30
|
```
|
|
16
31
|
|
|
17
32
|
see [giggles.zzzzion.com](https://giggles.zzzzion.com) for API documentation and live demos.
|
|
18
|
-
|
|
19
|
-
## sample ui components
|
|
20
|
-
|
|
21
|
-
for a full list of UI components, see [giggles/ui](https://giggles.zzzzion.com/ui). here are a few samples:
|
|
22
|
-
|
|
23
|
-
### viewport
|
|
24
|
-
|
|
25
|
-

|
|
26
|
-
|
|
27
|
-
### markdown
|
|
28
|
-
|
|
29
|
-
<img width="594" height="603" alt="image" src="https://github.com/user-attachments/assets/fc5648e4-3791-450c-adea-44b7057db071" />
|
|
30
|
-
|
|
31
|
-
### code block
|
|
32
|
-
|
|
33
|
-
supports syntax highlighting with [prism](https://prismjs.com/index.html#supported-languages). just import 'prism/language' and you're good to go!
|
|
34
|
-
|
|
35
|
-
<img width="548" height="527" alt="code-block" src="https://github.com/user-attachments/assets/fd9952fa-55ea-4c70-aadb-7a772d791018" />
|
|
36
|
-
|
|
37
|
-
### multi-select
|
|
38
|
-
|
|
39
|
-

|
|
40
|
-
|
|
41
|
-
### spinner
|
|
42
|
-
|
|
43
|
-
ported from [charmbracelet/bubbles](https://github.com/charmbracelet/bubbles/blob/master/spinner/spinner.go).
|
|
44
|
-
|
|
45
|
-

|
package/dist/index.js
CHANGED
|
@@ -1,3 +1,6 @@
|
|
|
1
|
+
import {
|
|
2
|
+
AlternateScreen
|
|
3
|
+
} from "./chunk-N2MMNJV3.js";
|
|
1
4
|
import {
|
|
2
5
|
FocusGroup,
|
|
3
6
|
FocusNodeContext,
|
|
@@ -12,9 +15,6 @@ import {
|
|
|
12
15
|
useKeybindingRegistry,
|
|
13
16
|
useKeybindings
|
|
14
17
|
} from "./chunk-CKA5JJ4B.js";
|
|
15
|
-
import {
|
|
16
|
-
AlternateScreen
|
|
17
|
-
} from "./chunk-N2MMNJV3.js";
|
|
18
18
|
import {
|
|
19
19
|
ThemeProvider,
|
|
20
20
|
useTheme
|
package/dist/markdown/index.js
CHANGED
|
@@ -43,13 +43,24 @@ function TokenRenderer({ token }) {
|
|
|
43
43
|
] });
|
|
44
44
|
case "list":
|
|
45
45
|
return /* @__PURE__ */ jsx(Box, { flexDirection: "column", marginY: 1, children: token.items.map((item, idx) => /* @__PURE__ */ jsxs(Box, { children: [
|
|
46
|
-
/* @__PURE__ */ jsx(Text, { children: token.ordered ? `${idx + 1}. ` :
|
|
46
|
+
/* @__PURE__ */ jsx(Text, { children: token.ordered ? `${idx + 1}. ` : item.checked === true ? `${theme.checkedIndicator} ` : item.checked === false ? `${theme.uncheckedIndicator} ` : `${theme.indicator} ` }),
|
|
47
47
|
/* @__PURE__ */ jsx(Box, { flexDirection: "column", children: item.tokens.map((t, i) => /* @__PURE__ */ jsx(TokenRenderer, { token: t }, i)) })
|
|
48
48
|
] }, idx)) });
|
|
49
|
+
case "html": {
|
|
50
|
+
const stripped = token.text.replace(/<[^>]*>/g, "").trim();
|
|
51
|
+
return stripped ? /* @__PURE__ */ jsx(Text, { dimColor: true, children: stripped }) : null;
|
|
52
|
+
}
|
|
49
53
|
case "table":
|
|
50
54
|
return /* @__PURE__ */ jsx(TableRenderer, { token });
|
|
51
55
|
case "hr":
|
|
52
56
|
return /* @__PURE__ */ jsx(Text, { dimColor: true, children: "\u2500".repeat(40) });
|
|
57
|
+
case "text": {
|
|
58
|
+
const textToken = token;
|
|
59
|
+
if (textToken.tokens && textToken.tokens.length > 0) {
|
|
60
|
+
return /* @__PURE__ */ jsx(Text, { children: renderInline(textToken.tokens, theme) });
|
|
61
|
+
}
|
|
62
|
+
return /* @__PURE__ */ jsx(Text, { children: textToken.text });
|
|
63
|
+
}
|
|
53
64
|
case "space":
|
|
54
65
|
return null;
|
|
55
66
|
default:
|
|
@@ -93,6 +104,12 @@ function renderInline(tokens, theme) {
|
|
|
93
104
|
token.text || token.href,
|
|
94
105
|
"]"
|
|
95
106
|
] }, idx);
|
|
107
|
+
case "escape":
|
|
108
|
+
return /* @__PURE__ */ jsx(Text, { children: token.text }, idx);
|
|
109
|
+
case "html": {
|
|
110
|
+
const stripped = token.text.replace(/<[^>]*>/g, "");
|
|
111
|
+
return stripped ? /* @__PURE__ */ jsx(Text, { children: stripped }, idx) : null;
|
|
112
|
+
}
|
|
96
113
|
case "br":
|
|
97
114
|
return /* @__PURE__ */ jsx(Text, { children: "\n" }, idx);
|
|
98
115
|
case "del":
|