Skip to main content

ASCII Art & Terminal Renderer

A small command-line application for rendering images, videos, and procedural 3D experiments directly in a terminal.

The project treats the terminal as a character-based framebuffer. Pixel brightness selects an ASCII character, ANSI escape sequences provide true color and screen updates, and mathematical renderers supply geometry, projection, lighting, and depth.

source pixels or 3D geometry
              ↓
      brightness / lighting
              ↓
        character mapping
              ↓
       optional ANSI color
              ↓
            terminal

Features

  • One ascii-art command for every renderer.
  • Still-image conversion with automatic aspect-ratio correction.
  • Monochrome and ANSI true-color video playback.
  • Optional synchronized audio through FFplay.
  • Frame dropping to limit long-term audio/video drift.
  • Configurable FPS, width, character ramp, color smoothing, and inversion.
  • Automatic fitting to the current terminal.
  • Five procedural demos: cube, sphere, donut, planet, and black hole.
  • Safe terminal cleanup after completion, errors, or Ctrl+C.
  • Compatibility entry points for the original scripts.

Requirements

  • Python 3.10 or newer.
  • Pillow for still images.
  • NumPy for video frame processing.
  • FFmpeg for video decoding.
  • FFplay for audio playback, unless --no-audio is used.
  • FFprobe is recommended for detecting the source video's dimensions. A 16:9 fallback is used when it is unavailable.

Check the external video tools:

ffmpeg -version
ffplay -version
ffprobe -version

On Windows, install an FFmpeg distribution containing all three programs and ensure its executable directory is on PATH.

Installation

Install the published package from PyPI:

python -m pip install --upgrade pip
python -m pip install terminal-ascii-art

Confirm that the command is available:

ascii-art --version
ascii-art list

If ascii-art is not found because your Python scripts directory is not on PATH, use the module form:

python -m terminal_ascii_art list

Python installations normally include pip. If python -m pip --version reports that pip is missing, bootstrap it with:

python -m ensurepip --upgrade

Install from source

Clone the repository and enter it:

git clone https://github.com/TFQ0/ASCII-Art.git
cd ASCII-Art

Create and activate a virtual environment:

py -m venv .venv
.venv\Scripts\Activate.ps1

Install the project in editable mode:

python -m pip install -e .

The editable installation provides the ascii-art command. The same interface can also be invoked as a Python module:

python -m terminal_ascii_art list

Quick start

Replace the example paths below with paths to your own image and video files.

List every available renderer:

ascii-art list

Convert an image:

ascii-art image "C:\path\to\photo.jpg" --width 100

Play a monochrome video with audio:

ascii-art video "C:\path\to\video.mp4"

Play a true-color video:

ascii-art video "C:\path\to\video.mp4" --color --fps 20 --width 120

Run a procedural demo:

ascii-art demo cube

Press Ctrl+C to stop an animation or video.

Input files do not need to be inside the repository. Quote paths that contain spaces. For example, in PowerShell:

ascii-art video "E:\Videos\Rena Circulation.mp4" --color --charset detailed --fps 20 --width 120

The equivalent Git Bash path is:

ascii-art video "/e/Videos/Rena Circulation.mp4" --color --charset detailed --fps 20 --width 120

Image rendering

ascii-art image IMAGE [options]

Examples:

# Print the result in the terminal
ascii-art image photo.png --width 120

# Write plain ASCII to a UTF-8 text file
ascii-art image photo.png --width 120 --output output\photo.txt

# Use a longer character ramp and reverse its brightness direction
ascii-art image photo.png --charset detailed --invert

Options:

Option Purpose
--width N Maximum output width. Default: 100.
--height N Optional maximum output height.
--charset NAME classic, detailed, or letters.
--invert Reverse the dark-to-bright ramp.
-o, --output PATH Write the rendered text to a file.

The source ratio is preserved while accounting for terminal cells being approximately twice as tall as they are wide.

Video rendering

ascii-art video VIDEO [options]

The default mode is monochrome with audio enabled. Add --color to preserve approximate source colors using ANSI 24-bit foreground codes.

Examples:

# Monochrome video without audio
ascii-art video clip.mp4 --no-audio

# Detailed true-color playback
ascii-art video clip.mp4 --color --charset detailed --width 160 --fps 20

# Add motion trails
ascii-art video clip.mp4 --color --smoothing 0.35

# Delay audio by 0.5 seconds
ascii-art video clip.mp4 --audio-delay 0.5

Options:

Option Purpose
--color Enable ANSI true-color output.
--fps N Target playback rate. Default: 20.
--width N Maximum render width. Default: 160.
--smoothing N Temporal blend from 0 to 1; 1 is crisp.
--quant N Color quantization step used to reduce ANSI output. Default: 4.
--max-frame-skip N Consecutive frames that may be dropped to catch up. Default: 5.
--no-audio Do not start FFplay.
--audio-delay N Shift audio by -30 to +30 seconds; positive values delay it.
--charset NAME classic, detailed, or letters.
--invert Reverse the selected brightness ramp.

The video pipeline is:

                       ┌─ FFmpeg → scaled raw frames → NumPy → ASCII → terminal
