@zaly/tui 0.0.4

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 (228) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +59 -0
  3. package/assets/schemas/theme.schema.json +899 -0
  4. package/assets/themes/LICENSE-tokyonight.txt +201 -0
  5. package/assets/themes/NOTICES.md +69 -0
  6. package/assets/themes/ayu-dark.json +119 -0
  7. package/assets/themes/catppuccin-frappe.json +124 -0
  8. package/assets/themes/catppuccin-latte.json +124 -0
  9. package/assets/themes/catppuccin-macchiato.json +124 -0
  10. package/assets/themes/catppuccin-mocha.json +124 -0
  11. package/assets/themes/dracula-soft.json +119 -0
  12. package/assets/themes/dracula.json +119 -0
  13. package/assets/themes/everforest-dark.json +118 -0
  14. package/assets/themes/everforest-light.json +118 -0
  15. package/assets/themes/github-dark.json +123 -0
  16. package/assets/themes/github-light.json +123 -0
  17. package/assets/themes/gruvbox-dark-medium.json +112 -0
  18. package/assets/themes/kanagawa-dragon.json +115 -0
  19. package/assets/themes/kanagawa-wave.json +115 -0
  20. package/assets/themes/material-theme-palenight.json +114 -0
  21. package/assets/themes/min-dark.json +55 -0
  22. package/assets/themes/min-light.json +59 -0
  23. package/assets/themes/monokai.json +116 -0
  24. package/assets/themes/night-owl.json +116 -0
  25. package/assets/themes/nord.json +101 -0
  26. package/assets/themes/one-dark-pro.json +110 -0
  27. package/assets/themes/one-light.json +108 -0
  28. package/assets/themes/poimandres.json +123 -0
  29. package/assets/themes/rose-pine.json +98 -0
  30. package/assets/themes/solarized-dark.json +116 -0
  31. package/assets/themes/solarized-light.json +116 -0
  32. package/assets/themes/synthwave-84.json +100 -0
  33. package/assets/themes/tokyonight-day.json +157 -0
  34. package/assets/themes/tokyonight-moon.json +157 -0
  35. package/assets/themes/tokyonight-night.json +157 -0
  36. package/assets/themes/tokyonight-storm.json +157 -0
  37. package/assets/themes/vesper.json +103 -0
  38. package/assets/themes/vitesse-dark.json +126 -0
  39. package/assets/themes/vitesse-light.json +126 -0
  40. package/dist/ansi-Clq0ozyA.mjs +206 -0
  41. package/dist/ansi-Clq0ozyA.mjs.map +1 -0
  42. package/dist/ansi.d.mts +48 -0
  43. package/dist/ansi.d.mts.map +1 -0
  44. package/dist/ansi.mjs +2 -0
  45. package/dist/autocomplete-Dfw-yQDa.d.mts +100 -0
  46. package/dist/autocomplete-Dfw-yQDa.d.mts.map +1 -0
  47. package/dist/box-DyaByEiG.mjs +386 -0
  48. package/dist/box-DyaByEiG.mjs.map +1 -0
  49. package/dist/builder-D49ECBEf.mjs +385 -0
  50. package/dist/builder-D49ECBEf.mjs.map +1 -0
  51. package/dist/callbacks-CNjGNxVw.mjs +279 -0
  52. package/dist/callbacks-CNjGNxVw.mjs.map +1 -0
  53. package/dist/client-D6C_uczF.mjs +142 -0
  54. package/dist/client-D6C_uczF.mjs.map +1 -0
  55. package/dist/clipboard.d.mts +104 -0
  56. package/dist/clipboard.d.mts.map +1 -0
  57. package/dist/clipboard.mjs +404 -0
  58. package/dist/clipboard.mjs.map +1 -0
  59. package/dist/flex-Bguo-fUe.mjs +202 -0
  60. package/dist/flex-Bguo-fUe.mjs.map +1 -0
  61. package/dist/image-Cm5T-uw-.mjs +108 -0
  62. package/dist/image-Cm5T-uw-.mjs.map +1 -0
  63. package/dist/image.d.mts +123 -0
  64. package/dist/image.d.mts.map +1 -0
  65. package/dist/image.mjs +2 -0
  66. package/dist/index.d.mts +64 -0
  67. package/dist/index.d.mts.map +1 -0
  68. package/dist/index.mjs +222 -0
  69. package/dist/index.mjs.map +1 -0
  70. package/dist/input-B5Vy-iaa.d.mts +141 -0
  71. package/dist/input-B5Vy-iaa.d.mts.map +1 -0
  72. package/dist/inspect-D1d9t-ni.mjs +101 -0
  73. package/dist/inspect-D1d9t-ni.mjs.map +1 -0
  74. package/dist/inspect-D6FW_QUo.d.mts +67 -0
  75. package/dist/inspect-D6FW_QUo.d.mts.map +1 -0
  76. package/dist/kitty-JbCJC0iQ.mjs +673 -0
  77. package/dist/kitty-JbCJC0iQ.mjs.map +1 -0
  78. package/dist/markdown.d.mts +24 -0
  79. package/dist/markdown.d.mts.map +1 -0
  80. package/dist/markdown.mjs +2 -0
  81. package/dist/md.bun.d.mts +14 -0
  82. package/dist/md.bun.d.mts.map +1 -0
  83. package/dist/md.bun.mjs +28 -0
  84. package/dist/md.bun.mjs.map +1 -0
  85. package/dist/md.node.d.mts +14 -0
  86. package/dist/md.node.d.mts.map +1 -0
  87. package/dist/md.node.mjs +126 -0
  88. package/dist/md.node.mjs.map +1 -0
  89. package/dist/node-BZ7f6HzU.mjs +316 -0
  90. package/dist/node-BZ7f6HzU.mjs.map +1 -0
  91. package/dist/picker-D8OLb6kZ.d.mts +36 -0
  92. package/dist/picker-D8OLb6kZ.d.mts.map +1 -0
  93. package/dist/picker-ndVVt6qF.mjs +621 -0
  94. package/dist/picker-ndVVt6qF.mjs.map +1 -0
  95. package/dist/queries-DH3bj74K.d.mts +1963 -0
  96. package/dist/queries-DH3bj74K.d.mts.map +1 -0
  97. package/dist/reactive-f7NpAi69.mjs +623 -0
  98. package/dist/reactive-f7NpAi69.mjs.map +1 -0
  99. package/dist/registry-U654j61Y.mjs +356 -0
  100. package/dist/registry-U654j61Y.mjs.map +1 -0
  101. package/dist/render-DxVLqqB9.mjs +74 -0
  102. package/dist/render-DxVLqqB9.mjs.map +1 -0
  103. package/dist/renderer-CdLCkJB-.mjs +42 -0
  104. package/dist/renderer-CdLCkJB-.mjs.map +1 -0
  105. package/dist/renderer-CxL4xbkl.mjs +2644 -0
  106. package/dist/renderer-CxL4xbkl.mjs.map +1 -0
  107. package/dist/rolldown-runtime-D7D4PA-g.mjs +13 -0
  108. package/dist/search-FvGnswRl.d.mts +49 -0
  109. package/dist/search-FvGnswRl.d.mts.map +1 -0
  110. package/dist/select-CbmAZdpt.d.mts +116 -0
  111. package/dist/select-CbmAZdpt.d.mts.map +1 -0
  112. package/dist/services/logger.d.mts +2 -0
  113. package/dist/services/logger.mjs +71 -0
  114. package/dist/services/logger.mjs.map +1 -0
  115. package/dist/services/notifier.d.mts +17 -0
  116. package/dist/services/notifier.d.mts.map +1 -0
  117. package/dist/services/notifier.mjs +71 -0
  118. package/dist/services/notifier.mjs.map +1 -0
  119. package/dist/services/picker.d.mts +36 -0
  120. package/dist/services/picker.d.mts.map +1 -0
  121. package/dist/services/picker.mjs +137 -0
  122. package/dist/services/picker.mjs.map +1 -0
  123. package/dist/services/prompt.d.mts +30 -0
  124. package/dist/services/prompt.d.mts.map +1 -0
  125. package/dist/services/prompt.mjs +83 -0
  126. package/dist/services/prompt.mjs.map +1 -0
  127. package/dist/shiki-BrjVUkeh.mjs +423 -0
  128. package/dist/shiki-BrjVUkeh.mjs.map +1 -0
  129. package/dist/size-D8JogYLy.mjs +34 -0
  130. package/dist/size-D8JogYLy.mjs.map +1 -0
  131. package/dist/style.d.mts +10 -0
  132. package/dist/style.d.mts.map +1 -0
  133. package/dist/style.mjs +4 -0
  134. package/dist/text.d.mts +33 -0
  135. package/dist/text.d.mts.map +1 -0
  136. package/dist/text.mjs +111 -0
  137. package/dist/text.mjs.map +1 -0
  138. package/dist/theme.config-CU3B50HN.mjs +832 -0
  139. package/dist/theme.config-CU3B50HN.mjs.map +1 -0
  140. package/dist/themes.d.mts +113 -0
  141. package/dist/themes.d.mts.map +1 -0
  142. package/dist/themes.mjs +2 -0
  143. package/dist/tree-C28QOVIK.d.mts +23 -0
  144. package/dist/tree-C28QOVIK.d.mts.map +1 -0
  145. package/dist/types-B9Eh7k2v.d.mts +212 -0
  146. package/dist/types-B9Eh7k2v.d.mts.map +1 -0
  147. package/dist/types-D3jk1rtk.d.mts +140 -0
  148. package/dist/types-D3jk1rtk.d.mts.map +1 -0
  149. package/dist/utils-3M4D_AXZ.mjs +40 -0
  150. package/dist/utils-3M4D_AXZ.mjs.map +1 -0
  151. package/dist/widgets/autocomplete.d.mts +2 -0
  152. package/dist/widgets/autocomplete.mjs +165 -0
  153. package/dist/widgets/autocomplete.mjs.map +1 -0
  154. package/dist/widgets/box.d.mts +2 -0
  155. package/dist/widgets/box.mjs +2 -0
  156. package/dist/widgets/code.d.mts +48 -0
  157. package/dist/widgets/code.d.mts.map +1 -0
  158. package/dist/widgets/code.mjs +59 -0
  159. package/dist/widgets/code.mjs.map +1 -0
  160. package/dist/widgets/completions/actions.d.mts +41 -0
  161. package/dist/widgets/completions/actions.d.mts.map +1 -0
  162. package/dist/widgets/completions/actions.mjs +48 -0
  163. package/dist/widgets/completions/actions.mjs.map +1 -0
  164. package/dist/widgets/completions/files.d.mts +29 -0
  165. package/dist/widgets/completions/files.d.mts.map +1 -0
  166. package/dist/widgets/completions/files.mjs +42 -0
  167. package/dist/widgets/completions/files.mjs.map +1 -0
  168. package/dist/widgets/completions/github.d.mts +64 -0
  169. package/dist/widgets/completions/github.d.mts.map +1 -0
  170. package/dist/widgets/completions/github.mjs +137 -0
  171. package/dist/widgets/completions/github.mjs.map +1 -0
  172. package/dist/widgets/completions/index.d.mts +4 -0
  173. package/dist/widgets/completions/index.mjs +4 -0
  174. package/dist/widgets/diff.d.mts +57 -0
  175. package/dist/widgets/diff.d.mts.map +1 -0
  176. package/dist/widgets/diff.mjs +199 -0
  177. package/dist/widgets/diff.mjs.map +1 -0
  178. package/dist/widgets/divider.d.mts +11 -0
  179. package/dist/widgets/divider.d.mts.map +1 -0
  180. package/dist/widgets/divider.mjs +9 -0
  181. package/dist/widgets/divider.mjs.map +1 -0
  182. package/dist/widgets/image.d.mts +37 -0
  183. package/dist/widgets/image.d.mts.map +1 -0
  184. package/dist/widgets/image.mjs +77 -0
  185. package/dist/widgets/image.mjs.map +1 -0
  186. package/dist/widgets/input.d.mts +2 -0
  187. package/dist/widgets/input.mjs +497 -0
  188. package/dist/widgets/input.mjs.map +1 -0
  189. package/dist/widgets/log.d.mts +2 -0
  190. package/dist/widgets/log.mjs +130 -0
  191. package/dist/widgets/log.mjs.map +1 -0
  192. package/dist/widgets/markdown.d.mts +45 -0
  193. package/dist/widgets/markdown.d.mts.map +1 -0
  194. package/dist/widgets/markdown.mjs +124 -0
  195. package/dist/widgets/markdown.mjs.map +1 -0
  196. package/dist/widgets/overlay.d.mts +2 -0
  197. package/dist/widgets/overlay.mjs +18 -0
  198. package/dist/widgets/overlay.mjs.map +1 -0
  199. package/dist/widgets/picker.d.mts +2 -0
  200. package/dist/widgets/picker.mjs +2 -0
  201. package/dist/widgets/progress.d.mts +48 -0
  202. package/dist/widgets/progress.d.mts.map +1 -0
  203. package/dist/widgets/progress.mjs +48 -0
  204. package/dist/widgets/progress.mjs.map +1 -0
  205. package/dist/widgets/select.d.mts +2 -0
  206. package/dist/widgets/select.mjs +195 -0
  207. package/dist/widgets/select.mjs.map +1 -0
  208. package/dist/widgets/show.d.mts +55 -0
  209. package/dist/widgets/show.d.mts.map +1 -0
  210. package/dist/widgets/show.mjs +85 -0
  211. package/dist/widgets/show.mjs.map +1 -0
  212. package/dist/widgets/spinner.d.mts +65 -0
  213. package/dist/widgets/spinner.d.mts.map +1 -0
  214. package/dist/widgets/spinner.mjs +147 -0
  215. package/dist/widgets/spinner.mjs.map +1 -0
  216. package/dist/widgets/text.d.mts +2 -0
  217. package/dist/widgets/text.mjs +32 -0
  218. package/dist/widgets/text.mjs.map +1 -0
  219. package/dist/widgets/tree.d.mts +2 -0
  220. package/dist/widgets/tree.mjs +73 -0
  221. package/dist/widgets/tree.mjs.map +1 -0
  222. package/dist/widgets/widget.d.mts +49 -0
  223. package/dist/widgets/widget.d.mts.map +1 -0
  224. package/dist/widgets/widget.mjs +40 -0
  225. package/dist/widgets/widget.mjs.map +1 -0
  226. package/dist/worker-DjHuQSbY.mjs +27 -0
  227. package/dist/worker-DjHuQSbY.mjs.map +1 -0
  228. package/package.json +117 -0
@@ -0,0 +1,673 @@
1
+ import { isSSH } from "@zaly/shared/env";
2
+ //#region src/image/kitty.ts
3
+ const DIACRITICS = [
4
+ 773,
5
+ 781,
6
+ 782,
7
+ 784,
8
+ 786,
9
+ 829,
10
+ 830,
11
+ 831,
12
+ 838,
13
+ 842,
14
+ 843,
15
+ 844,
16
+ 848,
17
+ 849,
18
+ 850,
19
+ 855,
20
+ 859,
21
+ 867,
22
+ 868,
23
+ 869,
24
+ 870,
25
+ 871,
26
+ 872,
27
+ 873,
28
+ 874,
29
+ 875,
30
+ 876,
31
+ 877,
32
+ 878,
33
+ 879,
34
+ 1155,
35
+ 1156,
36
+ 1157,
37
+ 1158,
38
+ 1159,
39
+ 1426,
40
+ 1427,
41
+ 1428,
42
+ 1429,
43
+ 1431,
44
+ 1432,
45
+ 1433,
46
+ 1436,
47
+ 1437,
48
+ 1438,
49
+ 1439,
50
+ 1440,
51
+ 1441,
52
+ 1448,
53
+ 1449,
54
+ 1451,
55
+ 1452,
56
+ 1455,
57
+ 1476,
58
+ 1552,
59
+ 1553,
60
+ 1554,
61
+ 1555,
62
+ 1556,
63
+ 1557,
64
+ 1558,
65
+ 1559,
66
+ 1623,
67
+ 1624,
68
+ 1625,
69
+ 1626,
70
+ 1627,
71
+ 1629,
72
+ 1630,
73
+ 1750,
74
+ 1751,
75
+ 1752,
76
+ 1753,
77
+ 1754,
78
+ 1755,
79
+ 1756,
80
+ 1759,
81
+ 1760,
82
+ 1761,
83
+ 1762,
84
+ 1764,
85
+ 1767,
86
+ 1768,
87
+ 1771,
88
+ 1772,
89
+ 1840,
90
+ 1842,
91
+ 1843,
92
+ 1845,
93
+ 1846,
94
+ 1850,
95
+ 1853,
96
+ 1855,
97
+ 1856,
98
+ 1857,
99
+ 1859,
100
+ 1861,
101
+ 1863,
102
+ 1865,
103
+ 1866,
104
+ 2027,
105
+ 2028,
106
+ 2029,
107
+ 2030,
108
+ 2031,
109
+ 2032,
110
+ 2033,
111
+ 2035,
112
+ 2070,
113
+ 2071,
114
+ 2072,
115
+ 2073,
116
+ 2075,
117
+ 2076,
118
+ 2077,
119
+ 2078,
120
+ 2079,
121
+ 2080,
122
+ 2081,
123
+ 2082,
124
+ 2083,
125
+ 2085,
126
+ 2086,
127
+ 2087,
128
+ 2089,
129
+ 2090,
130
+ 2091,
131
+ 2092,
132
+ 2093,
133
+ 2385,
134
+ 2387,
135
+ 2388,
136
+ 3970,
137
+ 3971,
138
+ 3974,
139
+ 3975,
140
+ 4957,
141
+ 4958,
142
+ 4959,
143
+ 6109,
144
+ 6458,
145
+ 6679,
146
+ 6773,
147
+ 6774,
148
+ 6775,
149
+ 6776,
150
+ 6777,
151
+ 6778,
152
+ 6779,
153
+ 6780,
154
+ 7019,
155
+ 7021,
156
+ 7022,
157
+ 7023,
158
+ 7024,
159
+ 7025,
160
+ 7026,
161
+ 7027,
162
+ 7376,
163
+ 7377,
164
+ 7378,
165
+ 7386,
166
+ 7387,
167
+ 7392,
168
+ 7616,
169
+ 7617,
170
+ 7619,
171
+ 7620,
172
+ 7621,
173
+ 7622,
174
+ 7623,
175
+ 7624,
176
+ 7625,
177
+ 7627,
178
+ 7628,
179
+ 7633,
180
+ 7634,
181
+ 7635,
182
+ 7636,
183
+ 7637,
184
+ 7638,
185
+ 7639,
186
+ 7640,
187
+ 7641,
188
+ 7642,
189
+ 7643,
190
+ 7644,
191
+ 7645,
192
+ 7646,
193
+ 7647,
194
+ 7648,
195
+ 7649,
196
+ 7650,
197
+ 7651,
198
+ 7652,
199
+ 7653,
200
+ 7654,
201
+ 7678,
202
+ 8400,
203
+ 8401,
204
+ 8404,
205
+ 8405,
206
+ 8406,
207
+ 8407,
208
+ 8411,
209
+ 8412,
210
+ 8417,
211
+ 8423,
212
+ 8425,
213
+ 8432,
214
+ 11503,
215
+ 11504,
216
+ 11505,
217
+ 11744,
218
+ 11745,
219
+ 11746,
220
+ 11747,
221
+ 11748,
222
+ 11749,
223
+ 11750,
224
+ 11751,
225
+ 11752,
226
+ 11753,
227
+ 11754,
228
+ 11755,
229
+ 11756,
230
+ 11757,
231
+ 11758,
232
+ 11759,
233
+ 11760,
234
+ 11761,
235
+ 11762,
236
+ 11763,
237
+ 11764,
238
+ 11765,
239
+ 11766,
240
+ 11767,
241
+ 11768,
242
+ 11769,
243
+ 11770,
244
+ 11771,
245
+ 11772,
246
+ 11773,
247
+ 11774,
248
+ 11775,
249
+ 42607,
250
+ 42620,
251
+ 42621,
252
+ 42736,
253
+ 42737,
254
+ 43232,
255
+ 43233,
256
+ 43234,
257
+ 43235,
258
+ 43236,
259
+ 43237,
260
+ 43238,
261
+ 43239,
262
+ 43240,
263
+ 43241,
264
+ 43242,
265
+ 43243,
266
+ 43244,
267
+ 43245,
268
+ 43246,
269
+ 43247,
270
+ 43248,
271
+ 43249,
272
+ 43696,
273
+ 43698,
274
+ 43699,
275
+ 43703,
276
+ 43704,
277
+ 43710,
278
+ 43711,
279
+ 43713,
280
+ 65056,
281
+ 65057,
282
+ 65058,
283
+ 65059,
284
+ 65060,
285
+ 65061,
286
+ 65062,
287
+ 68111,
288
+ 68152,
289
+ 119173,
290
+ 119174,
291
+ 119175,
292
+ 119176,
293
+ 119177,
294
+ 119210,
295
+ 119211,
296
+ 119212,
297
+ 119213,
298
+ 119362,
299
+ 119363,
300
+ 119364
301
+ ].map((c) => String.fromCodePoint(c));
302
+ const PLACEHOLDER = String.fromCodePoint(1109742);
303
+ const CHUNK_SIZE = 4096;
304
+ const transmitCache = /* @__PURE__ */ new Map();
305
+ const known = {
306
+ ghostty: { inline: true },
307
+ kitty: { inline: true },
308
+ rio: { inline: false },
309
+ wezterm: { inline: false }
310
+ };
311
+ let prom = void 0;
312
+ let kitty = void 0;
313
+ const wrapTmux = (seq) => `\x1bPtmux;${seq.replaceAll("\x1B", "\x1B\x1B")}\x1b\\`;
314
+ /** Allocate a fresh 24-bit image id (1..0xFFFFFFFE). */
315
+ function allocateImageId() {
316
+ return Math.floor(Math.random() * 16777213) + 1;
317
+ }
318
+ /** Allocate a fresh 24-bit placement id. */
319
+ function allocatePlacementId() {
320
+ return Math.floor(Math.random() * 16777213) + 1;
321
+ }
322
+ var Kitty = class {
323
+ #support;
324
+ #wrap = (s) => s;
325
+ constructor(support) {
326
+ this.#support = support;
327
+ this.#wrap = support.wrap ?? ((s) => s);
328
+ }
329
+ get supported() {
330
+ return this.#support.ok;
331
+ }
332
+ get inline() {
333
+ return this.#support.ok && this.#support.inline === true;
334
+ }
335
+ /** Create a KGP request escape sequence */
336
+ request(attrs, data, opts = {}) {
337
+ const params = Object.entries(attrs).map(([k, v]) => `${k}=${v}`).join(",");
338
+ let encoded;
339
+ if (opts.base64 === false && typeof data === "string") encoded = data;
340
+ else if (data) encoded = toBase64(typeof data === "string" ? new TextEncoder().encode(data) : data);
341
+ const payload = encoded ? `;${encoded}` : "";
342
+ return this.#wrap(`\x1b_G${params}${payload}\x1b\\`);
343
+ }
344
+ /** Create a TerminalQuery that requests a KGP operation and parses the response. */
345
+ query(attrs, data, opts = {}) {
346
+ return {
347
+ match: (ev) => {
348
+ if (ev.kind !== "apc") return;
349
+ const kr = this.parse(ev.sequence);
350
+ if (!kr) return;
351
+ return {
352
+ ...ev,
353
+ ...kr
354
+ };
355
+ },
356
+ request: this.request(attrs, data, opts)
357
+ };
358
+ }
359
+ /** Probe the terminal for KGP support. Should return an error response. */
360
+ probe() {
361
+ return this.request({
362
+ i: 4294967290,
363
+ s: 10,
364
+ t: "s",
365
+ v: 2
366
+ }, "<error>");
367
+ }
368
+ /** Parse a KGP response escape sequence into a structured object. */
369
+ parse(res) {
370
+ if (!res.startsWith("\x1B_G") || !res.endsWith("\x1B\\")) return void 0;
371
+ const m = res.slice(3, -2).match(/^([^;]+);(.*)?$/);
372
+ if (!m) return void 0;
373
+ const [_, params, data] = m;
374
+ const attrs = {};
375
+ for (const pair of params.split(",")) {
376
+ const [k, v] = pair.split("=", 2);
377
+ if (k && v) attrs[k] = /^\d+$/.test(v) ? parseInt(v, 10) : v;
378
+ }
379
+ if (data === "OK") return {
380
+ attrs,
381
+ ok: true
382
+ };
383
+ const error = data?.match(/^([A-Z]+):\s*(.*)$/);
384
+ return {
385
+ attrs,
386
+ error: error ? {
387
+ code: error[1],
388
+ message: error[2]
389
+ } : {
390
+ code: "UNKNOWN",
391
+ message: data ?? ""
392
+ },
393
+ ok: false
394
+ };
395
+ }
396
+ placement(imageId, dims) {
397
+ if (!this.#support.ok) return;
398
+ if (this.#support.inline) return {
399
+ data: unicodePlaceholder(imageId, dims),
400
+ imageId,
401
+ inline: true,
402
+ seq: this.request({
403
+ U: 1,
404
+ a: "p",
405
+ c: dims.cols,
406
+ i: imageId,
407
+ q: 2,
408
+ r: dims.rows
409
+ })
410
+ };
411
+ const blank = " ".repeat(dims.cols);
412
+ const placementId = allocatePlacementId();
413
+ const seq = this.request({
414
+ a: "p",
415
+ i: imageId,
416
+ p: placementId,
417
+ C: 1,
418
+ c: dims.cols,
419
+ q: 2,
420
+ r: dims.rows
421
+ });
422
+ return {
423
+ data: Array.from({ length: dims.rows }).fill(blank),
424
+ imageId,
425
+ placementId,
426
+ seq
427
+ };
428
+ }
429
+ /** Delete an image and all its placements, or ALL images if `imageId` is omitted. */
430
+ deleteImage(imageId) {
431
+ return imageId === void 0 ? this.request({
432
+ a: "d",
433
+ d: "A",
434
+ q: 2
435
+ }) : this.request({
436
+ a: "d",
437
+ d: "I",
438
+ i: imageId,
439
+ q: 2
440
+ });
441
+ }
442
+ /** Delete a placement (keeps image data so it can be re-placed cheaply). */
443
+ deletePlacement(imageId, placementId) {
444
+ return this.request({
445
+ a: "d",
446
+ d: "i",
447
+ i: imageId,
448
+ p: placementId,
449
+ q: 2
450
+ });
451
+ }
452
+ /**
453
+ * Ensure an image has been transmitted to the terminal at least once.
454
+ * On the first call per `src`, returns the full `a=t,t=f` escape to be
455
+ * prepended to the caller's first row — the APC payload has zero display
456
+ * width, so layout sees through it. Subsequent calls return `transmit:
457
+ * ""` since the terminal already has the bytes under `imageId`.
458
+ *
459
+ * The caller is expected to combine this with `placement(...)` on every
460
+ * render to actually paint the image at the right cell rectangle.
461
+ */
462
+ async transmitOnce(info) {
463
+ if (!this.#support.ok) return void 0;
464
+ const { fileHash } = await import("@zaly/shared/detect");
465
+ const key = fileHash(info);
466
+ let entry = transmitCache.get(key);
467
+ if (entry === void 0) {
468
+ const { imageConvert } = await import("@zaly/shared/image");
469
+ const png = await imageConvert(info, "png");
470
+ if (!png) return void 0;
471
+ const id = allocateImageId();
472
+ entry = {
473
+ imageId: id,
474
+ sent: false,
475
+ seq: this.#support.remote || !png.path ? this.transmitBytes(id, png.data) : this.transmitFile(id, png.path)
476
+ };
477
+ transmitCache.set(key, entry);
478
+ }
479
+ if (entry.sent) {
480
+ entry.seq = "";
481
+ return { imageId: entry.imageId };
482
+ }
483
+ entry.sent = true;
484
+ return {
485
+ imageId: entry.imageId,
486
+ transmit: entry.seq
487
+ };
488
+ }
489
+ /**
490
+ * Transmit an image to the terminal by file path (`t=f`). Near-zero cost
491
+ * on the wire — the terminal opens and reads the file itself. `path`
492
+ * must be absolute and must point to a regular file; symlinks are
493
+ * followed by the terminal.
494
+ */
495
+ transmitFile(id, path) {
496
+ return this.request({
497
+ a: "t",
498
+ f: 100,
499
+ i: id,
500
+ q: 2,
501
+ t: "f"
502
+ }, path);
503
+ }
504
+ /**
505
+ * Remote/bytes transmission fallback (`t=d`) for when the terminal can't
506
+ * read local files — typical of SSH sessions. Base64-encodes and chunks
507
+ * the PNG payload at 4KB boundaries per the protocol.
508
+ */
509
+ transmitBytes(id, png) {
510
+ const base64 = toBase64(png);
511
+ const params = {
512
+ a: "t",
513
+ f: 100,
514
+ i: id,
515
+ q: 2,
516
+ t: "d"
517
+ };
518
+ if (base64.length <= CHUNK_SIZE) return this.request(params, base64, { base64: false });
519
+ const out = [];
520
+ let offset = 0;
521
+ let first = true;
522
+ while (offset < base64.length) {
523
+ const chunk = base64.slice(offset, offset + CHUNK_SIZE);
524
+ offset += CHUNK_SIZE;
525
+ const more = offset < base64.length ? 1 : 0;
526
+ out.push(this.request(first ? {
527
+ ...params,
528
+ m: more
529
+ } : { m: more }, chunk, { base64: false }));
530
+ first = false;
531
+ }
532
+ return out.join("");
533
+ }
534
+ };
535
+ /** Drop the per-src transmit cache. Mostly for tests. */
536
+ function resetTransmitCache() {
537
+ transmitCache.clear();
538
+ }
539
+ function resetKittyGraphics() {
540
+ resetTransmitCache();
541
+ prom = void 0;
542
+ kitty = void 0;
543
+ }
544
+ function intToRgb(color24bit) {
545
+ const r = color24bit >> 16 & 255;
546
+ const g = color24bit >> 8 & 255;
547
+ return {
548
+ b: color24bit & 255,
549
+ g,
550
+ r
551
+ };
552
+ }
553
+ function unicodePlaceholder(id, dims) {
554
+ const rgb = intToRgb(id);
555
+ const rows = Math.min(DIACRITICS.length, dims.rows);
556
+ const cols = Math.min(DIACRITICS.length, dims.cols);
557
+ const fg = `\x1b[38;2;${rgb.r};${rgb.g};${rgb.b}m`;
558
+ const img = [];
559
+ for (let r = 0; r < rows; r++) {
560
+ const line = [];
561
+ for (let c = 0; c < cols; c++) {
562
+ line.push(fg);
563
+ line.push(PLACEHOLDER);
564
+ line.push(DIACRITICS[r]);
565
+ line.push(DIACRITICS[c]);
566
+ }
567
+ line.push("\x1B[39m");
568
+ img.push(line.join(""));
569
+ }
570
+ return img;
571
+ }
572
+ function toBase64(bytes) {
573
+ if (typeof Buffer !== "undefined") return Buffer.from(bytes).toString("base64");
574
+ let binary = "";
575
+ for (const b of bytes) binary += String.fromCharCode(b);
576
+ return btoa(binary);
577
+ }
578
+ function bumpPlacements(rows) {
579
+ if (!kitty || kitty.inline) return;
580
+ const placements = [];
581
+ const ret = rows.map((row) => row.replace(/\x1b_Ga=p,i=(\d+),p=(\d+)/g, (_, i) => {
582
+ const imageId = parseInt(i, 10);
583
+ const placementId = allocatePlacementId();
584
+ placements.push({
585
+ i: imageId,
586
+ p: placementId
587
+ });
588
+ return `\x1b_Ga=p,i=${imageId},p=${placementId}`;
589
+ }));
590
+ if (!placements.length) return;
591
+ const k = kitty;
592
+ return {
593
+ delete: () => placements.map((p) => k.deletePlacement(p.i, p.p)).join(""),
594
+ rows: ret
595
+ };
596
+ }
597
+ async function detect(tq) {
598
+ const support = {
599
+ remote: isSSH,
600
+ tmux: !!process.env.TMUX,
601
+ wrap: process.env.TMUX ? wrapTmux : void 0
602
+ };
603
+ if (support.tmux) try {
604
+ const { spawnCmd } = await import("@zaly/shared/process");
605
+ await spawnCmd("tmux", "set", "-p", "allow-passthrough", "on");
606
+ support.wrap = wrapTmux;
607
+ } catch (error) {
608
+ return {
609
+ ...support,
610
+ error: `Failed to set allow-passthrough in tmux: ${error instanceof Error ? error.message : String(error)}`,
611
+ ok: false
612
+ };
613
+ }
614
+ const v = await tq.xtVersion({ wrap: support.wrap });
615
+ if (!v) return {
616
+ error: "Failed to query terminal name & version",
617
+ ok: false,
618
+ ...support
619
+ };
620
+ support.terminal = {
621
+ name: v.name,
622
+ version: v.version
623
+ };
624
+ const kgp = known[v.name.toLowerCase()];
625
+ if (kgp === false) return {
626
+ error: `Terminal ${v.name} does not support KGP`,
627
+ ok: false,
628
+ ...support
629
+ };
630
+ if (kgp === void 0) {
631
+ const k = new Kitty({
632
+ ...support,
633
+ error: "",
634
+ ok: false
635
+ });
636
+ if ((await tq.query({
637
+ match: (ev) => {
638
+ if (ev.kind === "apc" && ev.payload.startsWith("G")) return {
639
+ kgp: true,
640
+ ...ev
641
+ };
642
+ if (ev.kind === "csi" && ev.final === "c" && ev.params.startsWith("?")) return {
643
+ kgp: false,
644
+ ...ev
645
+ };
646
+ },
647
+ request: `${k.probe()}\x1b[c`,
648
+ timeout: 200
649
+ }))?.kgp !== true) return {
650
+ error: "Failed to query kitty graphics protocol",
651
+ ok: false,
652
+ ...support
653
+ };
654
+ }
655
+ return {
656
+ ...support,
657
+ inline: kgp?.inline,
658
+ ok: true,
659
+ terminal: {
660
+ name: v.name,
661
+ version: v.version
662
+ }
663
+ };
664
+ }
665
+ function loadKittyGraphics(tq) {
666
+ if (kitty) return kitty;
667
+ prom ??= (async () => kitty = new Kitty(await detect(tq)))();
668
+ return prom;
669
+ }
670
+ //#endregion
671
+ export { allocatePlacementId as a, resetKittyGraphics as c, allocateImageId as i, resetTransmitCache as l, Kitty as n, bumpPlacements as o, PLACEHOLDER as r, loadKittyGraphics as s, DIACRITICS as t };
672
+
673
+ //# sourceMappingURL=kitty-JbCJC0iQ.mjs.map