Concept: Full-Stack Integration & Multiplayer

Standalone, you boot the stack yourself (Quick Start). On the full Crimson stack, CrimsonCore ships the concrete pieces and drives them through GameFeatures - none of the types below live in CrimsonUI, but knowing them explains 'why does this already work' on the full stack.

What CrimsonCore pre-wires

Quick Start stepCrimsonCore shipsWhere
Game instanceB_CrimsonGameInstance (CrimsonCore's game instance; any class works)GameInstanceClass in DefaultEngine.ini
Local playerUCrimsonCoreLocalPlayer (CrimsonCore's local player; any class works)LocalPlayerClassName in DefaultEngine.ini
Viewport clientthe CrimsonUI class directlyGameViewportClientClassName
Policy + root layoutB_CrimsonGameUIPolicy + a root layout with all standard layers registeredDefaultUIPolicyClass in DefaultGame.ini
Layer/slot tagsHUD.Slot.* (the UI.Layer.* tags are native to CrimsonUI)CrimsonCore's Config/Tags ini
HUD pushUCrimsonGameFeatureAction_AddWidget (CrimsonUI) pushes W_CrimsonHUD_Layout (a UCrimsonHUDLayout) and fills HUD.Slot.* extension pointsExperience action sets (GameFeature content)

The GameFeature flow

UCrimsonGameFeatureAction_AddWidget (CrimsonUI) registers a GameFramework extension handler on the HUD class named by its HUDClass property - any AHUD, defaulting to all of them. When the HUD actor spawns on a client, the action resolves the local player and (a) pushes each configured layout class onto its UI.Layer.* layer via UCrimsonUIExtensions::PushContentToLayer_ForPlayer, and (b) registers each configured widget at its HUD.Slot.* extension point. Deactivating the feature pops and unregisters everything. This is why ACrimsonHUD (or a subclass) is required on the full stack: it is the anchor GameFeatures extend.

Multiplayer & authority

ConcernWhere it runsNetworking
Layouts, layers, pushes, dialogsOwning client onlyNone - a dedicated server has no local players and creates zero UI
HUD state sources (health, tags, inventory)Server-authoritative gameplay systemsReplicated to the client; UI reads the replicated state
UCrimsonTaggedWidget tag checksClient-side ASC (from the replicated PlayerState)Tags replicate via GAS; the widget just listens
Player-triggered actions from UI (buy, drop, use)UI calls into gameplay codeRoute through Server_ RPCs with _Validate or GAS abilities - never mutate authoritative state directly from a widget
Touch input injectionOwning client's Enhanced InputConsequences replicate through normal movement/ability channels
UI is never authoritative
Nothing in CrimsonUI replicates. Treat every widget event as an untrusted client request: forward it to a validated server RPC or a GAS ability and let the authoritative result replicate back into the UI.

Standalone checklist (what you own without CrimsonCore)

  • Nothing for the game instance or local player - any class works.
  • Layer tags beyond the native ones (UI.Layer.Game, UI.Layer.GameMenu, any HUD.Slot.*).
  • The policy + root layout Blueprints and UCrimsonUISettings entries.
  • Your own HUD push (PlayerController BeginPlay, GameMode, or your own GameFeature action).
  • Dialog widget classes if you use the messaging subsystem.