Skip to content

Latest commit

ย 

History

141 Commits

Folders and files

NameName
Last commit message
Last commit date
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 
ย 

Repository files navigation

NanoPNG

State-of-the-art image compression, right in your browser.

NanoPNG is a secure, privacy-focused image compressor that rivals server-side solutions like TinyPNG, but runs entirely on your device. No images are ever uploaded to a server.

License TypeScript Rust WebAssembly Next.js

๐Ÿš€ Vision

The goal of NanoPNG is to provide server-grade image optimization without the server. Modern browsers are powerful enough to handle complex image processing tasks like quantization, dithering, and format conversion. By leveraging Web Workers and WASM, we can deliver a tool that respects user privacy (zero data upload) while saving significant bandwidth.

โœจ Key Features

  • Privacy First: All processing happens locally. Your photos never leave your computer.
  • Rust/WASM Backend: High-performance image encoding powered by a custom Rust-based WebAssembly module (nanopng-core) for blazing fast compression.
  • Smart Compression: Automatically detects photo vs. graphic content and applies optimal compression strategies. Quick probe skips already-optimized images.
  • Batch Processing: Process up to 100 images simultaneously with parallel workers and O(1) priority queue scheduling. No limits, no subscriptions.
  • Intelligent Format Selection: Automatically chooses the best format (AVIF โ†’ WebP โ†’ PNG) based on browser support and image characteristics.
  • Format Conversion: Convert between PNG, JPEG, WebP, AVIF, and JPEG-XL formats with intelligent quality settings.
  • Wide Format Support: GIF, TIFF, and BMP input formats in addition to PNG, JPEG, WebP, AVIF, HEIC, and SVG.
  • Target Size Compression: Specify a target file size (e.g., "under 50KB") and the compressor will automatically adjust quality and dimensions.
  • Metadata Preservation: Automatically preserves critical metadata (EXIF orientation, ICC Color Profiles) often lost by standard canvas exports.
  • Image Analysis: Advanced photo vs. graphic detection using color histogram analysis, edge detection, and texture variance scoring.
  • Image Editing: Built-in blur, sharpen, crop, rotate/flip, and auto-trim operationsโ€”all processed locally.
  • Watermark/Overlay Support: Add watermarks or overlays to images before compression.
  • Fit Modes: Cover, contain, fill, inside, and outside modes for precise dimension control.
  • HEIC Support: Convert HEIC/HEIF images (common on iOS) to web-friendly formats.
  • SVG Optimization: Optimize SVG files with Safe (lossless) or Aggressive (smaller) modes using SVGO.
  • JPEG-XL Output: Experimental JPEG-XL encoding support (Safari 17+).
  • Progressive JPEG: MozJPEG-powered progressive JPEG encoding for optimized loading.
  • Near-Lossless WebP: Near-lossless WebP mode for maximum quality with smaller file sizes.
  • AVIF 10-bit Depth: Support for 10-bit AVIF encoding for HDR-quality images.
  • Before/After Comparison: Interactive slider to compare original and compressed images side-by-side.
  • Bulk Download: Download all optimized images as a ZIP archive.
  • Performance: Offloads heavy computational work to Web Workers with crash recovery, ensuring a smooth, non-blocking UI even with 4K+ images.
  • Brutalist UI: Clean, bold interface with dark mode support.

๐Ÿ›  Technical Architecture

NanoPNG is built with Next.js 14+, TypeScript, and Rust/WebAssembly, designed for performance and extensibility.

Core Technologies

  • Frontend: React-based UI with Drag & Drop zones (Shadcn UI + Tailwind CSS).
  • WASM Core: nanopng-core - Custom Rust-based WebAssembly module providing high-performance codecs:
    • PNG encoding with lossy quantization (imagequant) and lossless compression
    • JPEG encoding with quality optimization
    • AVIF encoding via ravif crate
    • WebP encoding via webp crate
  • Worker Pool: Parallel processing with O(1) priority queue scheduling, crash recovery, and queue size limits.
  • Smart Compression: Orchestration layer with quick probe to skip already-optimized images and auto-detection of photo vs. graphic content.
  • Supporting Libraries:
    • exifr: EXIF metadata extraction
    • heic2any: HEIC/HEIF format conversion
    • comlink: Worker communication

