I Built a Web UI for Chafa So You Don’t Have to Touch the Terminal (Unless You Want To)
A few months ago, I came across Chafa — a command-line tool that turns images into ANSI/ASCII art. If you’ve never tried it, it’s kind of brilliant. You point it at a PNG or JPEG, and it spits out a wall of colored text that looks eerily close to the original image — all using braille, Unicode blocks, or ASCII characters.
Naturally, I did what any curious dev would do:
I fed it a few pictures, sat back, and watched my terminal become an art gallery.
But then I had a thought:
What if you didn’t have to install anything? What if you could just drop an image into your browser and get the same result — instantly?
That’s how this started.
Introducing: Chafa Frontend
This is a minimal web app that wraps the Chafa CLI in a Flask server and adds a browser-based UI on top.
No terminal. No CLI flags. Just upload → configure → render.
I didn’t write the magic — Chafa does all the heavy lifting in the project. Ironally, most of the code in this repo is for getting material design working, or even just validation. All-in-all, this project just tries to make Chafa more accessible.
Why Build a Web UI for a CLI Tool?
Honestly? Because I wanted to use Chafa on a phone.
And I wanted to share ASCII with my friends who have never opened a terminal in their lives.
Also: I think good CLI tools deserve good UIs. Not because the CLI is lacking, but because a tool can be powerful and approachable at the same time.
How It Works
The frontend is a simple single-page app using Material Design 3 components — just enough UI to pick a file, select some Chafa options, and display the result. No frameworks, no build steps — just HTML/CSS/JS.
The backend is a lightweight Flask server. When you upload an image, here’s what happens:
- The image and selected options are sent to the backend.
- The backend validates the inputs, saves the image temporarily.
- It invokes
chafa
with the requested options. - The ANSI output is returned to the frontend and rendered in the browser using
ansi_up
.
Why Material Design 3?
No big reason — I just liked the idea of giving a CLI tool a polished, mobile-friendly interface. Material Web Components made it easy to prototype quickly and still look decent across devices. Mainly, I wanted to play around with some of the latest standards for material design - as most of my current projects have been using Material Design 2 components of some kind.
Lessons Learned
- Building for “non-technical users” forces you to think carefully about defaults and feedback.
- Even tools designed for terminals can benefit from a little UX thinking.
- Chafa is extremely fast. I never had to optimize anything — it just works.
- Material Design 3 (at least when working purely in DOM), feels like it has a long way to go. I read through the documentation looking for formatting, and was puzzled when the components wouldn't style properly. Once I read through the source code there were frequent mismatches which was a shame.
Final Thoughts
This isn’t a reinvention of image-to-ASCII conversion — that credit goes entirely to Chafa and Hans Petter Jansson. This is just a small wrapper to make it more usable in a browser context.
If you’re into terminal aesthetics, retro graphics, or building useful frontends around powerful backends — check it out! If you have any suggestions or extensions, feel free to let me know or fork it 🙂
Top comments (0)