Files
UE5-Modular-Game-Framework/docs/game/item-medkit.md

7.2 KiB

Item Example — MedKit (Consumable)

Item Type: Consumable Complexity: Low Systems Used: DA_ItemData, BP_ItemPickup, BPC_InventorySystem, BPC_ConsumableSystem, BPC_HealthSystem What You Learn: Consumable Data Asset, pickup actor, health restore, stackable item, quick-slot use


1. Create the DA_ItemData

1.1 — Create the Data Asset

Content Browser → Game/Items/
  Right-click → Miscellaneous → Data Asset
  Class: DA_ItemData
  Name: DA_Item_MedKit

1.2 — Fill Core Properties

Property Value Notes
Item Tag Framework.Item.Consumable.MedKit Unique identity
Display Name "MedKit" Player sees this
Description "A standard medical kit. Restores 25 health." Shown in inventory
Icon T_MedKit_Icon Any red/white cross texture for prototype
World Mesh SM_MedKit Soft reference — Construction Script resolves it
Weight 1.0 Light carry weight
Stack Limit 5 Can carry up to 5 in one stack
Item Type Consumable Triggers Consumable Data panel

1.3 — Fill Consumable Data

When ItemType == Consumable, the Consumable Data panel appears:

Field Value Notes
Health Restore 25.0 How much HP to restore (0-100 clamp)
Stress Reduce 0.0 Optional stress relief
Use Duration 2.0 Seconds to consume (animation time)
bConsumedOnUse ✓ (true) Item is removed from inventory after use

1.4 — Save

The Data Asset is ready. No other config needed for a simple consumable.


2. Create the BP_Pickup_MedKit

Follow the same pattern as the flashlight pickup, but simpler — no active-use actor needed.

2.1 — Create Blueprint

Content Browser → Game/Pickups/
  Right-click → Blueprint Class → Actor
  Name: BP_Pickup_MedKit

2.2 — Add Components

# Component Name Purpose
1 StaticMeshComponent Mesh Renders the medkit model
2 SphereComponent PickupTrigger Interaction radius (Sphere Radius → 150)

Select PickupTrigger → Details → Collision Presets → OverlapOnlyPawn

2.3 — Create ItemData Variable

+ Variable → Name: ItemData → Type: DA_ItemData → Object Reference

Select the variable → Details:

  • Instance Editable → ✓
  • CategoryPickup

2.4 — Wire Construction Script

[Construction Script]
  │
  ├─ ItemData → Is Valid? → Branch
  │    ├─ True:
  │    │    ├─ ItemData → Get World Mesh → Load Synchronous → Set Static Mesh (Mesh)
  │    │    └─ ItemData → Get Display Name → Set Actor Label
  │    └─ False:
  │         └─ Print String ("No ItemData assigned to BP_Pickup_MedKit")

2.5 — Add I_Interactable and Wire

Same pattern as flashlight. The key difference for consumables is stacking: the pickup can hold multiple units.

Event Interact
  │ Interactor: AActor*
  │
  ├─ Interactor → Get Component by Class (UBPC_InventorySystem) → Is Valid?
  │    │
  │    └─ True → [Inventory]
  │         │
  │         ├─ Can Add Item(ItemData, Quantity=1)
  │         │    │
  │         │    ├─ True → Add Item(ItemData, Quantity=1) → Destroy Actor → Return True
  │         │    │
  │         │    └─ False:
  │         │         ├─ Print "Inventory Full"
  │         │         └─ Return False

For multi-pickup stacks (e.g., picking up 3 medkits at once), set a Quantity variable (Integer, Instance Editable) and pass it to Add Item. The inventory auto-stacks identical items.

2.6 — Add Bobbing (optional)

Add a Timeline to Event BeginPlay with a sine wave for Z offset — same as flashlight example.


3. Wire Consumable Use (On Player Pawn)

When the player uses a consumable from their inventory or quick-slot:

3.1 — In BPC_ConsumableSystem (BP child on pawn)

Event Use Consumable (custom event)
  │ ItemData: DA_ItemData*
  │
  ├─ ItemData → Get Consumable Data (Break FItemConsumableData)
  │    │
  │    ├─ Health Restore > 0?
  │    │    └─ True:
  │    │         ├─ Get Owner → Get Component by Class (UBPC_HealthSystem)
  │    │         │    │
  │    │         │    └─ Is Valid? → True:
  │    │         │         └─ Apply Healing (HealthRestore, Healer=self)
  │    │         │              │
  │    │         │              └─ Print String: "Restored {HealthRestore} HP"
  │    │         │
  │    │         └─ False: Print "No HealthSystem found"
  │    │
  │    ├─ Stress Reduce > 0?
  │    │    └─ True:
  │    │         └─ Get BPC_StressSystem → Remove Stress (StressReduce)
  │    │
  │    ├─ bConsumedOnUse?
  │    │    └─ True:
  │    │         └─ Get BPC_InventorySystem → Remove Item (ItemData, 1)
  │    │
  │    └─ (Optional) Play sound, screen effect, widget animation

3.2 — Quick Test Without Full Integration

Bind a test key (e.g., IA_UseItem) in your player character:

Event InputAction (IA_UseItem, Pressed)
  │
  ├─ Get Component by Class (UBPC_InventorySystem)
  ├─ Get All Items → For Each Loop
  │    │
  │    ├─ Break FInventorySlot → Item
  │    ├─ Item → Get Item Type == Consumable?
  │    │    └─ True:
  │    │         ├─ Item → Get Consumable Data → Health Restore
  │    │         ├─ Get BPC_HealthSystem → Apply Healing (HealthRestore)
  │    │         ├─ Inventory → Remove Item (Item, 1)
  │    │         └─ Break (exit loop — only use one)
  │    │
  │    └─ Continue loop

4. Verification Checklist

  • Data Asset: DA_Item_MedKit has ItemType = Consumable, HealthRestore = 25, StackLimit = 5
  • Pickup in level: Mesh appears, bobs, interaction prompt shows "Pick up MedKit"
  • Inventory: Pick up medkit → appears in inventory slot. Pick up 4 more → they stack (quantity = 5). Pick up 6th → fails (stack limit).
  • Use: Press use item key → health increases by 25, stack count decreases by 1
  • Weight: Each medkit adds 1.0 to carry weight. Get Remaining Weight decreases by 1.0 per pickup.
  • Full inventory: Pick up medkit when no slots left → "Inventory Full" feedback, pickup remains in world

5. Key Concepts

Concept How It Works
Stacking StackLimit = 5 on the Data Asset. BPC_InventorySystem.AddItem() auto-finds existing stacks and adds to them instead of creating new slots.
Consumed on use bConsumedOnUse = trueBPC_ConsumableSystem calls RemoveItem() after applying effects. Set to false for reusable items (e.g., a reusable syringe with cooldown).
Soft references WorldMesh is a TSoftObjectPtr<UStaticMesh> — it doesn't load into memory until Construction Script resolves it. This keeps memory low when assets aren't in use.
Inventory weight BPC_InventorySystem.CurrentWeight auto-updates when items are added/removed. CanAddItem() checks weight capacity before pickup.