A media pane beside your AI coding agent. When Claude Code reads an image, it shows up here, sharp, in your terminal. Video plays at full frame rate. Audio gets a waveform. Nothing to type.
An open-source tool from HYPRGRPH · more tools
Claude Code can read an image and reason about it, but the terminal it runs in never shows that image to you. The CLI offers Ctrl+Click to open the file in an external viewer. The desktop app has a preview pane you open by clicking, for images and video. The chat app and the VS Code extension render images inline. In the terminal, seeing what the agent sees still means leaving it, and for a lot of people the terminal is the point.
Graphics-capable terminals don't solve this on their own. WezTerm, kitty, Ghostty, iTerm2, and Windows Terminal can all draw real images with Sixel or the Kitty graphics protocol, but Claude Code repaints its entire screen many times a second, and anything drawn into that screen is erased on the next frame. Several open issues track this (#36476, #54546, #6389) and there is no fix, because the fix is architectural.
The image has to live somewhere the agent isn't. Viewfinder is a second pane that the agent does not own. A small hook reports which file the agent just read, and the pane draws it. The terminal, the scrollback, and the keybindings stay exactly as they were.
It is automatic, it stays in the terminal, and it covers images, video, and audio. Around that core are the things a review pane needs: video as a contact sheet with a real player behind it, audio as a waveform, a tree of the folder around the file, a history grouped by project so parallel agents stay separate, an A/B flip between the last two files, and a key that copies the path for the next tool.
| video: contact sheet, space plays it in mpv | audio: waveform, space plays it |
|---|---|
![]() |
![]() |
Requires Python 3.12+ and ffmpeg. mpv is optional but recommended for video and audio playback.
uv tool install git+https://github.com/wexloops/viewfinder
# or: pipx install git+https://github.com/wexloops/viewfinderUpgrade with uv tool upgrade viewfinder (or pipx upgrade viewfinder). Then run vf doctor to check ffmpeg, mpv, terminal graphics, and the agent hook in one go.
vf open # split the current terminal and start the pane
vf show FILE... # push anything to it, from any shell, script, or agent
vf setup claude # add the Claude Code hook so reads show up automatically
vf doctor # check dependencies and setup, with the fix for anything missing
vf # run the pane in the current terminal (any split you made yourself)vf open knows Windows Terminal, tmux, WezTerm, and kitty. Anywhere else, make a split and run vf.
vf setup claude adds one PostToolUse hook to ~/.claude/settings.json and leaves everything else in the file as it was. --dry-run prints the change without writing it, and --remove takes the hook out again. The hook is equivalent to:
"hooks": {"PostToolUse": [{"matcher": "Read|mcp__filesystem__read_media_file",
"hooks": [{"type": "command", "command": "vf hook claude", "async": true}]}]}Codex CLI: vf hook codex accepts the same payload shape. Experimental, untested against a live Codex hook.
| key | action |
|---|---|
| arrows | move through the list, the viewer previews as you go |
| enter / click | open a folder, show a file, or fold a project in history |
| space | play video or audio with mpv. ESC or q comes back |
| n / p | next / previous in history (files that were moved or deleted are skipped) |
| c | compare: flip to the previous file, press again to flip back |
| m | filter the list: all media, images, video, audio |
| h | toggle the bottom panel between folder tree and history grouped by project |
| y / Y | copy the path / the native (Windows) path |
| o | open in the OS default app |
| O | open the containing folder, with the file selected |
| r | reload the current file |
| t | show or hide the bottom panel |
| f | fullscreen the viewer |
| backspace | tree: up one directory |
| ? | show the keys in the pane |
| q | quit |
- Images: png, jpg, gif, webp, bmp, tiff. Rendered with Sixel or the Kitty graphics protocol, letterboxed on black, upright from EXIF, transparency over black. Decoded once off the main thread, so browsing a folder of large renders stays smooth.
- Video: a 4x3 contact sheet on arrival, mpv playback on space. Frames are sampled by seeking, so a feature-length file builds its sheet about as fast as a short clip.
- Audio: a waveform on arrival, mpv playback on space.
- Files it can't show (corrupt, moved, deleted, or ffmpeg missing) get a plain message in the pane with the reason.
History is stored as JSONL in ~/.viewfinder/history.jsonl, tagged with the agent's working directory and session, so parallel agents on different projects stay separated. Set VIEWFINDER_HOME to keep state somewhere else.
| terminal | images | status |
|---|---|---|
| Windows Terminal 1.22+ (incl. WSL) | Sixel | tested |
| WezTerm | Sixel | tested |
| kitty, Ghostty | Kitty graphics | should work, untested |
| iTerm2 | Sixel | should work, untested |
| others | half-cell blocks | fallback |
Force a protocol with vf --protocol sixel|tgp|halfcell|unicode if detection gets it wrong. vf doctor shows what was detected. Inside tmux, graphics need set -g allow-passthrough on (tmux 3.4+).
vf show writes a path to ~/.viewfinder/queue. The pane polls that file four times a second and renders whatever lands there. The Claude Code hook is a five-line adapter that extracts the file path from the tool call and calls vf show. That is the whole protocol, so any tool can drive Viewfinder with one line of shell.
git clone https://github.com/wexloops/viewfinder && cd viewfinder
uv run --group dev pytestThe tests drive the real pane headlessly and never touch your own ~/.viewfinder or ~/.claude.
MIT. Built by David Wexler for HYPRGRPH.
HYPRGRPH
Viewfinder is one of the tools HYPRGRPH builds for its own work and shares openly. See the rest at hyprgrph.xyz.


