Rendering

Purpose

Rendering turns a completed snapshot of visual state into ordered backend draws and presentation. The game selects what to show; the renderer consumes copied values and retained resources without reading live simulation objects.

Interface

Types below are in CE::Rendering unless another namespace is shown.

Types and operations

API and purpose

FrameWriter, PassWriter, Frame
Build ordered passes in a borrowed slot, then publish complete retained visual state. Frame storage and writers; handoff.

DrawStyle2D, DrawPacket2D
Resolve sprite/tile/graphic/text resources and copied placement into complete packets. CPU submission.

Camera2D, Camera3D
Own camera state and provide matrices copied into a pass. Camera observations; camera task.

Resources::Pipeline, Resources::Material
Retain executable/fixed state and resolve typed material parameters. Parameters and ownership; manual construction.

Renderer, PresentationSurface
Consume completed frames and present through compatible graphics/platform adapters. Adapter catalogue; OpenGL owner.

Draw values and enums

Type

Choices and details

Materials::Builtin2D

Textured/TexturedStrip supply ordinary asset defaults; SolidColor/TexturedColor supply colored UI triangles. Default asset materials; default UI materials.

Pipelines::Blend

Opaque, StraightAlpha, PremultipliedAlpha, Additive; match source color/alpha convention. Pipeline and material state.

Pipelines::Depth, Pipelines::Cull

Depth comparison and face culling; camera dimensionality does not select these policies. Fixed state and pass constraints.

Geometry::Layout2D, Geometry::Topology

Match position/UV or colored vertices and triangles/triangle strips to the pipeline. Geometry and independent binding.

Parameters::Type, Parameters::Semantic

Declare parameter value types and custom/pass/draw semantics. Typed parameters.

ClipRegion2D

Logical rectangular clip retained with ordered draw state. Rectangular clipping.

Usage

Prepare draws from stable simulation state, then let Runtime publish and play the completed frame. The ordinary sprite path needs a retained asset, copied draw style and pass values; it needs no native graphics calls in the game hook.

        ---
config:
  theme: base
  themeVariables:
    fontFamily: system-ui, sans-serif
    fontSize: 14px
  flowchart:
    htmlLabels: true
    curve: linear
    nodeSpacing: 22
    rankSpacing: 38
    padding: 12
---
flowchart LR
    accTitle: Rendering · practical one-sprite draw
    accDescr: Local names omit Rendering::; ambiguous nested namespaces remain qualified. Arrows point toward dependencies. Application roles are rounded; named API operations have rounded corners. Dashed arrows mark optional choices.
    k0(["Application<br/>prepare_render_frame()"]):::app
    k1["FrameWriter"]:::focal
    k2["PassWriter"]:::focal
    k3["Camera2D"]:::focal
    k4("Submission::<br/>resolve_sprite()"):::focal
    k5["Submission::<br/>Context2D"]:::focal
    k6["Assets::Sprites::<br/>Asset"]:::neighbor
    k7["DrawStyle2D"]:::focal
    k8["DrawPacket2D"]:::focal
    k0 --> k1
    k1 --> k2
    k0 --> k3
    k0 --> k4
    k4 --> k5
    k4 --> k6
    k4 --> k7
    k4 --> k8
    k2 --> k8
    classDef focal fill:#e7f3ef,stroke:#387d6b,color:#153d33,stroke-width:1.2px
    classDef neighbor fill:#f0f3f8,stroke:#8c9bb1,color:#35445b,stroke-width:1px
    classDef app fill:#fff2df,stroke:#c09452,color:#674515,stroke-dasharray:5 3
    classDef system fill:#eaf0fc,stroke:#617fab,color:#263f69,stroke-width:1.2px
    linkStyle default stroke:#7e8fa7,stroke-width:1.2px

    

Local names omit Rendering:: where unambiguous. Explore this diagram and its other views →

The frame playback diagram follows the completed frame through Runtime to the renderer. The application map adds cameras, materials and other visual inputs.

Update, prepare and play

Stage

Application/engine work

Values crossing the boundary

Game update

Advance authoritative positions, cameras and animation on simulation.

Stable current state for the next preparation call.

prepare_render_frame()

Borrow FrameWriter, begin passes, resolve complete packets and add them in draw order.

Copied matrices/styles/parameters and retained resource handles. No game-object pointer is needed by playback.

