Hacktoberfest 2026: los issues que los mantenedores marcaron para octubre, abiertos y aptos para principiantes. Explorar issues de Hacktoberfest

feat: add terminal-native image preview to TUI

Cerrado
#1,355 1 comentario 0 reacciones 0 asignados Ver en GitHub

Los mantenedores suelen responder en 1 día

Nadie ha tomado este issue todavía.

Evaluación

Dificultad
5/5
Tiempo estimado
Más de una semana
Aptitud para principiantes
15/100
Tipo de issue
Nueva funcionalidad
Claridad
Bastante claro
Estado de actividad
Activo
Stack tecnológico
javascript
Área
cli

Línea de trabajo

Start with the image() renderer in src/tui/markdownText.js (around line 242), which currently emits raw markdown, and with readImageImpl in src/tools/image/readImage.js for the bytes. Check tests/unit/markdownText.test.js for the existing renderer tests. The issue requires an OpenSpec proposal and design sign-off before any code, so this is not ready to start. Done means the escape sequence is emitted for a supported terminal and the markdown fallback is kept otherwise.

Escrito por el modelo de indexación a partir del texto del issue.

Descripción

feature

Summary

Add terminal-native image preview to the TUI, rendering images directly in the terminal via the iTerm/Kitty inline-image protocol using the existing readImage tool and image tooling.

Motivation

Users want to preview images without leaving the terminal or opening an external viewer. The TUI currently has no way to render image content inline, forcing a context switch to view screenshots, diagrams, or other image assets.

Proposed Solution

Render images inline in the TUI using the iTerm/Kitty inline-image protocol. Reuse the existing readImage tool and image tooling to load image data, then emit the appropriate terminal escape sequences to display the image in place.

Dependencies

  • Terminal protocol support — iTerm2, Kitty, WezTerm, or a compatible terminal that supports the inline-image protocol. No npm package required; the feature relies on terminal-native escape sequences.
  • Existing tooling — Reuse the existing readImage tool and image handling code already present in the project.

Testing Strategy

  • Unit tests: Verify the image-to-escape-sequence conversion produces correct output for supported formats.
  • Integration test: Render an image through the TUI and confirm the inline-image protocol is emitted.
  • Edge cases: Unsupported terminal (no inline-image support), missing image file, very large image, and non-image file input.

Security Considerations

  • Credential storage: No credentials involved — this feature only reads local image files.
  • Input validation: Validate image paths and file types before reading to prevent path traversal and unexpected file reads.
  • OWASP: Restrict reads to allowed image paths; avoid reading arbitrary files based on user-controlled input.

Alternatives Considered

  • External viewer — Launching an external image viewer (e.g., open, xdg-open) is simpler but breaks the terminal-native workflow and requires a GUI.
  • ASCII/ANSI art rendering — Lower fidelity and not a true image preview.

OpenSpec Note

This project uses OpenSpec for feature development. If this request is approved, I will:

  1. Run /opsx:propose to generate a full proposal with specs and tasks
  2. Iterate on the design before any code is written
  3. Follow the task-driven implementation workflow

Additional Context

Split out from issue #1339 as part of the "Terminal image preview" group of TUI enhancements.

Audit Findings (for Issue #1355)

  • src/tui/markdownText.js — The image({ href, title, text, tokens }) renderer (line 242) currently emits the raw markdown ![text](href) string. This is the primary integration point: replace it with an inline-image escape sequence when the terminal supports the iTerm/Kitty protocol.
  • src/tools/image/readImage.js — readImageImpl returns { ok, mimeType, data } where data is base64 and mimeType is detected from the file extension via detectMimeType(). This is the source of image bytes for inline rendering. Note the image.maxSize config (default 100000 bytes on the base64 output) caps how large an image can be read — inline previews will inherit this limit.
  • src/tools/image/sendImage.js — sendImageImpl builds a data:<mimeType>;base64,<data> URI. The same data-URI construction pattern is reusable for the inline-image protocol payload.
  • src/tools/index.js — readImage is registered with filesystem:read permission and classified for search, research, coding, documentation, debug agent types. No new registration needed for the TUI renderer.
  • src/provider/imageDispatchMiddleware.js — Handles readImage results for LLM vision dispatch (multimodal image_url). This is the agent-side path; the TUI inline preview is a separate, terminal-side rendering concern and does not overlap with this middleware.
  • src/tui/messageBubble.js — Renders message content through MarkdownText (line 403/420). Inline images rendered by markdownText will flow through here automatically; no change needed unless image sizing/positioning requires a custom component.
  • Dependencies already present — ansi-escapes (v7.3.0) and ink (v8.0.0) are in package.json. ansi-escapes provides terminal escape helpers; verify whether it exposes an inline-image helper or whether the iTerm/Kitty escape sequence must be constructed manually.
  • Tests — Existing coverage at tests/unit/markdownText.test.js (renderer), tests/unit/tools/image/readImage.test.js, and tests/unit/tools/image/sendImage.test.js. New tests should extend markdownText.test.js for the image renderer and add a terminal-protocol detection test.

Fix Steps

  1. Detect terminal support — Add a helper (e.g., in src/tui/markdownText.js or a new src/tui/imagePreview.js) that detects whether the terminal supports the iTerm (OSC 1337) or Kitty (OSC 1337/APC) inline-image protocol. Use process.env.TERM_PROGRAM (iTerm.app, WezTerm, kitty) and/or process.env.KITTY_WINDOW_ID as signals.
  2. Build the inline-image escape sequence — Construct the protocol payload from the base64 data and mimeType returned by readImageImpl. For iTerm: \x1b]1337;File=inline=1;width=<w>;height=<h>;preserveAspectRatio=1:<base64>\x07. For Kitty: \x1b_Ga=T,f=100,<base64>\x1b\\. Reuse the data-URI construction pattern from sendImage.js.
  3. Wire into the markdown renderer — Replace the image() method in src/tui/markdownText.js (line 242) to emit the inline-image sequence when terminal support is detected, falling back to the current ![text](href) markdown otherwise.
  4. Handle image source resolution — The markdown href may be a local path or a URL. For local paths, read via readImageImpl (respecting the sandbox allowlist and image.maxSize); for remote URLs, fetch the bytes. Decide whether to support remote URLs in the MVP.
  5. Write unit tests — Extend tests/unit/markdownText.test.js to assert the inline-image escape sequence is emitted for supported terminals and the markdown fallback for unsupported ones. Add a test for the protocol-detection helper.
  6. Verify — Run npm run test, npm run lint, and npm run coverage to confirm no regressions.
Lenguaje dominante
JavaScript
Estrellas
3
Forks
0
Merge medio
1 h 27 min
PR fusionados (30 d)
235

Preparar el entorno

Primeros pasos

  1. Lee el issue completo y luego la guía de contribución del proyecto.
  2. Comenta en el issue que vas a ocuparte — evita que dos personas hagan lo mismo.
  3. Haz un fork del repositorio y trabaja en una rama.
  4. Abre un pull request que haga referencia al número del issue.

Más de avoidwork/madz

Todos los issues de avoidwork/madz

Issues similares

Más issues de JavaScript

Recibe los nuevos issues en tu correo

Un resumen breve de issues de GitHub para principiantes.