Overview
The existing GLITCH filter will be deprecated - though we can keep the existing filter under a new name eg legacy-glitch.
Instead, Scrawl-canvas will provide a set of small, composable glitch primitives that can be mixed and matched to create modern “glitch” looks (VHS, scanline, streaming errors, codec corruption, etc.).
This approach:
- Improves clarity and composability (each operator does one thing well)
- Matches the modular architecture of the current filter engine
- Keeps filters performant (O(n) row/column or 32-bit array operations)
- Makes it easier to define presets
What’s Already Possible (No New Filters Needed)
Channel Split / RGB Drift
Use: OFFSET (per-channel dx/dy) + optional GAUSSIAN_BLUR
Notes:
OFFSET already supports offsetRedX/Y, offsetGreenX/Y, offsetBlueX/Y, etc.
- Apply small-radius blur with
includeAlpha:false to simulate chroma bleed.
Quantize / Posterize / Banding
Use:
STEP_CHANNELS (bit-depth style stepping)
LOCK_CHANNELS_TO_LEVELS (explicit level locking)
REDUCE_PALETTE (palette quantization with optional dithering)
Noise Overlays (Grain, RF Snow)
Use: RANDOM_NOISE
noiseType: 'random' | 'ordered' | 'bluenoise'
- Combine with subtle vertical blur for analog “hum”.
Color-Space “Oops” (Range Crush / Chroma Smear)
Use: TINT_CHANNELS, MODULATE_CHANNELS, or OKLab filters
- Range crush via
MODULATE_CHANNELS (amplify/clamp)
- Chroma smear via channel-only blur:
Partially Covered (Workable via Chaining)
Row/Column Displace (Band “Tears”)
Current options:
- Deprecated
GLITCH has row shift logic
DISPLACE with a banded displacement map in lineMix
Recommendation: add a clean, seedable ROW_COL_DISPLACE primitive for performance and ergonomics.
Slice Repeat / Dropout
Current status: can fake dropouts via THRESHOLD + COMPOSE.
Missing: true “duplicate this slice” and “zero this span” operations.
Recommendation: implement a dedicated SLICE_REPEAT_DROPOUT primitive.
Scanline Mod (Sinusoidal Luminance)
Current status: not achievable with current per-grayweight filters.
Recommendation: add a cheap per-row modulation primitive.
New Filters to Add
1) ROW_COL_DISPLACE
Purpose: Shift rows/columns in random bands (VHS/scanline effect).
Arguments:
direction: 'x' | 'y' | 'both'
bands: { chance, heightMin, heightMax }
offset: { xMin, xMax, yMin, yMax }
edgeMode: 'wrap' | 'clamp' | 'transparent'
seed
Implementation notes:
- Bulk
Uint32Array subarray copies per band for speed; O(n)
2) SLICE_REPEAT_DROPOUT
Purpose: Duplicate or zero random horizontal slices (streaming tear).
Arguments:
repeat: { chance, widthMin, widthMax, offsetMin, offsetMax }
dropout: { chance, widthMin, widthMax }
wrapMode: 'row' | 'image'
seed
Implementation notes:
- Row-local
set and fill operations; O(n)
3) SCANLINE_MOD
Purpose: Apply per-row brightness modulation (sin wave or hum).
Arguments:
amp, freq, phase, bias = 0
includeAlpha = false
Implementation notes:
- Fast multiply/add scalar per row on R/G/B; O(n)
Overview
The existing
GLITCHfilter will be deprecated - though we can keep the existing filter under a new name eglegacy-glitch.Instead, Scrawl-canvas will provide a set of small, composable glitch primitives that can be mixed and matched to create modern “glitch” looks (VHS, scanline, streaming errors, codec corruption, etc.).
This approach:
What’s Already Possible (No New Filters Needed)
Channel Split / RGB Drift
Use:
OFFSET(per-channel dx/dy) + optionalGAUSSIAN_BLURNotes:
OFFSETalready supportsoffsetRedX/Y,offsetGreenX/Y,offsetBlueX/Y, etc.includeAlpha:falseto simulate chroma bleed.Quantize / Posterize / Banding
Use:
STEP_CHANNELS(bit-depth style stepping)LOCK_CHANNELS_TO_LEVELS(explicit level locking)REDUCE_PALETTE(palette quantization with optional dithering)Noise Overlays (Grain, RF Snow)
Use:
RANDOM_NOISEnoiseType: 'random' | 'ordered' | 'bluenoise'Color-Space “Oops” (Range Crush / Chroma Smear)
Use:
TINT_CHANNELS,MODULATE_CHANNELS, or OKLab filtersMODULATE_CHANNELS(amplify/clamp)Partially Covered (Workable via Chaining)
Row/Column Displace (Band “Tears”)
Current options:
GLITCHhas row shift logicDISPLACEwith a banded displacement map inlineMixRecommendation: add a clean, seedable
ROW_COL_DISPLACEprimitive for performance and ergonomics.Slice Repeat / Dropout
Current status: can fake dropouts via
THRESHOLD+COMPOSE.Missing: true “duplicate this slice” and “zero this span” operations.
Recommendation: implement a dedicated
SLICE_REPEAT_DROPOUTprimitive.Scanline Mod (Sinusoidal Luminance)
Current status: not achievable with current per-grayweight filters.
Recommendation: add a cheap per-row modulation primitive.
New Filters to Add
1)
ROW_COL_DISPLACEPurpose: Shift rows/columns in random bands (VHS/scanline effect).
Arguments:
direction: 'x' | 'y' | 'both'bands: { chance, heightMin, heightMax }offset: { xMin, xMax, yMin, yMax }edgeMode: 'wrap' | 'clamp' | 'transparent'seedImplementation notes:
Uint32Arraysubarray copies per band for speed; O(n)2)
SLICE_REPEAT_DROPOUTPurpose: Duplicate or zero random horizontal slices (streaming tear).
Arguments:
repeat: { chance, widthMin, widthMax, offsetMin, offsetMax }dropout: { chance, widthMin, widthMax }wrapMode: 'row' | 'image'seedImplementation notes:
setandfilloperations; O(n)3)
SCANLINE_MODPurpose: Apply per-row brightness modulation (sin wave or hum).
Arguments:
amp, freq, phase, bias = 0includeAlpha = falseImplementation notes: