Files
Lefteris Notas eeb1bf82c9 feat: Enhance interaction and inventory systems with new components and functionality
- Added BPC_UsableWorldObjectSystem for handling various interactable world objects with detailed manual implementation guide.
- Introduced BPC_ActiveItemSystem to manage quick slots and active item usage, including cycling and selection logic.
- Implemented BPC_DocumentArchiveSystem for managing collectible documents with read tracking and categorization.
- Developed BPC_JournalSystem for narrative entries with auto-adding features based on gameplay events.
- Created BPC_KeyItemSystem for key management with consumable and persistent key support.
- Enhanced BPC_FirearmSystem for ranged weapon mechanics, including hitscan and projectile firing.
- Updated BPC_MeleeSystem for melee combat with combo and blocking mechanics.
- Established BPC_ReloadSystem for managing weapon reloading processes, including partial reloads and state management.
2026-05-19 18:37:42 +03:00

9.2 KiB
Raw Permalink Blame History

BPC_MeleeSystem — Melee Weapon Component

Blueprint Spec — UE 5.55.7


Parent Class

ActorComponent

Dependencies

Purpose

Melee weapon specialization. Handles swing detection, hitbox overlap checking during windup / active frames, and combo chain sequencing. Supports light attacks, heavy attacks, charge attacks, and block/parry.

Variables

Name Type Description
ComboSection FName Active montage section for combo
ComboStep Int Current combo step index
bCanCombo Bool True during window after hit or end of swing
ComboWindowDuration Float Seconds to chain next attack
SwingMontage UAnimMontage Full melee animation set
HitDetectionCollision UCapsuleComponent Overlap collision for hit detection
bHitRegistered Bool Prevents multi-hit on same swing
HitActors Array Already hit this swing
SwingPhase ESwingPhase Windup / Active / Recovery / Idle
ChargeDuration Float Hold time for charged heavy attack
bIsBlocking Bool Currently blocking stance
ParryWindow Float Active parry frames in seconds
bParryActive Bool Within parry active window
StaggerDuration Float Hit reaction stun (self or target)

Enums

Enum Values Description
ESwingPhase Idle, WindUp, Active, Recovery, ParryWindow Attack animation phase
EAttackType LightAttack, HeavyAttack, ChargeAttack, SprintAttack, ParryRiposte Swing variant

Functions

Name Inputs Outputs Description
StartSwing AttackType: EAttackType Play montage section, set SwingPhase
OnSwingWindup Begin hit detection
OnSwingActive Enable HitDetectionCollision overlap
OnSwingHit HitResult: FHitResult Single hit registration
OnSwingRecovery Disable hit collision, check combo window
OnSwingComplete Return to Idle
StartBlock Play blocking animation
EndBlock Release block stance
ParryCheck IncomingAttack Bool If parry window active → counter
GetComboStep Int Return current combo index
ResetCombo Clear combo step counter

Blueprint Flow

[Combo Chain Logic]
  LightAttackInput →
    If SwingPhase == Idle:
        ComboStep = 0
        StartSwing(LightAttack)
    ElseIf SwingPhase == Active || SwingPhase == Recovery:
        If bCanCombo && ComboStep < MaxComboLength:
            ComboStep++
            StartSwing(LightAttack) — next section of montage

[OnSwingActive — called by Animation Notify]
  └─► HitDetectionCollision.SetCollisionEnabled(QueryOnly)
  └─► On overlap → OnSwingHit

[OnSwingHit]
  └─► If HitActor already in HitActors → return
  └─► Add HitActor to HitActors
  └─► If HitActor implements I_Damageable:
         BPC_DamageReceptionSystem.ApplyMeleeDamage(
             Damage = WeaponData.Damage * AttackTypeMultiplier,
             HitActor,
             HitLocation,
             ImpulseDirection
         )
  └─► BPC_CombatFeedbackComponent.PlayHitFX(HitResult)
  └─► ApplyStagger(HitActor)

[OnSwingRecovery — called by Animation Notify]
  └─► HitDetectionCollision.SetCollisionEnabled(NoCollision)
  └─► HitActors.Empty
  └─► Set bCanCombo = true
  └─► Start timer for ComboWindowDuration
  └─► If no combo input received → OnSwingComplete

[OnSwingComplete]
  └─► SwingPhase = Idle
  └─► bCanCombo = false
  └─► ComboStep = 0

[StartBlock]
  └─► bIsBlocking = true
  └─► Play block montage loop section
  └─► Owner movement speed reduced

[ParryCheck]
  └─► If bParryActive && incoming swing phase == Active:
         Play parry riposte animation
         Stagger incoming attacker
         Return true
  └─► Return false

Communications With

Target Method Why
BPC_DamageReceptionSystem Get Component Apply melee damage and stagger
BPC_CombatFeedbackComponent Get Component Swing whoosh, hit impact, block sparks
Owner Animation Blueprint Direct Query SwingPhase for animation state
Owner Character Movement Direct Reduce speed during block
Owner Character Input Direct Light / Heavy / Block input mapping
I_Damageable Interface Damage application on hit actors

Reuse Notes

  • Uses animation notifies for phase transitions (Notify_Windup, Notify_Active, Notify_Recovery, Notify_CanCombo, Notify_ParryWindow).
  • Combo system uses montage section names "Combo_1", "Combo_2", etc.
  • Hit collision is a simple box or capsule that exists only during Active phase.
  • Block reduces incoming damage via DamageReception; parry reflects stagger.
  • Renamed from BP_MeleeWeapon to BPC_MeleeSystem per Master naming convention.
  • Cross-references updated: BPC_DamageHandlerComponentBPC_DamageReceptionSystem.

Manual Implementation Guide

Class Setup

  1. Create Blueprint Class: Parent = ActorComponent, Name = BPC_MeleeSystem
  2. Attach to BP_WeaponBase subclass: BP_MeleeWeapon
  3. Add HitDetectionCollision (Capsule or Box component) to weapon — disabled by default

Variable Init (BeginPlay)

Event BeginPlay
  ├─ Set SwingPhase = Idle
  ├─ Set ComboStep = 0
  ├─ Set bCanCombo = false
  ├─ Set bIsBlocking = false
  ├─ Disable HitDetectionCollision (NoCollision)
  ├─ Get Owner Weapon → Read DA_WeaponData for: ComboWindowDuration, ChargeDuration, ParryWindow, StaggerDuration
  └─ Get Owner → Find BPC_DamageReceptionSystem → Cache

Function Implementations

StartSwing(AttackType: EAttackType)void

[Function: StartSwing]
  Step 1: Branch on SwingPhase != Idle AND SwingPhase != Recovery → Return (can't chain now)
  Step 2: Set SwingPhase = WindUp
  Step 3: Build montage section name:
    If this is combo: "Combo_" + ComboStep
    If AttackType == HeavyAttack: prefix "Heavy_"
    If AttackType == ChargeAttack: "Charge_"
  Step 4: Play Montage (SwingMontage, Section = built section name)
  Step 5: Set bHitRegistered = false, Clear HitActors array
  Step 6: Fire OnSwingStarted(AttackType, ComboStep)

Nodes: Switch on EAttackType, Build String, Play Montage (with Starting Section), Clear Array

OnSwingActive()void (Called by Animation Notify: "Notify_Active")

  Step 1: Set SwingPhase = Active
  Step 2: HitDetectionCollision.SetCollisionEnabled(QueryOnly)
  Step 3: Set bHitRegistered = false

OnSwingHit(HitResult)void (Called by HitDetectionCollision OnComponentBeginOverlap)

  Step 1: Get Hit Actor from Overlap → Cast to Actor
  Step 2: ForEach HitActors → if match found → Return (already hit this actor this swing)
  Step 3: Add HitActor to HitActors
  Step 4: If HitActor implements I_Damageable:
    Get BPC_DamageReceptionSystem → Call ApplyMeleeDamage:
      BaseDamage = WeaponData.Damage
      Multiplier: Light=1.0, Heavy=1.8, Charge=2.5, Sprint=1.5
      HitLocation = HitResult.ImpactPoint
      Apply impulse in swing direction
  Step 5: Get BPC_CombatFeedbackComponent → Call PlayHitFX(HitResult)
  Step 6: Apply Stagger to HitActor

OnSwingRecovery()void (Animation Notify: "Notify_Recovery")

  Step 1: Set SwingPhase = Recovery
  Step 2: HitDetectionCollision.SetCollisionEnabled(NoCollision)
  Step 3: Clear HitActors
  Step 4: Set bCanCombo = true
  Step 5: Start Timer (ComboWindowDuration) → On timer: if no combo received → OnSwingComplete()

OnSwingComplete()void

  Step 1: Set SwingPhase = Idle
  Step 2: Set bCanCombo = false
  Step 3: Set ComboStep = 0
  Step 4: Fire OnSwingFinished

StartBlock()void

  Step 1: Set bIsBlocking = true
  Step 2: Play block montage loop section
  Step 3: Get Owner Character → Get CharacterMovement → Set MaxWalkSpeed *= 0.5
  Step 4: Set ParryWindow timer: bParryActive = true for ParryWindow seconds
    On timer end → bParryActive = false

EndBlock()void

  Step 1: Set bIsBlocking = false
  Step 2: Stop block montage
  Step 3: Restore MaxWalkSpeed

Build Checklist

  • Create BPC_MeleeSystem, add to BP_MeleeWeapon
  • Add HitDetectionCollision component (Capsule/Box, NoCollision by default)
  • Create SwingMontage with sections: Combo_1, Combo_2, Combo_3, Heavy_1, Charge_1
  • Place Animation Notifies: Notify_Active, Notify_Recovery, Notify_CanCombo, Notify_ParryWindow
  • Implement phase state machine: Idle→WindUp→Active→Recovery→(combo)→Idle
  • Bind HitDetectionCollision.OnComponentBeginOverlap → OnSwingHit
  • Implement combo system with bCanCombo window timer
  • Implement block/parry with damage reduction and stagger reflection