Files
prosperon/docs/rendering.md
John Alanbrook 83b798e365 Add Hugo website and rewrite docs to match current engine
New Hugo site in website/ with prosperon.dev theme (blue/gold/castle
aesthetic), docs sidebar navigation, and content pages. Rewrote all
doc files to align with the actual codebase: compositor+film2d
rendering, use() modules (no global prosperon object), Pit language,
script+JSON entity model. Added entities.md, front matter to all
70+ API docs, and updated API index for current module architecture.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-23 18:09:55 -06:00

4.0 KiB

title, type
title type
Rendering docs

Rendering

Prosperon's rendering is data-driven. You create sprites and other drawables, set their properties, and the engine handles drawing them. You never touch the GPU directly.

The Model

Think of it like programming sprites on a classic console:

  1. Create a sprite (or text, shape, tilemap, particle emitter)
  2. Set its position, image, layer, and visual properties
  3. The engine draws everything each frame, sorted and batched automatically
var sprite = use('sprite')

var player = sprite({
  image: "player.png",
  pos: {x: 100, y: 200},
  layer: 5
})

// Move it later
player.pos.x = 150
player.pos.y = 250

That's it. The sprite is registered with the engine when created and drawn every frame until destroyed.

Coordinate System

There are two coordinate spaces:

World space is the game world. The camera's position determines what's visible. If the camera is at [100, 100], that world coordinate is at the center of the screen. X+ goes right, Y+ goes up.

HUD space is the screen itself. [0, 0] is the bottom-left corner, [camera.width, camera.height] is the top-right. HUD elements don't move with the camera.

Layers

Every drawable has a layer — an integer that determines draw order. Lower layers draw first (behind), higher layers draw last (in front).

Within a layer, objects can be sorted by different criteria:

  • explicit (default) — engine may reorder for performance
  • y-sort — sort by Y position, useful for top-down games where "lower" objects appear in front

Planes

Drawables are organized into planes. A plane is a named group that can have its own resolution, camera, and effects. By default, everything goes into the 'default' plane.

Planes render independently and composite onto the screen. This lets you have a game world at 320x240 pixel-art resolution and a HUD at native resolution, for example.

Effects

Planes and groups of sprites can have effects applied:

  • Bloom — threshold + multi-pass Gaussian blur
  • Mask — stencil masking using other sprites as the mask shape

Effects are declared in the compositor config and applied automatically. You tag sprites with groups, then apply effects to those groups.

Presentation Modes

The final composited frame is presented to the window in one of three modes:

Mode Behavior
stretch Fill the window, may distort
letterbox Fit inside window, preserve aspect ratio, black bars
integer_scale Scale by whole numbers only, nearest-neighbor, pixel-perfect

Camera

A camera defines the viewport into the world:

var camera = use('camera')
var cam = camera.make({
  pos: {x: 0, y: 0},
  width: 320,
  height: 240
})

The camera's width and height set the game's internal resolution. The pos determines what world coordinate is at the center of the screen.

Drawable Types

Type Module Description
Sprite sprite Textured quad with transform, tint, UV mapping
Text text2d Rendered text with font, size, wrapping
Shape shape2d SDF-rendered rectangles, circles, ellipses, pills
Tilemap tilemap2d Grid of tiles on a single layer
Particles particles2d Particle emitter producing sprite-like particles
Line line2d Polylines and line segments as triangle meshes

All drawable types share common properties: pos, layer, plane, groups, visible, opacity, tint.

How It Works Internally

For those curious about the pipeline (you don't need to know this to use Prosperon):

  1. Drawables register with film2d — the internal sprite registry
  2. Each frame, the compositor queries film2d for all visible drawables
  3. Drawables are sorted by layer, batched by texture/material
  4. Effect groups are rendered to intermediate targets, effects applied
  5. Planes composite to the screen via the SDL GPU backend
  6. The backend uses Metal, Vulkan, or DirectX depending on platform