Quick Start
By the end of this page you have the full UI stack running: a policy that creates one root layout per local player, tag-keyed layers registered on it, and a HUD layout pushed onto the Game layer at startup. Every screen you build later is a two-line push onto this stack.
CommonUI, EnhancedInput, and ModelViewViewModel are engine plugins that enable automatically with CrimsonUI.1. Enable the plugin
Open Edit -> Plugins, type Crimson in the search box, tick CrimsonUI's checkbox (and CrimsonCommon, its dependency), and restart the editor when prompted. For a Blueprint project that is the entire install - you never hand-edit the .uproject or any .Build.cs.
C++ projects: after enabling the plugin, add its module to your build file so your game code can use its types:
// YourGame.Build.csPublicDependencyModuleNames.Add("CrimsonUI");PublicDependencyModuleNames.Add("CrimsonCommon"); // policy/layout base layer
2. Set the Game Instance and Local Player classes
The UI manager boots off two classes from CrimsonCommon. UCrimsonCommonGameInstance broadcasts player-added/removed events the manager subscribes to; UCrimsonCommonLocalPlayer is the local-player type the manager requires (players of any other class are silently ignored). UCrimsonCommonGameInstance is Abstract, so make a subclass first.
UCrimsonUIManagerSubsystem casts the game instance to UCrimsonCommonGameInstance to hear about players, and only creates a layout for local players that are UCrimsonCommonLocalPlayer subclasses. Wrong class on either = no layout, no widgets, no error message.DefaultEngine.ini has the LocalPlayerClassName line.3. Set the viewport client
UCrimsonGameViewportClient (a UCommonGameViewportClient) drives hardware vs software cursor from the Platform.Trait.Input.HardwareCursor platform trait. CommonUI needs a UCommonGameViewportClient for its input routing, so set it even if you never touch cursors:
Open Edit -> Project Settings -> Engine -> General Settings, expand the Default Classes section, and set Game Viewport Client Class = Crimson Game Viewport Client. The editor prompts to restart - accept it, because the viewport client class is only swapped in on startup. No .ini editing needed; the picker writes the same GameViewportClientClassName line for you.
4. Give CommonUI its Click and Back actions
CommonUI's action router needs a Click and a Back input action to drive activatable widgets. Create two Input Action assets (Content Browser -> right-click -> Input -> Input Action), e.g. IA_UI_Confirm and IA_UI_Back, then register them. On UE 5.8 use the Enhanced Input path - it resolves live key bindings so button glyphs update on rebind:
; Config/DefaultGame.ini[/Script/CommonInput.CommonInputSettings]bEnableEnhancedInputSupport=TrueEnhancedInputClickAction=/Game/Input/IA_UI_Confirm.IA_UI_ConfirmEnhancedInputBackAction=/Game/Input/IA_UI_Back.IA_UI_Back
DefaultClickAction / DefaultBackAction under [/Script/CommonUI.CommonUISettings] instead, and CommonUI reads key bindings from a UCommonUIInputData DataTable. The Enhanced Input path above is recommended for new 5.8 projects. bEnableEnhancedInputSupport also unlocks the EscapeInputAction binding in How-To: HUD Layout & Escape Menu and per-layer input domains via an ActionDomainTable (see Concept: Input Routing & Activatable Widgets).UInputAction assets exist. Routing is exercised the first time you push an activatable widget (step 9).5. Define your layer tags
Layers are gameplay tags under the UI.Layer parent. CrimsonUI defines UI.Layer.Menu and UI.Layer.Modal natively (CrimsonCommon adds UI.Layer.ContextMenu); your project defines the rest. Add at least the Game layer in Project Settings -> Project -> GameplayTags -> Gameplay Tag List, or in ini:
; Config/DefaultGameplayTags.ini[/Script/GameplayTags.GameplayTagsSettings]+GameplayTagList=(Tag="UI.Layer.Game",DevComment="Always-visible HUD content")+GameplayTagList=(Tag="UI.Layer.GameMenu",DevComment="In-game menus: inventory, map")
RegisterLayer and the push functions restrict their tag pickers to the UI.Layer category (meta = (Categories = "UI.Layer")). A tag outside that parent will not appear in the dropdowns.UI.Layer field (step 6) lists UI.Layer.Game, UI.Layer.GameMenu, UI.Layer.Menu, UI.Layer.Modal, and UI.Layer.ContextMenu.6. Create the root layout Blueprint
The root layout is one widget Blueprint deriving from UCrimsonPrimaryGameLayout (CrimsonCommon). It holds one UCommonActivatableWidgetStack per layer and registers each stack under its tag.
In the Designer add an Overlay, then four Common Activatable Widget Stack children named GameStack, GameMenuStack, MenuStack, ModalStack (each slot set to fill). In the Event Graph, from Event On Initialized call Register Layer four times: (UI.Layer.Game, GameStack), (UI.Layer.GameMenu, GameMenuStack), (UI.Layer.Menu, MenuStack), (UI.Layer.Modal, ModalStack). Register Layer is callable because your Blueprint is the layout class - it does not appear on external references.
7. Create the policy Blueprint
The policy (UCrimsonGameUIPolicy, CrimsonCommon) decides which layout class to spawn and how local multiplayer shares the screen. Create a Blueprint Class with parent Crimson Game UI Policy, name it BP_UIPolicy, and set:
| Property | Value | Notes |
|---|---|---|
LayoutClass | BP_RootLayout | Required. The root layout instantiated per local player. |
LocalMultiplayerInteractionMode | PrimaryOnly (default) | PrimaryOnly = only the first local player gets UI. SingleToggle = one player at a time owns it. Simultaneous = every local player gets a layout (couch co-op). |
8. Point Project Settings at the policy
Open Project Settings -> Crimson -> Crimson UI (UCrimsonUISettings, saved to DefaultGame.ini) and set:
| Setting | Required | Description |
|---|---|---|
DefaultUIPolicyClass | Yes | Your BP_UIPolicy. Loaded once when the game instance initializes. |
ConfirmationDialogClass | For dialogs | A UCrimsonConfirmationScreen subclass - see How-To: Show Confirmation Dialogs. |
ErrorDialogClass | For dialogs | A UCrimsonConfirmationScreen subclass used by ShowError. |
UCrimsonUIManagerSubsystem::Initialize (game-instance startup). Null = no policy = no layout for any player. Changing it requires restarting PIE.BP_RootLayout instance exists. Empty screen is correct - nothing is pushed yet.9. Create a HUD layout and push it
Create a widget Blueprint BP_HUDLayout with parent Crimson HUD Layout (UCrimsonHUDLayout) - it is the always-present root HUD screen (leave its defaults alone for now; How-To: HUD Layout & Escape Menu wires the pause menu). Push it onto the Game layer when the local player is ready:
The node is Push Content To Layer For Player (async, from UCrimsonAsyncAction_PushToLayer). Its BeforePush pin fires with the created widget before activation - use it to set variables the widget reads on activate; AfterPush fires once it is live.
10. (Recommended) Set the HUD actor class
ACrimsonHUD registers itself with UGameFrameworkComponentManager, which lets GameFeature actions attach HUD widgets/components later, and feeds the ability-system debugger a useful actor list. Set it as your GameMode's HUD Class:
Open Project Settings -> Maps & Modes. Under Default Modes, set Default GameMode to your GameMode Blueprint, then set Selected GameMode -> HUD Class = Crimson HUD (or a Blueprint subclass of it). This saves onto your GameMode Blueprint - no .ini editing required.
The Selected GameMode rows are editable only while the Default GameMode is a Blueprint. You can set the same value directly on the GameMode Blueprint instead: open it and use Class Defaults -> Classes -> HUD Class.
B_CrimsonGameInstance, CrimsonCoreLocalPlayer, B_CrimsonGameUIPolicy, a root layout, and a GFA_AddWidget GameFeature action that pushes W_CrimsonHUD_Layout when the HUD spawns. See Concept: Full-Stack Integration & Multiplayer.