Architecture Overview

A high-level guide to the OpenGPEX engine architecture, its module structure, data flow, and the key design decisions that differentiate it from traditional web editors.


System Architecture Diagram

┌──────────────────────────────────────────────────────────────────────┐
│                         OpenGPEX Editor                                │
├──────────────────────────────────────────────────────────────────────┤
│                                                                       │
│  ┌─────────────┐   ┌──────────────┐   ┌───────────────────────────┐ │
│  │  Workspace   │   │    Stage     │   │        Plugins            │ │
│  │  (Layout)    │   │  (Viewport)  │   │  (Drawers, Overlays,     │ │
│  │              │   │              │   │   Options, Panels,        │ │
│  │  Slot Mgr    │   │  Camera      │   │   Backstage services)     │ │
│  │  Plugin Mgr  │   │  Interaction │   │                           │ │
│  └──────┬───────┘   └──────┬───────┘   └────────────┬──────────────┘ │
│         │                  │                         │                │
│         └──────────────────┼─────────────────────────┘                │
│                            │                                          │
│                   ┌────────▼────────┐                                 │
│                   │      Core       │                                 │
│                   ├─────────────────┤                                 │
│                   │  State (Store)  │  ← Normalized, Immer-powered   │
│                   │  Engine         │  ← Canvas2D + Worker backends   │
│                   │  Plugin Registry│  ← Dual-track (static/dynamic) │
│                   │  Geometry       │  ← Matrix math, spatial service │
│                   │  Storage        │  ← CAS (SHA-256), IndexedDB    │
│                   │  Types          │  ← Full TypeScript contracts    │
│                   └─────────────────┘                                 │
│                                                                       │
└──────────────────────────────────────────────────────────────────────┘

Module Dependency Graph

Dependencies flow inward — outer layers depend on inner layers, never the reverse.

Plugins  →  Workspace  →  Stage  →  Core
   │                                  ▲
   └──────────────────────────────────┘
              (via context hooks)
Layer Responsibility May Import
Core Engine, state, types, geometry, storage Nothing (leaf layer)
Stage Viewport rendering, interaction dispatch Core
Workspace Layout shell, slot management, plugin init Core, Stage
Plugins Business features (tools, panels, overlays) Core (via hooks), Widgets
Widgets Reusable UI components Nothing editor-specific

Data Flow: From User Action to Pixels

User Gesture (mouse/touch)
    │
    ▼
Interaction Dispatcher (stage/interaction/)
    │
    ├─── 60fps path ──► Fast Track (volatile ref, no React re-render)
    │                         │
    │                         ▼
    │                    Stage repaints immediately (requestAnimationFrame)
    │
    └─── Commit path ──► Command / Action
                              │
                              ▼
                         Reducer (Immer produce)
                              │
                              ├──► Undo Patch recorded
                              │
                              ▼
                         React re-render (selective via selectors)
                              │
                              ▼
                         Engine repaints canvas

Key Design Decisions

1. Dual-Track State (Fast Track + Persistent)

Traditional React editors suffer from 16ms+ re-render latency during drag operations. OpenGPEX solves this with a volatile mutable reference that bypasses React entirely during interactions, then commits once on pointer-up.

2. Normalized State with Immer

All entities (frames, layers) use a { byId, order } dictionary pattern for O(1) lookups. Combined with Immer's structural sharing, this yields minimal undo patches and zero unnecessary re-renders.

3. Content-Addressable Storage (CAS)

Every image asset is stored by its SHA-256 hash. Duplicate images share a single blob. Layer operations create metadata-only derivatives, preserving original pixels immutably.

4. Isomorphic Rendering Pipeline

A single atomic painter function (drawLayerInstance) is shared between the main-thread Canvas2D engine and the Web Worker compositor. This eliminates coordinate drift between preview and export.

5. Plugin-First Architecture

The editor ships zero hardcoded UI. Every panel, tool, and overlay — including crop, layers, undo — is a plugin registered through the same metadata contract as user-authored plugins.


Core Subsystems

Subsystem Description Deep-Dive
State Management Normalized store with Immer + Zustand patterns State Management
Actions & Commands 4-layer dispatch (Atomic → Fast → Facade → Bus) Actions & Commands
Fast Track Volatile overlay for 60fps interaction Fast Track
Rendering Tiled chunks, mipmaps, Worker synthesis Rendering Pipeline
Spatial Screen/World/Local coordinate transforms Spatial Service
Undo/Redo Incremental JSON Patches with viewport stability Undo/Redo
Interactions Unified gesture dispatcher & transactions Interaction System
Engine PixelService facade, Worker proxy, backends Engine & Workers
Cloud GPEX-Cloud integration protocol Cloud Integration
Plugins Metadata-driven registry with dual-track loading Plugin Overview

Comparison with Traditional Editors

Aspect Traditional Web Editor OpenGPEX
Large images OOM crash at ~8K Tiled rendering handles 16K+
Drag performance Jank (full React cycle) 60fps (Fast Track bypass)
Undo memory Full-state snapshots (MB each) JSON Patches (bytes each)
Extensibility Monolithic codebase Plugin slots with IoC registry
Pixel integrity Destructive edits CAS-backed non-destructive
Export fidelity Preview ≠ export Isomorphic single painter

Next Steps


Last updated: 2026-06-14