From 9e3b790929c144b40e69ac9cb42fa4fb2082304d Mon Sep 17 00:00:00 2001 From: Taylor Holliday Date: Fri, 5 Sep 2025 08:34:35 -0700 Subject: [PATCH 1/3] Create CLAUDE.md --- CLAUDE.md | 84 +++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 84 insertions(+) create mode 100644 CLAUDE.md diff --git a/CLAUDE.md b/CLAUDE.md new file mode 100644 index 000000000..fbd06d65b --- /dev/null +++ b/CLAUDE.md @@ -0,0 +1,84 @@ +# CLAUDE.md + +This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository. + +## Project Overview + +Rasterizer is a GPU-accelerated 2D vector graphics engine for macOS, written in C++11 and Metal. It's designed to be up to 60x faster than CPU rendering, ideal for vector animated UI. The engine supports SVG and PDF rendering with reference-quality anti-aliasing. + +## Build Commands + +The project uses Xcode for building: + +```bash +# Build and run the demo app (preferred for performance) +xcodebuild -project Rasterizer.xcodeproj -scheme "Run Rasterizer" -configuration Release build + +# Build debug version +xcodebuild -project Rasterizer.xcodeproj -scheme "Debug Rasterizer" build + +# Open in Xcode +open Rasterizer.xcodeproj +``` + +The Xcode project builds out of the box with all dependencies included. For best performance, use the "Run Rasterizer" scheme. + +## Architecture + +### Core Components + +- **Rasterizer Engine (`src/`)**: Core C++ rendering engine with Metal GPU acceleration + - `Rasterizer.hpp`: Main API interface with Path, Scene, and SceneList classes + - `Rasterizer.h`: Configuration constants and definitions + - `Shaders.metal`: GPU shaders for rendering pipeline + +- **Platform Layer (`Apple/`)**: macOS-specific integration + - `RasterizerLayer.*`: CAMetalLayer subclass for Metal rendering + - `RasterizerView.*`: NSView wrapper for user interaction + - `RasterizerCG.hpp`: Core Graphics integration utilities + - `RasterizerRenderer.hpp`: Platform-specific rendering logic + +- **Demo Application (`Demo/`)**: Reference implementation and testing + - `DemoView.*`: Main demo interface with file loading and interaction + - `Document.*`: Document-based app architecture + - `RasterizerDemo.hpp`: Demo-specific rendering logic + - `Concentrichron.hpp`: Performance animation demo + +- **Format Support (`src/`)**: File format parsers + - `RasterizerSVG.hpp`: SVG path parsing using NanoSVG + - `RasterizerPDF.hpp`: PDF rendering using PDFium + - `RasterizerFont.hpp`: Font rendering using STB TrueType + - `RasterizerWinding.hpp`: Path winding rule algorithms + +### Rendering Pipeline + +The engine follows a two-stage rendering approach: +1. **Filled paths**: Rasterized to float mask buffer, then to color buffer +2. **Stroked paths**: Rasterized directly to color buffer with GPU triangulation + +Small fills use direct geometry copying, while large fills use a "fat scanlines" algorithm on device-space geometry. The GPU holds no persistent state - frames are written to double-buffered shared memory. + +### External Dependencies + +All dependencies are included in `lib/`: +- **PDFium**: PDF parsing and rendering (`lib/pdfium/`) +- **NanoSVG**: SVG parsing (`lib/nanosvg.*`) +- **STB TrueType**: Font rendering (`lib/stb_truetype.*`) +- **XXHash**: Fast hashing (`lib/xxhash.*`) + +## Demo App Controls + +- **File Operations**: Open SVG/PDF files via menu or drag-and-drop +- **PDF Navigation**: `-`/`+` keys to change pages +- **Canvas Control**: Trackpad/mouse drag to pan, pinch/scroll to zoom/rotate +- **Precision Control**: Hold `Shift` to zoom/rotate around pointer instead of center +- **Typography**: `Cmd+T` to open font panel +- **Performance Demo**: `T` key to toggle vector animation demo + +## Development Notes + +- The codebase uses C++11 features and Objective-C++ for macOS integration +- Metal shaders require Xcode's shader compiler +- Performance is optimized for macOS with batch parallelism on CPU stages +- The rendering algorithm uses novel "windowed-inverse-lerp" for pixel coverage calculation +- License is personal-use only (commercial license required separately) \ No newline at end of file From 9f6fe1bcb870620b4d2799ac831b50eeb47b2d00 Mon Sep 17 00:00:00 2001 From: Taylor Holliday Date: Fri, 5 Sep 2025 08:41:58 -0700 Subject: [PATCH 2/3] add doc comments --- Rasterizer/src/Shaders.metal | 45 ++++++++++++++++++++++++++++++++++++ 1 file changed, 45 insertions(+) diff --git a/Rasterizer/src/Shaders.metal b/Rasterizer/src/Shaders.metal index 89207310a..9bea78195 100644 --- a/Rasterizer/src/Shaders.metal +++ b/Rasterizer/src/Shaders.metal @@ -76,6 +76,9 @@ struct Edge { // https://www.shadertoy.com/view/4dsfRS +// Squared distance to a quadratic Bézier curve using Cardano's formula +// Algorithm: Solves the cubic equation to find the closest point on the curve +// Uses numerical stabilization for degenerate cases near inflection points float sqBezier(float2 p0, float2 p1, float2 p2) { // Calculate roots. float2 vb = p1 - p0, va, vc = { p0.y - p2.y, p2.x - p0.x }, rp1; @@ -106,6 +109,9 @@ float sqBezier(float2 p0, float2 p1, float2 p2) { return min(dot(pt0, pt0), dot(pt1, pt1)); } +// Distance-based winding contribution calculation +// Algorithm: Computes anti-aliased coverage using distance from line to pixel center +// Uses normalized distance to line segment with coverage scaling by window height float dwinding(float x0, float y0, float x1, float y1, float w0, float w1) { float cover, s, wm, dx, ax, dy, ay, dist; cover = w1 - w0, s = 1.0 / cover, wm = 0.5 * (w0 + w1); @@ -167,6 +173,9 @@ struct OpaquesVertex float4 color; }; +// Vertex shader for rendering solid filled shapes without anti-aliasing +// Algorithm: Simple quad rendering with depth sorting for overlapping paths +// Transforms instance cells to screen space and assigns colors by path index vertex OpaquesVertex opaques_vertex_main(const device Colorant *colors [[buffer(0)]], const device Instance *instances [[buffer(1)]], constant float *width [[buffer(10)]], constant float *height [[buffer(11)]], @@ -187,6 +196,8 @@ vertex OpaquesVertex opaques_vertex_main(const device Colorant *colors [[buffer( return vert; } +// Fragment shader for opaque shape rendering +// Algorithm: Direct color output without blending or anti-aliasing fragment float4 opaques_fragment_main(OpaquesVertex vert [[stage_in]]) { return vert.color; @@ -200,6 +211,10 @@ struct FastMoleculesVertex float x0, y0, x1, y1, x2, y2, x3, y3, x4, y4; }; +// Vertex shader for fast linear segment molecules (small path segments) +// Algorithm: Transforms up to 4 line segments from path space to screen space +// Optimizes small fills by batch-processing multiple segments per instance +// Computes tight bounding boxes and applies coordinate transformations vertex FastMoleculesVertex fast_molecules_vertex_main(const device Edge *edges [[buffer(1)]], const device Segment *segments [[buffer(2)]], const device Transform *ctms [[buffer(4)]], @@ -251,6 +266,9 @@ vertex FastMoleculesVertex fast_molecules_vertex_main(const device Edge *edges [ return vert; } +// Fragment shader for fast molecule anti-aliasing +// Algorithm: Sums winding contributions from up to 4 linear segments +// Uses the lineWinding function for sub-pixel accurate coverage calculation fragment float4 fast_molecules_fragment_main(FastMoleculesVertex vert [[stage_in]]) { return lineWinding(vert.x0, vert.y0, vert.x1, vert.y1) @@ -269,6 +287,10 @@ struct QuadMoleculesVertex bool isCurve; }; +// Vertex shader for quadratic curve molecules +// Algorithm: Processes single quadratic Bézier curve or linear segment +// Converts curve control points to proper quadratic form with midpoint adjustment +// Transforms from compressed 16-bit coordinates to screen space vertex QuadMoleculesVertex quad_molecules_vertex_main(const device Edge *edges [[buffer(1)]], const device Segment *segments [[buffer(2)]], const device Transform *ctms [[buffer(4)]], @@ -323,6 +345,9 @@ vertex QuadMoleculesVertex quad_molecules_vertex_main(const device Edge *edges [ return vert; } +// Fragment shader for quadratic curve anti-aliasing +// Algorithm: Computes exact winding contribution for quadratic Bézier curves +// Uses analytical quadratic winding calculation for sub-pixel accuracy fragment float4 quad_molecules_fragment_main(QuadMoleculesVertex vert [[stage_in]]) { return quadraticWinding(vert.x0, vert.y0, vert.x1, vert.y1, vert.x2, vert.y2); @@ -337,6 +362,10 @@ struct EdgesVertex uint32_t idx0, idx1; }; +// Vertex shader for edge-based rendering (fat scanlines algorithm) +// Algorithm: Processes pairs of path segments that span cell boundaries +// Computes optimal bounding rectangles for segments, handling both linear and quadratic curves +// Used for larger fills where molecule approach becomes inefficient vertex EdgesVertex edges_vertex_main(const device Edge *edges [[buffer(1)]], const device Segment *segments [[buffer(2)]], const device Transform *ctms [[buffer(4)]], @@ -396,6 +425,9 @@ vertex EdgesVertex edges_vertex_main(const device Edge *edges [[buffer(1)]], return vert; } +// Fragment shader for fast edge rendering (linear segments only) +// Algorithm: Processes up to 2 line segments per pixel for scanline rendering +// Part of the fat scanlines algorithm for efficient large area filling fragment float4 fast_edges_fragment_main( EdgesVertex vert [[stage_in]], const device Segment *segments [[buffer(2)]], @@ -419,6 +451,9 @@ fragment float4 fast_edges_fragment_main( return winding; } +// Fragment shader for quadratic edge rendering +// Algorithm: Handles both linear and quadratic segments in scanline rendering +// Uses appropriate winding calculation based on segment type fragment float4 quad_edges_fragment_main( EdgesVertex vert [[stage_in]], const device Segment *segments [[buffer(2)]], @@ -450,6 +485,11 @@ struct InstancesVertex uint32_t iz, iid; }; +// Main vertex shader for path instance rendering +// Algorithm: Handles both filled shapes and stroked outlines with complex geometry +// For strokes: Computes miter joints, end caps, and curve thickness compensation +// For fills: Transforms cell quads and prepares for mask buffer sampling +// Implements sophisticated stroke geometry with proper joins and caps vertex InstancesVertex instances_vertex_main( const device Instance *instances [[buffer(1)]], const device Transform *ctms [[buffer(4)]], @@ -551,6 +591,11 @@ vertex InstancesVertex instances_vertex_main( return vert; } +// Main fragment shader for final path rendering +// Algorithm: Combines stroke and fill rendering with clipping and blending +// For strokes: Uses distance fields and caps for anti-aliased edges +// For fills: Samples mask buffer and applies even-odd or non-zero winding rules +// Implements analytical clipping with sub-pixel accuracy fragment float4 instances_fragment_main(InstancesVertex vert [[stage_in]], const device Colorant *colors [[buffer(0)]], const device Instance *instances [[buffer(1)]], From 2a453a9265b6f44983178278e84fa75bdfce7d89 Mon Sep 17 00:00:00 2001 From: Taylor Holliday Date: Sat, 6 Sep 2025 10:08:17 -0700 Subject: [PATCH 3/3] Revert "Create CLAUDE.md" This reverts commit 9e3b790929c144b40e69ac9cb42fa4fb2082304d. --- CLAUDE.md | 84 ------------------------------------------------------- 1 file changed, 84 deletions(-) delete mode 100644 CLAUDE.md diff --git a/CLAUDE.md b/CLAUDE.md deleted file mode 100644 index fbd06d65b..000000000 --- a/CLAUDE.md +++ /dev/null @@ -1,84 +0,0 @@ -# CLAUDE.md - -This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository. - -## Project Overview - -Rasterizer is a GPU-accelerated 2D vector graphics engine for macOS, written in C++11 and Metal. It's designed to be up to 60x faster than CPU rendering, ideal for vector animated UI. The engine supports SVG and PDF rendering with reference-quality anti-aliasing. - -## Build Commands - -The project uses Xcode for building: - -```bash -# Build and run the demo app (preferred for performance) -xcodebuild -project Rasterizer.xcodeproj -scheme "Run Rasterizer" -configuration Release build - -# Build debug version -xcodebuild -project Rasterizer.xcodeproj -scheme "Debug Rasterizer" build - -# Open in Xcode -open Rasterizer.xcodeproj -``` - -The Xcode project builds out of the box with all dependencies included. For best performance, use the "Run Rasterizer" scheme. - -## Architecture - -### Core Components - -- **Rasterizer Engine (`src/`)**: Core C++ rendering engine with Metal GPU acceleration - - `Rasterizer.hpp`: Main API interface with Path, Scene, and SceneList classes - - `Rasterizer.h`: Configuration constants and definitions - - `Shaders.metal`: GPU shaders for rendering pipeline - -- **Platform Layer (`Apple/`)**: macOS-specific integration - - `RasterizerLayer.*`: CAMetalLayer subclass for Metal rendering - - `RasterizerView.*`: NSView wrapper for user interaction - - `RasterizerCG.hpp`: Core Graphics integration utilities - - `RasterizerRenderer.hpp`: Platform-specific rendering logic - -- **Demo Application (`Demo/`)**: Reference implementation and testing - - `DemoView.*`: Main demo interface with file loading and interaction - - `Document.*`: Document-based app architecture - - `RasterizerDemo.hpp`: Demo-specific rendering logic - - `Concentrichron.hpp`: Performance animation demo - -- **Format Support (`src/`)**: File format parsers - - `RasterizerSVG.hpp`: SVG path parsing using NanoSVG - - `RasterizerPDF.hpp`: PDF rendering using PDFium - - `RasterizerFont.hpp`: Font rendering using STB TrueType - - `RasterizerWinding.hpp`: Path winding rule algorithms - -### Rendering Pipeline - -The engine follows a two-stage rendering approach: -1. **Filled paths**: Rasterized to float mask buffer, then to color buffer -2. **Stroked paths**: Rasterized directly to color buffer with GPU triangulation - -Small fills use direct geometry copying, while large fills use a "fat scanlines" algorithm on device-space geometry. The GPU holds no persistent state - frames are written to double-buffered shared memory. - -### External Dependencies - -All dependencies are included in `lib/`: -- **PDFium**: PDF parsing and rendering (`lib/pdfium/`) -- **NanoSVG**: SVG parsing (`lib/nanosvg.*`) -- **STB TrueType**: Font rendering (`lib/stb_truetype.*`) -- **XXHash**: Fast hashing (`lib/xxhash.*`) - -## Demo App Controls - -- **File Operations**: Open SVG/PDF files via menu or drag-and-drop -- **PDF Navigation**: `-`/`+` keys to change pages -- **Canvas Control**: Trackpad/mouse drag to pan, pinch/scroll to zoom/rotate -- **Precision Control**: Hold `Shift` to zoom/rotate around pointer instead of center -- **Typography**: `Cmd+T` to open font panel -- **Performance Demo**: `T` key to toggle vector animation demo - -## Development Notes - -- The codebase uses C++11 features and Objective-C++ for macOS integration -- Metal shaders require Xcode's shader compiler -- Performance is optimized for macOS with batch parallelism on CPU stages -- The rendering algorithm uses novel "windowed-inverse-lerp" for pixel coverage calculation -- License is personal-use only (commercial license required separately) \ No newline at end of file