Replace vaxis NewImage/Resize (which spawns goroutines that panic in
sixel encoder) with direct halfblock character rendering. Each terminal
cell uses upper-half-block with RGB fg/bg colors for 2x vertical
resolution. Pre-renders in background goroutine, Draw() just paints
pre-computed cells. Works in any 24-bit color terminal.
The go-sixel library panics on certain image dimensions during Resize().
Added panic recovery in drawImage() that falls back to alt text display.
Cleaned up all debug logging from the investigation.
- Decode images in background goroutine, not in Draw()
- Show [loading image...] placeholder until decode completes
- Skip pv.term.Draw() when composite is active (pager got no input)
- Thread-safe access to decoded image cache via sync.Mutex
- Invalidate callback triggers redraw when images finish decoding
Composite mode now handles j/k/g/G/PgUp/PgDown/mouse wheel for scrolling.
Text uses the configured default style. Images render inline via Vaxis.
Emails without images still use the standard pager path.
The composite renderer bypassed the pager (less) for any email with images,
losing colors, scrolling, and search. Now always forward to the pager with
[image: alt] text placeholders. Image refs are still extracted and stored
for future inline rendering.