ink-sdl 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/LICENSE +21 -0
- package/README.md +189 -0
- package/dist/index.d.ts +891 -0
- package/dist/index.js +2280 -0
- package/package.json +65 -0
- package/src/fonts/CozetteVector.ttf +0 -0
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,891 @@
|
|
|
1
|
+
import { EventEmitter } from 'events';
|
|
2
|
+
import { Writable, Readable } from 'stream';
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* SDL Type Definitions
|
|
6
|
+
*/
|
|
7
|
+
/** Opaque pointer type for SDL handles (windows, renderers, textures, etc.) */
|
|
8
|
+
type SDLPointer = unknown;
|
|
9
|
+
/**
|
|
10
|
+
* Keyboard event from SDL
|
|
11
|
+
*/
|
|
12
|
+
interface SdlKeyEvent {
|
|
13
|
+
keycode: number;
|
|
14
|
+
pressed: boolean;
|
|
15
|
+
repeat: boolean;
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
/**
|
|
19
|
+
* SDL2 FFI Bindings
|
|
20
|
+
*
|
|
21
|
+
* Provides minimal SDL2 and SDL2_ttf bindings for window-based rendering
|
|
22
|
+
* using koffi for foreign function interface.
|
|
23
|
+
*/
|
|
24
|
+
|
|
25
|
+
/**
|
|
26
|
+
* SDL2 API wrapper class
|
|
27
|
+
*
|
|
28
|
+
* Provides type-safe access to SDL2 functions for window rendering.
|
|
29
|
+
*/
|
|
30
|
+
declare class SDL2API {
|
|
31
|
+
private lib;
|
|
32
|
+
private initialized;
|
|
33
|
+
private _SDL_Init;
|
|
34
|
+
private _SDL_Quit;
|
|
35
|
+
private _SDL_GetError;
|
|
36
|
+
private _SDL_CreateWindow;
|
|
37
|
+
private _SDL_DestroyWindow;
|
|
38
|
+
private _SDL_SetWindowTitle;
|
|
39
|
+
private _SDL_GetWindowSize;
|
|
40
|
+
private _SDL_RaiseWindow;
|
|
41
|
+
private _SDL_CreateRenderer;
|
|
42
|
+
private _SDL_DestroyRenderer;
|
|
43
|
+
private _SDL_RenderClear;
|
|
44
|
+
private _SDL_RenderPresent;
|
|
45
|
+
private _SDL_RenderCopy;
|
|
46
|
+
private _SDL_SetRenderDrawColor;
|
|
47
|
+
private _SDL_CreateTexture;
|
|
48
|
+
private _SDL_DestroyTexture;
|
|
49
|
+
private _SDL_UpdateTexture;
|
|
50
|
+
private _SDL_CreateTextureFromSurface;
|
|
51
|
+
private _SDL_SetTextureBlendMode;
|
|
52
|
+
private _SDL_SetTextureColorMod;
|
|
53
|
+
private _SDL_FreeSurface;
|
|
54
|
+
private _SDL_GetRendererOutputSize;
|
|
55
|
+
private _SDL_RenderFillRect;
|
|
56
|
+
private _SDL_SetRenderTarget;
|
|
57
|
+
private _SDL_GL_GetDrawableSize;
|
|
58
|
+
private _SDL_PollEvent;
|
|
59
|
+
constructor();
|
|
60
|
+
private bindFunctions;
|
|
61
|
+
/**
|
|
62
|
+
* Initialize SDL with the given subsystems
|
|
63
|
+
*/
|
|
64
|
+
init(flags?: number): boolean;
|
|
65
|
+
/**
|
|
66
|
+
* Shutdown SDL
|
|
67
|
+
*/
|
|
68
|
+
quit(): void;
|
|
69
|
+
/**
|
|
70
|
+
* Get the last SDL error message
|
|
71
|
+
*/
|
|
72
|
+
getError(): string;
|
|
73
|
+
/**
|
|
74
|
+
* Create a window
|
|
75
|
+
*/
|
|
76
|
+
createWindow(title: string, x: number, y: number, width: number, height: number, flags: number): SDLPointer;
|
|
77
|
+
/**
|
|
78
|
+
* Destroy a window
|
|
79
|
+
*/
|
|
80
|
+
destroyWindow(window: SDLPointer): void;
|
|
81
|
+
/**
|
|
82
|
+
* Set window title
|
|
83
|
+
*/
|
|
84
|
+
setWindowTitle(window: SDLPointer, title: string): void;
|
|
85
|
+
/**
|
|
86
|
+
* Get window size
|
|
87
|
+
*/
|
|
88
|
+
getWindowSize(window: SDLPointer): {
|
|
89
|
+
width: number;
|
|
90
|
+
height: number;
|
|
91
|
+
};
|
|
92
|
+
/**
|
|
93
|
+
* Raise window to front and give it keyboard focus
|
|
94
|
+
*/
|
|
95
|
+
raiseWindow(window: SDLPointer): void;
|
|
96
|
+
/**
|
|
97
|
+
* Create a renderer for a window
|
|
98
|
+
*/
|
|
99
|
+
createRenderer(window: SDLPointer, index?: number, flags?: number): SDLPointer;
|
|
100
|
+
/**
|
|
101
|
+
* Destroy a renderer
|
|
102
|
+
*/
|
|
103
|
+
destroyRenderer(renderer: SDLPointer): void;
|
|
104
|
+
/**
|
|
105
|
+
* Clear the renderer
|
|
106
|
+
*/
|
|
107
|
+
renderClear(renderer: SDLPointer): void;
|
|
108
|
+
/**
|
|
109
|
+
* Present the renderer (flip buffers)
|
|
110
|
+
*/
|
|
111
|
+
renderPresent(renderer: SDLPointer): void;
|
|
112
|
+
/**
|
|
113
|
+
* Copy texture to renderer
|
|
114
|
+
*/
|
|
115
|
+
renderCopy(renderer: SDLPointer, texture: SDLPointer, srcRect?: SDLPointer | null, dstRect?: SDLPointer | null): void;
|
|
116
|
+
/**
|
|
117
|
+
* Set render draw color
|
|
118
|
+
*/
|
|
119
|
+
setRenderDrawColor(renderer: SDLPointer, r: number, g: number, b: number, a?: number): void;
|
|
120
|
+
/**
|
|
121
|
+
* Create a texture
|
|
122
|
+
*/
|
|
123
|
+
createTexture(renderer: SDLPointer, format: number, access: number, width: number, height: number): SDLPointer;
|
|
124
|
+
/**
|
|
125
|
+
* Destroy a texture
|
|
126
|
+
*/
|
|
127
|
+
destroyTexture(texture: SDLPointer): void;
|
|
128
|
+
/**
|
|
129
|
+
* Update texture with pixel data
|
|
130
|
+
*/
|
|
131
|
+
updateTexture(texture: SDLPointer, pixels: Buffer, pitch: number): void;
|
|
132
|
+
/**
|
|
133
|
+
* Create a texture from an SDL surface
|
|
134
|
+
*/
|
|
135
|
+
createTextureFromSurface(renderer: SDLPointer, surface: SDLPointer): SDLPointer;
|
|
136
|
+
/**
|
|
137
|
+
* Set texture blend mode
|
|
138
|
+
*/
|
|
139
|
+
setTextureBlendMode(texture: SDLPointer, blendMode: number): void;
|
|
140
|
+
/**
|
|
141
|
+
* Set texture color modulation (tint)
|
|
142
|
+
*/
|
|
143
|
+
setTextureColorMod(texture: SDLPointer, r: number, g: number, b: number): void;
|
|
144
|
+
/**
|
|
145
|
+
* Free an SDL surface
|
|
146
|
+
*/
|
|
147
|
+
freeSurface(surface: SDLPointer): void;
|
|
148
|
+
/**
|
|
149
|
+
* Get the output size of a renderer (physical pixels)
|
|
150
|
+
*/
|
|
151
|
+
getRendererOutputSize(renderer: SDLPointer): {
|
|
152
|
+
width: number;
|
|
153
|
+
height: number;
|
|
154
|
+
};
|
|
155
|
+
/**
|
|
156
|
+
* Fill a rectangle with the current draw color
|
|
157
|
+
*/
|
|
158
|
+
renderFillRect(renderer: SDLPointer, rect: Buffer | null): void;
|
|
159
|
+
/**
|
|
160
|
+
* Set the render target (null for default window)
|
|
161
|
+
*/
|
|
162
|
+
setRenderTarget(renderer: SDLPointer, texture: SDLPointer | null): void;
|
|
163
|
+
/**
|
|
164
|
+
* Get drawable size (physical pixels) for HiDPI windows
|
|
165
|
+
*/
|
|
166
|
+
getDrawableSize(window: SDLPointer): {
|
|
167
|
+
width: number;
|
|
168
|
+
height: number;
|
|
169
|
+
};
|
|
170
|
+
/**
|
|
171
|
+
* Get the scale factor between logical and physical pixels
|
|
172
|
+
*/
|
|
173
|
+
getScaleFactor(window: SDLPointer): number;
|
|
174
|
+
/**
|
|
175
|
+
* Get the scale factor using renderer output size (more reliable for non-GL windows)
|
|
176
|
+
*/
|
|
177
|
+
getScaleFactorFromRenderer(window: SDLPointer, renderer: SDLPointer): number;
|
|
178
|
+
/**
|
|
179
|
+
* Poll for pending events
|
|
180
|
+
*/
|
|
181
|
+
pollEvent(): {
|
|
182
|
+
type: number;
|
|
183
|
+
windowEvent?: number;
|
|
184
|
+
keycode?: number;
|
|
185
|
+
pressed?: boolean;
|
|
186
|
+
repeat?: boolean;
|
|
187
|
+
} | null;
|
|
188
|
+
/**
|
|
189
|
+
* Check if SDL is initialized
|
|
190
|
+
*/
|
|
191
|
+
isInitialized(): boolean;
|
|
192
|
+
}
|
|
193
|
+
/**
|
|
194
|
+
* Get the SDL2 API singleton
|
|
195
|
+
*/
|
|
196
|
+
declare const getSDL2: () => SDL2API;
|
|
197
|
+
/**
|
|
198
|
+
* Check if SDL2 is available without throwing
|
|
199
|
+
*/
|
|
200
|
+
declare const isSDL2Available: () => boolean;
|
|
201
|
+
/**
|
|
202
|
+
* Create an SDL_Rect buffer for use with SDL functions
|
|
203
|
+
*/
|
|
204
|
+
declare const createSDLRect: (x: number, y: number, w: number, h: number) => Buffer;
|
|
205
|
+
/**
|
|
206
|
+
* SDL_ttf API wrapper class for TrueType font rendering
|
|
207
|
+
*/
|
|
208
|
+
declare class SDL_ttfAPI {
|
|
209
|
+
private lib;
|
|
210
|
+
private initialized;
|
|
211
|
+
private _TTF_Init;
|
|
212
|
+
private _TTF_Quit;
|
|
213
|
+
private _TTF_OpenFont;
|
|
214
|
+
private _TTF_CloseFont;
|
|
215
|
+
private _TTF_RenderUTF8_Blended;
|
|
216
|
+
private _TTF_SizeUTF8;
|
|
217
|
+
constructor();
|
|
218
|
+
private bindFunctions;
|
|
219
|
+
/**
|
|
220
|
+
* Initialize SDL_ttf
|
|
221
|
+
*/
|
|
222
|
+
init(): boolean;
|
|
223
|
+
/**
|
|
224
|
+
* Shutdown SDL_ttf
|
|
225
|
+
*/
|
|
226
|
+
quit(): void;
|
|
227
|
+
/**
|
|
228
|
+
* Get the last SDL_ttf error message
|
|
229
|
+
*/
|
|
230
|
+
getError(): string;
|
|
231
|
+
/**
|
|
232
|
+
* Open a TrueType font file
|
|
233
|
+
*/
|
|
234
|
+
openFont(file: string, ptsize: number): SDLPointer;
|
|
235
|
+
/**
|
|
236
|
+
* Close a font
|
|
237
|
+
*/
|
|
238
|
+
closeFont(font: SDLPointer): void;
|
|
239
|
+
/**
|
|
240
|
+
* Render UTF-8 text to a surface with blended (anti-aliased) rendering
|
|
241
|
+
*/
|
|
242
|
+
renderTextBlended(font: SDLPointer, text: string, r: number, g: number, b: number, a?: number): SDLPointer;
|
|
243
|
+
/**
|
|
244
|
+
* Get the dimensions of rendered text without actually rendering
|
|
245
|
+
*/
|
|
246
|
+
sizeText(font: SDLPointer, text: string): {
|
|
247
|
+
width: number;
|
|
248
|
+
height: number;
|
|
249
|
+
};
|
|
250
|
+
/**
|
|
251
|
+
* Check if SDL_ttf is initialized
|
|
252
|
+
*/
|
|
253
|
+
isInitialized(): boolean;
|
|
254
|
+
}
|
|
255
|
+
/**
|
|
256
|
+
* Get the SDL_ttf API singleton
|
|
257
|
+
*/
|
|
258
|
+
declare const getSDL_ttf: () => SDL_ttfAPI;
|
|
259
|
+
/**
|
|
260
|
+
* Check if SDL_ttf is available without throwing
|
|
261
|
+
*/
|
|
262
|
+
declare const isSDL_ttfAvailable: () => boolean;
|
|
263
|
+
|
|
264
|
+
/**
|
|
265
|
+
* ANSI Parser for SDL UI Rendering
|
|
266
|
+
*
|
|
267
|
+
* Parses terminal ANSI escape sequences and converts them to draw commands
|
|
268
|
+
* for rendering in an SDL window.
|
|
269
|
+
*/
|
|
270
|
+
/** RGB color value */
|
|
271
|
+
interface Color {
|
|
272
|
+
r: number;
|
|
273
|
+
g: number;
|
|
274
|
+
b: number;
|
|
275
|
+
}
|
|
276
|
+
/** Types of draw commands */
|
|
277
|
+
type DrawCommandType = "text" | "clear_screen" | "clear_line" | "cursor_move" | "set_fg" | "set_bg" | "reset_style" | "set_bold" | "set_dim" | "set_reverse";
|
|
278
|
+
/** A single draw command from parsed ANSI output */
|
|
279
|
+
interface DrawCommand {
|
|
280
|
+
type: DrawCommandType;
|
|
281
|
+
text?: string;
|
|
282
|
+
row?: number;
|
|
283
|
+
col?: number;
|
|
284
|
+
color?: Color;
|
|
285
|
+
enabled?: boolean;
|
|
286
|
+
}
|
|
287
|
+
/**
|
|
288
|
+
* ANSI sequence parser
|
|
289
|
+
*
|
|
290
|
+
* Parses ANSI escape sequences from terminal output and produces
|
|
291
|
+
* draw commands for SDL rendering.
|
|
292
|
+
*/
|
|
293
|
+
declare class AnsiParser {
|
|
294
|
+
private cursorRow;
|
|
295
|
+
private cursorCol;
|
|
296
|
+
private fgColor;
|
|
297
|
+
private bgColor;
|
|
298
|
+
private bold;
|
|
299
|
+
/**
|
|
300
|
+
* Parse an ANSI string and return draw commands
|
|
301
|
+
*/
|
|
302
|
+
parse(input: string): DrawCommand[];
|
|
303
|
+
/**
|
|
304
|
+
* Process an escape sequence and emit draw commands
|
|
305
|
+
*/
|
|
306
|
+
private processEscapeSequence;
|
|
307
|
+
/**
|
|
308
|
+
* Process cursor position sequence
|
|
309
|
+
*/
|
|
310
|
+
private processCursorPosition;
|
|
311
|
+
/**
|
|
312
|
+
* Process erase display sequence
|
|
313
|
+
*/
|
|
314
|
+
private processEraseDisplay;
|
|
315
|
+
/**
|
|
316
|
+
* Process erase line sequence
|
|
317
|
+
*/
|
|
318
|
+
private processEraseLine;
|
|
319
|
+
/**
|
|
320
|
+
* Process SGR (Select Graphic Rendition) sequence
|
|
321
|
+
*/
|
|
322
|
+
private processSGR;
|
|
323
|
+
/**
|
|
324
|
+
* Parse extended color (256-color or 24-bit)
|
|
325
|
+
*/
|
|
326
|
+
private parseExtendedColor;
|
|
327
|
+
/**
|
|
328
|
+
* Reset all styles to default
|
|
329
|
+
*/
|
|
330
|
+
private resetStyle;
|
|
331
|
+
/**
|
|
332
|
+
* Get current cursor position
|
|
333
|
+
*/
|
|
334
|
+
getCursor(): {
|
|
335
|
+
row: number;
|
|
336
|
+
col: number;
|
|
337
|
+
};
|
|
338
|
+
/**
|
|
339
|
+
* Get current foreground color
|
|
340
|
+
*/
|
|
341
|
+
getFgColor(): Color;
|
|
342
|
+
/**
|
|
343
|
+
* Get current background color
|
|
344
|
+
*/
|
|
345
|
+
getBgColor(): Color;
|
|
346
|
+
/**
|
|
347
|
+
* Reset parser state
|
|
348
|
+
*/
|
|
349
|
+
reset(): void;
|
|
350
|
+
}
|
|
351
|
+
|
|
352
|
+
/**
|
|
353
|
+
* SDL Text Renderer
|
|
354
|
+
*
|
|
355
|
+
* Handles TrueType font loading and text rendering with glyph caching
|
|
356
|
+
* for efficient SDL UI rendering.
|
|
357
|
+
*/
|
|
358
|
+
|
|
359
|
+
/**
|
|
360
|
+
* SDL Text Renderer
|
|
361
|
+
*
|
|
362
|
+
* Loads TTF fonts and renders text with glyph caching for performance.
|
|
363
|
+
* Supports HiDPI displays by scaling font size based on scale factor.
|
|
364
|
+
*/
|
|
365
|
+
declare class TextRenderer {
|
|
366
|
+
private sdl;
|
|
367
|
+
private ttf;
|
|
368
|
+
private font;
|
|
369
|
+
private renderer;
|
|
370
|
+
private baseFontSize;
|
|
371
|
+
private scaleFactor;
|
|
372
|
+
private glyphCache;
|
|
373
|
+
private accessCounter;
|
|
374
|
+
private charWidth;
|
|
375
|
+
private charHeight;
|
|
376
|
+
constructor(renderer: SDLPointer, options?: {
|
|
377
|
+
fontSize?: number;
|
|
378
|
+
scaleFactor?: number;
|
|
379
|
+
fontPath?: string;
|
|
380
|
+
});
|
|
381
|
+
/**
|
|
382
|
+
* Get the path to the bundled Cozette font
|
|
383
|
+
*/
|
|
384
|
+
private getDefaultFontPath;
|
|
385
|
+
/**
|
|
386
|
+
* Load a TTF font at the current scaled size
|
|
387
|
+
*/
|
|
388
|
+
private loadFont;
|
|
389
|
+
/**
|
|
390
|
+
* Update scale factor (for HiDPI display changes)
|
|
391
|
+
*/
|
|
392
|
+
updateScaleFactor(scaleFactor: number): void;
|
|
393
|
+
/**
|
|
394
|
+
* Get character dimensions
|
|
395
|
+
*/
|
|
396
|
+
getCharDimensions(): {
|
|
397
|
+
width: number;
|
|
398
|
+
height: number;
|
|
399
|
+
};
|
|
400
|
+
/**
|
|
401
|
+
* Generate cache key for a glyph
|
|
402
|
+
*/
|
|
403
|
+
private getCacheKey;
|
|
404
|
+
/**
|
|
405
|
+
* Get or create a cached glyph texture
|
|
406
|
+
*/
|
|
407
|
+
private getGlyph;
|
|
408
|
+
/**
|
|
409
|
+
* Evict least recently used glyphs
|
|
410
|
+
*/
|
|
411
|
+
private evictOldGlyphs;
|
|
412
|
+
/**
|
|
413
|
+
* Render a single character at the specified position
|
|
414
|
+
*/
|
|
415
|
+
renderChar(char: string, x: number, y: number, color: Color): void;
|
|
416
|
+
/**
|
|
417
|
+
* Render a string of text at the specified position
|
|
418
|
+
*/
|
|
419
|
+
renderText(text: string, x: number, y: number, color: Color): void;
|
|
420
|
+
/**
|
|
421
|
+
* Get text dimensions
|
|
422
|
+
*/
|
|
423
|
+
measureText(text: string): {
|
|
424
|
+
width: number;
|
|
425
|
+
height: number;
|
|
426
|
+
};
|
|
427
|
+
/**
|
|
428
|
+
* Clear the glyph cache
|
|
429
|
+
*/
|
|
430
|
+
clearCache(): void;
|
|
431
|
+
/**
|
|
432
|
+
* Get cache statistics
|
|
433
|
+
*/
|
|
434
|
+
getCacheStats(): {
|
|
435
|
+
size: number;
|
|
436
|
+
maxSize: number;
|
|
437
|
+
};
|
|
438
|
+
/**
|
|
439
|
+
* Clean up resources
|
|
440
|
+
*/
|
|
441
|
+
destroy(): void;
|
|
442
|
+
}
|
|
443
|
+
|
|
444
|
+
/**
|
|
445
|
+
* SDL UI Renderer
|
|
446
|
+
*
|
|
447
|
+
* Main renderer for Ink-based UI in SDL mode. Intercepts ANSI output
|
|
448
|
+
* from Ink and renders it to an SDL window using text rendering.
|
|
449
|
+
*/
|
|
450
|
+
|
|
451
|
+
interface SdlUiRendererOptions {
|
|
452
|
+
width?: number;
|
|
453
|
+
height?: number;
|
|
454
|
+
title?: string;
|
|
455
|
+
vsync?: boolean;
|
|
456
|
+
fontSize?: number;
|
|
457
|
+
scaleFactor?: number | null;
|
|
458
|
+
}
|
|
459
|
+
/**
|
|
460
|
+
* SDL UI Renderer
|
|
461
|
+
*
|
|
462
|
+
* Renders Ink UI to an SDL window by parsing ANSI sequences and
|
|
463
|
+
* drawing text with SDL_ttf.
|
|
464
|
+
*/
|
|
465
|
+
declare class SdlUiRenderer {
|
|
466
|
+
private sdl;
|
|
467
|
+
private window;
|
|
468
|
+
private renderer;
|
|
469
|
+
private textRenderer;
|
|
470
|
+
private ansiParser;
|
|
471
|
+
private inputBridge;
|
|
472
|
+
private windowWidth;
|
|
473
|
+
private windowHeight;
|
|
474
|
+
private columns;
|
|
475
|
+
private rows;
|
|
476
|
+
private charWidth;
|
|
477
|
+
private charHeight;
|
|
478
|
+
private fgColor;
|
|
479
|
+
private bgColor;
|
|
480
|
+
private bold;
|
|
481
|
+
private dim;
|
|
482
|
+
private reverse;
|
|
483
|
+
private shouldQuit;
|
|
484
|
+
private pendingCommands;
|
|
485
|
+
private scaleFactor;
|
|
486
|
+
private userScaleFactor;
|
|
487
|
+
constructor(options?: SdlUiRendererOptions);
|
|
488
|
+
/**
|
|
489
|
+
* Initialize SDL window and renderer
|
|
490
|
+
*/
|
|
491
|
+
private initSDL;
|
|
492
|
+
/**
|
|
493
|
+
* Update terminal dimensions based on window size
|
|
494
|
+
*/
|
|
495
|
+
private updateTerminalDimensions;
|
|
496
|
+
/**
|
|
497
|
+
* Get terminal dimensions
|
|
498
|
+
*/
|
|
499
|
+
getDimensions(): {
|
|
500
|
+
columns: number;
|
|
501
|
+
rows: number;
|
|
502
|
+
};
|
|
503
|
+
/**
|
|
504
|
+
* Process ANSI output from Ink
|
|
505
|
+
*/
|
|
506
|
+
processAnsi(output: string): void;
|
|
507
|
+
/**
|
|
508
|
+
* Render pending commands and present
|
|
509
|
+
*/
|
|
510
|
+
present(): void;
|
|
511
|
+
/**
|
|
512
|
+
* Execute a single draw command
|
|
513
|
+
*/
|
|
514
|
+
private executeCommand;
|
|
515
|
+
/**
|
|
516
|
+
* Render text at position
|
|
517
|
+
*/
|
|
518
|
+
private renderText;
|
|
519
|
+
/**
|
|
520
|
+
* Clear the entire screen
|
|
521
|
+
*/
|
|
522
|
+
clear(): void;
|
|
523
|
+
/**
|
|
524
|
+
* Clear a line from a specific position
|
|
525
|
+
*/
|
|
526
|
+
private clearLine;
|
|
527
|
+
/**
|
|
528
|
+
* Process SDL events
|
|
529
|
+
*/
|
|
530
|
+
processEvents(): SdlKeyEvent[];
|
|
531
|
+
/**
|
|
532
|
+
* Convert SDL key event to terminal sequence
|
|
533
|
+
*/
|
|
534
|
+
keyEventToSequence(event: SdlKeyEvent): string | null;
|
|
535
|
+
/**
|
|
536
|
+
* Handle window resize
|
|
537
|
+
*/
|
|
538
|
+
private handleResize;
|
|
539
|
+
/**
|
|
540
|
+
* Check if quit was requested
|
|
541
|
+
*/
|
|
542
|
+
shouldClose(): boolean;
|
|
543
|
+
/**
|
|
544
|
+
* Get cursor position
|
|
545
|
+
*/
|
|
546
|
+
getCursorPos(): {
|
|
547
|
+
x: number;
|
|
548
|
+
y: number;
|
|
549
|
+
};
|
|
550
|
+
/**
|
|
551
|
+
* Get the SDL window
|
|
552
|
+
*/
|
|
553
|
+
getWindow(): SDLPointer | null;
|
|
554
|
+
/**
|
|
555
|
+
* Get the SDL renderer
|
|
556
|
+
*/
|
|
557
|
+
getRenderer(): SDLPointer | null;
|
|
558
|
+
/**
|
|
559
|
+
* Set the scale factor
|
|
560
|
+
*/
|
|
561
|
+
setScaleFactor(scaleFactor: number | null): void;
|
|
562
|
+
/**
|
|
563
|
+
* Get current scale factor
|
|
564
|
+
*/
|
|
565
|
+
getScaleFactor(): number;
|
|
566
|
+
/**
|
|
567
|
+
* Clean up resources
|
|
568
|
+
*/
|
|
569
|
+
destroy(): void;
|
|
570
|
+
/**
|
|
571
|
+
* Reset state for reuse
|
|
572
|
+
*/
|
|
573
|
+
reset(): void;
|
|
574
|
+
}
|
|
575
|
+
|
|
576
|
+
/**
|
|
577
|
+
* SDL Output Stream for Ink
|
|
578
|
+
*
|
|
579
|
+
* A Writable stream that intercepts Ink's ANSI output and renders it
|
|
580
|
+
* to an SDL window.
|
|
581
|
+
*/
|
|
582
|
+
|
|
583
|
+
/**
|
|
584
|
+
* SDL Output Stream
|
|
585
|
+
*
|
|
586
|
+
* Wraps an SdlUiRenderer in a Node.js Writable stream that Ink
|
|
587
|
+
* can use as stdout.
|
|
588
|
+
*/
|
|
589
|
+
declare class SdlOutputStream extends Writable {
|
|
590
|
+
/** TTY interface property expected by Ink */
|
|
591
|
+
isTTY: boolean;
|
|
592
|
+
private uiRenderer;
|
|
593
|
+
constructor(uiRenderer: SdlUiRenderer);
|
|
594
|
+
/**
|
|
595
|
+
* Get terminal columns
|
|
596
|
+
*/
|
|
597
|
+
get columns(): number;
|
|
598
|
+
/**
|
|
599
|
+
* Get terminal rows
|
|
600
|
+
*/
|
|
601
|
+
get rows(): number;
|
|
602
|
+
/**
|
|
603
|
+
* Notify Ink of resize
|
|
604
|
+
*/
|
|
605
|
+
notifyResize(): void;
|
|
606
|
+
/**
|
|
607
|
+
* Implement Writable._write
|
|
608
|
+
*/
|
|
609
|
+
_write(chunk: Buffer | string, _encoding: BufferEncoding, callback: (error?: Error | null) => void): void;
|
|
610
|
+
/**
|
|
611
|
+
* Get the underlying renderer
|
|
612
|
+
*/
|
|
613
|
+
getRenderer(): SdlUiRenderer;
|
|
614
|
+
/**
|
|
615
|
+
* Clear the screen
|
|
616
|
+
*/
|
|
617
|
+
clear(): void;
|
|
618
|
+
/**
|
|
619
|
+
* Write a string directly (bypasses Writable buffering)
|
|
620
|
+
*/
|
|
621
|
+
writeSync(text: string): void;
|
|
622
|
+
/**
|
|
623
|
+
* Get cursor position
|
|
624
|
+
*/
|
|
625
|
+
getCursorPos(): {
|
|
626
|
+
x: number;
|
|
627
|
+
y: number;
|
|
628
|
+
};
|
|
629
|
+
}
|
|
630
|
+
|
|
631
|
+
/**
|
|
632
|
+
* SDL Input Stream for Ink
|
|
633
|
+
*
|
|
634
|
+
* A Readable stream that provides keyboard input to Ink from SDL events.
|
|
635
|
+
* Implements the TTY interface expected by Ink.
|
|
636
|
+
*/
|
|
637
|
+
|
|
638
|
+
/**
|
|
639
|
+
* SDL Input Stream
|
|
640
|
+
*
|
|
641
|
+
* Wraps SDL keyboard events in a Node.js Readable stream that Ink
|
|
642
|
+
* can use as stdin.
|
|
643
|
+
*/
|
|
644
|
+
declare class SdlInputStream extends Readable {
|
|
645
|
+
/** TTY interface properties expected by Ink */
|
|
646
|
+
isTTY: boolean;
|
|
647
|
+
isRaw: boolean;
|
|
648
|
+
private buffer;
|
|
649
|
+
private waiting;
|
|
650
|
+
constructor();
|
|
651
|
+
/**
|
|
652
|
+
* Push a key sequence into the stream
|
|
653
|
+
*/
|
|
654
|
+
pushKey(sequence: string): void;
|
|
655
|
+
/**
|
|
656
|
+
* Implement Readable._read
|
|
657
|
+
*/
|
|
658
|
+
_read(): void;
|
|
659
|
+
/**
|
|
660
|
+
* Set raw mode (no-op for SDL, we're always raw)
|
|
661
|
+
*/
|
|
662
|
+
setRawMode(_mode: boolean): this;
|
|
663
|
+
/**
|
|
664
|
+
* Check if stream has buffered data
|
|
665
|
+
*/
|
|
666
|
+
hasData(): boolean;
|
|
667
|
+
/**
|
|
668
|
+
* Clear the input buffer
|
|
669
|
+
*/
|
|
670
|
+
clear(): void;
|
|
671
|
+
/**
|
|
672
|
+
* Close the stream
|
|
673
|
+
*/
|
|
674
|
+
close(): void;
|
|
675
|
+
/**
|
|
676
|
+
* Keep the event loop alive (no-op for SDL)
|
|
677
|
+
*/
|
|
678
|
+
ref(): this;
|
|
679
|
+
/**
|
|
680
|
+
* Allow event loop to exit (no-op for SDL)
|
|
681
|
+
*/
|
|
682
|
+
unref(): this;
|
|
683
|
+
}
|
|
684
|
+
|
|
685
|
+
/**
|
|
686
|
+
* SDL Streams for Ink
|
|
687
|
+
*
|
|
688
|
+
* Factory function to create stdin/stdout streams that render to SDL.
|
|
689
|
+
*/
|
|
690
|
+
|
|
691
|
+
/**
|
|
692
|
+
* Options for creating SDL streams
|
|
693
|
+
*/
|
|
694
|
+
interface SdlStreamsOptions {
|
|
695
|
+
/** Window title */
|
|
696
|
+
title?: string;
|
|
697
|
+
/** Window width in pixels */
|
|
698
|
+
width?: number;
|
|
699
|
+
/** Window height in pixels */
|
|
700
|
+
height?: number;
|
|
701
|
+
/** Enable vsync */
|
|
702
|
+
vsync?: boolean;
|
|
703
|
+
/** Font size in points */
|
|
704
|
+
fontSize?: number;
|
|
705
|
+
/** Override scale factor (null = auto-detect) */
|
|
706
|
+
scaleFactor?: number | null;
|
|
707
|
+
}
|
|
708
|
+
/**
|
|
709
|
+
* SDL Window wrapper that emits events
|
|
710
|
+
*/
|
|
711
|
+
declare class SdlWindow extends EventEmitter {
|
|
712
|
+
private renderer;
|
|
713
|
+
private eventLoopHandle;
|
|
714
|
+
private inputStream;
|
|
715
|
+
private outputStream;
|
|
716
|
+
private closed;
|
|
717
|
+
constructor(renderer: SdlUiRenderer, inputStream: SdlInputStream, outputStream: SdlOutputStream);
|
|
718
|
+
/**
|
|
719
|
+
* Start the SDL event loop
|
|
720
|
+
*/
|
|
721
|
+
private startEventLoop;
|
|
722
|
+
/**
|
|
723
|
+
* Get terminal dimensions
|
|
724
|
+
*/
|
|
725
|
+
getDimensions(): {
|
|
726
|
+
columns: number;
|
|
727
|
+
rows: number;
|
|
728
|
+
};
|
|
729
|
+
/**
|
|
730
|
+
* Set window title
|
|
731
|
+
*/
|
|
732
|
+
setTitle(title: string): void;
|
|
733
|
+
/**
|
|
734
|
+
* Clear the screen
|
|
735
|
+
*/
|
|
736
|
+
clear(): void;
|
|
737
|
+
/**
|
|
738
|
+
* Close the window
|
|
739
|
+
*/
|
|
740
|
+
close(): void;
|
|
741
|
+
/**
|
|
742
|
+
* Check if window is closed
|
|
743
|
+
*/
|
|
744
|
+
isClosed(): boolean;
|
|
745
|
+
/**
|
|
746
|
+
* Get the output stream
|
|
747
|
+
*/
|
|
748
|
+
getOutputStream(): SdlOutputStream;
|
|
749
|
+
}
|
|
750
|
+
/**
|
|
751
|
+
* Result of createSdlStreams
|
|
752
|
+
*/
|
|
753
|
+
interface SdlStreams {
|
|
754
|
+
/** Readable stream for keyboard input */
|
|
755
|
+
stdin: SdlInputStream;
|
|
756
|
+
/** Writable stream for ANSI output */
|
|
757
|
+
stdout: SdlOutputStream;
|
|
758
|
+
/** SDL window wrapper with events */
|
|
759
|
+
window: SdlWindow;
|
|
760
|
+
}
|
|
761
|
+
/**
|
|
762
|
+
* Create SDL streams for use with Ink
|
|
763
|
+
*
|
|
764
|
+
* @example
|
|
765
|
+
* ```typescript
|
|
766
|
+
* import { render, Text, Box } from "ink";
|
|
767
|
+
* import { createSdlStreams } from "ink-sdl";
|
|
768
|
+
*
|
|
769
|
+
* const App = () => (
|
|
770
|
+
* <Box flexDirection="column">
|
|
771
|
+
* <Text color="green">Hello from SDL!</Text>
|
|
772
|
+
* </Box>
|
|
773
|
+
* );
|
|
774
|
+
*
|
|
775
|
+
* const { stdin, stdout, window } = createSdlStreams({
|
|
776
|
+
* title: "My App",
|
|
777
|
+
* width: 800,
|
|
778
|
+
* height: 600,
|
|
779
|
+
* });
|
|
780
|
+
*
|
|
781
|
+
* render(<App />, { stdin, stdout });
|
|
782
|
+
*
|
|
783
|
+
* window.on("close", () => process.exit(0));
|
|
784
|
+
* ```
|
|
785
|
+
*/
|
|
786
|
+
declare const createSdlStreams: (options?: SdlStreamsOptions) => SdlStreams;
|
|
787
|
+
|
|
788
|
+
/**
|
|
789
|
+
* SDL Input Bridge
|
|
790
|
+
*
|
|
791
|
+
* Maps SDL keyboard events to terminal escape sequences for Ink compatibility.
|
|
792
|
+
*/
|
|
793
|
+
|
|
794
|
+
/**
|
|
795
|
+
* Terminal-style key event for Ink
|
|
796
|
+
*/
|
|
797
|
+
interface InkKeyEvent {
|
|
798
|
+
sequence: string;
|
|
799
|
+
name: string;
|
|
800
|
+
ctrl: boolean;
|
|
801
|
+
meta: boolean;
|
|
802
|
+
shift: boolean;
|
|
803
|
+
}
|
|
804
|
+
/**
|
|
805
|
+
* Track modifier key state
|
|
806
|
+
*/
|
|
807
|
+
interface ModifierState {
|
|
808
|
+
shift: boolean;
|
|
809
|
+
ctrl: boolean;
|
|
810
|
+
alt: boolean;
|
|
811
|
+
}
|
|
812
|
+
/**
|
|
813
|
+
* SDL to Terminal Input Bridge
|
|
814
|
+
*
|
|
815
|
+
* Converts SDL keyboard events to terminal-compatible sequences
|
|
816
|
+
* that Ink can understand.
|
|
817
|
+
*/
|
|
818
|
+
declare class InputBridge {
|
|
819
|
+
private modifiers;
|
|
820
|
+
/**
|
|
821
|
+
* Process an SDL key event and return terminal sequence
|
|
822
|
+
*/
|
|
823
|
+
processKeyEvent(event: SdlKeyEvent): string | null;
|
|
824
|
+
/**
|
|
825
|
+
* Check if a keycode is a modifier key
|
|
826
|
+
*/
|
|
827
|
+
private isModifierKey;
|
|
828
|
+
/**
|
|
829
|
+
* Update modifier key state
|
|
830
|
+
*/
|
|
831
|
+
private updateModifierState;
|
|
832
|
+
/**
|
|
833
|
+
* Get terminal escape sequence for special keys
|
|
834
|
+
*/
|
|
835
|
+
private getSpecialKeySequence;
|
|
836
|
+
/**
|
|
837
|
+
* Get Ctrl+key sequence
|
|
838
|
+
*/
|
|
839
|
+
private getCtrlSequence;
|
|
840
|
+
/**
|
|
841
|
+
* Convert SDL key event to Ink-style key event
|
|
842
|
+
*/
|
|
843
|
+
toInkKeyEvent(event: SdlKeyEvent): InkKeyEvent | null;
|
|
844
|
+
/**
|
|
845
|
+
* Get human-readable key name
|
|
846
|
+
*/
|
|
847
|
+
private getKeyName;
|
|
848
|
+
/**
|
|
849
|
+
* Reset modifier state
|
|
850
|
+
*/
|
|
851
|
+
reset(): void;
|
|
852
|
+
/**
|
|
853
|
+
* Get current modifier state
|
|
854
|
+
*/
|
|
855
|
+
getModifiers(): ModifierState;
|
|
856
|
+
}
|
|
857
|
+
|
|
858
|
+
/**
|
|
859
|
+
* ink-sdl
|
|
860
|
+
*
|
|
861
|
+
* Render Ink TUI applications to an SDL window instead of the terminal.
|
|
862
|
+
*
|
|
863
|
+
* @example
|
|
864
|
+
* ```typescript
|
|
865
|
+
* import { render, Text, Box } from "ink";
|
|
866
|
+
* import { createSdlStreams } from "ink-sdl";
|
|
867
|
+
*
|
|
868
|
+
* const App = () => (
|
|
869
|
+
* <Box flexDirection="column">
|
|
870
|
+
* <Text color="green">Hello from SDL!</Text>
|
|
871
|
+
* </Box>
|
|
872
|
+
* );
|
|
873
|
+
*
|
|
874
|
+
* const { stdin, stdout, window } = createSdlStreams({
|
|
875
|
+
* title: "My App",
|
|
876
|
+
* width: 800,
|
|
877
|
+
* height: 600,
|
|
878
|
+
* });
|
|
879
|
+
*
|
|
880
|
+
* render(<App />, { stdin, stdout });
|
|
881
|
+
*
|
|
882
|
+
* window.on("close", () => process.exit(0));
|
|
883
|
+
* ```
|
|
884
|
+
*/
|
|
885
|
+
|
|
886
|
+
/**
|
|
887
|
+
* Check if SDL is available for rendering
|
|
888
|
+
*/
|
|
889
|
+
declare const isSdlAvailable: () => boolean;
|
|
890
|
+
|
|
891
|
+
export { AnsiParser, type Color, type DrawCommand, type InkKeyEvent, InputBridge, SDL2API, type SDLPointer, SDL_ttfAPI, SdlInputStream, type SdlKeyEvent, SdlOutputStream, type SdlStreams, type SdlStreamsOptions, SdlUiRenderer, type SdlUiRendererOptions, SdlWindow, TextRenderer, createSDLRect, createSdlStreams, getSDL2, getSDL_ttf, isSDL2Available, isSDL_ttfAvailable, isSdlAvailable };
|