source video ──────────┤
                       └─ FFplay → audio

The renderer uses a wall-clock schedule. When terminal rendering falls behind, it can discard a bounded number of decoded frames instead of allowing drift to grow continuously.

Procedural demos

ascii-art demo NAME [options]

Available names:

Demo Technique
cube Vertex rotation, perspective projection, face normals, back-face culling, triangle filling, and interpolated depth buffering.
sphere Per-cell sphere reconstruction and directional lighting.
donut Parametric torus sampling, normal-based lighting, perspective, and depth buffering.
planet Rotating sphere with procedural terrain, a night side, and an atmospheric rim.
blackhole Polar-coordinate accretion disk, deterministic stars, asymmetric glow, and a photon-ring effect.

Examples:

ascii-art demo donut --fps 30
ascii-art demo planet --width 120 --charset detailed
ascii-art demo blackhole --width 140 --height 50

Every demo accepts --width, --height, --fps, --charset, and --invert. Dimensions are reduced when necessary to fit the terminal.

Character ramps

Character ramps are ordered from dark to bright:

classic:   " .:-=+*#%@"
detailed:  a longer ramp with finer brightness changes
letters:   a dense, text-like ramp

To add a procedural demo:

  1. Create a module under terminal_ascii_art/renderers/.
  2. Implement render_frame(frame_index, width, height, ramp) -> str.
  3. Register it in terminal_ascii_art/renderers/__init__.py.
  4. Add a renderer-contract or algorithm-specific test.
  5. Document the new demo here.

Testing

Install the project and run the test suite from the repository root:

python -m pip install -e .
python -m unittest discover -s tests -v

Publishing a release

Releases are published from TFQ0/ASCII-Art by .github/workflows/publish.yml. The workflow runs the tests on the supported Python versions, builds and validates the wheel and source distribution, and publishes them to PyPI through Trusted Publishing.

Before the first release, configure a PyPI Trusted Publisher for the terminal-ascii-art project with these exact values:

  • Owner: TFQ0
  • Repository: ASCII-Art
  • Workflow: publish.yml
  • Environment: pypi

The GitHub pypi environment permits tags matching v*. If the account that creates the release is its only required reviewer, Prevent self-review must be disabled or another reviewer must be added.

For every release:

  1. Update __version__ in terminal_ascii_art/__init__.py. Package metadata reads the version from this single source.

  2. Run the tests.

  3. Build and validate the distributions locally:

    python -m pip install --upgrade build twine
    python -m build
    python -m twine check dist/*
    
  4. Commit and push the release changes.

  5. Create a GitHub release whose tag exactly matches the package version with a v prefix, such as v0.1.1.

Publishing a GitHub release triggers the workflow. PyPI does not allow an existing release file or version to be overwritten, so each published version must be unique.

Performance and limitations

Terminal output is much slower than GPU rendering. Performance depends on the CPU, terminal emulator, selected width, FPS, character ramp, and whether ANSI color is enabled.

Useful starting points:

  • 80 columns for low overhead.
  • 120 columns for balanced detail.
  • 160 columns for high detail on a capable terminal.
  • Monochrome mode when color output is too expensive.
  • A larger --quant value to reduce ANSI color changes.

License

This project is distributed under the MIT License.

Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

terminal_ascii_art-0.1.1.tar.gz (23.6 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

terminal_ascii_art-0.1.1-py3-none-any.whl (21.9 kB view details)

Uploaded Python 3

File details

Details for the file terminal_ascii_art-0.1.1.tar.gz.

File metadata

  • Download URL: terminal_ascii_art-0.1.1.tar.gz
  • Upload date:
  • Size: 23.6 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/7.0.0 CPython/3.13.14

File hashes

Hashes for terminal_ascii_art-0.1.1.tar.gz
Algorithm Hash digest
SHA256 3dc2be114e4eeb04037110e175a72faaad79470097464026d29b02403478e9aa
MD5 a16373b962894ef1220dae2cb34ea585
BLAKE2b-256 ede1e3a5619c1adc510b48fee449495c2f6d62c837985f58e850ae9309aa2a90

See more details on using hashes here.

Provenance

The following attestation bundles were made for terminal_ascii_art-0.1.1.tar.gz:

Publisher: publish.yml on TFQ0/ASCII-Art

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file terminal_ascii_art-0.1.1-py3-none-any.whl.

File metadata

File hashes

Hashes for terminal_ascii_art-0.1.1-py3-none-any.whl
Algorithm Hash digest
SHA256 bfbe8adf3a90f5ebcc3c4ac4c9010c6cffec616d74dc1ec4fb775eefb87631aa
MD5 fd3e123dac3870bd83fffc1398bde9bf
BLAKE2b-256 b6a7255990724aabec6c444eea94d2dcea3881439b955b7a5de6d4c594961b8e

See more details on using hashes here.

Provenance

The following attestation bundles were made for terminal_ascii_art-0.1.1-py3-none-any.whl:

Publisher: publish.yml on TFQ0/ASCII-Art

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Release history Release notifications | RSS feed

0.1.2

2 files

This release

0.1.1 This release

2 files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page