asciify-engine 1.0.117 → 1.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 +35 -1
- package/dist/backgrounds.cjs +1 -0
- package/dist/backgrounds.d.cts +401 -0
- package/dist/backgrounds.d.ts +401 -0
- package/dist/backgrounds.js +1 -0
- package/dist/core.cjs +1 -0
- package/dist/core.d.cts +1265 -0
- package/dist/core.d.ts +1265 -0
- package/dist/core.js +1 -0
- package/dist/index.cjs +1 -1
- package/dist/index.d.cts +2 -1668
- package/dist/index.d.ts +2 -1668
- package/dist/index.js +1 -1
- package/examples/media-background.ts +22 -0
- package/package.json +26 -3
- package/skills/asciify-engine/SKILL.md +76 -749
- package/skills/asciify-engine/agents/openai.yaml +2 -2
- package/skills/asciify-engine/examples/layered-hero.css +30 -0
- package/skills/asciify-engine/examples/layered-hero.html +31 -0
- package/skills/asciify-engine/examples/layered-hero.js +78 -0
- package/skills/asciify-engine/references/layered-hero.md +45 -0
- package/skills/asciify-engine/references/media-api.md +109 -0
- package/skills/asciify-engine/references/studio-effects.md +51 -0
- package/dist/index.cjs.map +0 -1
- package/dist/index.js.map +0 -1
package/dist/index.d.ts
CHANGED
|
@@ -1,1668 +1,2 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
type AnimationStyle = 'none' | 'wave' | 'pulse' | 'rain' | 'breathe' | 'sparkle' | 'glitch' | 'spiral' | 'typewriter' | 'scatter' | 'waveField' | 'ripple' | 'melt' | 'orbit' | 'cellular';
|
|
4
|
-
type ArtStyle = 'classic' | 'particles' | 'letters' | 'claudeCode' | 'art' | 'terminal' | 'box' | 'lines' | 'braille' | 'katakana' | 'musical' | 'emoji' | 'circles' | 'shadows' | 'starfield' | 'geometric' | 'pipes' | 'waves' | 'shards' | 'smoke' | 'ascii' | 'interface' | 'prompt' | 'data' | 'humanist' | 'mesh';
|
|
5
|
-
type HoverEffect = 'spotlight' | 'magnify' | 'repel' | 'glow' | 'colorShift' | 'attract' | 'shatter' | 'trail' | 'glitchText';
|
|
6
|
-
type HoverShape = 'circle' | 'box';
|
|
7
|
-
type HoverPreset = 'none' | 'subtle' | 'flashlight' | 'magnifier' | 'forceField' | 'neon' | 'fire' | 'ice' | 'gravity' | 'shatter' | 'ghost' | 'glitchReveal';
|
|
8
|
-
type SourceCropUnit = 'percent' | 'pixel';
|
|
9
|
-
type SourceCropAnchor = 'center' | 'top' | 'bottom' | 'left' | 'right' | 'top-left' | 'top-right' | 'bottom-left' | 'bottom-right';
|
|
10
|
-
interface SourceCrop {
|
|
11
|
-
/** Legacy crop origin on the source media. Percent values use 0–1. Default: centered when cropped */
|
|
12
|
-
x?: number;
|
|
13
|
-
/** Legacy crop origin on the source media. Percent values use 0–1. Default: centered when cropped */
|
|
14
|
-
y?: number;
|
|
15
|
-
/** Legacy crop width on the source media. Percent values use 0–1. Default: mirrors `height` to preserve proportions */
|
|
16
|
-
width?: number;
|
|
17
|
-
/** Legacy crop height on the source media. Percent values use 0–1. Default: mirrors `width` to preserve proportions */
|
|
18
|
-
height?: number;
|
|
19
|
-
/** CSS-like crop inset from the top edge. Percent values use 0–1. */
|
|
20
|
-
top?: number;
|
|
21
|
-
/** CSS-like crop inset from the right edge. Percent values use 0–1. */
|
|
22
|
-
right?: number;
|
|
23
|
-
/** CSS-like crop inset from the bottom edge. Percent values use 0–1. */
|
|
24
|
-
bottom?: number;
|
|
25
|
-
/** CSS-like crop inset from the left edge. Percent values use 0–1. */
|
|
26
|
-
left?: number;
|
|
27
|
-
/**
|
|
28
|
-
* Keep the source aspect ratio when deriving a crop from a single `width` or
|
|
29
|
-
* `height`. CSS-like side insets (`top`, `right`, `bottom`, `left`) already
|
|
30
|
-
* define an exact source view box, and `asciifyVideo` sizes from that crop
|
|
31
|
-
* aspect so the output does not stretch. Default: `true`.
|
|
32
|
-
*/
|
|
33
|
-
preserveAspect?: boolean;
|
|
34
|
-
/** Bias auto-centered crops toward an edge or corner. Default: `'center'` */
|
|
35
|
-
anchor?: SourceCropAnchor;
|
|
36
|
-
/** Interpret values as normalized percentages or source pixels. Default: `'percent'` */
|
|
37
|
-
unit?: SourceCropUnit;
|
|
38
|
-
}
|
|
39
|
-
/**
|
|
40
|
-
* Named colour palette presets — pass as `colorMode` for themed rendering.
|
|
41
|
-
* Applied as a post-process colour remap over the standard grayscale output.
|
|
42
|
-
*/
|
|
43
|
-
type PaletteTheme = 'dracula' | 'monokai' | 'nord' | 'catppuccin' | 'solarized' | 'gruvbox';
|
|
44
|
-
declare const PALETTE_THEMES: Record<PaletteTheme, {
|
|
45
|
-
name: string;
|
|
46
|
-
accent: string;
|
|
47
|
-
bg: string;
|
|
48
|
-
fg: string;
|
|
49
|
-
}>;
|
|
50
|
-
type SourceType = 'image' | 'video' | 'gif' | null;
|
|
51
|
-
interface AsciiOptions {
|
|
52
|
-
/** Character cell size in pixels. Smaller = more detail, more cells. Default: `10` */
|
|
53
|
-
fontSize: number;
|
|
54
|
-
/** Extra horizontal spacing between characters (pixels). Default: `1` */
|
|
55
|
-
charSpacing: number;
|
|
56
|
-
/**
|
|
57
|
-
* Brightness adjustment applied before luminance mapping.
|
|
58
|
-
* Range −1 (black) → 0 (unchanged) → 1 (white). Default: `0`
|
|
59
|
-
*/
|
|
60
|
-
brightness: number;
|
|
61
|
-
/**
|
|
62
|
-
* Contrast boost applied before luminance mapping.
|
|
63
|
-
* `0` = unchanged, positive values increase contrast, negative decrease it.
|
|
64
|
-
* Default: `0`
|
|
65
|
-
*/
|
|
66
|
-
contrast: number;
|
|
67
|
-
/**
|
|
68
|
-
* Character density ramp — ordered from lightest to darkest.
|
|
69
|
-
* Use `CHARSETS` for pre-built ramps or supply your own string.
|
|
70
|
-
* Default: `' .:-=+*#%@'`
|
|
71
|
-
*/
|
|
72
|
-
charset: string;
|
|
73
|
-
/**
|
|
74
|
-
* Colour output mode.
|
|
75
|
-
* - `'grayscale'` — white-on-black monochrome
|
|
76
|
-
* - `'fullcolor'` — samples pixel colours from the source
|
|
77
|
-
* - `'matrix'` — green phosphor terminal look
|
|
78
|
-
* - `'accent'` — single accent colour with intensity-driven brightness
|
|
79
|
-
* Default: `'grayscale'`
|
|
80
|
-
*/
|
|
81
|
-
colorMode: ColorMode;
|
|
82
|
-
/**
|
|
83
|
-
* The accent colour used when `colorMode` is `'accent'` or `'matrix'`.
|
|
84
|
-
* Any CSS colour string. Default: `'#d4ff00'`
|
|
85
|
-
*/
|
|
86
|
-
/**
|
|
87
|
-
* Hex color string used when `colorMode` is `'accent'`.
|
|
88
|
-
* Set to `'auto'` to let the engine pick contrasting ink automatically:
|
|
89
|
-
* dark ink (`#0d0d0d`) in light mode, light ink (`#faf9f7`) in dark mode.
|
|
90
|
-
*/
|
|
91
|
-
accentColor: string;
|
|
92
|
-
/**
|
|
93
|
-
* Invert luminance mapping (light pixels → dense chars). Default: `false`
|
|
94
|
-
*
|
|
95
|
-
* Set to `'auto'` to let the engine detect the OS color scheme:
|
|
96
|
-
* - Light mode → inverts (bright pixel = dark char = visible on white background)
|
|
97
|
-
* - Dark mode → normal (bright pixel = bright char = visible on dark background)
|
|
98
|
-
*/
|
|
99
|
-
invert: boolean | 'auto';
|
|
100
|
-
/**
|
|
101
|
-
* Render mode.
|
|
102
|
-
* - `'ascii'` — characters drawn as text
|
|
103
|
-
* - `'dots'` — each cell rendered as a filled circle (particle look)
|
|
104
|
-
* Default: `'ascii'`
|
|
105
|
-
*/
|
|
106
|
-
renderMode: RenderMode;
|
|
107
|
-
/**
|
|
108
|
-
* Per-character animation driven over time.
|
|
109
|
-
* Applies wave, glitch, rain-drop, spiral, and other effects to the rendered text.
|
|
110
|
-
* Default: `'none'`
|
|
111
|
-
*/
|
|
112
|
-
animationStyle: AnimationStyle;
|
|
113
|
-
/** Speed multiplier for `animationStyle` effects. Default: `1` */
|
|
114
|
-
animationSpeed: number;
|
|
115
|
-
/**
|
|
116
|
-
* Size of each dot relative to the cell when `renderMode === 'dots'`.
|
|
117
|
-
* `1` fills the whole cell, `0.5` draws half-size circles. Default: `0.8`
|
|
118
|
-
*/
|
|
119
|
-
dotSizeRatio: number;
|
|
120
|
-
/**
|
|
121
|
-
* Floyd-Steinberg dither strength applied to the luminance map.
|
|
122
|
-
* `0` = no dithering, `1` = full dithering. Default: `0`
|
|
123
|
-
*/
|
|
124
|
-
ditherStrength: number;
|
|
125
|
-
/**
|
|
126
|
-
* Assumed aspect ratio (width ÷ height) of a single output character.
|
|
127
|
-
* Controls how many rows vs columns are generated — must match your rendering
|
|
128
|
-
* environment to preserve the source image's proportions.
|
|
129
|
-
* - `0.55` — browser monospace at `line-height: 1.09` (default)
|
|
130
|
-
* - `0.52` — browser monospace at `line-height: 1.15`
|
|
131
|
-
* - `0.5` — most terminal emulators
|
|
132
|
-
* Default: `0.55`
|
|
133
|
-
*/
|
|
134
|
-
charAspect: number;
|
|
135
|
-
/**
|
|
136
|
-
* Auto-stretch the luminance range before charset mapping.
|
|
137
|
-
* When `true`, the darkest pixel in the frame maps to the first charset character
|
|
138
|
-
* and the brightest to the last, maximising perceived detail and contrast.
|
|
139
|
-
* Particularly useful for images with low inherent contrast or muted tones.
|
|
140
|
-
* Default: `false`
|
|
141
|
-
*/
|
|
142
|
-
normalize: boolean;
|
|
143
|
-
/**
|
|
144
|
-
* Overall intensity of the hover / cursor interaction effect.
|
|
145
|
-
* `0` disables the effect. Default: `0`
|
|
146
|
-
*/
|
|
147
|
-
hoverStrength: number;
|
|
148
|
-
/**
|
|
149
|
-
* Radius of the hover interaction zone as a fraction of the canvas size.
|
|
150
|
-
* `0.1` = 10% of canvas width. Default: `0.2`
|
|
151
|
-
*/
|
|
152
|
-
hoverRadius: number;
|
|
153
|
-
/**
|
|
154
|
-
* Which cursor interaction style to apply when `hoverStrength > 0`.
|
|
155
|
-
* See `HoverPreset` or `HOVER_PRESETS` for ready-made configurations.
|
|
156
|
-
* Default: `'spotlight'`
|
|
157
|
-
*/
|
|
158
|
-
hoverEffect: HoverEffect;
|
|
159
|
-
/**
|
|
160
|
-
* Tint colour used by hover effects such as spotlight, glow, and colorShift.
|
|
161
|
-
* Any CSS colour string. Default: `'#ffffff'`
|
|
162
|
-
*/
|
|
163
|
-
hoverColor: string;
|
|
164
|
-
/**
|
|
165
|
-
* Shape of the hover interaction zone.
|
|
166
|
-
* - `'circle'` — radial falloff (default)
|
|
167
|
-
* - `'box'` — rectangular zone, text fills a block around the cursor
|
|
168
|
-
* Default: `'circle'`
|
|
169
|
-
*/
|
|
170
|
-
hoverShape: HoverShape;
|
|
171
|
-
/**
|
|
172
|
-
* Text string revealed by the `'glitchText'` hover effect.
|
|
173
|
-
* Characters around the cursor scramble and resolve into this text.
|
|
174
|
-
* Supports `\n` for multi-line reveals.
|
|
175
|
-
*
|
|
176
|
-
* Pass an **array** of strings to cycle through different words based on
|
|
177
|
-
* the cursor's grid region — the engine picks one via a spatial hash so
|
|
178
|
-
* each area of the canvas shows a different word.
|
|
179
|
-
*
|
|
180
|
-
* Default: `'ASCIIFY'`
|
|
181
|
-
*
|
|
182
|
-
* @example
|
|
183
|
-
* // Single word:
|
|
184
|
-
* options: { hoverEffect: 'glitchText', hoverText: 'HELLO' }
|
|
185
|
-
*
|
|
186
|
-
* // Word pool — different text at different cursor positions:
|
|
187
|
-
* options: { hoverEffect: 'glitchText', hoverText: ['DEPLOY', 'SCALE', 'SHIP', 'BUILD'] }
|
|
188
|
-
*/
|
|
189
|
-
hoverText: string | string[];
|
|
190
|
-
/**
|
|
191
|
-
* Art style preset applied at render time.
|
|
192
|
-
* Shorthand for a specific combination of `charset`, `renderMode`, and `colorMode`.
|
|
193
|
-
* See `ART_STYLE_PRESETS` for the full list. Default: `'classic'`
|
|
194
|
-
*/
|
|
195
|
-
artStyle: ArtStyle;
|
|
196
|
-
/**
|
|
197
|
-
* Custom repeating text used when `artStyle` is `'letters'` or when you set
|
|
198
|
-
* a custom charset. Leave empty to use the selected `charset`. Default: `''`
|
|
199
|
-
*/
|
|
200
|
-
customText: string;
|
|
201
|
-
/**
|
|
202
|
-
* Chroma-key colour to remove from the source (green screen / blue screen).
|
|
203
|
-
* Pixels whose RGB distance from this colour is within `chromaKeyTolerance`
|
|
204
|
-
* are keyed out: their character becomes a space and alpha is set to 0,
|
|
205
|
-
* letting the canvas background show through.
|
|
206
|
-
*
|
|
207
|
-
* - `true` — **smart green screen**: heuristic detection (`g > r*1.4 && g > b*1.4`)
|
|
208
|
-
* catches every shade of green screen (lime, broadcast, chroma green) with no
|
|
209
|
-
* config. Works on virtually all studio/streaming footage.
|
|
210
|
-
* - `'blue-screen'` — **smart blue screen**: same heuristic for blue.
|
|
211
|
-
* - `{ r, g, b }` or CSS colour string — custom key colour + `chromaKeyTolerance`
|
|
212
|
-
* - `null` / `false` — disabled (default)
|
|
213
|
-
*
|
|
214
|
-
* @example
|
|
215
|
-
* // Standard green screen — zero config:
|
|
216
|
-
* options: { chromaKey: true }
|
|
217
|
-
*
|
|
218
|
-
* // Blue screen — zero config:
|
|
219
|
-
* options: { chromaKey: 'blue-screen' }
|
|
220
|
-
*
|
|
221
|
-
* // Custom CSS colour:
|
|
222
|
-
* options: { chromaKey: '#00b140', chromaKeyTolerance: 70 }
|
|
223
|
-
*/
|
|
224
|
-
chromaKey: {
|
|
225
|
-
r: number;
|
|
226
|
-
g: number;
|
|
227
|
-
b: number;
|
|
228
|
-
} | string | boolean | null;
|
|
229
|
-
/**
|
|
230
|
-
* Euclidean RGB tolerance radius for chroma-key detection.
|
|
231
|
-
* `0` = exact match only, `441` ≈ key out everything.
|
|
232
|
-
* Higher values remove more pixels. Default: `60`
|
|
233
|
-
*/
|
|
234
|
-
chromaKeyTolerance: number;
|
|
235
|
-
/**
|
|
236
|
-
* Extra normalized padding kept around the detected chroma-key foreground when
|
|
237
|
-
* `asciifyVideo` auto-trims keyed video content inside `sourceCrop`.
|
|
238
|
-
* `0` hugs the visible foreground. `0.01` keeps 1% safety padding.
|
|
239
|
-
* Default: `0.002`
|
|
240
|
-
*/
|
|
241
|
-
chromaKeyTrimPadding: number;
|
|
242
|
-
/**
|
|
243
|
-
* Minimum source-pixel luminance for chroma-key foreground auto-trim.
|
|
244
|
-
* Raise this when faint edge noise is counted as content and prevents a
|
|
245
|
-
* keyed subject from filling a preserved-ratio layout. Range `0–255`.
|
|
246
|
-
* Default: `0`
|
|
247
|
-
*/
|
|
248
|
-
chromaKeyTrimLuminanceThreshold: number;
|
|
249
|
-
/**
|
|
250
|
-
* How keyed video foreground trimming is applied when `chromaKey` and
|
|
251
|
-
* `sourceCrop` are enabled.
|
|
252
|
-
*
|
|
253
|
-
* - `'range'` samples the video/scroll range once and keeps a stable union
|
|
254
|
-
* crop. Best default for consistent framing.
|
|
255
|
-
* - `'frame'` remeasures each rendered frame and expands the crop to the
|
|
256
|
-
* render aspect. Best for scroll-scrubbed hero footage where foreground
|
|
257
|
-
* position changes and pure contain leaves empty edges.
|
|
258
|
-
* - `'off'` disables automatic keyed foreground trimming.
|
|
259
|
-
*
|
|
260
|
-
* Default: `'range'`
|
|
261
|
-
*/
|
|
262
|
-
chromaKeyTrimMode: 'range' | 'frame' | 'off';
|
|
263
|
-
/**
|
|
264
|
-
* Optional source crop applied before ASCII sampling.
|
|
265
|
-
*
|
|
266
|
-
* Use this when the media has empty edges or a subject that should be framed
|
|
267
|
-
* tighter without changing the destination canvas size.
|
|
268
|
-
*
|
|
269
|
-
* @example
|
|
270
|
-
* // Remove 15% from the top and 15% from the bottom, preserving proportions:
|
|
271
|
-
* options: { sourceCrop: { top: 0.15, bottom: 0.15 } }
|
|
272
|
-
*
|
|
273
|
-
* @example
|
|
274
|
-
* // Keep 70% of the source, preserve proportions, and center it:
|
|
275
|
-
* options: { sourceCrop: { height: 0.7 } }
|
|
276
|
-
*
|
|
277
|
-
* @example
|
|
278
|
-
* // Use an exact source window when manual framing should override proportions:
|
|
279
|
-
* options: { sourceCrop: { x: 0.05, y: 0.08, width: 0.9, height: 0.9, preserveAspect: false } }
|
|
280
|
-
*/
|
|
281
|
-
sourceCrop?: SourceCrop | null;
|
|
282
|
-
/**
|
|
283
|
-
* Array of charset strings to cycle through over time.
|
|
284
|
-
* The engine picks `charsetFrames[Math.floor(time * charsetFps) % length]` on each
|
|
285
|
-
* render tick, re-mapping characters from stored cell luminance.
|
|
286
|
-
* Pairs beautifully with `animationStyle` and `asciiBackground`.
|
|
287
|
-
*
|
|
288
|
-
* Use `CHARSET_SEQUENCES` for curated combinations or build your own:
|
|
289
|
-
* @example
|
|
290
|
-
* options: { charsetFrames: CHARSET_SEQUENCES.cosmic }
|
|
291
|
-
* options: { charsetFrames: [CHARSETS.standard, CHARSETS.blocks, CHARSETS.circles] }
|
|
292
|
-
*/
|
|
293
|
-
charsetFrames?: string[];
|
|
294
|
-
/** Cycle rate for `charsetFrames` in frames-per-second. Default: `2` */
|
|
295
|
-
charsetFps?: number;
|
|
296
|
-
}
|
|
297
|
-
interface AsciiCell {
|
|
298
|
-
char: string;
|
|
299
|
-
r: number;
|
|
300
|
-
g: number;
|
|
301
|
-
b: number;
|
|
302
|
-
a: number;
|
|
303
|
-
/** Stored dithered luminance (0–255). Present when the frame was generated by the engine. Used for dynamic charset re-selection at render time via `charsetFrames`. */
|
|
304
|
-
lum?: number;
|
|
305
|
-
}
|
|
306
|
-
type AsciiFrame = AsciiCell[][];
|
|
307
|
-
interface AsciiResult {
|
|
308
|
-
frames: AsciiFrame[];
|
|
309
|
-
cols: number;
|
|
310
|
-
rows: number;
|
|
311
|
-
fps: number;
|
|
312
|
-
}
|
|
313
|
-
declare const CHARSETS: {
|
|
314
|
-
readonly standard: " .:-=+*#%@";
|
|
315
|
-
readonly blocks: " ░▒▓█";
|
|
316
|
-
readonly minimal: " .:+";
|
|
317
|
-
readonly dense: " .'`^\",:;Il!i><~+_-?][}{1)(|/tfjrxnuvczXYUJCLQ0OZmwqpdbkhao*#MW&8%B@$";
|
|
318
|
-
readonly binary: "01";
|
|
319
|
-
readonly dots: " ⠁⠃⠇⡇⣇⣧⣷⣿";
|
|
320
|
-
readonly letters: "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
|
|
321
|
-
readonly claudeCode: " ╔╗╚╝║═╠╣╦╩╬░▒▓█│─┌┐└┘├┤┬┴┼";
|
|
322
|
-
readonly box: " ▪◾◼■█";
|
|
323
|
-
readonly lines: " ˗‐–—―━";
|
|
324
|
-
readonly braille: " ⠁⠂⠃⠄⠅⠆⠇⠈⠉⠊⠋⠌⠍⠎⠏⠐⠑⠒⠓⠔⠕⠖⠗⠘⠙⠚⠛⠜⠝⠞⠟⠠⠡⠢⠣⠤⠥⠦⠧⠨⠩⠪⠫⠬⠭⠮⠯⠰⠱⠲⠳⠴⠵⠶⠷⠸⠹⠺⠻⠼⠽⠾⠿⡀⡁⡂⡃⡄⡅⡆⡇⣀⣁⣂⣃⣄⣅⣆⣇⣈⣉⣊⣋⣌⣍⣎⣏⣐⣑⣒⣓⣔⣕⣖⣗⣘⣙⣚⣛⣜⣝⣞⣟⣠⣡⣢⣣⣤⣥⣦⣧⣨⣩⣪⣫⣬⣭⣮⣯⣰⣱⣲⣳⣴⣵⣶⣷⣸⣹⣺⣻⣼⣽⣾⣿";
|
|
325
|
-
readonly katakana: " ヲァィゥェォャュョッアイウエオカキクケコサシスセソタチツテトナニヌネノハヒフヘホマミムメモヤユヨラリルレロワン";
|
|
326
|
-
readonly musical: " ♩♪♫♬♭♮♯";
|
|
327
|
-
readonly emoji: " ⬛🟫🟥🟧🟨🟩🟦🟪⬜";
|
|
328
|
-
readonly circles: " .·:∘○◦°•∙";
|
|
329
|
-
readonly shadows: " ·∘◦○◎⊙●◉";
|
|
330
|
-
readonly starfield: " ˙·∘∗✦✧★◆●";
|
|
331
|
-
readonly geometric: " ·△▷◇◈◆▣■█";
|
|
332
|
-
readonly pipes: " ╶─┐└├┤┬┴┼╬▒▓█";
|
|
333
|
-
readonly waves: " ˜∼≈〰≋∿∾∭∫";
|
|
334
|
-
readonly shards: " ╱╲╳◤◥◣◢△▲◆◼█";
|
|
335
|
-
readonly smoke: " ·˙⁚⁖∶∷⋮⋰⋱∴∵";
|
|
336
|
-
/** All printable ASCII characters ordered from airy punctuation to dense symbols. */
|
|
337
|
-
readonly ascii: " .'`^\",:;~-_+<>i!lI?/\\|()[]{}1tfjrxnuvczXYUJCLQ0OZmwqpdbkhao*#MW&8%B@$";
|
|
338
|
-
/** Clean product UI glyphs inspired by command palettes, panes, controls, and focus rings. */
|
|
339
|
-
readonly interface: " ·•-–—+=:;<>[]{}()⌘⌥⇧⌃↵↗↘◇◆◈□■";
|
|
340
|
-
/** Prompt, shell, and assistant transcript glyphs for modern AI/dev surfaces. */
|
|
341
|
-
readonly prompt: " .:;>_`/\\|{}[]()=+*#@$";
|
|
342
|
-
/** Analytical/data-viz glyphs: sparse dots into nodes, diamonds, and dense blocks. */
|
|
343
|
-
readonly data: " ·∙•◦○●◇◆◈▱▰▣█";
|
|
344
|
-
/** Warm editorial/math symbols for quieter Claude-like and research-oriented pages. */
|
|
345
|
-
readonly humanist: " ·˙,:;∴∵∷∶⁚⋮⋯∼≈≋∞";
|
|
346
|
-
/** Dense network/mesh characters for agent maps, model graphs, and infrastructure visuals. */
|
|
347
|
-
readonly mesh: " ·╶╴╷╵─│┌┐└┘├┤┬┴┼╬░▒▓█";
|
|
348
|
-
};
|
|
349
|
-
/**
|
|
350
|
-
* Curated charset sequences for use with `charsetFrames`.
|
|
351
|
-
* Each sequence morphs between 2–3 complementary charsets over time,
|
|
352
|
-
* creating a living texture effect.
|
|
353
|
-
*
|
|
354
|
-
* @example
|
|
355
|
-
* asciiBackground('#hero', { charsetFrames: CHARSET_SEQUENCES.cosmic })
|
|
356
|
-
*/
|
|
357
|
-
declare const CHARSET_SEQUENCES: {
|
|
358
|
-
/** Stars → softcircles → orbs — dreamy space feel */
|
|
359
|
-
readonly cosmic: string[];
|
|
360
|
-
/** Katakana → braille dots → binary — hacker rain */
|
|
361
|
-
readonly rain: string[];
|
|
362
|
-
/** Box pipes → Claude glyphs → classic — terminal morph */
|
|
363
|
-
readonly terminal: string[];
|
|
364
|
-
/** Shards → blocks → squares — shattering crystal */
|
|
365
|
-
readonly crystal: string[];
|
|
366
|
-
/** Wave glyphs → smoke dots → circles — fluid / organic */
|
|
367
|
-
readonly fluid: string[];
|
|
368
|
-
/** Dense classic → art → blocks — maximum detail pulse */
|
|
369
|
-
readonly pulse: string[];
|
|
370
|
-
/** Braille → shadows → smoke — ethereal / dream-like */
|
|
371
|
-
readonly dream: string[];
|
|
372
|
-
/** Geometric shapes → shards → starfield — sci-fi angular */
|
|
373
|
-
readonly angular: string[];
|
|
374
|
-
/** Interface controls → prompts → data nodes — clean assistant/product motion */
|
|
375
|
-
readonly assistant: string[];
|
|
376
|
-
/** Mesh → data → ASCII — alive network signal with readable texture */
|
|
377
|
-
readonly signal: string[];
|
|
378
|
-
/** Humanist symbols → waves → smoke — soft research/editorial motion */
|
|
379
|
-
readonly editorial: string[];
|
|
380
|
-
};
|
|
381
|
-
type CharsetSequenceKey = keyof typeof CHARSET_SEQUENCES;
|
|
382
|
-
type CharsetKey = keyof typeof CHARSETS;
|
|
383
|
-
/**
|
|
384
|
-
* Art Style presets — each one sets render mode, charset, color mode, etc.
|
|
385
|
-
*/
|
|
386
|
-
declare const ART_STYLE_PRESETS: Record<ArtStyle, Partial<AsciiOptions>>;
|
|
387
|
-
/**
|
|
388
|
-
* Higher-level living presets for output that should feel active immediately.
|
|
389
|
-
* They intentionally compose existing primitives so renderers and integrations
|
|
390
|
-
* can consume them as a normal `Partial<AsciiOptions>`.
|
|
391
|
-
*/
|
|
392
|
-
declare const LIVING_STYLE_PRESETS: {
|
|
393
|
-
readonly agentField: {
|
|
394
|
-
readonly charsetFrames: string[];
|
|
395
|
-
readonly charsetFps: 1.6;
|
|
396
|
-
readonly animationStyle: "breathe";
|
|
397
|
-
readonly animationSpeed: 0.75;
|
|
398
|
-
readonly ditherStrength: 0.12;
|
|
399
|
-
readonly hoverEffect: "glow";
|
|
400
|
-
readonly hoverStrength: 0.42;
|
|
401
|
-
readonly hoverRadius: 0.18;
|
|
402
|
-
readonly hoverColor: "#f4f1ea";
|
|
403
|
-
readonly normalize: true;
|
|
404
|
-
readonly fontSize?: number | undefined;
|
|
405
|
-
readonly charSpacing?: number | undefined;
|
|
406
|
-
readonly brightness?: number | undefined;
|
|
407
|
-
readonly contrast?: number | undefined;
|
|
408
|
-
readonly charset?: string | undefined;
|
|
409
|
-
readonly colorMode?: ColorMode | undefined;
|
|
410
|
-
readonly accentColor?: string | undefined;
|
|
411
|
-
readonly invert?: boolean | "auto" | undefined;
|
|
412
|
-
readonly renderMode?: RenderMode | undefined;
|
|
413
|
-
readonly dotSizeRatio?: number | undefined;
|
|
414
|
-
readonly charAspect?: number | undefined;
|
|
415
|
-
readonly hoverShape?: HoverShape | undefined;
|
|
416
|
-
readonly hoverText?: string | string[] | undefined;
|
|
417
|
-
readonly artStyle?: ArtStyle | undefined;
|
|
418
|
-
readonly customText?: string | undefined;
|
|
419
|
-
readonly chromaKey?: string | boolean | {
|
|
420
|
-
r: number;
|
|
421
|
-
g: number;
|
|
422
|
-
b: number;
|
|
423
|
-
} | null | undefined;
|
|
424
|
-
readonly chromaKeyTolerance?: number | undefined;
|
|
425
|
-
readonly chromaKeyTrimPadding?: number | undefined;
|
|
426
|
-
readonly chromaKeyTrimLuminanceThreshold?: number | undefined;
|
|
427
|
-
readonly chromaKeyTrimMode?: "range" | "frame" | "off" | undefined;
|
|
428
|
-
readonly sourceCrop?: SourceCrop | null;
|
|
429
|
-
};
|
|
430
|
-
readonly liquidSignal: {
|
|
431
|
-
readonly charsetFrames: string[];
|
|
432
|
-
readonly charsetFps: 2.4;
|
|
433
|
-
readonly animationStyle: "melt";
|
|
434
|
-
readonly animationSpeed: 0.65;
|
|
435
|
-
readonly ditherStrength: 0.45;
|
|
436
|
-
readonly hoverEffect: "repel";
|
|
437
|
-
readonly hoverStrength: 0.55;
|
|
438
|
-
readonly hoverRadius: 0.22;
|
|
439
|
-
readonly hoverColor: "#8fd3ff";
|
|
440
|
-
readonly normalize: true;
|
|
441
|
-
readonly fontSize?: number | undefined;
|
|
442
|
-
readonly charSpacing?: number | undefined;
|
|
443
|
-
readonly brightness?: number | undefined;
|
|
444
|
-
readonly contrast?: number | undefined;
|
|
445
|
-
readonly charset?: string | undefined;
|
|
446
|
-
readonly colorMode?: ColorMode | undefined;
|
|
447
|
-
readonly accentColor?: string | undefined;
|
|
448
|
-
readonly invert?: boolean | "auto" | undefined;
|
|
449
|
-
readonly renderMode?: RenderMode | undefined;
|
|
450
|
-
readonly dotSizeRatio?: number | undefined;
|
|
451
|
-
readonly charAspect?: number | undefined;
|
|
452
|
-
readonly hoverShape?: HoverShape | undefined;
|
|
453
|
-
readonly hoverText?: string | string[] | undefined;
|
|
454
|
-
readonly artStyle?: ArtStyle | undefined;
|
|
455
|
-
readonly customText?: string | undefined;
|
|
456
|
-
readonly chromaKey?: string | boolean | {
|
|
457
|
-
r: number;
|
|
458
|
-
g: number;
|
|
459
|
-
b: number;
|
|
460
|
-
} | null | undefined;
|
|
461
|
-
readonly chromaKeyTolerance?: number | undefined;
|
|
462
|
-
readonly chromaKeyTrimPadding?: number | undefined;
|
|
463
|
-
readonly chromaKeyTrimLuminanceThreshold?: number | undefined;
|
|
464
|
-
readonly chromaKeyTrimMode?: "range" | "frame" | "off" | undefined;
|
|
465
|
-
readonly sourceCrop?: SourceCrop | null;
|
|
466
|
-
};
|
|
467
|
-
readonly cursorGravity: {
|
|
468
|
-
readonly charsetFrames: string[];
|
|
469
|
-
readonly charsetFps: 1.2;
|
|
470
|
-
readonly animationStyle: "orbit";
|
|
471
|
-
readonly animationSpeed: 0.9;
|
|
472
|
-
readonly ditherStrength: 0.2;
|
|
473
|
-
readonly hoverEffect: "attract";
|
|
474
|
-
readonly hoverStrength: 0.82;
|
|
475
|
-
readonly hoverRadius: 0.24;
|
|
476
|
-
readonly hoverColor: "#ffffff";
|
|
477
|
-
readonly normalize: true;
|
|
478
|
-
readonly fontSize?: number | undefined;
|
|
479
|
-
readonly charSpacing?: number | undefined;
|
|
480
|
-
readonly brightness?: number | undefined;
|
|
481
|
-
readonly contrast?: number | undefined;
|
|
482
|
-
readonly charset?: string | undefined;
|
|
483
|
-
readonly colorMode?: ColorMode | undefined;
|
|
484
|
-
readonly accentColor?: string | undefined;
|
|
485
|
-
readonly invert?: boolean | "auto" | undefined;
|
|
486
|
-
readonly renderMode?: RenderMode | undefined;
|
|
487
|
-
readonly dotSizeRatio?: number | undefined;
|
|
488
|
-
readonly charAspect?: number | undefined;
|
|
489
|
-
readonly hoverShape?: HoverShape | undefined;
|
|
490
|
-
readonly hoverText?: string | string[] | undefined;
|
|
491
|
-
readonly artStyle?: ArtStyle | undefined;
|
|
492
|
-
readonly customText?: string | undefined;
|
|
493
|
-
readonly chromaKey?: string | boolean | {
|
|
494
|
-
r: number;
|
|
495
|
-
g: number;
|
|
496
|
-
b: number;
|
|
497
|
-
} | null | undefined;
|
|
498
|
-
readonly chromaKeyTolerance?: number | undefined;
|
|
499
|
-
readonly chromaKeyTrimPadding?: number | undefined;
|
|
500
|
-
readonly chromaKeyTrimLuminanceThreshold?: number | undefined;
|
|
501
|
-
readonly chromaKeyTrimMode?: "range" | "frame" | "off" | undefined;
|
|
502
|
-
readonly sourceCrop?: SourceCrop | null;
|
|
503
|
-
};
|
|
504
|
-
readonly editorialPulse: {
|
|
505
|
-
readonly charsetFrames: string[];
|
|
506
|
-
readonly charsetFps: 0.9;
|
|
507
|
-
readonly animationStyle: "ripple";
|
|
508
|
-
readonly animationSpeed: 0.55;
|
|
509
|
-
readonly ditherStrength: 0.18;
|
|
510
|
-
readonly hoverEffect: "spotlight";
|
|
511
|
-
readonly hoverStrength: 0.35;
|
|
512
|
-
readonly hoverRadius: 0.2;
|
|
513
|
-
readonly hoverColor: "#fff8ea";
|
|
514
|
-
readonly normalize: true;
|
|
515
|
-
readonly fontSize?: number | undefined;
|
|
516
|
-
readonly charSpacing?: number | undefined;
|
|
517
|
-
readonly brightness?: number | undefined;
|
|
518
|
-
readonly contrast?: number | undefined;
|
|
519
|
-
readonly charset?: string | undefined;
|
|
520
|
-
readonly colorMode?: ColorMode | undefined;
|
|
521
|
-
readonly accentColor?: string | undefined;
|
|
522
|
-
readonly invert?: boolean | "auto" | undefined;
|
|
523
|
-
readonly renderMode?: RenderMode | undefined;
|
|
524
|
-
readonly dotSizeRatio?: number | undefined;
|
|
525
|
-
readonly charAspect?: number | undefined;
|
|
526
|
-
readonly hoverShape?: HoverShape | undefined;
|
|
527
|
-
readonly hoverText?: string | string[] | undefined;
|
|
528
|
-
readonly artStyle?: ArtStyle | undefined;
|
|
529
|
-
readonly customText?: string | undefined;
|
|
530
|
-
readonly chromaKey?: string | boolean | {
|
|
531
|
-
r: number;
|
|
532
|
-
g: number;
|
|
533
|
-
b: number;
|
|
534
|
-
} | null | undefined;
|
|
535
|
-
readonly chromaKeyTolerance?: number | undefined;
|
|
536
|
-
readonly chromaKeyTrimPadding?: number | undefined;
|
|
537
|
-
readonly chromaKeyTrimLuminanceThreshold?: number | undefined;
|
|
538
|
-
readonly chromaKeyTrimMode?: "range" | "frame" | "off" | undefined;
|
|
539
|
-
readonly sourceCrop?: SourceCrop | null;
|
|
540
|
-
};
|
|
541
|
-
readonly terminalFlow: {
|
|
542
|
-
readonly charsetFrames: string[];
|
|
543
|
-
readonly charsetFps: 3;
|
|
544
|
-
readonly animationStyle: "rain";
|
|
545
|
-
readonly animationSpeed: 1.1;
|
|
546
|
-
readonly ditherStrength: 0.22;
|
|
547
|
-
readonly hoverEffect: "glitchText";
|
|
548
|
-
readonly hoverStrength: 0.65;
|
|
549
|
-
readonly hoverRadius: 0.16;
|
|
550
|
-
readonly hoverColor: "#d4ff00";
|
|
551
|
-
readonly hoverText: ["BUILD", "SHIP", "RUN", "ASK", "MODEL"];
|
|
552
|
-
readonly normalize: true;
|
|
553
|
-
readonly fontSize?: number | undefined;
|
|
554
|
-
readonly charSpacing?: number | undefined;
|
|
555
|
-
readonly brightness?: number | undefined;
|
|
556
|
-
readonly contrast?: number | undefined;
|
|
557
|
-
readonly charset?: string | undefined;
|
|
558
|
-
readonly colorMode?: ColorMode | undefined;
|
|
559
|
-
readonly accentColor?: string | undefined;
|
|
560
|
-
readonly invert?: boolean | "auto" | undefined;
|
|
561
|
-
readonly renderMode?: RenderMode | undefined;
|
|
562
|
-
readonly dotSizeRatio?: number | undefined;
|
|
563
|
-
readonly charAspect?: number | undefined;
|
|
564
|
-
readonly hoverShape?: HoverShape | undefined;
|
|
565
|
-
readonly artStyle?: ArtStyle | undefined;
|
|
566
|
-
readonly customText?: string | undefined;
|
|
567
|
-
readonly chromaKey?: string | boolean | {
|
|
568
|
-
r: number;
|
|
569
|
-
g: number;
|
|
570
|
-
b: number;
|
|
571
|
-
} | null | undefined;
|
|
572
|
-
readonly chromaKeyTolerance?: number | undefined;
|
|
573
|
-
readonly chromaKeyTrimPadding?: number | undefined;
|
|
574
|
-
readonly chromaKeyTrimLuminanceThreshold?: number | undefined;
|
|
575
|
-
readonly chromaKeyTrimMode?: "range" | "frame" | "off" | undefined;
|
|
576
|
-
readonly sourceCrop?: SourceCrop | null;
|
|
577
|
-
};
|
|
578
|
-
};
|
|
579
|
-
type LivingStylePresetKey = keyof typeof LIVING_STYLE_PRESETS;
|
|
580
|
-
declare const DEFAULT_OPTIONS: AsciiOptions;
|
|
581
|
-
/**
|
|
582
|
-
* Hover presets — one-click configurations for the hover system.
|
|
583
|
-
*/
|
|
584
|
-
declare const HOVER_PRESETS: Record<HoverPreset, {
|
|
585
|
-
label: string;
|
|
586
|
-
options: Partial<AsciiOptions>;
|
|
587
|
-
}>;
|
|
588
|
-
|
|
589
|
-
/**
|
|
590
|
-
* Core frame-to-canvas renderer and source-to-frame converters.
|
|
591
|
-
*/
|
|
592
|
-
|
|
593
|
-
interface AsciiTextFrame {
|
|
594
|
-
rows: string[];
|
|
595
|
-
cols: number;
|
|
596
|
-
rowCount: number;
|
|
597
|
-
colors?: Uint8ClampedArray;
|
|
598
|
-
}
|
|
599
|
-
/** Clear shared renderer caches. Useful for long-lived editors that cycle many fonts/charsets. */
|
|
600
|
-
declare function clearAsciifyCaches(): void;
|
|
601
|
-
/**
|
|
602
|
-
* Convert an image element or canvas to a single ASCII frame.
|
|
603
|
-
*/
|
|
604
|
-
declare function imageToAsciiFrame(source: HTMLImageElement | HTMLVideoElement | HTMLCanvasElement, options: AsciiOptions, targetWidth?: number, targetHeight?: number): {
|
|
605
|
-
frame: AsciiFrame;
|
|
606
|
-
cols: number;
|
|
607
|
-
rows: number;
|
|
608
|
-
};
|
|
609
|
-
/**
|
|
610
|
-
* Convert a source into pre-shaped text rows for fast monochrome/accent ASCII.
|
|
611
|
-
*
|
|
612
|
-
* This is the high-performance path for dense video scrubbers. It keeps the
|
|
613
|
-
* expensive pixel sampling work, but avoids allocating one object per cell and
|
|
614
|
-
* lets the renderer draw one string per row instead of one `fillText` per cell.
|
|
615
|
-
*/
|
|
616
|
-
declare function imageToAsciiTextFrame(source: HTMLImageElement | HTMLVideoElement | HTMLCanvasElement, options: AsciiOptions, targetWidth?: number, targetHeight?: number): AsciiTextFrame;
|
|
617
|
-
declare function renderTextFrameToCanvas(ctx: CanvasRenderingContext2D, textFrame: AsciiTextFrame, options: AsciiOptions, canvasWidth: number, canvasHeight: number): void;
|
|
618
|
-
/**
|
|
619
|
-
* Extract frames from a video element for ASCII animation.
|
|
620
|
-
*/
|
|
621
|
-
declare function videoToAsciiFrames(video: HTMLVideoElement, options: AsciiOptions, targetWidth: number, targetHeight: number, targetFps?: number, maxDuration?: number, onProgress?: (progress: number) => void, startTime?: number): Promise<{
|
|
622
|
-
frames: AsciiFrame[];
|
|
623
|
-
cols: number;
|
|
624
|
-
rows: number;
|
|
625
|
-
fps: number;
|
|
626
|
-
}>;
|
|
627
|
-
/**
|
|
628
|
-
* Extract video frames into compact text rows for high-density monochrome/accent
|
|
629
|
-
* animations. This mirrors videoToAsciiFrames but avoids object-per-cell frames.
|
|
630
|
-
*/
|
|
631
|
-
declare function videoToAsciiTextFrames(video: HTMLVideoElement, options: AsciiOptions, targetWidth: number, targetHeight: number, targetFps?: number, maxDuration?: number, onProgress?: (progress: number) => void, startTime?: number): Promise<{
|
|
632
|
-
frames: AsciiTextFrame[];
|
|
633
|
-
cols: number;
|
|
634
|
-
rows: number;
|
|
635
|
-
fps: number;
|
|
636
|
-
}>;
|
|
637
|
-
/**
|
|
638
|
-
* Extract frames from an animated GIF file buffer.
|
|
639
|
-
*/
|
|
640
|
-
declare function gifToAsciiFrames(buffer: ArrayBuffer, options: AsciiOptions, targetWidth: number, targetHeight: number, onProgress?: (progress: number) => void): Promise<{
|
|
641
|
-
frames: AsciiFrame[];
|
|
642
|
-
cols: number;
|
|
643
|
-
rows: number;
|
|
644
|
-
fps: number;
|
|
645
|
-
}>;
|
|
646
|
-
/**
|
|
647
|
-
* Extract animated GIF frames into compact text rows for high-density
|
|
648
|
-
* monochrome/accent playback. Keeps the legacy object-frame extractor intact
|
|
649
|
-
* for full-color and interactive modes.
|
|
650
|
-
*/
|
|
651
|
-
declare function gifToAsciiTextFrames(buffer: ArrayBuffer, options: AsciiOptions, targetWidth: number, targetHeight: number, onProgress?: (progress: number) => void): Promise<{
|
|
652
|
-
frames: AsciiTextFrame[];
|
|
653
|
-
cols: number;
|
|
654
|
-
rows: number;
|
|
655
|
-
fps: number;
|
|
656
|
-
}>;
|
|
657
|
-
/**
|
|
658
|
-
* Render an ASCII frame to a canvas context.
|
|
659
|
-
* Supports both ASCII text mode and Dots mode.
|
|
660
|
-
*/
|
|
661
|
-
declare function renderFrameToCanvas(ctx: CanvasRenderingContext2D, frame: AsciiFrame, options: AsciiOptions, canvasWidth: number, canvasHeight: number, time?: number, hoverPos?: {
|
|
662
|
-
x: number;
|
|
663
|
-
y: number;
|
|
664
|
-
intensity?: number;
|
|
665
|
-
} | null): void;
|
|
666
|
-
|
|
667
|
-
/**
|
|
668
|
-
* Simple one-call asciify API.
|
|
669
|
-
* Wraps imageToAsciiFrame + renderFrameToCanvas behind easy-to-use helpers.
|
|
670
|
-
*/
|
|
671
|
-
|
|
672
|
-
interface AsciifySimpleOptions {
|
|
673
|
-
/** Character size in pixels. Default: 10 */
|
|
674
|
-
fontSize?: number;
|
|
675
|
-
/**
|
|
676
|
-
* Art style preset — controls charset, render mode, and color mode together.
|
|
677
|
-
* Shorthand for spreading `ART_STYLE_PRESETS[artStyle]` into options.
|
|
678
|
-
* Default: `'classic'`
|
|
679
|
-
*/
|
|
680
|
-
artStyle?: ArtStyle;
|
|
681
|
-
/** Extra options to merge on top of the preset */
|
|
682
|
-
options?: Partial<AsciiOptions>;
|
|
683
|
-
}
|
|
684
|
-
type ScrollTriggerInstance = {
|
|
685
|
-
kill?: () => void;
|
|
686
|
-
};
|
|
687
|
-
type ScrollTriggerLike = {
|
|
688
|
-
create: (vars: Record<string, unknown>) => ScrollTriggerInstance;
|
|
689
|
-
};
|
|
690
|
-
type GsapLike = {
|
|
691
|
-
registerPlugin?: (...plugins: unknown[]) => void;
|
|
692
|
-
ScrollTrigger?: ScrollTriggerLike;
|
|
693
|
-
};
|
|
694
|
-
interface VideoScrollScrubOptions {
|
|
695
|
-
/**
|
|
696
|
-
* Element that controls scroll progress. Accepts an HTMLElement or selector.
|
|
697
|
-
* When used through `asciifyVideo`, defaults to `fitTo` or the canvas.
|
|
698
|
-
*/
|
|
699
|
-
trigger?: HTMLElement | string | null;
|
|
700
|
-
/**
|
|
701
|
-
* GSAP instance. Pass this with ScrollTrigger for native GSAP scrub support.
|
|
702
|
-
*
|
|
703
|
-
* @example
|
|
704
|
-
* asciifyVideo('/hero.mp4', canvas, {
|
|
705
|
-
* fitTo: '#hero',
|
|
706
|
-
* scroll: { gsap, ScrollTrigger }
|
|
707
|
-
* });
|
|
708
|
-
*/
|
|
709
|
-
gsap?: GsapLike;
|
|
710
|
-
/** GSAP ScrollTrigger plugin. Optional when available as `gsap.ScrollTrigger`. */
|
|
711
|
-
ScrollTrigger?: ScrollTriggerLike;
|
|
712
|
-
/** GSAP start value. Native fallback ignores this and uses viewport progress. */
|
|
713
|
-
start?: string;
|
|
714
|
-
/** GSAP end value. Native fallback ignores this and uses viewport progress. */
|
|
715
|
-
end?: string;
|
|
716
|
-
/** GSAP scrub value. Default: `true`. Native fallback always scrubs. */
|
|
717
|
-
scrub?: boolean | number;
|
|
718
|
-
/**
|
|
719
|
-
* Multiply scroll progress before mapping it to video time.
|
|
720
|
-
* `2` reaches the end of the clip in half the scroll distance, `0.5` makes it
|
|
721
|
-
* take twice as much scroll. Default: `1`.
|
|
722
|
-
*/
|
|
723
|
-
speed?: number;
|
|
724
|
-
/** Video time to map from. Defaults to trim start or `0`. */
|
|
725
|
-
from?: number;
|
|
726
|
-
/** Video time to map to. Defaults to trim end or video duration. */
|
|
727
|
-
to?: number;
|
|
728
|
-
/** Optional progress transform before mapping to video time. */
|
|
729
|
-
ease?: (progress: number) => number;
|
|
730
|
-
/** Called whenever scroll progress updates. */
|
|
731
|
-
onUpdate?: (progress: number, video: HTMLVideoElement) => void;
|
|
732
|
-
}
|
|
733
|
-
type CanvasObjectFit = 'contain' | 'cover' | 'fill' | 'none' | 'scale-down';
|
|
734
|
-
type CanvasBleed = number | string | {
|
|
735
|
-
x?: number | string;
|
|
736
|
-
y?: number | string;
|
|
737
|
-
};
|
|
738
|
-
interface AsciifyVideoOptions extends AsciifySimpleOptions {
|
|
739
|
-
/**
|
|
740
|
-
* Fit the canvas to a container element, maintaining the video's aspect ratio.
|
|
741
|
-
* Accepts an HTMLElement or a CSS selector string. The canvas is resized on
|
|
742
|
-
* load and again whenever the container resizes (via ResizeObserver).
|
|
743
|
-
* `stop()` automatically disconnects the observer.
|
|
744
|
-
*
|
|
745
|
-
* @example
|
|
746
|
-
* // Fill the hero div, re-size on window resize automatically:
|
|
747
|
-
* asciifyVideo('/clip.mp4', canvas, { fitTo: '#hero' });
|
|
748
|
-
*/
|
|
749
|
-
fitTo?: HTMLElement | string | null;
|
|
750
|
-
/**
|
|
751
|
-
* CSS object-fit behavior for the visible canvas when `fitTo` or explicit
|
|
752
|
-
* `width`/`height` is used. This controls visual framing only; ASCII sampling
|
|
753
|
-
* resolution remains independent. When `options.sourceCrop` is present, the
|
|
754
|
-
* engine sizes from the resolved crop aspect to avoid stretch.
|
|
755
|
-
*
|
|
756
|
-
* Use `'cover'` for full-bleed heroes and `'contain'` for previews.
|
|
757
|
-
* Default: `'contain'`.
|
|
758
|
-
*/
|
|
759
|
-
objectFit?: CanvasObjectFit;
|
|
760
|
-
/**
|
|
761
|
-
* CSS object-position for the visible canvas, e.g. `'center bottom'` or
|
|
762
|
-
* `'50% 62%'`. Useful with `objectFit: 'cover'`.
|
|
763
|
-
*/
|
|
764
|
-
objectPosition?: string;
|
|
765
|
-
/**
|
|
766
|
-
* Visual scale applied with the CSS individual `scale` property. This is a
|
|
767
|
-
* layout-safe way to overfill a container without changing source proportions
|
|
768
|
-
* or overriding an app's `transform` styles.
|
|
769
|
-
*/
|
|
770
|
-
scale?: number;
|
|
771
|
-
/**
|
|
772
|
-
* Visible CSS width for the canvas. Numbers are pixels; strings are used as
|
|
773
|
-
* provided (`'100%'`, `'100vw'`, `min(100vw, 1200px)`, etc.).
|
|
774
|
-
*/
|
|
775
|
-
width?: number | string;
|
|
776
|
-
/**
|
|
777
|
-
* Visible CSS height for the canvas. Numbers are pixels; strings are used as
|
|
778
|
-
* provided.
|
|
779
|
-
*/
|
|
780
|
-
height?: number | string;
|
|
781
|
-
/**
|
|
782
|
-
* Extra visible overfill added around the fitted canvas box before
|
|
783
|
-
* object-fit sizing. Useful for full-bleed ASCII heroes where glyph side
|
|
784
|
-
* bearings or character-cell quantization can leave a small edge gap even
|
|
785
|
-
* when the source media and canvas are full width.
|
|
786
|
-
*
|
|
787
|
-
* Numbers are pixels. Strings support `%`, `px`, `vw`, and `vh`. Pass an
|
|
788
|
-
* object to control axes independently, e.g. `{ x: '2vw', y: 0 }`.
|
|
789
|
-
*/
|
|
790
|
-
bleed?: CanvasBleed;
|
|
791
|
-
/**
|
|
792
|
-
* Pre-extract all video frames into memory before starting playback.
|
|
793
|
-
* Useful for short clips where you need frame-perfect control.
|
|
794
|
-
*
|
|
795
|
-
* Default: `false` — streams live directly from the playing video (instant
|
|
796
|
-
* start, constant memory, unlimited duration).
|
|
797
|
-
*
|
|
798
|
-
* ⚠️ Memory-intensive. Capped at 10 s / 300 frames.
|
|
799
|
-
*/
|
|
800
|
-
preExtract?: boolean;
|
|
801
|
-
/**
|
|
802
|
-
* Target render FPS.
|
|
803
|
-
* - In pre-extracted mode, this controls how many frames are decoded into memory.
|
|
804
|
-
* - In live mode, this throttles expensive ASCII frame rendering while the
|
|
805
|
-
* backing video continues decoding normally.
|
|
806
|
-
*
|
|
807
|
-
* Lower values use less CPU/memory and make scroll scrubbing cheaper.
|
|
808
|
-
* Defaults to `18` for pre-extracted scroll scrub and unthrottled rendering
|
|
809
|
-
* for normal live playback.
|
|
810
|
-
*/
|
|
811
|
-
fps?: number;
|
|
812
|
-
/**
|
|
813
|
-
* Maximum long-edge render dimension for video frame extraction.
|
|
814
|
-
* Raise this for full-width or 4K heroes so the canvas is not upscaled by CSS.
|
|
815
|
-
* Default: `2048`.
|
|
816
|
-
*/
|
|
817
|
-
maxRenderDimension?: number;
|
|
818
|
-
/**
|
|
819
|
-
* Trim the video to a specific time range (in seconds).
|
|
820
|
-
* - `start` — seek to this time before playback begins. Default: `0`
|
|
821
|
-
* - `end` — loop back to `start` when this time is reached.
|
|
822
|
-
* In `preExtract` mode, only frames up to `end` are extracted.
|
|
823
|
-
*
|
|
824
|
-
* @example
|
|
825
|
-
* // Play only seconds 2–8, looping:
|
|
826
|
-
* asciifyVideo('/clip.mp4', canvas, { trim: { start: 2, end: 8 } });
|
|
827
|
-
*/
|
|
828
|
-
trim?: {
|
|
829
|
-
start?: number;
|
|
830
|
-
end?: number;
|
|
831
|
-
};
|
|
832
|
-
/**
|
|
833
|
-
* Sync video time to scroll progress.
|
|
834
|
-
*
|
|
835
|
-
* - `true` uses native scroll scrubbing with `fitTo`/canvas as the trigger.
|
|
836
|
-
* - Passing `gsap` + `ScrollTrigger` uses GSAP ScrollTrigger.
|
|
837
|
-
*
|
|
838
|
-
* @example
|
|
839
|
-
* await asciifyVideo('/hero.mp4', canvas, {
|
|
840
|
-
* fitTo: '#hero',
|
|
841
|
-
* scroll: true
|
|
842
|
-
* });
|
|
843
|
-
*
|
|
844
|
-
* @example
|
|
845
|
-
* await asciifyVideo('/hero.mp4', canvas, {
|
|
846
|
-
* fitTo: '#hero',
|
|
847
|
-
* scroll: { gsap, ScrollTrigger, start: 'top bottom', end: 'bottom top', scrub: 1 }
|
|
848
|
-
* });
|
|
849
|
-
*/
|
|
850
|
-
scroll?: boolean | VideoScrollScrubOptions;
|
|
851
|
-
/**
|
|
852
|
-
* Called once when the video metadata is loaded and playback has started.
|
|
853
|
-
* Receives the backing video element.
|
|
854
|
-
*/
|
|
855
|
-
onReady?: (video: HTMLVideoElement) => void;
|
|
856
|
-
/**
|
|
857
|
-
* Maximum number of decoded text frames kept in memory for live scroll scrub.
|
|
858
|
-
* The cache is nearest-frame and bounded; lower values reduce memory for long
|
|
859
|
-
* clips while preserving smooth scrubbing around the current scroll position.
|
|
860
|
-
* Default: `90`.
|
|
861
|
-
*/
|
|
862
|
-
maxCachedFrames?: number;
|
|
863
|
-
/** Called after every rendered frame. */
|
|
864
|
-
onFrame?: () => void;
|
|
865
|
-
}
|
|
866
|
-
/** @deprecated Use {@link AsciifyVideoOptions} */
|
|
867
|
-
type AsciifyLiveVideoOptions = AsciifyVideoOptions;
|
|
868
|
-
/**
|
|
869
|
-
* Sync an HTMLVideoElement's currentTime to scroll progress.
|
|
870
|
-
*
|
|
871
|
-
* If `gsap` and `ScrollTrigger` are supplied, the helper uses GSAP. Otherwise
|
|
872
|
-
* it falls back to a tiny native scroll listener. Returns a cleanup function.
|
|
873
|
-
*/
|
|
874
|
-
declare function createVideoScrollScrub(video: HTMLVideoElement, opts?: VideoScrollScrubOptions): () => void;
|
|
875
|
-
interface CanvasRenderSizeInput {
|
|
876
|
-
sourceWidth: number;
|
|
877
|
-
sourceHeight: number;
|
|
878
|
-
cssWidth?: number;
|
|
879
|
-
cssHeight?: number;
|
|
880
|
-
/** Accepted for callers that pass complete display context; DPR is applied separately by the canvas backing buffer. */
|
|
881
|
-
dpr?: number;
|
|
882
|
-
maxRenderDimension?: number;
|
|
883
|
-
}
|
|
884
|
-
declare function computeCanvasRenderSize({ sourceWidth, sourceHeight, cssWidth, cssHeight, maxRenderDimension, }: CanvasRenderSizeInput): {
|
|
885
|
-
renderW: number;
|
|
886
|
-
renderH: number;
|
|
887
|
-
};
|
|
888
|
-
/**
|
|
889
|
-
* Convert an image/video/canvas element to ASCII art and render it onto a canvas.
|
|
890
|
-
*
|
|
891
|
-
* When hover options are active (`hoverStrength > 0` in `options`), the engine
|
|
892
|
-
* automatically sets up mouse tracking and a `requestAnimationFrame` loop so
|
|
893
|
-
* the hover effect works out of the box. In that case, a `stop()` function is
|
|
894
|
-
* returned to tear down the loop and listeners.
|
|
895
|
-
*
|
|
896
|
-
* @example
|
|
897
|
-
* // Static (no hover):
|
|
898
|
-
* await asciify('/photo.jpg', canvas);
|
|
899
|
-
*
|
|
900
|
-
* // With hover — returns a cleanup handle:
|
|
901
|
-
* const stop = await asciify('/photo.jpg', canvas, {
|
|
902
|
-
* options: { hoverEffect: 'glitchText', hoverStrength: 0.8, hoverText: 'HI' }
|
|
903
|
-
* });
|
|
904
|
-
* // later: stop?.();
|
|
905
|
-
*/
|
|
906
|
-
declare function asciify(source: HTMLImageElement | HTMLVideoElement | HTMLCanvasElement | string, canvas: HTMLCanvasElement, { fontSize, artStyle, options }?: AsciifySimpleOptions): Promise<(() => void) | void>;
|
|
907
|
-
/**
|
|
908
|
-
* Fetch a GIF, convert it to ASCII, and start an animation loop on a canvas.
|
|
909
|
-
* Returns a `stop()` function that cancels the loop.
|
|
910
|
-
*
|
|
911
|
-
* @example
|
|
912
|
-
* const stop = await asciifyGif('animation.gif', canvas);
|
|
913
|
-
* // later: stop();
|
|
914
|
-
*/
|
|
915
|
-
declare function asciifyGif(source: string | ArrayBuffer, canvas: HTMLCanvasElement, { fontSize, artStyle, options }?: AsciifySimpleOptions): Promise<() => void>;
|
|
916
|
-
/**
|
|
917
|
-
* Render a video as ASCII art on a canvas. Defaults to live streaming —
|
|
918
|
-
* instant start, constant memory, unlimited duration.
|
|
919
|
-
*
|
|
920
|
-
* Pass `{ preExtract: true }` to pre-decode all frames before playback starts
|
|
921
|
-
* (useful for short clips that need frame-perfect looping).
|
|
922
|
-
*
|
|
923
|
-
* Pass `{ fitTo: '#container' }` to automatically size and re-size the canvas
|
|
924
|
-
* to fill a container element, maintaining the video's aspect ratio.
|
|
925
|
-
*
|
|
926
|
-
* Returns a `stop()` function that cancels the loop and cleans up.
|
|
927
|
-
*
|
|
928
|
-
* ⚠️ Never set the backing `<video>` to `display: none` — browsers skip GPU
|
|
929
|
-
* frame decoding for hidden elements. When given a URL string, this function
|
|
930
|
-
* handles that automatically.
|
|
931
|
-
*
|
|
932
|
-
* @example
|
|
933
|
-
* // Minimal
|
|
934
|
-
* const stop = await asciifyVideo('/clip.mp4', canvas);
|
|
935
|
-
*
|
|
936
|
-
* // Fit to container, re-size on window resize:
|
|
937
|
-
* const stop = await asciifyVideo('/clip.mp4', canvas, { fitTo: '#hero' });
|
|
938
|
-
*
|
|
939
|
-
* // Pre-extract frames (old behavior):
|
|
940
|
-
* const stop = await asciifyVideo('/clip.mp4', canvas, { preExtract: true });
|
|
941
|
-
*/
|
|
942
|
-
declare function asciifyVideo(source: HTMLVideoElement | string, canvas: HTMLCanvasElement, { fontSize, artStyle, options, fitTo, objectFit, objectPosition, scale, width, height, bleed, preExtract, fps, maxRenderDimension, trim, scroll, maxCachedFrames, onReady, onFrame, }?: AsciifyVideoOptions): Promise<() => void>;
|
|
943
|
-
/**
|
|
944
|
-
* @deprecated Use {@link asciifyVideo} instead — it now defaults to live streaming
|
|
945
|
-
* and accepts the same options including `fitTo` and `preExtract`.
|
|
946
|
-
*/
|
|
947
|
-
declare function asciifyLiveVideo(source: HTMLVideoElement | string, canvas: HTMLCanvasElement, opts?: AsciifyVideoOptions): Promise<() => void>;
|
|
948
|
-
|
|
949
|
-
interface WaveBackgroundOptions {
|
|
950
|
-
/** Font size in CSS pixels (default: 13) */
|
|
951
|
-
fontSize?: number;
|
|
952
|
-
/** Character aspect ratio width/height (default: 0.62) */
|
|
953
|
-
charAspect?: number;
|
|
954
|
-
/** Line height multiplier (default: 1.4) */
|
|
955
|
-
lineHeightRatio?: number;
|
|
956
|
-
/** Character set from dark→bright (default: ' .:-=+*#%@') */
|
|
957
|
-
chars?: string;
|
|
958
|
-
/** Base colour — use '{a}' as alpha placeholder */
|
|
959
|
-
baseColor?: string;
|
|
960
|
-
/** Accent colour applied near the cursor and on wave peaks (default: '#d4ff00') */
|
|
961
|
-
accentColor?: string;
|
|
962
|
-
/** Accent threshold: normalised intensity above which accent kicks in (default: 0.52) */
|
|
963
|
-
accentThreshold?: number;
|
|
964
|
-
/** How strongly the mouse influences local intensity (default: 0.55) */
|
|
965
|
-
mouseInfluence?: number;
|
|
966
|
-
/** Radial falloff for mouse influence (default: 2.8) */
|
|
967
|
-
mouseFalloff?: number;
|
|
968
|
-
/** Base wave animation speed (default: 1) */
|
|
969
|
-
speed?: number;
|
|
970
|
-
/** Enable vortex swirl effect around cursor (default: true) */
|
|
971
|
-
vortex?: boolean;
|
|
972
|
-
/** Enable sparkle / pop flicker (default: true) */
|
|
973
|
-
sparkles?: boolean;
|
|
974
|
-
/** Enable a slow global breathe pulse (default: true) */
|
|
975
|
-
breathe?: boolean;
|
|
976
|
-
/** Light mode: swap fill colours to dark-on-light (default: false) */
|
|
977
|
-
lightMode?: boolean;
|
|
978
|
-
}
|
|
979
|
-
declare function renderWaveBackground(ctx: CanvasRenderingContext2D, width: number, height: number, time: number, mousePos?: {
|
|
980
|
-
x: number;
|
|
981
|
-
y: number;
|
|
982
|
-
}, options?: WaveBackgroundOptions): void;
|
|
983
|
-
|
|
984
|
-
interface RainBackgroundOptions {
|
|
985
|
-
fontSize?: number;
|
|
986
|
-
/** Characters drawn in columns */
|
|
987
|
-
chars?: string;
|
|
988
|
-
/** Head / accent colour (default: '#d4ff00') */
|
|
989
|
-
accentColor?: string;
|
|
990
|
-
/** Custom character colour */
|
|
991
|
-
color?: string;
|
|
992
|
-
/** Global speed multiplier (default: 1) */
|
|
993
|
-
speed?: number;
|
|
994
|
-
/** Fraction of columns active at once 0-1 (default: 0.55) */
|
|
995
|
-
density?: number;
|
|
996
|
-
/** Number of cells in the fading tail (default: 14) */
|
|
997
|
-
tailLength?: number;
|
|
998
|
-
/** Light mode (default: false) */
|
|
999
|
-
lightMode?: boolean;
|
|
1000
|
-
}
|
|
1001
|
-
declare function renderRainBackground(ctx: CanvasRenderingContext2D, width: number, height: number, time: number, options?: RainBackgroundOptions): void;
|
|
1002
|
-
|
|
1003
|
-
interface StarsBackgroundOptions {
|
|
1004
|
-
fontSize?: number;
|
|
1005
|
-
/** Characters used as stars */
|
|
1006
|
-
chars?: string;
|
|
1007
|
-
/** Accent/trail colour for fast near-edge stars (default: '#d4ff00') */
|
|
1008
|
-
accentColor?: string;
|
|
1009
|
-
/** Custom base colour */
|
|
1010
|
-
color?: string;
|
|
1011
|
-
/** Global speed multiplier (default: 1) */
|
|
1012
|
-
speed?: number;
|
|
1013
|
-
/** Number of star particles (default: 180) */
|
|
1014
|
-
count?: number;
|
|
1015
|
-
/** Light mode (default: false) */
|
|
1016
|
-
lightMode?: boolean;
|
|
1017
|
-
}
|
|
1018
|
-
declare function renderStarsBackground(ctx: CanvasRenderingContext2D, width: number, height: number, time: number, mousePos?: {
|
|
1019
|
-
x: number;
|
|
1020
|
-
y: number;
|
|
1021
|
-
}, options?: StarsBackgroundOptions): void;
|
|
1022
|
-
|
|
1023
|
-
interface PulseBackgroundOptions {
|
|
1024
|
-
fontSize?: number;
|
|
1025
|
-
/** Characters to tile (default: '. · ○ ◎ ●') */
|
|
1026
|
-
chars?: string;
|
|
1027
|
-
/** Ring peak colour (default: '#00ffcc') */
|
|
1028
|
-
accentColor?: string;
|
|
1029
|
-
/** Custom base colour */
|
|
1030
|
-
color?: string;
|
|
1031
|
-
/** Number of simultaneous rings (default: 5) */
|
|
1032
|
-
rings?: number;
|
|
1033
|
-
/** Animation speed (default: 1) */
|
|
1034
|
-
speed?: number;
|
|
1035
|
-
/** Ring edge sharpness 1–10 (default: 4) */
|
|
1036
|
-
sharpness?: number;
|
|
1037
|
-
/** Light mode (default: false) */
|
|
1038
|
-
lightMode?: boolean;
|
|
1039
|
-
}
|
|
1040
|
-
declare function renderPulseBackground(ctx: CanvasRenderingContext2D, width: number, height: number, time: number, mousePos?: {
|
|
1041
|
-
x: number;
|
|
1042
|
-
y: number;
|
|
1043
|
-
}, options?: PulseBackgroundOptions): void;
|
|
1044
|
-
|
|
1045
|
-
interface NoiseBackgroundOptions {
|
|
1046
|
-
/** Font size in CSS pixels (default: 14). */
|
|
1047
|
-
fontSize?: number;
|
|
1048
|
-
/** Character ramp dark → bright (default: ' .·:;=+*#%@░▒▓'). */
|
|
1049
|
-
chars?: string;
|
|
1050
|
-
/** Accent colour on intensity peaks (default: '#d4ff00'). */
|
|
1051
|
-
accentColor?: string;
|
|
1052
|
-
/** Custom base character colour (any CSS colour string). */
|
|
1053
|
-
color?: string;
|
|
1054
|
-
/** Number of noise octaves for FBM detail (default: 4, max: 6). */
|
|
1055
|
-
octaves?: number;
|
|
1056
|
-
/** Drift / scroll speed (default: 1). */
|
|
1057
|
-
speed?: number;
|
|
1058
|
-
/** Noise scale — lower = larger blobs (default: 1). */
|
|
1059
|
-
scale?: number;
|
|
1060
|
-
/** Accent threshold 0-1 (default: 0.78). */
|
|
1061
|
-
accentThreshold?: number;
|
|
1062
|
-
/** Mouse warp radius 0-1 (default: 0.3). */
|
|
1063
|
-
mouseWarp?: number;
|
|
1064
|
-
/** Light mode (default: false). */
|
|
1065
|
-
lightMode?: boolean;
|
|
1066
|
-
}
|
|
1067
|
-
declare function renderNoiseBackground(ctx: CanvasRenderingContext2D, width: number, height: number, time: number, mousePos?: {
|
|
1068
|
-
x: number;
|
|
1069
|
-
y: number;
|
|
1070
|
-
}, options?: NoiseBackgroundOptions): void;
|
|
1071
|
-
|
|
1072
|
-
interface GridBackgroundOptions {
|
|
1073
|
-
/** Font size in CSS pixels (default: 12). */
|
|
1074
|
-
fontSize?: number;
|
|
1075
|
-
/** Character set (default: '·-=+|/'). */
|
|
1076
|
-
chars?: string;
|
|
1077
|
-
/** Accent / scan-band colour (default: '#d4ff00'). */
|
|
1078
|
-
accentColor?: string;
|
|
1079
|
-
/** Custom base character colour (any CSS colour string). */
|
|
1080
|
-
color?: string;
|
|
1081
|
-
/** Number of scan bands visible at once (default: 3). */
|
|
1082
|
-
bands?: number;
|
|
1083
|
-
/** Band travel speed (default: 1). */
|
|
1084
|
-
speed?: number;
|
|
1085
|
-
/** Band width as fraction of canvas height (default: 0.12). */
|
|
1086
|
-
bandWidth?: number;
|
|
1087
|
-
/** Enable cursor disruption glitch zone (default: true). */
|
|
1088
|
-
glitch?: boolean;
|
|
1089
|
-
/** Light mode (default: false). */
|
|
1090
|
-
lightMode?: boolean;
|
|
1091
|
-
}
|
|
1092
|
-
declare function renderGridBackground(ctx: CanvasRenderingContext2D, width: number, height: number, time: number, mousePos?: {
|
|
1093
|
-
x: number;
|
|
1094
|
-
y: number;
|
|
1095
|
-
}, options?: GridBackgroundOptions): void;
|
|
1096
|
-
|
|
1097
|
-
interface AuroraBackgroundOptions {
|
|
1098
|
-
/** Character grid density. Default 14. */
|
|
1099
|
-
fontSize?: number;
|
|
1100
|
-
/** Character ramp from sparse to dense. */
|
|
1101
|
-
chars?: string;
|
|
1102
|
-
/** Base character color. Default theme-aware white/black. */
|
|
1103
|
-
color?: string;
|
|
1104
|
-
/** Accent color for intensity peaks. Default '#d4ff00'. */
|
|
1105
|
-
accentColor?: string;
|
|
1106
|
-
/** Animation speed multiplier. Default 1. */
|
|
1107
|
-
speed?: number;
|
|
1108
|
-
/** Number of wave layers stacked. More = richer interference. Default 5. */
|
|
1109
|
-
layers?: number;
|
|
1110
|
-
/** Wave spread/softness — higher = broader, more diffuse bands. Default 1.2. */
|
|
1111
|
-
softness?: number;
|
|
1112
|
-
/** Mouse distortion radius (0–1). Elegant ripple that follows the cursor. Default 0.2. */
|
|
1113
|
-
mouseRipple?: number;
|
|
1114
|
-
/** Force light mode (dark chars on light bg). Default false. */
|
|
1115
|
-
lightMode?: boolean;
|
|
1116
|
-
}
|
|
1117
|
-
declare function renderAuroraBackground(ctx: CanvasRenderingContext2D, width: number, height: number, time: number, mousePos?: {
|
|
1118
|
-
x: number;
|
|
1119
|
-
y: number;
|
|
1120
|
-
}, options?: AuroraBackgroundOptions): void;
|
|
1121
|
-
|
|
1122
|
-
interface SilkBackgroundOptions {
|
|
1123
|
-
/** Character grid density. Default 13. */
|
|
1124
|
-
fontSize?: number;
|
|
1125
|
-
/** Base character color. Default theme-aware white/black. */
|
|
1126
|
-
color?: string;
|
|
1127
|
-
/** Accent color for intensity peaks. Default '#d4ff00'. */
|
|
1128
|
-
accentColor?: string;
|
|
1129
|
-
/** Animation speed multiplier. Default 0.4 (intentionally slow). */
|
|
1130
|
-
speed?: number;
|
|
1131
|
-
/** Number of flow-field layers. More = richer ribbons. Default 4. */
|
|
1132
|
-
layers?: number;
|
|
1133
|
-
/** Flow turbulence (0–2). Higher = more folded, tangled ribbons. Default 0.8. */
|
|
1134
|
-
turbulence?: number;
|
|
1135
|
-
/** Force light mode. Default false. */
|
|
1136
|
-
lightMode?: boolean;
|
|
1137
|
-
}
|
|
1138
|
-
declare function renderSilkBackground(ctx: CanvasRenderingContext2D, width: number, height: number, time: number, options?: SilkBackgroundOptions): void;
|
|
1139
|
-
|
|
1140
|
-
interface VoidBackgroundOptions {
|
|
1141
|
-
/** Character grid density. Default 13. */
|
|
1142
|
-
fontSize?: number;
|
|
1143
|
-
/** Character ramp. Default space-to-dense. */
|
|
1144
|
-
chars?: string;
|
|
1145
|
-
/** Base character color. Default theme-aware. */
|
|
1146
|
-
color?: string;
|
|
1147
|
-
/** Accent color for the inner singularity ring. Default '#d4ff00'. */
|
|
1148
|
-
accentColor?: string;
|
|
1149
|
-
/** Animation speed multiplier. Default 1. */
|
|
1150
|
-
speed?: number;
|
|
1151
|
-
/** Gravity well radius (fraction of canvas width). Default 0.38. */
|
|
1152
|
-
radius?: number;
|
|
1153
|
-
/** Spiral tightness — higher = more rotation per unit distance. Default 3. */
|
|
1154
|
-
swirl?: number;
|
|
1155
|
-
/** Force light mode. Default false. */
|
|
1156
|
-
lightMode?: boolean;
|
|
1157
|
-
}
|
|
1158
|
-
declare function renderVoidBackground(ctx: CanvasRenderingContext2D, width: number, height: number, time: number, mousePos?: {
|
|
1159
|
-
x: number;
|
|
1160
|
-
y: number;
|
|
1161
|
-
}, options?: VoidBackgroundOptions): void;
|
|
1162
|
-
|
|
1163
|
-
interface MorphBackgroundOptions {
|
|
1164
|
-
/** Character grid density. Default 14. */
|
|
1165
|
-
fontSize?: number;
|
|
1166
|
-
/** Character ramp. Default clean gradient. */
|
|
1167
|
-
chars?: string;
|
|
1168
|
-
/** Base character color. Default theme-aware. */
|
|
1169
|
-
color?: string;
|
|
1170
|
-
/** Accent color for intensity peaks. Default '#d4ff00'. */
|
|
1171
|
-
accentColor?: string;
|
|
1172
|
-
/** Animation speed multiplier. Default 0.5 (intentionally slow). */
|
|
1173
|
-
speed?: number;
|
|
1174
|
-
/** How many frequency harmonics per cell. More = richer shimmer. Default 3. */
|
|
1175
|
-
harmonics?: number;
|
|
1176
|
-
/** Force light mode. Default false. */
|
|
1177
|
-
lightMode?: boolean;
|
|
1178
|
-
}
|
|
1179
|
-
declare function renderMorphBackground(ctx: CanvasRenderingContext2D, width: number, height: number, time: number, options?: MorphBackgroundOptions): void;
|
|
1180
|
-
|
|
1181
|
-
interface FireBackgroundOptions {
|
|
1182
|
-
/** Font size in CSS pixels (default: 13) */
|
|
1183
|
-
fontSize?: number;
|
|
1184
|
-
/** Characters mapped from cool→hot (default: ' .,:;i+xX#&@') */
|
|
1185
|
-
chars?: string;
|
|
1186
|
-
/** Base flame colour (default: '#ff4500') */
|
|
1187
|
-
color?: string;
|
|
1188
|
-
/** Secondary hot-tip colour (default: '#ffe066') */
|
|
1189
|
-
hotColor?: string;
|
|
1190
|
-
/** Flame intensity 0–1 (default: 0.85) */
|
|
1191
|
-
intensity?: number;
|
|
1192
|
-
/** Horizontal wind force -1..1 (default: 0) */
|
|
1193
|
-
wind?: number;
|
|
1194
|
-
/** Global speed multiplier (default: 1) */
|
|
1195
|
-
speed?: number;
|
|
1196
|
-
/** Light mode: invert text colours (default: false) */
|
|
1197
|
-
lightMode?: boolean;
|
|
1198
|
-
}
|
|
1199
|
-
declare function renderFireBackground(ctx: CanvasRenderingContext2D, width: number, height: number, time: number, options?: FireBackgroundOptions): void;
|
|
1200
|
-
|
|
1201
|
-
interface DnaBackgroundOptions {
|
|
1202
|
-
/** Font size in CSS pixels (default: 13) */
|
|
1203
|
-
fontSize?: number;
|
|
1204
|
-
/** Characters for strand nodes (default: 'ATCG') */
|
|
1205
|
-
baseChars?: string;
|
|
1206
|
-
/** Characters for the connectors between strands (default: '-=≡') */
|
|
1207
|
-
bridgeChars?: string;
|
|
1208
|
-
/** Primary strand colour (default: '#00e5ff') */
|
|
1209
|
-
color?: string;
|
|
1210
|
-
/** Secondary strand colour (default: '#ff4081') */
|
|
1211
|
-
color2?: string;
|
|
1212
|
-
/** Bridge / connector colour (default: '#88ffcc') */
|
|
1213
|
-
bridgeColor?: string;
|
|
1214
|
-
/** Speed multiplier (default: 1) */
|
|
1215
|
-
speed?: number;
|
|
1216
|
-
/** Number of helix columns (default: auto, ~1 per 80px) */
|
|
1217
|
-
helixCount?: number;
|
|
1218
|
-
/** Light mode (default: false) */
|
|
1219
|
-
lightMode?: boolean;
|
|
1220
|
-
}
|
|
1221
|
-
declare function renderDnaBackground(ctx: CanvasRenderingContext2D, width: number, height: number, time: number, options?: DnaBackgroundOptions): void;
|
|
1222
|
-
|
|
1223
|
-
interface TerrainBackgroundOptions {
|
|
1224
|
-
/** Font size in CSS pixels (default: 13) */
|
|
1225
|
-
fontSize?: number;
|
|
1226
|
-
/** Characters for terrain density (default: ' .,:;+*#@') */
|
|
1227
|
-
chars?: string;
|
|
1228
|
-
/** Foreground ground colour (default: '#4caf50') */
|
|
1229
|
-
color?: string;
|
|
1230
|
-
/** Sky / star colour (default: '#1a237e') */
|
|
1231
|
-
skyColor?: string;
|
|
1232
|
-
/** Peak / snow-cap colour (default: '#e0e0e0') */
|
|
1233
|
-
peakColor?: string;
|
|
1234
|
-
/** Horizontal scroll speed (default: 1) */
|
|
1235
|
-
speed?: number;
|
|
1236
|
-
/** Terrain roughness 0.1–1 (default: 0.55) */
|
|
1237
|
-
roughness?: number;
|
|
1238
|
-
/** Mountain height fraction 0–1 (default: 0.55) */
|
|
1239
|
-
heightScale?: number;
|
|
1240
|
-
/** Show faint background stars (default: true) */
|
|
1241
|
-
stars?: boolean;
|
|
1242
|
-
/** Light mode (default: false) */
|
|
1243
|
-
lightMode?: boolean;
|
|
1244
|
-
}
|
|
1245
|
-
declare function renderTerrainBackground(ctx: CanvasRenderingContext2D, width: number, height: number, time: number, options?: TerrainBackgroundOptions): void;
|
|
1246
|
-
|
|
1247
|
-
interface CircuitBackgroundOptions {
|
|
1248
|
-
/** Font size in CSS pixels (default: 13) */
|
|
1249
|
-
fontSize?: number;
|
|
1250
|
-
/** Trace characters (default: '─│┌┐└┘├┤┬┴┼') */
|
|
1251
|
-
chars?: string;
|
|
1252
|
-
/** Trace colour (default: '#00ff88') */
|
|
1253
|
-
color?: string;
|
|
1254
|
-
/** Signal pulse colour (default: '#ffffff') */
|
|
1255
|
-
pulseColor?: string;
|
|
1256
|
-
/** Fraction of cells that have a trace (default: 0.38) */
|
|
1257
|
-
density?: number;
|
|
1258
|
-
/** Signal pulse speed (default: 1) */
|
|
1259
|
-
speed?: number;
|
|
1260
|
-
/** Light mode (default: false) */
|
|
1261
|
-
lightMode?: boolean;
|
|
1262
|
-
}
|
|
1263
|
-
declare function renderCircuitBackground(ctx: CanvasRenderingContext2D, width: number, height: number, time: number, options?: CircuitBackgroundOptions): void;
|
|
1264
|
-
|
|
1265
|
-
/**
|
|
1266
|
-
* ASCII Background — public entry point for the backgrounds sub-system.
|
|
1267
|
-
*
|
|
1268
|
-
* Exports:
|
|
1269
|
-
* - All 10 render functions
|
|
1270
|
-
* - All 10 option interfaces
|
|
1271
|
-
* - `AsciiBackgroundOptions` — combined union type + mount options
|
|
1272
|
-
* - `asciiBackground()` — the drop-in mount helper
|
|
1273
|
-
* - `mountWaveBackground` / `MountWaveOptions` — deprecated aliases
|
|
1274
|
-
*/
|
|
1275
|
-
|
|
1276
|
-
/**
|
|
1277
|
-
* Combined options for `asciiBackground()`. Extends all 10 background option
|
|
1278
|
-
* interfaces so every background's options can be passed through one object.
|
|
1279
|
-
*/
|
|
1280
|
-
interface AsciiBackgroundOptions extends WaveBackgroundOptions, RainBackgroundOptions, StarsBackgroundOptions, PulseBackgroundOptions, NoiseBackgroundOptions, GridBackgroundOptions, AuroraBackgroundOptions, SilkBackgroundOptions, VoidBackgroundOptions, MorphBackgroundOptions, FireBackgroundOptions, DnaBackgroundOptions, TerrainBackgroundOptions, CircuitBackgroundOptions {
|
|
1281
|
-
/**
|
|
1282
|
-
* Which background to render (default: 'wave').
|
|
1283
|
-
* - 'wave' — interactive ASCII field with vortex, sparkles, breathe
|
|
1284
|
-
* - 'rain' — digital column rain (Matrix-style falling characters)
|
|
1285
|
-
* - 'stars' — 3D star-warp / hyperspace chars fly toward the viewer
|
|
1286
|
-
* - 'pulse' — concentric ASCII ripples radiating from the mouse
|
|
1287
|
-
* - 'noise' — slow-drifting organic fractal noise field
|
|
1288
|
-
* - 'grid' — CRT-style horizontal scan bands with cursor glitch zone
|
|
1289
|
-
* - 'aurora' — premium slow-drifting light bands
|
|
1290
|
-
* - 'silk' — smooth directional flow-field ribbons
|
|
1291
|
-
* - 'void' — gravitational singularity follows the cursor
|
|
1292
|
-
* - 'morph' — per-cell multi-frequency shimmer
|
|
1293
|
-
* - 'fire' — upward cellular-automata flame simulation
|
|
1294
|
-
* - 'dna' — double-helix strand scrolling with base-pair chars
|
|
1295
|
-
* - 'terrain' — scrolling ASCII side-scroll heightmap landscape
|
|
1296
|
-
* - 'circuit' — procedural PCB traces with traveling signal pulses
|
|
1297
|
-
*/
|
|
1298
|
-
type?: 'wave' | 'rain' | 'stars' | 'pulse' | 'noise' | 'grid' | 'aurora' | 'silk' | 'void' | 'morph' | 'fire' | 'dna' | 'terrain' | 'circuit';
|
|
1299
|
-
/** CSS opacity applied to the canvas element (default: 0.2) */
|
|
1300
|
-
opacity?: number;
|
|
1301
|
-
/** Extra CSS class names added to the injected canvas */
|
|
1302
|
-
className?: string;
|
|
1303
|
-
/** z-index of the canvas (default: 0) */
|
|
1304
|
-
zIndex?: number;
|
|
1305
|
-
/**
|
|
1306
|
-
* Colour scheme handling (default: 'auto').
|
|
1307
|
-
* - 'auto' — follows system prefers-color-scheme and updates live
|
|
1308
|
-
* - 'dark' — always render bright chars on dark background
|
|
1309
|
-
* - 'light' — always render dark chars on light background
|
|
1310
|
-
*/
|
|
1311
|
-
colorScheme?: 'auto' | 'light' | 'dark';
|
|
1312
|
-
/**
|
|
1313
|
-
* Custom character colour. Accepts any CSS colour string: hex, rgb(), hsl().
|
|
1314
|
-
* Overrides the default white/black for ASCII chars.
|
|
1315
|
-
* @example '#6b8700'
|
|
1316
|
-
*/
|
|
1317
|
-
color?: string;
|
|
1318
|
-
}
|
|
1319
|
-
/**
|
|
1320
|
-
* All supported background type identifiers — single source of truth for
|
|
1321
|
-
* counts, type-safe option values, and documentation.
|
|
1322
|
-
*/
|
|
1323
|
-
declare const BACKGROUND_TYPES: readonly ["wave", "rain", "stars", "pulse", "noise", "grid", "aurora", "silk", "void", "morph", "fire", "dna", "terrain", "circuit"];
|
|
1324
|
-
type BackgroundType = typeof BACKGROUND_TYPES[number];
|
|
1325
|
-
/**
|
|
1326
|
-
* Drop-in helper that mounts an interactive ASCII background onto any element.
|
|
1327
|
-
* Injects a canvas, wires DPR resize, mouse tracking, and the RAF loop.
|
|
1328
|
-
* Auto-detects light/dark mode and stays in sync if the system theme changes.
|
|
1329
|
-
*
|
|
1330
|
-
* Returns a `destroy()` function to clean everything up.
|
|
1331
|
-
*
|
|
1332
|
-
* @example
|
|
1333
|
-
* ```ts
|
|
1334
|
-
* // 1 line:
|
|
1335
|
-
* const { destroy } = asciiBackground('#hero', { opacity: 0.2 });
|
|
1336
|
-
*
|
|
1337
|
-
* // React — return destroy as cleanup:
|
|
1338
|
-
* useEffect(() => asciiBackground(ref.current).destroy, []);
|
|
1339
|
-
* ```
|
|
1340
|
-
*/
|
|
1341
|
-
declare function asciiBackground(target: string | HTMLElement | null, options?: AsciiBackgroundOptions): {
|
|
1342
|
-
destroy: () => void;
|
|
1343
|
-
};
|
|
1344
|
-
/** @deprecated Use `asciiBackground` instead. */
|
|
1345
|
-
declare const mountWaveBackground: typeof asciiBackground;
|
|
1346
|
-
/** @deprecated Use `AsciiBackgroundOptions` instead. */
|
|
1347
|
-
type MountWaveOptions = AsciiBackgroundOptions;
|
|
1348
|
-
|
|
1349
|
-
/**
|
|
1350
|
-
* asciiText — pure string output (no canvas required).
|
|
1351
|
-
* Converts an image/video/canvas element to a plain-text ASCII string
|
|
1352
|
-
* suitable for server-side rendering, clipboard export, or terminal output.
|
|
1353
|
-
*/
|
|
1354
|
-
|
|
1355
|
-
/**
|
|
1356
|
-
* Convert any image/video/canvas source to a plain multi-line string of ASCII.
|
|
1357
|
-
*
|
|
1358
|
-
* @example
|
|
1359
|
-
* ```ts
|
|
1360
|
-
* const text = asciiText(imgEl, { fontSize: 8, colorMode: 'grayscale' });
|
|
1361
|
-
* console.log(text);
|
|
1362
|
-
* ```
|
|
1363
|
-
*
|
|
1364
|
-
* @example SSR (Node/JSDOM)
|
|
1365
|
-
* ```ts
|
|
1366
|
-
* const { createCanvas, loadImage } = require('@napi-rs/canvas');
|
|
1367
|
-
* const img = await loadImage('./photo.jpg');
|
|
1368
|
-
* const canvas = createCanvas(img.width, img.height);
|
|
1369
|
-
* const ctx = canvas.getContext('2d');
|
|
1370
|
-
* ctx.drawImage(img, 0, 0);
|
|
1371
|
-
* const text = asciiText(canvas as unknown as HTMLCanvasElement, { fontSize: 10 });
|
|
1372
|
-
* ```
|
|
1373
|
-
*/
|
|
1374
|
-
declare function asciiText(source: HTMLImageElement | HTMLVideoElement | HTMLCanvasElement, options?: Partial<AsciiOptions>, targetWidth?: number, targetHeight?: number): string;
|
|
1375
|
-
/**
|
|
1376
|
-
* Convert any source to an ASCII string with ANSI 256-colour escape codes.
|
|
1377
|
-
* Works in any terminal that supports ANSI colours.
|
|
1378
|
-
*
|
|
1379
|
-
* @example
|
|
1380
|
-
* ```ts
|
|
1381
|
-
* process.stdout.write(asciiTextAnsi(imgEl, { fontSize: 8 }));
|
|
1382
|
-
* ```
|
|
1383
|
-
*/
|
|
1384
|
-
declare function asciiTextAnsi(source: HTMLImageElement | HTMLVideoElement | HTMLCanvasElement, options?: Partial<AsciiOptions>, targetWidth?: number, targetHeight?: number): string;
|
|
1385
|
-
|
|
1386
|
-
/**
|
|
1387
|
-
* text-frame.ts — Build and render ASCII frames from tiling text patterns.
|
|
1388
|
-
*
|
|
1389
|
-
* Enables interactive text backgrounds with the full hover-effect system
|
|
1390
|
-
* (spotlight, magnify, repel, glow, colorShift, …) without needing an image
|
|
1391
|
-
* source.
|
|
1392
|
-
*
|
|
1393
|
-
* @example — basic usage
|
|
1394
|
-
* ```ts
|
|
1395
|
-
* import { renderTextBackground } from 'asciify-engine';
|
|
1396
|
-
*
|
|
1397
|
-
* function tick(ctx, w, h, mousePos) {
|
|
1398
|
-
* renderTextBackground(ctx, w, h, 'asciify·engine·v1·', {
|
|
1399
|
-
* hoverEffect: 'spotlight',
|
|
1400
|
-
* hoverColor: '#d4ff00',
|
|
1401
|
-
* }, mousePos);
|
|
1402
|
-
* requestAnimationFrame(() => tick(ctx, w, h, mousePos));
|
|
1403
|
-
* }
|
|
1404
|
-
* ```
|
|
1405
|
-
*
|
|
1406
|
-
* @example — build the frame yourself and pass it to renderFrameToCanvas
|
|
1407
|
-
* ```ts
|
|
1408
|
-
* import { buildTextFrame, renderFrameToCanvas, DEFAULT_OPTIONS } from 'asciify-engine';
|
|
1409
|
-
*
|
|
1410
|
-
* const frame = buildTextFrame('hello world · ', 80, 24);
|
|
1411
|
-
* renderFrameToCanvas(ctx, frame, {
|
|
1412
|
-
* ...DEFAULT_OPTIONS,
|
|
1413
|
-
* hoverEffect: 'repel',
|
|
1414
|
-
* hoverStrength: 0.9,
|
|
1415
|
-
* hoverColor: '#a0e8ff',
|
|
1416
|
-
* }, width, height, 0, mousePos);
|
|
1417
|
-
* ```
|
|
1418
|
-
*/
|
|
1419
|
-
|
|
1420
|
-
interface TextBackgroundOptions {
|
|
1421
|
-
/**
|
|
1422
|
-
* Character size in pixels.
|
|
1423
|
-
* Controls the grid density: smaller → more cells, finer text.
|
|
1424
|
-
* @default 10
|
|
1425
|
-
*/
|
|
1426
|
-
fontSize?: number;
|
|
1427
|
-
/**
|
|
1428
|
-
* Line-height multiplier applied on top of `fontSize` to derive row height.
|
|
1429
|
-
* Matches the default monospace aspect ratio used by the renderer.
|
|
1430
|
-
* @default 1.6
|
|
1431
|
-
*/
|
|
1432
|
-
lineHeight?: number;
|
|
1433
|
-
/**
|
|
1434
|
-
* Base colour for the text cells (inactive state).
|
|
1435
|
-
* Accepts any CSS hex or rgb string.
|
|
1436
|
-
* @default '#505050'
|
|
1437
|
-
*/
|
|
1438
|
-
color?: string;
|
|
1439
|
-
/**
|
|
1440
|
-
* Base alpha for the text cells, 0–255.
|
|
1441
|
-
* @default 100
|
|
1442
|
-
*/
|
|
1443
|
-
opacity?: number;
|
|
1444
|
-
/**
|
|
1445
|
-
* Which hover effect to activate when `hoverPos` is supplied.
|
|
1446
|
-
* @default 'spotlight'
|
|
1447
|
-
*/
|
|
1448
|
-
hoverEffect?: HoverEffect;
|
|
1449
|
-
/**
|
|
1450
|
-
* Intensity of the hover distortion / glow, 0–1.
|
|
1451
|
-
* @default 0.85
|
|
1452
|
-
*/
|
|
1453
|
-
hoverStrength?: number;
|
|
1454
|
-
/**
|
|
1455
|
-
* Normalised radius of the hover influence zone, 0–1.
|
|
1456
|
-
* @default 0.18
|
|
1457
|
-
*/
|
|
1458
|
-
hoverRadius?: number;
|
|
1459
|
-
/**
|
|
1460
|
-
* Accent colour applied by the hover effect.
|
|
1461
|
-
* @default '#d4ff00'
|
|
1462
|
-
*/
|
|
1463
|
-
hoverColor?: string;
|
|
1464
|
-
}
|
|
1465
|
-
/**
|
|
1466
|
-
* Build an `AsciiFrame` filled with a tiling text pattern.
|
|
1467
|
-
*
|
|
1468
|
-
* The `text` string is repeated (wrapping at column boundaries) across every
|
|
1469
|
-
* cell of the `cols × rows` grid. Each cell carries the supplied base colour
|
|
1470
|
-
* and opacity as `{r, g, b, a}` values.
|
|
1471
|
-
*
|
|
1472
|
-
* The returned frame can be passed directly to `renderFrameToCanvas` with any
|
|
1473
|
-
* `AsciiOptions` including hover effects.
|
|
1474
|
-
*
|
|
1475
|
-
* @param text - Pattern string to tile across the grid (e.g. `'hello · '`)
|
|
1476
|
-
* @param cols - Number of character columns
|
|
1477
|
-
* @param rows - Number of character rows
|
|
1478
|
-
* @param color - Base RGB colour string for the cells (default: `'#505050'`)
|
|
1479
|
-
* @param opacity - Base alpha 0–255 (default: `100`)
|
|
1480
|
-
*/
|
|
1481
|
-
declare function buildTextFrame(text: string, cols: number, rows: number, color?: string, opacity?: number): AsciiFrame;
|
|
1482
|
-
/**
|
|
1483
|
-
* All-in-one: build a tiling text grid and render it to a canvas with the
|
|
1484
|
-
* full hover-effect system (spotlight, magnify, repel, glow, colorShift, …).
|
|
1485
|
-
*
|
|
1486
|
-
* Call this inside a `requestAnimationFrame` loop, passing updated `hoverPos`
|
|
1487
|
-
* each frame to get smooth interactive effects.
|
|
1488
|
-
*
|
|
1489
|
-
* @param ctx - 2D rendering context of the target canvas
|
|
1490
|
-
* @param width - Canvas logical width in pixels
|
|
1491
|
-
* @param height - Canvas logical height in pixels
|
|
1492
|
-
* @param text - Pattern string to tile (e.g. `'asciify·engine·v1·'`)
|
|
1493
|
-
* @param options - {@link TextBackgroundOptions}
|
|
1494
|
-
* @param hoverPos - Normalised mouse position `{x, y}` in 0–1 range,
|
|
1495
|
-
* optionally with an `intensity` multiplier (0–1).
|
|
1496
|
-
* Pass `null` or omit to render without hover.
|
|
1497
|
-
*/
|
|
1498
|
-
declare function renderTextBackground(ctx: CanvasRenderingContext2D, width: number, height: number, text: string, options?: TextBackgroundOptions, hoverPos?: {
|
|
1499
|
-
x: number;
|
|
1500
|
-
y: number;
|
|
1501
|
-
intensity?: number;
|
|
1502
|
-
} | null): void;
|
|
1503
|
-
|
|
1504
|
-
interface SnapshotOptions {
|
|
1505
|
-
/**
|
|
1506
|
-
* Image format.
|
|
1507
|
-
* - 'png' — lossless (default)
|
|
1508
|
-
* - 'jpeg' — smaller, no transparency
|
|
1509
|
-
* - 'webp' — best compression with transparency
|
|
1510
|
-
*/
|
|
1511
|
-
format?: 'png' | 'jpeg' | 'webp';
|
|
1512
|
-
/** 0–1 quality for jpeg/webp. Default: 0.92 */
|
|
1513
|
-
quality?: number;
|
|
1514
|
-
/**
|
|
1515
|
-
* Scale factor applied before capture. Default: 1.
|
|
1516
|
-
* Use 2 for a high-resolution export at 2× the canvas size.
|
|
1517
|
-
*/
|
|
1518
|
-
scale?: number;
|
|
1519
|
-
}
|
|
1520
|
-
/**
|
|
1521
|
-
* Capture a single frame from a canvas as a Blob.
|
|
1522
|
-
*
|
|
1523
|
-
* @example
|
|
1524
|
-
* ```ts
|
|
1525
|
-
* const blob = await captureSnapshot(canvas);
|
|
1526
|
-
* const url = URL.createObjectURL(blob);
|
|
1527
|
-
* ```
|
|
1528
|
-
*/
|
|
1529
|
-
declare function captureSnapshot(canvas: HTMLCanvasElement, { format, quality, scale }?: SnapshotOptions): Promise<Blob>;
|
|
1530
|
-
/**
|
|
1531
|
-
* Capture a single frame and immediately trigger a browser download.
|
|
1532
|
-
*
|
|
1533
|
-
* @example
|
|
1534
|
-
* ```ts
|
|
1535
|
-
* await snapshotAndDownload(canvas);
|
|
1536
|
-
* await snapshotAndDownload(canvas, { format: 'jpeg', filename: 'my-art' });
|
|
1537
|
-
* ```
|
|
1538
|
-
*/
|
|
1539
|
-
declare function snapshotAndDownload(canvas: HTMLCanvasElement, options?: SnapshotOptions & {
|
|
1540
|
-
filename?: string;
|
|
1541
|
-
}): Promise<void>;
|
|
1542
|
-
|
|
1543
|
-
/**
|
|
1544
|
-
* asciifyWebcam — live webcam → ASCII art on canvas.
|
|
1545
|
-
*
|
|
1546
|
-
* Requests camera access, attaches the stream to a hidden video element, and
|
|
1547
|
-
* runs a rAF loop that converts each frame to ASCII and renders it onto a
|
|
1548
|
-
* supplied canvas.
|
|
1549
|
-
*
|
|
1550
|
-
* @example
|
|
1551
|
-
* const stop = await asciifyWebcam(canvas);
|
|
1552
|
-
* // later: stop();
|
|
1553
|
-
*
|
|
1554
|
-
* @example
|
|
1555
|
-
* const stop = await asciifyWebcam(canvas, {
|
|
1556
|
-
* fontSize: 8,
|
|
1557
|
-
* style: 'terminal',
|
|
1558
|
-
* mirror: true, // horizontal flip (selfie mode)
|
|
1559
|
-
* constraints: { facingMode: 'user' },
|
|
1560
|
-
* });
|
|
1561
|
-
*/
|
|
1562
|
-
|
|
1563
|
-
interface WebcamOptions {
|
|
1564
|
-
/** Character size in pixels. Default: 10 */
|
|
1565
|
-
fontSize?: number;
|
|
1566
|
-
/** Art style preset. Default: 'classic' */
|
|
1567
|
-
style?: ArtStyle;
|
|
1568
|
-
/** Extra AsciiOptions merged on top of the preset */
|
|
1569
|
-
options?: Partial<AsciiOptions>;
|
|
1570
|
-
/**
|
|
1571
|
-
* Called every frame to get the latest options. Takes priority over `options`.
|
|
1572
|
-
* Use this to keep the rendering in sync with live UI controls without
|
|
1573
|
-
* restarting the camera.
|
|
1574
|
-
*
|
|
1575
|
-
* @example
|
|
1576
|
-
* const optionsRef = useRef(currentOptions);
|
|
1577
|
-
* optionsRef.current = currentOptions;
|
|
1578
|
-
* asciifyWebcam(canvas, { liveOptions: () => optionsRef.current });
|
|
1579
|
-
*/
|
|
1580
|
-
liveOptions?: () => Partial<AsciiOptions>;
|
|
1581
|
-
/**
|
|
1582
|
-
* Flip the output horizontally so it reads like a mirror / selfie camera.
|
|
1583
|
-
* Default: true
|
|
1584
|
-
*/
|
|
1585
|
-
mirror?: boolean;
|
|
1586
|
-
/**
|
|
1587
|
-
* Passed directly to `getUserMedia({ video: constraints })`.
|
|
1588
|
-
* Defaults to `{ facingMode: 'user' }`.
|
|
1589
|
-
*/
|
|
1590
|
-
constraints?: MediaTrackConstraints;
|
|
1591
|
-
/**
|
|
1592
|
-
* Device pixel ratio used to compute logical render dimensions from the
|
|
1593
|
-
* canvas's physical pixel size. Defaults to `window.devicePixelRatio ?? 1`.
|
|
1594
|
-
* Set this when you size the canvas at physical resolution (e.g. width × dpr)
|
|
1595
|
-
* so that ASCII column/row counts are based on CSS pixels, not physical ones.
|
|
1596
|
-
*/
|
|
1597
|
-
dpr?: number;
|
|
1598
|
-
}
|
|
1599
|
-
/**
|
|
1600
|
-
* Start a live webcam ASCII-art loop and render it onto `canvas`.
|
|
1601
|
-
* Returns a `stop()` function that cancels the loop and releases the camera.
|
|
1602
|
-
*
|
|
1603
|
-
* Throws if the browser doesn't support `getUserMedia` or the user denies
|
|
1604
|
-
* camera permission.
|
|
1605
|
-
*/
|
|
1606
|
-
declare function asciifyWebcam(canvas: HTMLCanvasElement, { fontSize, style, options, liveOptions, mirror, constraints, dpr: dprOverride, }?: WebcamOptions): Promise<() => void>;
|
|
1607
|
-
|
|
1608
|
-
/**
|
|
1609
|
-
* big-text.ts — ASCII text rendering via an embedded 7×7 bitmap font.
|
|
1610
|
-
*
|
|
1611
|
-
* Each character is defined as 7 rows × 7 pixels stored as compact bit-patterns.
|
|
1612
|
-
* No canvas, no font files, no pixel-sampling — output is always crisp and readable.
|
|
1613
|
-
*
|
|
1614
|
-
* @example
|
|
1615
|
-
* ```ts
|
|
1616
|
-
* import { asciifyText } from 'asciify-engine';
|
|
1617
|
-
* console.log(asciifyText('Hello!'));
|
|
1618
|
-
* console.log(asciifyText('v2', { scale: 2, char: '#' }));
|
|
1619
|
-
* ```
|
|
1620
|
-
*/
|
|
1621
|
-
interface BigTextOptions {
|
|
1622
|
-
/**
|
|
1623
|
-
* Character used for ink pixels. Any single grapheme — emoji work too.
|
|
1624
|
-
* @default '█'
|
|
1625
|
-
*/
|
|
1626
|
-
char?: string;
|
|
1627
|
-
/**
|
|
1628
|
-
* Pixel scale factor.
|
|
1629
|
-
* `1` = each font pixel → 1 char (output is 7 rows tall).
|
|
1630
|
-
* `2` = each pixel → 2×2 chars (14 rows tall), etc.
|
|
1631
|
-
* @default 1
|
|
1632
|
-
*/
|
|
1633
|
-
scale?: number;
|
|
1634
|
-
/** Foreground colour (canvas output only). @default '#d4ff00' */
|
|
1635
|
-
color?: string;
|
|
1636
|
-
/** Background colour (canvas output only). @default transparent */
|
|
1637
|
-
bgColor?: string;
|
|
1638
|
-
/** Physical character cell size in px (canvas output only). @default 10 */
|
|
1639
|
-
fontSize?: number;
|
|
1640
|
-
}
|
|
1641
|
-
/**
|
|
1642
|
-
* Convert a string to multi-line ASCII text art.
|
|
1643
|
-
*
|
|
1644
|
-
* Uses an embedded 7×7 pixel bitmap font — no font files, no install step,
|
|
1645
|
-
* works in every JS environment (browser, Node, Deno, Bun).
|
|
1646
|
-
*
|
|
1647
|
-
* @example
|
|
1648
|
-
* ```ts
|
|
1649
|
-
* import { asciifyText } from 'asciify-engine';
|
|
1650
|
-
* console.log(asciifyText('Hello!'));
|
|
1651
|
-
* console.log(asciifyText('v2.0', { char: '#' }));
|
|
1652
|
-
* console.log(asciifyText('WOW', { scale: 2, char: '▓' }));
|
|
1653
|
-
* ```
|
|
1654
|
-
*/
|
|
1655
|
-
declare function asciifyText(text: string, options?: BigTextOptions): string;
|
|
1656
|
-
/**
|
|
1657
|
-
* Render ASCII text directly onto an HTMLCanvasElement.
|
|
1658
|
-
* The canvas is automatically resized to fit the output.
|
|
1659
|
-
*
|
|
1660
|
-
* @example
|
|
1661
|
-
* ```ts
|
|
1662
|
-
* import { renderTextToCanvas } from 'asciify-engine';
|
|
1663
|
-
* renderTextToCanvas(canvas, 'Hello!', { color: '#d4ff00', scale: 2 });
|
|
1664
|
-
* ```
|
|
1665
|
-
*/
|
|
1666
|
-
declare function renderTextToCanvas(canvas: HTMLCanvasElement, text: string, options?: BigTextOptions): void;
|
|
1667
|
-
|
|
1668
|
-
export { ART_STYLE_PRESETS, type AnimationStyle, type ArtStyle, type AsciiBackgroundOptions, type AsciiCell, type AsciiFrame, type AsciiOptions, type AsciiResult, type AsciiTextFrame, type AsciifyLiveVideoOptions, type AsciifySimpleOptions, type AsciifyVideoOptions, type AuroraBackgroundOptions, BACKGROUND_TYPES, type BackgroundType, type BigTextOptions, CHARSETS, CHARSET_SEQUENCES, type CanvasBleed, type CanvasObjectFit, type CanvasRenderSizeInput, type CharsetKey, type CharsetSequenceKey, type CircuitBackgroundOptions, type ColorMode, DEFAULT_OPTIONS, type DnaBackgroundOptions, type FireBackgroundOptions, type GridBackgroundOptions, HOVER_PRESETS, type HoverEffect, type HoverPreset, type HoverShape, LIVING_STYLE_PRESETS, type LivingStylePresetKey, type MorphBackgroundOptions, type MountWaveOptions, type NoiseBackgroundOptions, PALETTE_THEMES, type PaletteTheme, type PulseBackgroundOptions, type RainBackgroundOptions, type RenderMode, type SilkBackgroundOptions, type SnapshotOptions, type SourceType, type StarsBackgroundOptions, type TerrainBackgroundOptions, type TextBackgroundOptions, type VideoScrollScrubOptions, type VoidBackgroundOptions, type WaveBackgroundOptions, type WebcamOptions, asciiBackground, asciiText, asciiTextAnsi, asciify, asciifyGif, asciifyLiveVideo, asciifyText, asciifyVideo, asciifyWebcam, buildTextFrame, captureSnapshot, clearAsciifyCaches, computeCanvasRenderSize, createVideoScrollScrub, gifToAsciiFrames, gifToAsciiTextFrames, imageToAsciiFrame, imageToAsciiTextFrame, mountWaveBackground, renderAuroraBackground, renderCircuitBackground, renderDnaBackground, renderFireBackground, renderFrameToCanvas, renderGridBackground, renderMorphBackground, renderNoiseBackground, renderPulseBackground, renderRainBackground, renderSilkBackground, renderStarsBackground, renderTerrainBackground, renderTextBackground, renderTextFrameToCanvas, renderTextToCanvas, renderVoidBackground, renderWaveBackground, snapshotAndDownload, videoToAsciiFrames, videoToAsciiTextFrames };
|
|
1
|
+
export { ART_STYLE_PRESETS, AnimationStyle, ArtStyle, AsciiCell, AsciiFrame, AsciiOptions, AsciiResult, AsciiTextFrame, AsciifyLiveVideoOptions, AsciifySimpleOptions, AsciifyVideoOptions, BigTextOptions, CHARSETS, CHARSET_SEQUENCES, CanvasBleed, CanvasObjectFit, CanvasRenderSizeInput, CharsetKey, CharsetSequenceKey, ColorMode, DEFAULT_OPTIONS, HOVER_PRESETS, HoverEffect, HoverPreset, HoverShape, LIVING_STYLE_PRESETS, LivingStylePresetKey, PALETTE_THEMES, PaletteTheme, RenderMode, SnapshotOptions, SourceType, TextBackgroundOptions, VideoScrollScrubOptions, WebcamOptions, asciiText, asciiTextAnsi, asciify, asciifyGif, asciifyLiveVideo, asciifyText, asciifyVideo, asciifyWebcam, buildTextFrame, captureSnapshot, clearAsciifyCaches, computeCanvasRenderSize, createVideoScrollScrub, gifToAsciiFrames, gifToAsciiTextFrames, imageToAsciiFrame, imageToAsciiTextFrame, renderFrameToCanvas, renderTextBackground, renderTextFrameToCanvas, renderTextToCanvas, snapshotAndDownload, videoToAsciiFrames, videoToAsciiTextFrames } from './core.js';
|
|
2
|
+
export { AsciiBackgroundOptions, AuroraBackgroundOptions, BACKGROUND_TYPES, BackgroundType, CircuitBackgroundOptions, DnaBackgroundOptions, FireBackgroundOptions, GridBackgroundOptions, MorphBackgroundOptions, MountWaveOptions, NoiseBackgroundOptions, PulseBackgroundOptions, RainBackgroundOptions, SilkBackgroundOptions, StarsBackgroundOptions, TerrainBackgroundOptions, VoidBackgroundOptions, WaveBackgroundOptions, asciiBackground, mountWaveBackground, renderAuroraBackground, renderCircuitBackground, renderDnaBackground, renderFireBackground, renderGridBackground, renderMorphBackground, renderNoiseBackground, renderPulseBackground, renderRainBackground, renderSilkBackground, renderStarsBackground, renderTerrainBackground, renderVoidBackground, renderWaveBackground } from './backgrounds.js';
|