Skip to main content

A Python library for programmatic thumbnail generation

Project description

QuickThumb

A Python library for programmatic thumbnail generation with support for layers, gradients, and flexible styling.

Features

  • Dual API: Use Python method chaining or JSON configuration
  • Layer-based composition: Stack backgrounds, text, and decorations
  • Flexible sizing: Aspect ratios (16:9, 9:16, 4:3, 1:1, 1.91:1, 4:5) or explicit dimensions
  • Rich backgrounds: Solid colors, linear/radial gradients, images with blend modes
  • Advanced text styling: Custom fonts, strokes, alignment, bold/italic
  • Multiple output formats: PNG, JPEG, WebP
  • Type-safe: Full type hints with Pydantic validation

Installation

# Using uv (recommended)
uv pip install quickthumb

# Using pip
pip install quickthumb

Quick Start

Python API

from quickthumb import Canvas, LinearGradient, BlendMode, Stroke

# Create a 1920x1080 thumbnail
canvas = Canvas(1920, 1080)

# Add a gradient background
canvas.background(
    gradient=LinearGradient(45, [("#FF5733", 0.0), ("#3333FF", 1.0)]),
    opacity=0.8,
    blend_mode=BlendMode.MULTIPLY
)

# Add title text with stroke
canvas.text(
    "Python Tutorial",
    font="Roboto",
    size=72,
    color="#FFFFFF",
    align=("center", "middle"),
    effects=[Stroke(width=3, color="#000000")],
    bold=True
)

# Add an outline
canvas.outline(width=10, color="#FFFFFF")

# Render to file
canvas.render("thumbnail.png")

Using Aspect Ratios

from quickthumb import Canvas

# Create 16:9 canvas with base width 1920
canvas = Canvas.from_aspect_ratio("16:9", base_width=1920)

# For YouTube thumbnails (16:9)
canvas = Canvas.from_aspect_ratio("16:9", base_width=1280)

# For Instagram posts (1:1)
canvas = Canvas.from_aspect_ratio("1:1", base_width=1080)

JSON Configuration

from quickthumb import Canvas

# Load from JSON string

config = """
{
    "size": {"width": 1920, "height": 1080},
    "layers": [
        {
            "type": "background",
            "color": "#2c3e50",
            "opacity": 1.0
        },
        {
            "type": "text",
            "content": "Hello World",
            "font": "Arial",
            "size": 72,
            "color": "#FFFFFF",
            "align": ["center", "middle"]
        },
        {
            "type": "outline",
            "width": 5,
            "color": "#ecf0f1",
        }
    ]
}
"""
canvas = Canvas.from_json(config)
canvas.render("output.png")

Advanced Examples

Multiple Background Layers with Blend Modes

from quickthumb import Canvas, LinearGradient, RadialGradient, BlendMode

canvas = Canvas(1920, 1080)

# Base solid color
canvas.background(color="#2c3e50")

# Gradient overlay
canvas.background(
    gradient=LinearGradient(135, [("#e74c3c", 0.0), ("#3498db", 1.0)]),
    opacity=0.6,
    blend_mode=BlendMode.OVERLAY
)

# Image texture
canvas.background(
    image="texture.png",
    opacity=0.3,
    blend_mode=BlendMode.MULTIPLY,
    fit="cover"
)

Text with Custom Positioning

canvas = Canvas(1920, 1080)

# Absolute positioning (pixels)
canvas.text("Top Left", position=(50, 50), color="#FFFFFF")

# Percentage positioning
canvas.text("Centered", position=("50%", "50%"), color="#FFFFFF")

# Alignment-based positioning
canvas.text(
    "Bottom Right",
    align=("right", "bottom"),
    color="#FFFFFF"
)

Radial Gradients

from quickthumb import Canvas, RadialGradient

canvas = Canvas(1920, 1080)
canvas.background(
    gradient=RadialGradient(
        stops=[("#3498db", 0.0), ("#1a252f", 1.0)],
        center=(0.5, 0.5)  # Center position (0-1 range)
    )
)

