UE5.8 Motion Warping 专题系列

UE5.8 Motion Warping 专题(一):先做一个能对齐的翻越/近战动画

从启用插件、角色添加 MotionWarpingComponent、动画加 Motion Warping Notify State、配置 Skew Warp,到运行时传入 VaultTarget 或 AttackTarget,跑通第一个对齐案例。

总览

第一篇不要先背算法。我们先做一个肉眼可验收的案例:角色离矮墙距离不固定,播放同一个翻越 Montage,但最后都落到墙另一侧的 VaultTarget。近战项目也可以把矮墙换成敌人胸前的 AttackTarget,原理一样。

UE5.8 Motion Warping 专题(一):先做一个能对齐的翻越/近战动画 配图
第一个案例只追求闭环:准备 root motion 动画,标窗口,传目标,观察角色是否稳定落到目标。

编辑器步骤

  1. 启用 Motion Warping 插件。UE5.8 的插件默认不启用,且标记为 Beta。
  2. 在角色蓝图或 C++ 角色上添加 UMotionWarpingComponent。角色最好是 ACharacter,默认会走 UMotionWarpingCharacterAdapter
  3. 准备一段带 root motion 的 Montage,例如 M_Vault_LowWall。先在动画预览里确认根骨确实往前移动。
  4. 打开 Montage,在需要修正位移的时间段添加 AnimNotifyState_MotionWarping
  5. Notify 的 RootMotionModifier 选择 Skew Warp
  6. Warp Target NameVaultTarget。这个名字必须和运行时代码完全一致。
  7. 初学建议先开 Warp TranslationWarp RotationIgnore Z Axis 先开,Rotation MethodSlerp
  8. 角色播放 Montage 之前,向 UMotionWarpingComponent 写入目标 Transform。

最小 C++ 示例

#include "MotionWarpingComponent.h"

void AMyCharacter::PlayVaultMontage(const FTransform& VaultTargetTransform)
{
    UMotionWarpingComponent* MotionWarping = FindComponentByClass<UMotionWarpingComponent>();
    if (!MotionWarping || !VaultMontage)
    {
        return;
    }

    MotionWarping->AddOrUpdateWarpTargetFromTransform(
        TEXT("VaultTarget"),
        VaultTargetTransform);

    PlayAnimMontage(VaultMontage);
}

蓝图里就是同一件事:在 Play Montage 前调用 Add or Update Warp Target from Transform,名字填 VaultTarget,Transform 来自关卡里的目标点、墙体 Socket、敌人组件或一次 Trace 算出的落点。

使用案例:矮墙翻越

做三个测试点:离墙 120cm、180cm、240cm。动画原始 root motion 可能只适合 180cm。如果 Motion Warping 生效,三次翻越都会把窗口内的位移重新分配,让角色落到 VaultTarget。如果 120cm 会穿墙,说明窗口开始太晚;如果 240cm 会冲刺过猛,说明距离超出动画可承受范围,需要换更长动画或限制交互距离。

使用案例:近战吸附

近战攻击通常不是把角色拉到敌人中心,而是拉到敌人前方一个偏移点:敌人 Transform 向后 80cm,Yaw 面向敌人。目标名可以叫 AttackTarget。动画窗口覆盖出刀前的踏步,不要覆盖命中后的收招,否则命中后角色还会继续被拉。

架构分析

Motion Warping 的输入不是“我想移动到哪里”,而是“这段动画 root motion 本来要怎么走,现在要对齐到哪里”。Notify Window 是修改范围,Warp Target 是对齐目标,Modifier 是修改策略。三者缺一不可。

运行时流程是:组件收到目标,Montage 播放到 Notify Window,UAnimNotifyState_MotionWarping::OnBecomeRelevant 复制 Notify 里的 Modifier 模板,组件每帧更新 Modifier 状态,最后在 root motion 转世界空间前改掉本帧 delta。

常见坑

  • 目标写在 PlayAnimMontage 之后:第一帧窗口可能已经错过目标。
  • 动画 root motion 被 AnimBP 或 Montage 设置禁用:窗口能触发,但没有可改的位移。
  • WarpTargetName 大小写或空格不一致。
  • 目标 Transform 用墙体中心,实际需要落点在墙后。
  • 只测一个距离,看不出动画是否被过度拉伸。

源码依据

UMotionWarpingComponent 暴露 AddOrUpdateWarpTargetFromTransformAddOrUpdateWarpTargetFromLocationAddOrUpdateWarpTargetFromLocationAndRotationAddOrUpdateWarpTargetFromComponentUAnimNotifyState_MotionWarping 保存一个 RootMotionModifier 模板。URootMotionModifier_SkewWarp 是默认最常用的平移/旋转修正实现。

源码路径索引

  • MotionWarping/MotionWarping.uplugin
  • MotionWarping/Public/MotionWarpingComponent.h
  • MotionWarping/Public/AnimNotifyState_MotionWarping.h
  • MotionWarping/Public/RootMotionModifier_SkewWarp.h