前言
UE5 使用了一个最新的输入架构EnhancedInput(增强输入系统)
简介
增强输入框架就是改进一些过往问题的新答案。它以模块化的方式解耦了从输入的按键配置到事件处理的逻辑处理过程,通过提供输入动作(UInputAction)、输入修改器(UInputModifier)、输入触发器(UInputTrigger)和输入映射环境(UInputMappingContext)这些可组合功能,在新的增强玩家输入(UEnhancedPlayerInput)和增强输入组件( UEnhancedInputComponent)的配合下提供了更灵活和更便利的输入配置和处理功能。
考虑到基于 虚幻引擎5(UE5)的项目可能需要更多高级输入功能,例如复杂的输入处理、运行时重新映射输入,我们开发了增强输入插件(Enhanced Input Plugin),以便开发者拥抱次世代项目,同时又能向后兼容 虚幻引擎4(UE4)中的默认输入系统。
目标:
重新梳理简化: Axis/Action —> Action(统一)
运行时重新映射输入场景: UInputMappingContext
对初级用户易配置。大量默认行为实现,Tap/Hold…
对高级用户易扩展,可继承子类扩展
- 修改器:修改输入值
- 触发器:决定触发条件
- 优先级:配置输入场景优先级
模块化,不再只依赖Ini配置,以资源asset方式配置,堆栈式分隔逻辑
提高性能,不需要检查所有输入,只需要关心当前的场景和绑定
UE5正式替换掉旧有输入系统
关键词
○ IC: Input Component 输入组件
○ IA: Input Actions 输入动作
○ IMC: Input Mapping Contexts (输入映射上下文 IA 的集合)
○ PMI: Player Mappable Input Config (玩家可映射输入配置 IMC 的集合)
○ IM: 输入修饰符 Input Modifies
○ IT: 输入触发器 InputTriggers
IMC
一套当前的Key->InputAction的映射集合
多个IMC同时作用,高优先级的会先处理,如果没有则触发到低优先级的
高优先级的Key绑定会屏蔽低优先级的绑定
流程图
Trigger 与 UI 事件 对应关系
1 2 3 4 5 6 7 8
| UInputTriggerDoubleTap --> OnDoubleClicked UInputTriggerDown --> OnDownClicked UInputTriggerPressed --> OnPressed UInputTriggerReleased --> OnReleased UInputTriggerHold --> OnHold UInputTriggerHoldAndRelease --> OnHoldAndRelease UInputTriggerPulse --> OnPulse UInputTriggerTap --> OnTap
|
CPP绑定
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69
|
UPROPERTY(EditDefaultsOnly, BlueprintReadWrite, Category="EnhancedInput", meta=(AllowPrivateAccess="true")) TObjectPtr<UInputMappingContext> InputMappingContext;
UPROPERTY(EditDefaultsOnly, BlueprintReadWrite, Category="EnhancedInput|Action", meta=(AllowPrivateAccess="true")) TObjectPtr<UInputAction> IA_MoveForward;
UPROPERTY(EditDefaultsOnly, BlueprintReadWrite, Category="EnhancedInput|Action", meta=(AllowPrivateAccess="true")) TObjectPtr<UInputAction> IA_MoveRight;
UPROPERTY(EditDefaultsOnly, BlueprintReadWrite, Category="EnhancedInput|Action", meta=(AllowPrivateAccess="true")) TObjectPtr<UInputAction> IA_Turn;
UPROPERTY(EditDefaultsOnly, BlueprintReadWrite, Category="EnhancedInput|Action", meta=(AllowPrivateAccess="true")) TObjectPtr<UInputAction> IA_LookUp;
UPROPERTY(EditDefaultsOnly, BlueprintReadWrite, Category="EnhancedInput|Action", meta=(AllowPrivateAccess="true")) TObjectPtr<UInputAction> IA_Jump;
UPROPERTY(EditDefaultsOnly, BlueprintReadWrite, Category="EnhancedInput|Action", meta=(AllowPrivateAccess="true")) TObjectPtr<UInputAction> IA_Fire;
void AMyCharacter::SetupPlayerInputComponent(UInputComponent* PlayerInputComponent) { Super::SetupPlayerInputComponent(PlayerInputComponent);
if(APlayerController* PC = CastChecked<APlayerController>(GetController())) { if(UEnhancedInputLocalPlayerSubsystem* Subsystem = ULocalPlayer::GetSubsystem<UEnhancedInputLocalPlayerSubsystem>(PC->GetLocalPlayer())) { Subsystem->AddMappingContext(InputMappingContext, 100); } }
if(UEnhancedInputComponent* EnhancedInputComponent = CastChecked<UEnhancedInputComponent>(PlayerInputComponent)) { if(IA_MoveForward) { EnhancedInputComponent->BindAction(IA_MoveForward, ETriggerEvent::Triggered, this, &AMyCharacter::MoveForward); }
if(IA_MoveRight) { EnhancedInputComponent->BindAction(IA_MoveRight, ETriggerEvent::Triggered, this, &AMyCharacter::MoveRight); }
if(IA_Turn) { EnhancedInputComponent->BindAction(IA_Turn, ETriggerEvent::Triggered, this, &AMyCharacter::TurnAtRate); }
if(IA_LookUp) { EnhancedInputComponent->BindAction(IA_LookUp, ETriggerEvent::Triggered, this, &AMyCharacter::LookUpAtRate); }
if(IA_Jump) { EnhancedInputComponent->BindAction(IA_Jump, ETriggerEvent::Started, this, &AMyCharacter::OnJump); EnhancedInputComponent->BindAction(IA_Jump, ETriggerEvent::Completed, this, &AMyCharacter::OnStopJumping); } } }
|
QA
为什么IMC和IA都有Triggers和Modifiers?
因为一个操作配置在IA里面相当于是全局的,如果两个都配了,两个都起作用,先是IMC里的起作用,再是IA里起作用。(比如:IMC、IA里都配了Negate,那么最终的值就是正的。)
如果有一个重攻击的Action,在IA里配上相应的全局Trigger,在各个不同的IMC里只需要改按键,不需要每一个再配一套Trigger。(IA全局 IMC当前)实践
IMC BindAction
- 初始情况应该在哪里开始应用IMC
- 后续运行时在蓝图中如何切换IMC
- 何时Remove IMC
- 在哪里绑定Action和Axis
- 在蓝图中如何BindAction
实践
初始情况应该在哪里开始应用IMC


何时Remove IMC

IMC BindAction最佳实践
- 分层的IMC设计:基本输入(移动),武器/载具,行为/Buff
- Add(IMC,Priority),规划好Priority的值, IMC的Priorit体现的是Key和InputAction之间的映射关系,但是找到InputAction之后,还是依然按照InputStack的顺序来处理。
- Pawn上可携带多个IMC,但只Apply一个 IMC不一定跟Pawn绑定关联,可根据运行时逻辑灵活Add
- IMC代表输入的逻辑处理环境,BindAction代表输入事件该由谁来处理的职责

Debug
调试手段
ShowDebug EnhancedInput 显示调试界面
Input.+action ActionName Value 强制添加某个 action 的输入
Input.-action ActionName 移除某 Action 的输入
Input.+key key Value 添加某 Key 的输入
Input.-key keyName 移除某 key 的输入
参考
Lyra 待更新
UE5-Lyra中的输入系统(增强输入) - 知乎
UE5 – EnhancedInput(增强输入系统) - 知乎
虎跳龙拿–新一代增强输入框架EnhancedInput | Epic 大钊
EnHanced Input - 知乎