Color Formats

QuickThumb supports multiple color formats:

# Hex strings
canvas.background(color="#FF5733")
canvas.background(color="#FF5733AA")  # With alpha

# RGB tuples
canvas.background(color=(255, 87, 51))

# RGBA tuples
canvas.background(color=(255, 87, 51, 200))

Text Effects

Add visual effects to text using effect classes:

from quickthumb import Canvas, Stroke

canvas = Canvas(1920, 1080)

# Text with stroke outline
canvas.text(
    "Bold Title",
    size=96,
    color="#FFFFFF",
    align=("center", "middle"),
    effects=[Stroke(width=3, color="#000000")]
)

# Multiple effects
canvas.text(
    "Epic Title",
    size=96,
    color="#FFFFFF",
    effects=[
        Stroke(width=5, color="#000000"),
        Stroke(width=2, color="#FF0000"),
    ]
)

Available Effects:

  • Stroke(width, color) - Adds an outline around text

Development

Setup

# Clone the repository
git clone https://github.com/sjquant/quickthumb.git
cd quickthumb

# Install dependencies with uv
uv sync

Running Tests

# Run all tests
uv run pytest tests/ -v

# Run with coverage
uv run pytest tests/ --cov=quickthumb --cov-report=html

# Type checking with ty
uv run ty quickthumb/

# Linting
uv run ruff check quickthumb/

API Design

For detailed API design, see DESIGN.md.

Canvas Methods

  • Canvas(width, height) - Create canvas with explicit dimensions
  • Canvas.from_aspect_ratio(ratio, base_width) - Create from aspect ratio
  • Canvas.from_json(source) - Load from JSON string
  • .background(color=..., gradient=..., image=..., opacity=..., blend_mode=...) - Add background layer
  • .text(content, font=..., size=..., color=..., align=..., effects=..., bold=..., italic=...) - Add text layer
  • .outline(width, color, offset=...) - Add outline decoration
  • .render(output_path, format=..., quality=...) - Render to file
  • .to_json() - Serialize to json string

Blend Modes

  • BlendMode.NORMAL - Default blending
  • BlendMode.MULTIPLY - Multiply colors
  • BlendMode.OVERLAY - Overlay effect
  • BlendMode.SCREEN - Screen effect
  • BlendMode.DARKEN - Darken
  • BlendMode.LIGHTEN - Lighten

License

MIT License - see LICENSE for details.

Contributing

Contributions are welcome! Please feel free to submit a Pull Request.

Project details


Download files

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

Source Distribution

quickthumb-0.1.1.tar.gz (4.3 MB view details)

Uploaded Source

Built Distribution

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

quickthumb-0.1.1-py3-none-any.whl (16.5 kB view details)

Uploaded Python 3

File details

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

File metadata

  • Download URL: quickthumb-0.1.1.tar.gz
  • Upload date:
  • Size: 4.3 MB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: uv/0.9.27 {"installer":{"name":"uv","version":"0.9.27","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

File hashes

Hashes for quickthumb-0.1.1.tar.gz
Algorithm Hash digest
SHA256 4dbd91f930cc474cc4b242c6666eb735c5eee7b1ba25393e3f42fbe18dd9969f
MD5 022771ea4ced96575afccf3a610f8371
BLAKE2b-256 b57c0743d0171b749a398b1655a8a3c8974de476c4c304e9a34180c547896819

See more details on using hashes here.

File details

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

File metadata

  • Download URL: quickthumb-0.1.1-py3-none-any.whl
  • Upload date:
  • Size: 16.5 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: uv/0.9.27 {"installer":{"name":"uv","version":"0.9.27","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

File hashes

Hashes for quickthumb-0.1.1-py3-none-any.whl
Algorithm Hash digest
SHA256 27a9a46d2eef8790e0acab7878e289228fae318af5c7b7a723f72631901adcb6
MD5 1efd063a05933e1fb79a613c43c623bf
BLAKE2b-256 526576a4e2891e76072ed894101faffac52a7265d47763f69bde7af74624253a

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page