Runtime playback and recycling

Graphics consumes a completed Frame, presents it and releases recycled frame owners.

Earlier generations stay alive while any frame, scene or application handle retains them.

Preparation may be skipped under concurrent backpressure. Advance essential state during update so skipped visual preparation cannot stop animation or change gameplay. See frame publication.

Uses

Consumer

Dependency

Integration boundary

Submission::resolve_sprite(), resolve_tile() and resolve_graphic()

Retained Assets and Rendering::DrawStyle2D

Resolve geometry ranges, image bindings, material and copied transform without uploading or advancing playback.

Submission::resolve_text()

Text::Rendering::Generation from Text

Resolve already uploaded glyphs; no font discovery, shaping or rasterization is repeated.

Rendering::DrawPacket2D

Resources: geometry, material and resolved image/sampler parameters

Retain exact immutable generations, including when the original game object is gone.

Renderer and presentation adapters

Rendering::PresentationSurface and Display

Native drawing/presentation stays on the graphics/platform owner with compatible live contexts.

Used by

Consumer

Entry point

Responsibility

Application game implementing Game::AbstractGame

prepare_render_frame() and its borrowed Rendering::FrameWriter

Select visible objects, pass order and copied camera state. Do not retain frame/pass writers.

GUI UI::TGUI::Scene and UI::RmlUi::Scene

Scene::write(frame)

Append an uploaded UI pass at the application’s chosen position. Rendering playback does not query live widgets or documents.

Runtime::GameRuntime

Complete frame publication, renderer playback and recycling

Coordinate execution and resource release across the simulation/graphics boundary.

Choose a submission path

Visual

Normal path

Application choice

Sprite or atlas tile

resolve_sprite() / resolve_tile()

Current grid cell and per-object style; an empty material uses the asset’s retained default.

Whole image

resolve_graphic()

Retain Assets::Graphics::Asset; use its independent-triangle geometry.

Unicode label

resolve_text()

Retain the uploaded text generation. Positioned text runs are an explicit alternative with a compatible shader contract.

Toolkit UI

Scene::write(frame)

Adopt a complete scene before preparation; choose its order relative to world/HUD passes.

CPU submission defines image insertion and parameter precedence. Camera dimensionality does not select blend, depth or culling policy; those belong to the material’s pipeline and pass constraints.

Contracts

Frame/pass writers borrow a runtime-owned slot for one preparation call. Do not retain them or issue native graphics operations from preparation. Draw packets resolve resources, transforms and parameters before publication; playback does not need the source game object or animation cursor. Pipelines supply complete validated fixed state and material parameter bindings must match their contracts.

Camera matrices are borrowed references until copied into a pass. Camera mutation is unsynchronized. Frame preparation can be skipped under concurrent backpressure; advance gameplay/animation during update rather than while drawing.

Lifecycle

Create/upload resources during platform-owned initialization or dispatched upload work. Update camera and authoritative state on simulation. Prepare, publish, consume and recycle frames through runtime. Recycling drops retained packet generations on graphics; game cleanup precedes backend closure.

Execution

Update and frame preparation share the selected simulation owner. Native draw, presentation and retirement maintenance run on graphics. Concurrent mode transfers complete slots; it does not grant the renderer access to mutable simulation members. The newest completed frame may supersede an older waiting frame without skipping authoritative game updates.

Integration

A preparation hook begins a pass with copied camera values:

auto pass = frame.begin_pass(camera_.projection_matrix(), camera_.view_matrix());
const CE::Rendering::Submission::Context2D context{
    pass.semantics(), pass.parameters(), pass.constraints()
};
pass.add(CE::Rendering::Submission::resolve_sprite(*sprite_, cell_, style_, context));

The application supplies the retained sprite and valid cell. Context2D inserts the ordinary image binding on texture unit zero by default; use an explicit image override or manual binding only when the material needs it. An empty style_.material uses the compatible material retained during loading; no application shader setup is needed for ordinary drawing. Set a material and custom parameters in the style when an object needs a different appearance; see per-object materials. See First Game for complete initialization, transform and cleanup wiring.

Limits and further reading

Cameras do not choose a scene policy or synchronize game state. World/entity organization belongs to the application. Read pipelines, materials and submission, frame ownership, resource retirement, camera task guide and Frame interfaces.