Processing Pipeline

  1. Quick Probe: Estimates compressibility at reduced resolution. Skips already-optimized images (< 3% savings).
  2. Image Analysis: Classifies as Photo, Graphic, or Mixed using:
    • Unique color count with logarithmic scaling
    • Solid region ratio detection
    • Edge sharpness analysis
    • Transparency detection
  3. Format Detection & Decoding: Supports PNG, JPEG, WebP, AVIF, HEIC/HEIF, and SVG. Converts HEIC to decodable format if needed.
  4. Compression:
    • PNG: Lossy (imagequant palette reduction) or lossless with optimal filtering (Rust/WASM)
    • JPEG: Quality-optimized encoding with dimension validation (Rust/WASM)
    • WebP/AVIF: Modern format encoding with quality tuning (Rust/WASM)
    • SVG: Safe or Aggressive optimization via SVGO (JavaScript Worker)
  5. Target Size Loop: Binary search quality adjustment with resize fallback for target size constraints.
  6. Metadata Injection: Extracts EXIF/ICC chunks from source and injects them into the optimized Blob.
  7. Size Validation: Ensures compressed output is smaller than original; reverts if not.

Format Selection Strategy

  • Photos: Prefers AVIF (if supported) โ†’ WebP โ†’ JPEG with perceptual quality settings
  • Graphics: Prefers AVIF (if supported) โ†’ WebP โ†’ Quantized PNG with palette optimization
  • Transparency: Automatically selects PNG format when alpha channel detected

๐Ÿ Roadmap & Next Steps

We are actively working on pushing the boundaries of in-browser compression.

Completed โœ…

  • Rust/WASM Backend: Full integration of nanopng-core for PNG, JPEG, WebP, and AVIF encoding.
  • Smart Compression: Auto-detection of photo vs. graphic content with optimized compression strategies.
  • Target Size Compression: Binary search quality adjustment with resize fallback.
  • Worker Pool Improvements: O(1) priority queue, crash recovery, and queue size limits.
  • SVG Optimization: Safe and Aggressive modes using SVGO with Web Worker processing.
  • GIF, TIFF, BMP Support: Input format support for legacy image formats.
  • JPEG-XL Output: Experimental JPEG-XL encoding (browser support varies).
  • Image Editing: Blur, sharpen, crop, rotate/flip, and auto-trim operations.
  • Watermark/Overlay: Add watermarks or overlays to images.
  • Near-Lossless WebP: Near-lossless mode for maximum quality WebP output.
  • Fit Modes: Cover, contain, fill, inside, and outside dimension modes.
  • AVIF 10-bit Depth: HDR-quality AVIF encoding with 10-bit color depth.
  • Progressive JPEG: MozJPEG-powered progressive JPEG encoding.

In Progress ๐Ÿšง

  • PWA Support: Full offline capabilities with service worker caching.

Future ๐Ÿ”ฎ

  • CLI Tool: Command-line interface for batch processing.
  • Image Optimization API: Programmatic API for developers to integrate compression into their workflows.
  • Video Frame Extraction: Extract and optimize frames from video files.

๐Ÿš€ Getting Started

Prerequisites

  • Node.js 18+ and npm
  • Rust toolchain (for building WASM module)
  • wasm-pack (cargo install wasm-pack)

Installation

# Clone the repository
git clone https://github.com/nawwwal/nanopng.git
cd nanopng

# Install dependencies
npm install

# Build the Rust/WASM module
npm run wasm:build

# Run development server
npm run dev

Open http://localhost:3000 in your browser.

Building for Production

# Build WASM and Next.js app
npm run wasm:build
npm run build
npm start

Development Commands

Command Description
npm run dev Start development server
npm run build Build for production
npm run wasm:build Build Rust/WASM module
npm run wasm:dev Build WASM in dev mode
npm test Run test suite (33 tests)
npm run lint Run ESLint

