@outfitter/cli 0.1.0-rc.2 → 0.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.
- package/README.md +21 -32
- package/dist/actions.d.ts +12 -1
- package/dist/actions.js +170 -3
- package/dist/borders/index.d.ts +3 -0
- package/dist/borders/index.js +13 -0
- package/dist/box/index.d.ts +4 -0
- package/dist/box/index.js +13 -0
- package/dist/cli.js +1 -1
- package/dist/colors/index.d.ts +3 -0
- package/dist/colors/index.js +18 -0
- package/dist/command.d.ts +40 -3
- package/dist/command.js +45 -3
- package/dist/demo/index.d.ts +78 -0
- package/dist/demo/index.js +148 -0
- package/dist/demo/registry.d.ts +7 -0
- package/dist/demo/registry.js +28 -0
- package/dist/demo/renderers/borders.d.ts +7 -0
- package/dist/demo/renderers/borders.js +17 -0
- package/dist/demo/renderers/box.d.ts +7 -0
- package/dist/demo/renderers/box.js +18 -0
- package/dist/demo/renderers/colors.d.ts +7 -0
- package/dist/demo/renderers/colors.js +18 -0
- package/dist/demo/renderers/indicators.d.ts +7 -0
- package/dist/demo/renderers/indicators.js +17 -0
- package/dist/demo/renderers/list.d.ts +7 -0
- package/dist/demo/renderers/list.js +19 -0
- package/dist/demo/renderers/markdown.d.ts +7 -0
- package/dist/demo/renderers/markdown.js +18 -0
- package/dist/demo/renderers/progress.d.ts +7 -0
- package/dist/demo/renderers/progress.js +17 -0
- package/dist/demo/renderers/spinner.d.ts +7 -0
- package/dist/demo/renderers/spinner.js +19 -0
- package/dist/demo/renderers/table.d.ts +7 -0
- package/dist/demo/renderers/table.js +19 -0
- package/dist/demo/renderers/text.d.ts +7 -0
- package/dist/demo/renderers/text.js +16 -0
- package/dist/demo/renderers/tree.d.ts +7 -0
- package/dist/demo/renderers/tree.js +18 -0
- package/dist/demo/section.d.ts +5 -0
- package/dist/demo/section.js +23 -0
- package/dist/demo/templates.d.ts +4 -0
- package/dist/demo/templates.js +10 -0
- package/dist/demo/types.d.ts +3 -0
- package/dist/demo/types.js +8 -0
- package/dist/index.d.ts +5 -8
- package/dist/index.js +9 -43
- package/dist/input.d.ts +163 -2
- package/dist/input.js +425 -11
- package/dist/list/index.d.ts +3 -0
- package/dist/list/index.js +9 -0
- package/dist/output.js +1 -1
- package/dist/pagination.d.ts +62 -2
- package/dist/pagination.js +84 -6
- package/dist/preset/full.d.ts +14 -0
- package/dist/preset/full.js +41 -0
- package/dist/preset/standard.d.ts +11 -0
- package/dist/preset/standard.js +30 -0
- package/dist/prompt/confirm.d.ts +4 -0
- package/dist/prompt/confirm.js +9 -0
- package/dist/prompt/group.d.ts +4 -0
- package/dist/prompt/group.js +9 -0
- package/dist/prompt/index.d.ts +7 -0
- package/dist/prompt/index.js +32 -0
- package/dist/prompt/select.d.ts +4 -0
- package/dist/prompt/select.js +11 -0
- package/dist/prompt/text.d.ts +4 -0
- package/dist/prompt/text.js +11 -0
- package/dist/prompt/types.d.ts +3 -0
- package/dist/prompt/types.js +8 -0
- package/dist/prompt/validators.d.ts +2 -0
- package/dist/prompt/validators.js +8 -0
- package/dist/render/borders.d.ts +2 -0
- package/dist/render/borders.js +15 -0
- package/dist/render/box.d.ts +3 -0
- package/dist/render/box.js +23 -0
- package/dist/render/colors.d.ts +1 -1
- package/dist/render/colors.js +6 -3
- package/dist/render/date.js +1 -1
- package/dist/render/format-relative.js +1 -1
- package/dist/render/format.js +1 -1
- package/dist/render/heading.d.ts +3 -0
- package/dist/render/heading.js +14 -0
- package/dist/render/index.d.ts +26 -7
- package/dist/render/index.js +160 -26
- package/dist/render/indicators.d.ts +2 -0
- package/dist/render/indicators.js +14 -0
- package/dist/render/json.js +1 -1
- package/dist/render/layout.d.ts +5 -0
- package/dist/render/layout.js +25 -0
- package/dist/render/list.d.ts +2 -2
- package/dist/render/list.js +2 -2
- package/dist/render/markdown.js +4 -4
- package/dist/render/progress.js +1 -1
- package/dist/render/separator.d.ts +3 -0
- package/dist/render/separator.js +14 -0
- package/dist/render/shapes.js +10 -9
- package/dist/render/spinner.d.ts +2 -0
- package/dist/render/spinner.js +12 -0
- package/dist/render/stack.d.ts +3 -0
- package/dist/render/stack.js +38 -0
- package/dist/render/table.d.ts +2 -1
- package/dist/render/table.js +6 -5
- package/dist/render/text.d.ts +1 -1
- package/dist/render/text.js +7 -4
- package/dist/render/tree.d.ts +2 -2
- package/dist/render/tree.js +5 -3
- package/dist/render/types.d.ts +2 -0
- package/dist/render/types.js +1 -0
- package/dist/shared/@outfitter/cli-0ggcy7fa.js +20 -0
- package/dist/shared/@outfitter/cli-0psys2vm.js +7 -0
- package/dist/shared/@outfitter/cli-1bghjef6.js +352 -0
- package/dist/shared/@outfitter/cli-1kwbnt86.d.ts +45 -0
- package/dist/shared/@outfitter/cli-2g8bx1aq.d.ts +50 -0
- package/dist/shared/@outfitter/cli-34fqr7bp.js +37 -0
- package/dist/shared/@outfitter/cli-3b7ed3rm.d.ts +97 -0
- package/dist/shared/@outfitter/cli-3dxmmy4c.d.ts +20 -0
- package/dist/shared/@outfitter/cli-3f12z5kf.d.ts +83 -0
- package/dist/shared/@outfitter/cli-3t2zaenc.d.ts +59 -0
- package/dist/shared/@outfitter/{cli-dds0qqvm.d.ts → cli-4cb5g831.d.ts} +2 -0
- package/dist/shared/@outfitter/cli-4w2a1rfy.d.ts +23 -0
- package/dist/shared/@outfitter/cli-4x6pqnez.js +20 -0
- package/dist/shared/@outfitter/cli-671sxkhj.js +146 -0
- package/dist/shared/@outfitter/cli-6bztk73z.d.ts +51 -0
- package/dist/shared/@outfitter/cli-6fxffp8k.js +1 -0
- package/dist/shared/@outfitter/cli-6j9qynm8.js +118 -0
- package/dist/shared/@outfitter/cli-6m988kh0.d.ts +61 -0
- package/dist/shared/@outfitter/cli-74ba31gz.js +134 -0
- package/dist/shared/@outfitter/cli-7gnrb8cr.js +214 -0
- package/dist/shared/@outfitter/cli-7nm6edvh.d.ts +17 -0
- package/dist/shared/@outfitter/cli-85fg2vr5.js +123 -0
- package/dist/shared/@outfitter/cli-8a8xrzhy.js +20 -0
- package/dist/shared/@outfitter/cli-8bwaw3pz.js +7 -0
- package/dist/shared/@outfitter/cli-8rx4g3s5.d.ts +41 -0
- package/dist/shared/@outfitter/cli-8xsmsbbd.d.ts +223 -0
- package/dist/shared/@outfitter/cli-96b2p4td.d.ts +56 -0
- package/dist/shared/@outfitter/cli-9khk3cbq.d.ts +190 -0
- package/dist/shared/@outfitter/cli-9mtjjykw.js +67 -0
- package/dist/shared/@outfitter/{cli-ag0w4pk0.js → cli-9nbyj2bt.js} +60 -21
- package/dist/shared/@outfitter/{cli-azzk8a1d.js → cli-afhjqmg3.js} +7 -3
- package/dist/shared/@outfitter/cli-an9j0h80.js +117 -0
- package/dist/shared/@outfitter/cli-ay411nbr.js +122 -0
- package/dist/shared/@outfitter/cli-b0tzqgnf.d.ts +132 -0
- package/dist/shared/@outfitter/cli-b5c2k0d7.js +39 -0
- package/dist/shared/@outfitter/cli-b5epywry.js +1 -0
- package/dist/shared/@outfitter/cli-bcmcaz1b.js +23 -0
- package/dist/shared/@outfitter/cli-bf3vma4q.js +61 -0
- package/dist/shared/@outfitter/cli-cf1xexgn.d.ts +53 -0
- package/dist/shared/@outfitter/cli-cs45xd6q.js +59 -0
- package/dist/shared/@outfitter/cli-d7jpshq5.d.ts +128 -0
- package/dist/shared/@outfitter/{cli-jbj78ac5.js → cli-d9ad0rqj.js} +6 -1
- package/dist/shared/@outfitter/cli-daw296mv.js +61 -0
- package/dist/shared/@outfitter/cli-e5ms1y0x.d.ts +91 -0
- package/dist/shared/@outfitter/cli-e73v3qqy.d.ts +93 -0
- package/dist/shared/@outfitter/cli-en6zn6sj.js +1 -0
- package/dist/shared/@outfitter/cli-ep2cvtk8.js +48 -0
- package/dist/shared/@outfitter/cli-f75h8e94.js +7 -0
- package/dist/shared/@outfitter/cli-fakncnjp.d.ts +106 -0
- package/dist/shared/@outfitter/cli-feb5j90n.js +94 -0
- package/dist/shared/@outfitter/cli-h20jc0bs.d.ts +66 -0
- package/dist/shared/@outfitter/cli-hnpbqmc8.d.ts +328 -0
- package/dist/shared/@outfitter/cli-j4n8gaf3.js +95 -0
- package/dist/shared/@outfitter/cli-jejfypgf.js +85 -0
- package/dist/shared/@outfitter/{cli-wqc652mx.js → cli-jhcdwvpn.js} +8 -8
- package/dist/shared/@outfitter/{cli-v9mjsvjh.js → cli-jjemfdta.js} +13 -46
- package/dist/shared/@outfitter/cli-kc84wmch.js +267 -0
- package/dist/shared/@outfitter/cli-ktqme80d.js +7 -0
- package/dist/shared/@outfitter/cli-mq0jp15z.js +1 -0
- package/dist/shared/@outfitter/cli-mymyavvj.d.ts +26 -0
- package/dist/shared/@outfitter/cli-n17gt1dz.js +19 -0
- package/dist/shared/@outfitter/cli-n9dbh0hp.js +51 -0
- package/dist/shared/@outfitter/cli-nvvc92c8.js +128 -0
- package/dist/shared/@outfitter/cli-p1m5dhrs.js +169 -0
- package/dist/shared/@outfitter/cli-p38sfxyk.js +25 -0
- package/dist/shared/@outfitter/cli-p3dqm1vd.js +22 -0
- package/dist/shared/@outfitter/cli-p9j1phge.js +20 -0
- package/dist/shared/@outfitter/cli-pkxmzavm.js +62 -0
- package/dist/shared/@outfitter/cli-q8r6jarq.d.ts +24 -0
- package/dist/shared/@outfitter/{cli-2y3kxew8.d.ts → cli-qj83y5wj.d.ts} +22 -9
- package/dist/shared/@outfitter/cli-qjfc3j11.d.ts +112 -0
- package/dist/shared/@outfitter/cli-qp4cbhqr.js +70 -0
- package/dist/shared/@outfitter/cli-s0kkx9m1.d.ts +164 -0
- package/dist/shared/@outfitter/cli-snxj55n6.js +43 -0
- package/dist/shared/@outfitter/cli-swwxvjvm.d.ts +24 -0
- package/dist/shared/@outfitter/cli-sx67mmfx.d.ts +98 -0
- package/dist/shared/@outfitter/cli-tarpsa8a.js +30 -0
- package/dist/shared/@outfitter/cli-thvzhjd1.js +126 -0
- package/dist/shared/@outfitter/cli-tqewy503.d.ts +36 -0
- package/dist/shared/@outfitter/cli-tvw1xrdj.js +20 -0
- package/dist/shared/@outfitter/cli-v1tzwxkt.js +32 -0
- package/dist/shared/@outfitter/cli-vd60dj65.js +1 -0
- package/dist/shared/@outfitter/cli-vp88gxev.js +279 -0
- package/dist/shared/@outfitter/cli-vstbkzky.d.ts +74 -0
- package/dist/shared/@outfitter/cli-vtg0sqk2.d.ts +54 -0
- package/dist/shared/@outfitter/cli-w5y3xepp.js +20 -0
- package/dist/shared/@outfitter/cli-x4cavvc0.js +1 -0
- package/dist/shared/@outfitter/cli-xep6v2c0.js +52 -0
- package/dist/shared/@outfitter/cli-xg5y5fhk.js +86 -0
- package/dist/shared/@outfitter/{cli-n51t773m.d.ts → cli-xsaheemc.d.ts} +44 -4
- package/dist/shared/@outfitter/cli-xvqtqjxk.js +82 -0
- package/dist/shared/@outfitter/cli-y25tt8nc.d.ts +48 -0
- package/dist/streaming/ansi.d.ts +2 -0
- package/dist/streaming/ansi.js +8 -0
- package/dist/streaming/index.d.ts +4 -0
- package/dist/streaming/index.js +17 -0
- package/dist/streaming/spinner.d.ts +3 -0
- package/dist/streaming/spinner.js +10 -0
- package/dist/streaming/writer.d.ts +2 -0
- package/dist/streaming/writer.js +9 -0
- package/dist/table/index.d.ts +4 -0
- package/dist/table/index.js +13 -0
- package/dist/terminal/detection.js +5 -2
- package/dist/terminal/index.js +6 -2
- package/dist/theme/context.d.ts +9 -0
- package/dist/theme/context.js +14 -0
- package/dist/theme/create.d.ts +8 -0
- package/dist/theme/create.js +12 -0
- package/dist/theme/index.d.ts +17 -0
- package/dist/theme/index.js +42 -0
- package/dist/theme/presets/bold.d.ts +8 -0
- package/dist/theme/presets/bold.js +12 -0
- package/dist/theme/presets/default.d.ts +8 -0
- package/dist/theme/presets/default.js +11 -0
- package/dist/theme/presets/index.d.ts +12 -0
- package/dist/theme/presets/index.js +24 -0
- package/dist/theme/presets/minimal.d.ts +8 -0
- package/dist/theme/presets/minimal.js +12 -0
- package/dist/theme/presets/rounded.d.ts +8 -0
- package/dist/theme/presets/rounded.js +12 -0
- package/dist/theme/resolve.d.ts +8 -0
- package/dist/theme/resolve.js +11 -0
- package/dist/theme/types.d.ts +7 -0
- package/dist/theme/types.js +1 -0
- package/dist/tree/index.d.ts +3 -0
- package/dist/tree/index.js +11 -0
- package/dist/types.js +1 -1
- package/package.json +168 -54
- package/dist/shared/@outfitter/cli-2vs2gxa8.js +0 -429
- package/dist/shared/@outfitter/cli-2yq94zst.d.ts +0 -39
- package/dist/shared/@outfitter/cli-6xc869x1.js +0 -26
- package/dist/shared/@outfitter/cli-7km1e58p.js +0 -85
- package/dist/shared/@outfitter/cli-8r0bnyyx.js +0 -43
- package/dist/shared/@outfitter/cli-afecwfrn.d.ts +0 -13
- package/dist/shared/@outfitter/cli-bt423m6y.js +0 -4
- package/dist/shared/@outfitter/cli-d4fegbad.d.ts +0 -66
- package/dist/shared/@outfitter/cli-e0ecw3x1.js +0 -64
- package/dist/shared/@outfitter/cli-fheaaa6b.js +0 -25
- package/dist/shared/@outfitter/cli-j361wp3g.d.ts +0 -41
- package/dist/shared/@outfitter/cli-p0m2fc51.js +0 -172
- package/dist/shared/@outfitter/cli-tyajr8qa.d.ts +0 -63
- package/dist/shared/@outfitter/cli-zs6jy1am.d.ts +0 -164
|
@@ -0,0 +1,132 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* List rendering utilities.
|
|
3
|
+
*
|
|
4
|
+
* Renders arrays as bullet lists with optional nesting and multiple styles.
|
|
5
|
+
*
|
|
6
|
+
* @packageDocumentation
|
|
7
|
+
*/
|
|
8
|
+
/**
|
|
9
|
+
* Available list styles for {@link renderList}.
|
|
10
|
+
*
|
|
11
|
+
* - `dash`: Uses - character (default)
|
|
12
|
+
* - `bullet`: Uses • character
|
|
13
|
+
* - `number`: Uses 1. for top-level, a. for nested, i. for deeply nested
|
|
14
|
+
* - `checkbox`: Uses ☐ for unchecked, ☑ for checked
|
|
15
|
+
*/
|
|
16
|
+
type ListStyle = "dash" | "bullet" | "number" | "checkbox";
|
|
17
|
+
/**
|
|
18
|
+
* Options for customizing list rendering.
|
|
19
|
+
*
|
|
20
|
+
* @example
|
|
21
|
+
* ```typescript
|
|
22
|
+
* // Numbered list with custom indent
|
|
23
|
+
* renderList(items, { style: "number", indent: 4 });
|
|
24
|
+
*
|
|
25
|
+
* // Checkbox list with some items checked
|
|
26
|
+
* renderList(items, { style: "checkbox", checked: new Set([1, 3]) });
|
|
27
|
+
* ```
|
|
28
|
+
*/
|
|
29
|
+
interface ListOptions {
|
|
30
|
+
/**
|
|
31
|
+
* The list style to use.
|
|
32
|
+
* @default "dash"
|
|
33
|
+
*/
|
|
34
|
+
style?: ListStyle;
|
|
35
|
+
/**
|
|
36
|
+
* Indices of checked top-level items (0-indexed) for checkbox style.
|
|
37
|
+
* Only applies to top-level items. For nested items, use the
|
|
38
|
+
* `checked` property on {@link NestedListItem} instead.
|
|
39
|
+
*/
|
|
40
|
+
checked?: Set<number>;
|
|
41
|
+
/**
|
|
42
|
+
* Number of spaces per indentation level.
|
|
43
|
+
* @default 2
|
|
44
|
+
*/
|
|
45
|
+
indent?: number;
|
|
46
|
+
}
|
|
47
|
+
/**
|
|
48
|
+
* A list item with optional nested children for {@link renderList}.
|
|
49
|
+
*
|
|
50
|
+
* @example
|
|
51
|
+
* ```typescript
|
|
52
|
+
* const item: NestedListItem = {
|
|
53
|
+
* text: "Parent item",
|
|
54
|
+
* children: ["Child 1", "Child 2"],
|
|
55
|
+
* };
|
|
56
|
+
*
|
|
57
|
+
* // Checkbox item with checked state
|
|
58
|
+
* const checkboxItem: NestedListItem = {
|
|
59
|
+
* text: "Completed task",
|
|
60
|
+
* checked: true,
|
|
61
|
+
* };
|
|
62
|
+
*
|
|
63
|
+
* // Mixed styles: numbered parent with bullet children
|
|
64
|
+
* const mixedItem: NestedListItem = {
|
|
65
|
+
* text: "Section 1",
|
|
66
|
+
* childStyle: "bullet",
|
|
67
|
+
* children: ["Unordered item A", "Unordered item B"],
|
|
68
|
+
* };
|
|
69
|
+
* ```
|
|
70
|
+
*/
|
|
71
|
+
interface NestedListItem {
|
|
72
|
+
/** The text content of this list item */
|
|
73
|
+
text: string;
|
|
74
|
+
/** Optional nested child items (strings or nested items) */
|
|
75
|
+
children?: Array<string | NestedListItem>;
|
|
76
|
+
/** Whether this item is checked (for checkbox style) */
|
|
77
|
+
checked?: boolean;
|
|
78
|
+
/** Override style for children (enables mixed numbered/bullet lists) */
|
|
79
|
+
childStyle?: ListStyle;
|
|
80
|
+
}
|
|
81
|
+
/**
|
|
82
|
+
* A list item that can be either a simple string or a nested item with children.
|
|
83
|
+
*
|
|
84
|
+
* @example
|
|
85
|
+
* ```typescript
|
|
86
|
+
* const items: ListItem[] = [
|
|
87
|
+
* "Simple item",
|
|
88
|
+
* { text: "Parent", children: ["Child 1", "Child 2"] },
|
|
89
|
+
* ];
|
|
90
|
+
* ```
|
|
91
|
+
*/
|
|
92
|
+
type ListItem = string | NestedListItem;
|
|
93
|
+
/**
|
|
94
|
+
* Renders items as a list with optional nesting and multiple styles.
|
|
95
|
+
*
|
|
96
|
+
* Supports both simple string items and nested items with children.
|
|
97
|
+
* The default style uses dash (-) characters.
|
|
98
|
+
*
|
|
99
|
+
* For numbered lists, child items are indented to align with the parent's
|
|
100
|
+
* content (after the marker), creating proper visual hierarchy.
|
|
101
|
+
*
|
|
102
|
+
* @param items - Array of list items (strings or nested items)
|
|
103
|
+
* @param options - Optional configuration for style, checked items, and indent
|
|
104
|
+
* @returns Formatted list string
|
|
105
|
+
*
|
|
106
|
+
* @example
|
|
107
|
+
* ```typescript
|
|
108
|
+
* // Simple dash list (default)
|
|
109
|
+
* console.log(renderList(["First", "Second", "Third"]));
|
|
110
|
+
* // - First
|
|
111
|
+
* // - Second
|
|
112
|
+
* // - Third
|
|
113
|
+
*
|
|
114
|
+
* // Numbered list with nesting
|
|
115
|
+
* console.log(renderList([
|
|
116
|
+
* { text: "First section", children: [
|
|
117
|
+
* { text: "Subsection A", children: ["Detail i", "Detail ii"] },
|
|
118
|
+
* ]},
|
|
119
|
+
* ], { style: "number" }));
|
|
120
|
+
* // 1. First section
|
|
121
|
+
* // a. Subsection A
|
|
122
|
+
* // i. Detail i
|
|
123
|
+
* // ii. Detail ii
|
|
124
|
+
*
|
|
125
|
+
* // Checkbox list
|
|
126
|
+
* console.log(renderList(["Todo 1", "Todo 2"], { style: "checkbox", checked: new Set([1]) }));
|
|
127
|
+
* // ☐ Todo 1
|
|
128
|
+
* // ☑ Todo 2
|
|
129
|
+
* ```
|
|
130
|
+
*/
|
|
131
|
+
declare function renderList(items: ListItem[], options?: ListOptions): string;
|
|
132
|
+
export { ListStyle, ListOptions, NestedListItem, ListItem, renderList };
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
// @bun
|
|
2
|
+
// packages/cli/src/render/tree.ts
|
|
3
|
+
var TREE_GUIDES = {
|
|
4
|
+
single: { vertical: "\u2502 ", fork: "\u251C\u2500\u2500 ", end: "\u2514\u2500\u2500 " },
|
|
5
|
+
heavy: { vertical: "\u2503 ", fork: "\u2523\u2501\u2501 ", end: "\u2517\u2501\u2501 " },
|
|
6
|
+
double: { vertical: "\u2551 ", fork: "\u2560\u2550\u2550 ", end: "\u255A\u2550\u2550 " },
|
|
7
|
+
rounded: { vertical: "\u2502 ", fork: "\u251C\u2500\u2500 ", end: "\u2570\u2500\u2500 " }
|
|
8
|
+
};
|
|
9
|
+
function renderTree(tree, options) {
|
|
10
|
+
const guide = TREE_GUIDES[options?.guide ?? "single"];
|
|
11
|
+
const maxDepth = options?.maxDepth;
|
|
12
|
+
const renderLabel = options?.renderLabel ?? ((key) => key);
|
|
13
|
+
const lines = [];
|
|
14
|
+
const renderNode = (key, value, prefix, isLast, depth) => {
|
|
15
|
+
if (maxDepth !== undefined && depth >= maxDepth) {
|
|
16
|
+
return;
|
|
17
|
+
}
|
|
18
|
+
const connector = isLast ? guide.end : guide.fork;
|
|
19
|
+
const label = renderLabel(key, value, depth);
|
|
20
|
+
lines.push(prefix + connector + label);
|
|
21
|
+
if (value !== null && typeof value === "object") {
|
|
22
|
+
const entries2 = Object.entries(value);
|
|
23
|
+
const childPrefix = prefix + (isLast ? " " : guide.vertical);
|
|
24
|
+
entries2.forEach(([childKey, childValue], index) => {
|
|
25
|
+
const childIsLast = index === entries2.length - 1;
|
|
26
|
+
renderNode(childKey, childValue, childPrefix, childIsLast, depth + 1);
|
|
27
|
+
});
|
|
28
|
+
}
|
|
29
|
+
};
|
|
30
|
+
const entries = Object.entries(tree);
|
|
31
|
+
entries.forEach(([key, value], index) => {
|
|
32
|
+
const isLast = index === entries.length - 1;
|
|
33
|
+
renderNode(key, value, "", isLast, 0);
|
|
34
|
+
});
|
|
35
|
+
return lines.join(`
|
|
36
|
+
`);
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
export { TREE_GUIDES, renderTree };
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
// @bun
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
// @bun
|
|
2
|
+
import {
|
|
3
|
+
createCancelledError
|
|
4
|
+
} from "./cli-8bwaw3pz.js";
|
|
5
|
+
|
|
6
|
+
// packages/cli/src/prompt/confirm.ts
|
|
7
|
+
import { confirm, isCancel } from "@clack/prompts";
|
|
8
|
+
import { Result } from "better-result";
|
|
9
|
+
async function promptConfirm(options) {
|
|
10
|
+
const confirmOptions = {
|
|
11
|
+
message: options.message
|
|
12
|
+
};
|
|
13
|
+
if (options.initialValue !== undefined) {
|
|
14
|
+
confirmOptions.initialValue = options.initialValue;
|
|
15
|
+
}
|
|
16
|
+
const result = await confirm(confirmOptions);
|
|
17
|
+
if (isCancel(result)) {
|
|
18
|
+
return Result.err(createCancelledError());
|
|
19
|
+
}
|
|
20
|
+
return Result.ok(result);
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
export { promptConfirm };
|
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
// @bun
|
|
2
|
+
import {
|
|
3
|
+
createCancelledError
|
|
4
|
+
} from "./cli-8bwaw3pz.js";
|
|
5
|
+
|
|
6
|
+
// packages/cli/src/prompt/select.ts
|
|
7
|
+
import { isCancel, multiselect, select } from "@clack/prompts";
|
|
8
|
+
import { Result } from "better-result";
|
|
9
|
+
async function promptSelect(options) {
|
|
10
|
+
const clackOptions = options.options.map((opt) => {
|
|
11
|
+
const mapped = {
|
|
12
|
+
value: opt.value,
|
|
13
|
+
label: opt.label
|
|
14
|
+
};
|
|
15
|
+
if (opt.hint !== undefined) {
|
|
16
|
+
mapped.hint = opt.hint;
|
|
17
|
+
}
|
|
18
|
+
return mapped;
|
|
19
|
+
});
|
|
20
|
+
const selectOptions = {
|
|
21
|
+
message: options.message,
|
|
22
|
+
options: clackOptions
|
|
23
|
+
};
|
|
24
|
+
if (options.initialValue !== undefined) {
|
|
25
|
+
selectOptions.initialValue = options.initialValue;
|
|
26
|
+
}
|
|
27
|
+
const result = await select(selectOptions);
|
|
28
|
+
if (isCancel(result)) {
|
|
29
|
+
return Result.err(createCancelledError());
|
|
30
|
+
}
|
|
31
|
+
return Result.ok(result);
|
|
32
|
+
}
|
|
33
|
+
async function promptMultiSelect(options) {
|
|
34
|
+
const clackOptions = options.options.map((opt) => {
|
|
35
|
+
const mapped = {
|
|
36
|
+
value: opt.value,
|
|
37
|
+
label: opt.label
|
|
38
|
+
};
|
|
39
|
+
if (opt.hint !== undefined) {
|
|
40
|
+
mapped.hint = opt.hint;
|
|
41
|
+
}
|
|
42
|
+
return mapped;
|
|
43
|
+
});
|
|
44
|
+
const multiselectOptions = {
|
|
45
|
+
message: options.message,
|
|
46
|
+
options: clackOptions
|
|
47
|
+
};
|
|
48
|
+
if (options.initialValues !== undefined) {
|
|
49
|
+
multiselectOptions.initialValues = options.initialValues;
|
|
50
|
+
}
|
|
51
|
+
if (options.required !== undefined) {
|
|
52
|
+
multiselectOptions.required = options.required;
|
|
53
|
+
}
|
|
54
|
+
const result = await multiselect(multiselectOptions);
|
|
55
|
+
if (isCancel(result)) {
|
|
56
|
+
return Result.err(createCancelledError());
|
|
57
|
+
}
|
|
58
|
+
return Result.ok(result);
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
export { promptSelect, promptMultiSelect };
|
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Minimal writable stream interface.
|
|
3
|
+
*/
|
|
4
|
+
interface WritableStream {
|
|
5
|
+
write(str: string): boolean;
|
|
6
|
+
isTTY?: boolean;
|
|
7
|
+
}
|
|
8
|
+
/**
|
|
9
|
+
* Options for creating a stream writer.
|
|
10
|
+
*/
|
|
11
|
+
interface StreamWriterOptions {
|
|
12
|
+
/** Target stream (defaults to process.stdout) */
|
|
13
|
+
stream?: WritableStream;
|
|
14
|
+
}
|
|
15
|
+
/**
|
|
16
|
+
* Interface for managing in-place terminal output.
|
|
17
|
+
*/
|
|
18
|
+
interface StreamWriter {
|
|
19
|
+
/** Write content (replaces current content) */
|
|
20
|
+
write(content: string): void;
|
|
21
|
+
/** Update content in place */
|
|
22
|
+
update(content: string): void;
|
|
23
|
+
/** Persist current content and move to new line */
|
|
24
|
+
persist(): void;
|
|
25
|
+
/** Clear current content */
|
|
26
|
+
clear(): void;
|
|
27
|
+
}
|
|
28
|
+
/**
|
|
29
|
+
* Creates a stream writer for in-place terminal updates.
|
|
30
|
+
*
|
|
31
|
+
* The writer tracks the number of lines written and can update them in place.
|
|
32
|
+
* In non-TTY mode, it falls back to simple line-by-line output.
|
|
33
|
+
*
|
|
34
|
+
* @param options - Writer configuration
|
|
35
|
+
* @returns StreamWriter instance
|
|
36
|
+
*
|
|
37
|
+
* @example
|
|
38
|
+
* ```typescript
|
|
39
|
+
* import { createStreamWriter } from "@outfitter/cli/streaming";
|
|
40
|
+
*
|
|
41
|
+
* const writer = createStreamWriter();
|
|
42
|
+
*
|
|
43
|
+
* writer.write("Processing...");
|
|
44
|
+
* // Do some work
|
|
45
|
+
* writer.update("Processing... 50%");
|
|
46
|
+
* // Do more work
|
|
47
|
+
* writer.update("Processing... 100%");
|
|
48
|
+
* writer.persist();
|
|
49
|
+
* writer.write("Done!");
|
|
50
|
+
* ```
|
|
51
|
+
*/
|
|
52
|
+
declare function createStreamWriter(options?: StreamWriterOptions): StreamWriter;
|
|
53
|
+
export { WritableStream, StreamWriterOptions, StreamWriter, createStreamWriter };
|
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
// @bun
|
|
2
|
+
import {
|
|
3
|
+
BORDERS,
|
|
4
|
+
init_borders
|
|
5
|
+
} from "./cli-85fg2vr5.js";
|
|
6
|
+
import {
|
|
7
|
+
ANSI,
|
|
8
|
+
init_colors
|
|
9
|
+
} from "./cli-9nbyj2bt.js";
|
|
10
|
+
|
|
11
|
+
// packages/cli/src/theme/presets/default.ts
|
|
12
|
+
init_borders();
|
|
13
|
+
init_colors();
|
|
14
|
+
var defaultTheme = {
|
|
15
|
+
name: "default",
|
|
16
|
+
border: "single",
|
|
17
|
+
borderChars: BORDERS.single,
|
|
18
|
+
treeGuide: "single",
|
|
19
|
+
delimiter: "bullet",
|
|
20
|
+
markers: {
|
|
21
|
+
default: { type: "indicator", category: "marker", name: "circleOutline" },
|
|
22
|
+
current: { type: "indicator", category: "marker", name: "circleDot" },
|
|
23
|
+
focused: { type: "indicator", category: "marker", name: "pointer" },
|
|
24
|
+
checked: { type: "indicator", category: "marker", name: "checkboxChecked" },
|
|
25
|
+
disabled: { type: "indicator", category: "marker", name: "dash" },
|
|
26
|
+
success: { type: "indicator", category: "status", name: "success" },
|
|
27
|
+
warning: { type: "indicator", category: "status", name: "warning" },
|
|
28
|
+
error: { type: "indicator", category: "status", name: "error" },
|
|
29
|
+
info: { type: "indicator", category: "status", name: "info" }
|
|
30
|
+
},
|
|
31
|
+
listBullet: { unicode: "\u2022", fallback: "-" },
|
|
32
|
+
checkbox: {
|
|
33
|
+
checked: { unicode: "\u2611", fallback: "[x]" },
|
|
34
|
+
unchecked: { unicode: "\u2610", fallback: "[ ]" }
|
|
35
|
+
},
|
|
36
|
+
colors: {
|
|
37
|
+
success: ANSI.green,
|
|
38
|
+
warning: ANSI.yellow,
|
|
39
|
+
error: ANSI.red,
|
|
40
|
+
info: ANSI.blue,
|
|
41
|
+
primary: "",
|
|
42
|
+
secondary: ANSI.gray,
|
|
43
|
+
muted: ANSI.dim,
|
|
44
|
+
accent: ANSI.cyan,
|
|
45
|
+
highlight: ANSI.bold,
|
|
46
|
+
link: `${ANSI.cyan}${ANSI.underline}`,
|
|
47
|
+
destructive: ANSI.brightRed,
|
|
48
|
+
subtle: `${ANSI.dim}${ANSI.gray}`
|
|
49
|
+
},
|
|
50
|
+
spacing: {
|
|
51
|
+
boxPadding: 1,
|
|
52
|
+
listIndent: 2,
|
|
53
|
+
stackGap: 0,
|
|
54
|
+
horizontalGap: 1
|
|
55
|
+
},
|
|
56
|
+
spinner: "dots"
|
|
57
|
+
};
|
|
58
|
+
|
|
59
|
+
export { defaultTheme };
|
|
@@ -0,0 +1,128 @@
|
|
|
1
|
+
import { CaseMode, SeparatorStyle } from "./cli-6bztk73z";
|
|
2
|
+
import { Theme } from "./cli-xsaheemc";
|
|
3
|
+
/**
|
|
4
|
+
* Options for creating a demo section.
|
|
5
|
+
*/
|
|
6
|
+
interface SectionOptions {
|
|
7
|
+
/** Separator character style (default: "─") */
|
|
8
|
+
separator?: SeparatorStyle;
|
|
9
|
+
/** Case transformation (default: "title") */
|
|
10
|
+
case?: CaseMode;
|
|
11
|
+
}
|
|
12
|
+
/**
|
|
13
|
+
* Options for creating a subsection.
|
|
14
|
+
*/
|
|
15
|
+
interface SubsectionOptions {
|
|
16
|
+
/** Separator character style (default: "─") */
|
|
17
|
+
separator?: SeparatorStyle;
|
|
18
|
+
/** Case transformation (default: "title") */
|
|
19
|
+
case?: CaseMode;
|
|
20
|
+
}
|
|
21
|
+
/**
|
|
22
|
+
* Creates a demo section heading.
|
|
23
|
+
*
|
|
24
|
+
* Sections are major divisions in a demo, rendered with title case text
|
|
25
|
+
* and thin Unicode line separators by default.
|
|
26
|
+
*
|
|
27
|
+
* @param title - The section title
|
|
28
|
+
* @param options - Optional rendering options
|
|
29
|
+
* @returns Formatted section heading string
|
|
30
|
+
*
|
|
31
|
+
* @example
|
|
32
|
+
* ```typescript
|
|
33
|
+
* import { demoSection } from "@outfitter/cli/demo";
|
|
34
|
+
*
|
|
35
|
+
* console.log(demoSection("Theme Colors"));
|
|
36
|
+
* // Theme Colors
|
|
37
|
+
* // ────────────
|
|
38
|
+
* ```
|
|
39
|
+
*/
|
|
40
|
+
declare function demoSection(title: string, options?: SectionOptions): string;
|
|
41
|
+
/**
|
|
42
|
+
* Creates a demo subsection heading.
|
|
43
|
+
*
|
|
44
|
+
* Subsections are minor divisions within a section, rendered with title case
|
|
45
|
+
* text and thin Unicode line separators by default.
|
|
46
|
+
*
|
|
47
|
+
* @param title - The subsection title
|
|
48
|
+
* @param options - Optional rendering options
|
|
49
|
+
* @returns Formatted subsection heading string
|
|
50
|
+
*
|
|
51
|
+
* @example
|
|
52
|
+
* ```typescript
|
|
53
|
+
* import { demoSubsection } from "@outfitter/cli/demo";
|
|
54
|
+
*
|
|
55
|
+
* console.log(demoSubsection("Status"));
|
|
56
|
+
* // Status
|
|
57
|
+
* // ──────
|
|
58
|
+
* ```
|
|
59
|
+
*/
|
|
60
|
+
declare function demoSubsection(title: string, options?: SubsectionOptions): string;
|
|
61
|
+
/**
|
|
62
|
+
* Creates a code block for demo sections.
|
|
63
|
+
*
|
|
64
|
+
* Code blocks are displayed when `showCode` is enabled and provide
|
|
65
|
+
* usage examples for the primitives being demonstrated.
|
|
66
|
+
*
|
|
67
|
+
* @param lines - Lines of code to display
|
|
68
|
+
* @param show - Whether to show the code block (default: true)
|
|
69
|
+
* @returns Array of code lines, or empty array if hidden
|
|
70
|
+
*
|
|
71
|
+
* @example
|
|
72
|
+
* ```typescript
|
|
73
|
+
* import { codeBlock } from "@outfitter/cli/demo";
|
|
74
|
+
*
|
|
75
|
+
* const code = codeBlock([
|
|
76
|
+
* 'import { renderBox } from "@outfitter/cli/render";',
|
|
77
|
+
* "",
|
|
78
|
+
* 'renderBox("Hello")',
|
|
79
|
+
* ], true);
|
|
80
|
+
* ```
|
|
81
|
+
*/
|
|
82
|
+
declare function codeBlock(lines: string[], show?: boolean): string[];
|
|
83
|
+
/**
|
|
84
|
+
* Creates a description line styled with muted theme.
|
|
85
|
+
*
|
|
86
|
+
* Descriptions provide contextual information about a demo section
|
|
87
|
+
* when `showDescriptions` is enabled.
|
|
88
|
+
*
|
|
89
|
+
* @param text - The description text
|
|
90
|
+
* @param theme - Theme for styling
|
|
91
|
+
* @param show - Whether to show the description (default: true)
|
|
92
|
+
* @returns Array with styled description, or empty array if hidden
|
|
93
|
+
*
|
|
94
|
+
* @example
|
|
95
|
+
* ```typescript
|
|
96
|
+
* import { description } from "@outfitter/cli/demo";
|
|
97
|
+
*
|
|
98
|
+
* const desc = description(
|
|
99
|
+
* "Control padding per side with an object.",
|
|
100
|
+
* theme,
|
|
101
|
+
* true
|
|
102
|
+
* );
|
|
103
|
+
* ```
|
|
104
|
+
*/
|
|
105
|
+
declare function description(text: string, theme: Theme, show?: boolean): string[];
|
|
106
|
+
/**
|
|
107
|
+
* Joins demo content with vertical spacing.
|
|
108
|
+
*
|
|
109
|
+
* Wraps `joinVertical` with demo-appropriate defaults.
|
|
110
|
+
*
|
|
111
|
+
* @param blocks - Content blocks to join
|
|
112
|
+
* @param gap - Lines of spacing between blocks (default: 1)
|
|
113
|
+
* @returns Combined string with blocks stacked
|
|
114
|
+
*
|
|
115
|
+
* @example
|
|
116
|
+
* ```typescript
|
|
117
|
+
* import { demoSection, demoContent } from "@outfitter/cli/demo";
|
|
118
|
+
*
|
|
119
|
+
* const output = demoContent([
|
|
120
|
+
* demoSection("Colors"),
|
|
121
|
+
* "Color examples here...",
|
|
122
|
+
* demoSection("Borders"),
|
|
123
|
+
* "Border examples here...",
|
|
124
|
+
* ]);
|
|
125
|
+
* ```
|
|
126
|
+
*/
|
|
127
|
+
declare function demoContent(blocks: string[], gap?: number): string;
|
|
128
|
+
export { SectionOptions, SubsectionOptions, demoSection, demoSubsection, codeBlock, description, demoContent };
|
|
@@ -1,4 +1,8 @@
|
|
|
1
1
|
// @bun
|
|
2
|
+
import {
|
|
3
|
+
__esm
|
|
4
|
+
} from "./cli-v1tzwxkt.js";
|
|
5
|
+
|
|
2
6
|
// packages/cli/src/terminal/detection.ts
|
|
3
7
|
import { getEnvBoolean } from "@outfitter/config";
|
|
4
8
|
function getEnvValue(key) {
|
|
@@ -66,5 +70,6 @@ function isInteractive(options) {
|
|
|
66
70
|
const isTTY = options?.isTTY ?? process.stdout.isTTY ?? false;
|
|
67
71
|
return isTTY;
|
|
68
72
|
}
|
|
73
|
+
var init_detection = () => {};
|
|
69
74
|
|
|
70
|
-
export { getEnvValue, hasNoColorEnv, resolveForceColorEnv, resolveColorEnv, supportsColor, getTerminalWidth, isInteractive };
|
|
75
|
+
export { getEnvValue, hasNoColorEnv, resolveForceColorEnv, resolveColorEnv, supportsColor, getTerminalWidth, isInteractive, init_detection };
|
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
// @bun
|
|
2
|
+
import {
|
|
3
|
+
renderProgress
|
|
4
|
+
} from "./cli-bc17qeh2.js";
|
|
5
|
+
import {
|
|
6
|
+
demoSection
|
|
7
|
+
} from "./cli-34fqr7bp.js";
|
|
8
|
+
|
|
9
|
+
// packages/cli/src/demo/renderers/progress.ts
|
|
10
|
+
function renderProgressDemo(config, _theme) {
|
|
11
|
+
const showCode = config.showCode ?? true;
|
|
12
|
+
const lines = [];
|
|
13
|
+
lines.push(demoSection("Basic Progress Bar"));
|
|
14
|
+
lines.push("");
|
|
15
|
+
if (showCode) {
|
|
16
|
+
lines.push('import { renderProgress } from "@outfitter/cli/render";');
|
|
17
|
+
lines.push("");
|
|
18
|
+
}
|
|
19
|
+
const percentages = [0, 25, 50, 75, 100];
|
|
20
|
+
for (const pct of percentages) {
|
|
21
|
+
const bar = renderProgress({ current: pct, total: 100 });
|
|
22
|
+
lines.push(`${pct.toString().padStart(3)}% ${bar}`);
|
|
23
|
+
}
|
|
24
|
+
lines.push("");
|
|
25
|
+
lines.push(demoSection("With Percentage Display"));
|
|
26
|
+
lines.push("");
|
|
27
|
+
if (showCode) {
|
|
28
|
+
lines.push("renderProgress({ current: 75, total: 100, showPercent: true })");
|
|
29
|
+
lines.push("");
|
|
30
|
+
}
|
|
31
|
+
lines.push(renderProgress({ current: 75, total: 100, showPercent: true }));
|
|
32
|
+
lines.push("");
|
|
33
|
+
lines.push(demoSection("Custom Width"));
|
|
34
|
+
lines.push("");
|
|
35
|
+
const widths = [10, 20, 30, 40];
|
|
36
|
+
for (const width of widths) {
|
|
37
|
+
if (showCode) {
|
|
38
|
+
lines.push(`renderProgress({ current: 50, total: 100, width: ${width} })`);
|
|
39
|
+
}
|
|
40
|
+
const bar = renderProgress({ current: 50, total: 100, width });
|
|
41
|
+
lines.push(` ${bar}`);
|
|
42
|
+
lines.push("");
|
|
43
|
+
}
|
|
44
|
+
lines.push(demoSection("Edge Cases"));
|
|
45
|
+
lines.push("");
|
|
46
|
+
lines.push("Empty (0%):");
|
|
47
|
+
lines.push(` ${renderProgress({ current: 0, total: 100 })}`);
|
|
48
|
+
lines.push("");
|
|
49
|
+
lines.push("Full (100%):");
|
|
50
|
+
lines.push(` ${renderProgress({ current: 100, total: 100 })}`);
|
|
51
|
+
lines.push("");
|
|
52
|
+
lines.push("Over 100% (capped):");
|
|
53
|
+
lines.push(` ${renderProgress({ current: 150, total: 100, showPercent: true })}`);
|
|
54
|
+
lines.push("");
|
|
55
|
+
lines.push("Negative (floored to 0%):");
|
|
56
|
+
lines.push(` ${renderProgress({ current: -10, total: 100, showPercent: true })}`);
|
|
57
|
+
return lines.join(`
|
|
58
|
+
`);
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
export { renderProgressDemo };
|
|
@@ -0,0 +1,91 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Spinner rendering utilities.
|
|
3
|
+
*
|
|
4
|
+
* Provides animated spinner frames for async operations with
|
|
5
|
+
* multiple styles and graceful degradation for non-TTY contexts.
|
|
6
|
+
*
|
|
7
|
+
* @packageDocumentation
|
|
8
|
+
*/
|
|
9
|
+
/**
|
|
10
|
+
* Available spinner animation styles.
|
|
11
|
+
*
|
|
12
|
+
* - `dots`: Braille dots animation (default, smooth)
|
|
13
|
+
* - `line`: Classic ASCII spinner (-\|/)
|
|
14
|
+
* - `arc`: Corner arc rotation
|
|
15
|
+
* - `circle`: Half-filled circle rotation
|
|
16
|
+
* - `bounce`: Bouncing dot (vertical)
|
|
17
|
+
* - `ping`: Bouncing dot in brackets (horizontal)
|
|
18
|
+
*/
|
|
19
|
+
type SpinnerStyle = "dots" | "line" | "arc" | "circle" | "bounce" | "ping";
|
|
20
|
+
/**
|
|
21
|
+
* Spinner animation frame definition.
|
|
22
|
+
*/
|
|
23
|
+
interface SpinnerFrames {
|
|
24
|
+
/** Array of characters to cycle through */
|
|
25
|
+
frames: string[];
|
|
26
|
+
/** Milliseconds between frame changes */
|
|
27
|
+
interval: number;
|
|
28
|
+
}
|
|
29
|
+
/**
|
|
30
|
+
* Predefined spinner animations.
|
|
31
|
+
*
|
|
32
|
+
* @example
|
|
33
|
+
* ```typescript
|
|
34
|
+
* const dotsSpinner = SPINNERS.dots;
|
|
35
|
+
* console.log(dotsSpinner.frames[0]); // "⠋"
|
|
36
|
+
* console.log(dotsSpinner.interval); // 80
|
|
37
|
+
* ```
|
|
38
|
+
*/
|
|
39
|
+
declare const SPINNERS: Record<SpinnerStyle, SpinnerFrames>;
|
|
40
|
+
/**
|
|
41
|
+
* Gets the spinner frame for a given elapsed time.
|
|
42
|
+
*
|
|
43
|
+
* Calculates which frame to display based on elapsed milliseconds
|
|
44
|
+
* and the spinner's interval setting. Automatically wraps around
|
|
45
|
+
* when the elapsed time exceeds a full cycle.
|
|
46
|
+
*
|
|
47
|
+
* @param style - The spinner style to use
|
|
48
|
+
* @param elapsed - Elapsed time in milliseconds since spinner started
|
|
49
|
+
* @returns The frame character to display
|
|
50
|
+
*
|
|
51
|
+
* @example
|
|
52
|
+
* ```typescript
|
|
53
|
+
* // Get frame at start
|
|
54
|
+
* getSpinnerFrame("dots", 0); // "⠋"
|
|
55
|
+
*
|
|
56
|
+
* // Get frame after 160ms
|
|
57
|
+
* getSpinnerFrame("dots", 160); // "⠹" (third frame)
|
|
58
|
+
*
|
|
59
|
+
* // Frames wrap around automatically
|
|
60
|
+
* const fullCycle = SPINNERS.dots.interval * SPINNERS.dots.frames.length;
|
|
61
|
+
* getSpinnerFrame("dots", fullCycle); // "⠋" (back to first)
|
|
62
|
+
* ```
|
|
63
|
+
*/
|
|
64
|
+
declare function getSpinnerFrame(style: SpinnerStyle, elapsed: number): string;
|
|
65
|
+
/**
|
|
66
|
+
* Renders a static spinner frame with optional message.
|
|
67
|
+
*
|
|
68
|
+
* This is the non-interactive version for logging and non-TTY contexts.
|
|
69
|
+
* For animated spinners, use the elapsed parameter with `getSpinnerFrame()`.
|
|
70
|
+
*
|
|
71
|
+
* @param style - The spinner style to use
|
|
72
|
+
* @param message - Optional message to display after the spinner
|
|
73
|
+
* @returns Formatted spinner string
|
|
74
|
+
*
|
|
75
|
+
* @example
|
|
76
|
+
* ```typescript
|
|
77
|
+
* // Simple spinner
|
|
78
|
+
* console.log(renderSpinner("dots"));
|
|
79
|
+
* // "⠋"
|
|
80
|
+
*
|
|
81
|
+
* // Spinner with message
|
|
82
|
+
* console.log(renderSpinner("dots", "Loading..."));
|
|
83
|
+
* // "⠋ Loading..."
|
|
84
|
+
*
|
|
85
|
+
* // For logs (non-TTY)
|
|
86
|
+
* logger.info(renderSpinner("line", "Fetching data"));
|
|
87
|
+
* // "- Fetching data"
|
|
88
|
+
* ```
|
|
89
|
+
*/
|
|
90
|
+
declare function renderSpinner(style: SpinnerStyle, message?: string): string;
|
|
91
|
+
export { SpinnerStyle, SpinnerFrames, SPINNERS, getSpinnerFrame, renderSpinner };
|