Placement Workflow (5.0.3 Node-centric)

This guide explains the 5.0.3 placement workflow for the maintenance lane.

Before you use this flow, complete the transcript-backed setup in Getting Started (5.0.3). The workflow here assumes the addon is enabled, the default actions are loaded, GBLevelContext is wired, and the first placeable can already be selected from the UI.

5.0.3 is node-centric: scene nodes, composition container wiring, and stateful services/systems cooperate to place objects. This workflow represents the complete lifecycle of a placement action.

Architecture context

In 5.0.3, placement is driven by node/state interactions:

  1. Build entry
    • UI or game code calls BuildingSystem.enter_build_mode(placeable)
  2. Input/Targeting
    • GridPositioner2D and TargetingShapeCast2D update targeting state
  3. Rule Validation
    • rules evaluate against runtime context
  4. Indicator Sync
    • preview/indicator feedback reflects current validity
  5. Commit/Reject
    • BuildingSystem.try_build() finalizes or rejects the action

Detailed Placement Workflow

Phase 1: Preparation & Validation Setup

Before placement can occur, the system must have a valid placeable and a ready scene context.

  • System Entry
    • call building_system.enter_build_mode(placeable)
  • Dependency Guard
    • the building system checks whether it is ready to build
  • Selected Placeable
    • selected_placeable is assigned
  • Preview Cleanup
    • previous preview state is cleared
  • Manipulation Reset
    • if a manipulation parent exists, it is reset before creating the new preview
  • Mode Switch
    • mode changes to BUILD
  • Preview Setup
    • a preview instance is created and placement setup runs for the selected rules

Phase 2: Runtime Validation

As the user moves the cursor, the active preview and its indicators are validated continuously.

  • Positioning
    • GridPositioner2D moves the preview root to tile centers
  • Target acquisition
    • TargetingShapeCast2D updates the targeted object
  • Rule context
    • rules receive GridTargetingState
  • Checks
    • bounds
    • collisions
    • placeable-specific constraints
    • optional gameplay rules such as SpendMaterialsRuleGeneric for inventory or cost spending
  • Result generation
    • rules return RuleResult
    • placement issues aggregate into PlacementReport

Phase 3: Execution & Commit

When the user confirms placement, the system attempts to commit the action.

  • Input path
    • build confirmation is handled by build input or explicit calls into the build system
  • Final validation
    • the active placement must still be valid
  • Instantiation
    • the final scene instance is created from the placeable/template path
  • Placement parent
    • the object is added under the configured GBLevelContext.objects_parent
  • Apply hooks
    • rules that implement side effects can run apply()
  • Cleanup
    • preview/indicator state is cleaned up

Common pitfalls

  • Direct property assignment
    • avoid driving placement by mutating selected_placeable directly
  • Missing level context
    • no objects_parent means final placement has nowhere valid to go
  • Dirty state
    • resource deductions and game-state side effects belong after successful placement
  • Preview confusion
    • preview objects are not the same as committed placed objects

State Management

A robust workflow relies on the shared runtime state being the source of truth.

  • do not duplicate validation logic in your UI
  • drive placement from system entry points
  • keep UI reactive to states/systems rather than reconstructing placement truth independently

What plugin users should remember

  • starting placement is a system call, not just a state change
  • level wiring is part of the workflow contract
  • placement rules are part of the runtime loop, not just static configuration
  • targeting and manipulation interact with placement through shared state