๐Ÿค Contribution Guidelines

We welcome contributions! Here's how to get started:

  1. Fork the repository.
  2. Clone your fork locally.
  3. Branch for your feature: git checkout -b feature/amazing-feature.
  4. Install dependencies: npm install
  5. Run development server: npm run dev
  6. Make your changes following our code standards.
  7. Test thoroughly with various image formats and sizes.
  8. Commit your changes with clear messages.
  9. Push to your fork and open a Pull Request.

Code Standards

  • Use TypeScript for strict type safety (no any, no @ts-ignore).
  • Use Rust for performance-critical encoding in crate/.
  • Ensure Linting passes (npm run lint).
  • Ensure Tests pass (npm test - 33 tests).
  • Keep heavy computational logic inside lib/workers or crate/.
  • Follow the existing architecture patterns:
    • Rust codecs in crate/src/codecs/
    • Services in lib/services/
    • Core algorithms in lib/core/
    • UI components in components/
    • Types in lib/types/

Project Structure

nanopng/
โ”œโ”€โ”€ app/                    # Next.js app directory
โ”œโ”€โ”€ components/             # React components
โ”‚   โ”œโ”€โ”€ ui/                # Shadcn UI components
โ”‚   โ””โ”€โ”€ editor/            # Image editor components
โ”œโ”€โ”€ crate/                  # Rust/WASM source code
โ”‚   โ”œโ”€โ”€ src/
โ”‚   โ”‚   โ”œโ”€โ”€ lib.rs         # WASM entry point
โ”‚   โ”‚   โ”œโ”€โ”€ filters.rs     # Blur, sharpen, and image filters
โ”‚   โ”‚   โ”œโ”€โ”€ transform.rs   # Crop, rotate, flip, auto-trim
โ”‚   โ”‚   โ””โ”€โ”€ codecs/        # PNG, JPEG, WebP, AVIF, GIF, TIFF, BMP encoders
โ”‚   โ””โ”€โ”€ Cargo.toml         # Rust dependencies
โ”œโ”€โ”€ lib/
โ”‚   โ”œโ”€โ”€ core/              # Core algorithms (image analysis, format detection)
โ”‚   โ”œโ”€โ”€ services/          # Business logic (compression orchestrator, image service)
โ”‚   โ”œโ”€โ”€ types/             # TypeScript type definitions
โ”‚   โ”œโ”€โ”€ hooks/             # React hooks (useWorkerPool)
โ”‚   โ”œโ”€โ”€ wasm/              # Compiled WASM modules (generated)
โ”‚   โ””โ”€โ”€ workers/           # Web Worker scripts (processor, pool)
โ”œโ”€โ”€ scripts/               # Build scripts (prepare-wasm.mjs)
โ””โ”€โ”€ public/                # Static assets

๐ŸŒ Browser Compatibility

NanoPNG works in all modern browsers that support:

  • Web Workers (for background processing)
  • Canvas API (for image encoding)
  • File API (for drag & drop)
  • WebAssembly (for Rust core features)

Format Support by Browser

Format Chrome/Edge Firefox Safari Notes
PNG โœ… โœ… โœ… Full support
JPEG โœ… โœ… โœ… Progressive via MozJPEG
WebP โœ… โœ… โœ… Safari 14+
AVIF โœ… โœ… โš ๏ธ Safari 17+ (encoding)
GIF โœ… โœ… โœ… Input only (static)
TIFF โœ… โœ… โœ… Input only
BMP โœ… โœ… โœ… Input only
HEIC โœ… โœ… โœ… Via heic2any
SVG โœ… โœ… โœ… Via SVGO
JXL โš ๏ธ โš ๏ธ โš ๏ธ Experimental

Note: AVIF encoding requires browser support. The app automatically falls back to WebP if AVIF encoding is not available. JPEG-XL (JXL) is experimental and browser support is limited.

๐Ÿ“„ License

MIT License - feel free to use this project for personal or commercial purposes.

About

Resources

Stars

0 stars

Watchers

0 watching

Forks

Contributors

Languages