github.com/trans/piebox
main / published Mar 4, 2026 / repository
Easy as pie photoalbum layouts
PieBox
A Crystal tool for creating picture books and comic books from tagged images. Given a YAML manifest of images with significance levels and modifiers, PieBox arranges them into page layouts on a 2x3 grid and renders to PDF.
How It Works
- You write a YAML manifest describing your images, their significance (
climax,epic,normal), and optional modifiers (vista,action) - The packer groups images into pages, choosing from 20 predefined grid layouts that best fit the image mix
- The renderer outputs a PDF with images placed in cells, scaled to fit (letterboxed), with optional captions and AI-generated dialogue
Significance Levels
- climax — Full page (cover, centerfold, finale)
- epic — Large cell: 1/2, 1/3, or 1/4 of page
- normal — Standard cell: 1/6 of page, can expand to 1/3 to fill gaps
Modifiers
- vista — Prefers landscape (wider-than-tall) cells
- action — Applies a visual effect preset:
split3— Crops image into 3 horizontal paneszoom_in— Progressive zoom sequence (3 panes)motion_lines— Overlay speed lines on the image
Book Types
- comic — Left-to-right, top-to-bottom reading flow; only uses flow-compatible layouts
- picture_book — No flow constraint; uses all available layouts
AI Text Generation (Optional)
PieBox can generate dialogue or narration for comic pages using either:
- Ollama — Local model (e.g. llama3)
- Anthropic — Claude Haiku API
Provide image descriptions in the manifest and PieBox generates short, punchy text for speech bubbles.
Requirements
- Crystal >= 1.19.1
libcairo2-dev(system package for PDF rendering)
Installation
shards install
crystal build src/piebox_cli.cr -o bin/piebox
Usage
Create a manifest
# piebox.yml
book_type: comic
title: "My Comic"
page_width: 210 # mm (A4 default)
page_height: 297
margin: 10
gutter: 5
# Optional AI config
ai:
backend: ollama
model: llama3
images:
- path: img/cover.png
significance: climax
caption: "The adventure begins"
- path: img/fight.png
significance: normal
modifiers: [action]
action_style: split3
description: "Hero punches villain"
- path: img/landscape.png
significance: epic
modifiers: [vista]
- path: img/panel1.png
significance: normal
- path: img/panel2.png
significance: normal
- path: img/finale.png
significance: climax
caption: "The end"
Run
# Basic usage
piebox piebox.yml -o mycomic.pdf
# Skip AI text generation
piebox piebox.yml -o mycomic.pdf --no-ai
# Help
piebox --help
Library Usage
require "piebox"
manifest = Piebox::Manifest.from_yaml(File.read("piebox.yml"))
images = manifest.to_image_tags
packer = Piebox::Packer.new(manifest.parsed_book_type)
pages = packer.pack(images)
renderer = Piebox::Renderer.new(manifest)
renderer.render(pages, "output.pdf")
Development
# Run specs
crystal spec
# Build
crystal build src/piebox_cli.cr
Current Limitations (v0.1)
- PNG images only
- Fixed 2x3 grid (6 units per page)
- No custom fonts or text styling
- Speech bubbles use basic positioning (upper-right of cell)
- AI backends require external setup (running Ollama instance or Anthropic API key)
License
MIT