UE4高級運動系統(Advanced Locomotion System V3)插件分析

Advanced Locomotion System V3是虛幻商城的一款第三方插件。它相比UE4的基礎走跑跳錶現,實現了更多動做遊戲裏經常使用的運動特性,雖然價格訂價不菲,依然備受關注。筆者試用了這款插件,確實很強大,適合做爲基礎插件來作FPS,ACT遊戲,所以簡單學習分析下這款插件。網絡

插件特色:

  1. 具有動做遊戲的常見特性,支持多種移動模式,步行,奔跑,衝刺,下蹲,Ragdoll
  2. 運動細節作得很到位,包括原地轉身,奔跑急停轉向,移動中身體傾斜,落地腿部緩衝,頭部Aim Offset(AO),腿部IK
  3. 支持網絡同步
  4. 純藍圖實現,適合策劃、開發學習應用

動畫樹分析

插件用了兩顆動畫樹,Mannequin_AnimBP和Mannequin_IK_AnimBP,前者掛載在人物Blueprint上,用來處理人物主體動畫;後者掛載在人物的Skeletal Mesh上,用做動畫後處理來實現腳部IK動畫。Mannequin_AnimBP動畫樹大致分爲地面動做、空中動做兩部分的處理。其中地面Locomotion的表現需求是最多的。
Mannequin_AnimBP主動畫狀態機架構

地面Locomotion

地面Locomotion算是動畫樹最複雜的狀態機了,能夠簡單分爲3層:學習

Locomotion第一層狀態機

站立姿式呼吸動畫

能夠看到第一層狀態機只是對第二層狀態機輸出動畫作了一個呼吸動畫的疊加。第二層狀態機輸出的Idle動畫實際上是靜止Pose,在這一層才統一疊加上呼吸動畫。動畫

移動Locomotion第二層狀態機

第二層狀態機只定義了幾種Locomotion狀態的過渡邏輯,能夠看到Locomotion有走停轉站四種狀態。ui

Locomotion第三層狀態機--Moving

第三層狀態機分別是走停轉站的動畫實現,其中走(Moving)的實現是最爲複雜的。能夠看到狀態機有不少動畫分支,所有是用BlendSpace,以Direction,Gait Value做爲輸入值來輸出移動動畫的。在此簡單解釋Gait Value,插件設計該變量將Walk/Run/Sprint三類狀態的速度值映射爲[1,3],動畫機內只關注跟Walk/Run/Sprint狀態相關的Gait Value,無須關注具體速度值。插件

人物有兩種轉身模式,一種是根據人物速度方向轉身(Velocity Direction Mode),一種是根據鏡頭方向轉身(Looking Direction Mode),這兩種轉身模式也造就了兩種移動模式,一般適用於在ACT/FPS遊戲裏切換格鬥/射擊和自由移動兩種移動模式。轉身模式經過變量ALS_RotationMode控制。設計

八方向移動

鏡頭方向轉身模式的八方向移動

以人物速度方向轉身的移動動畫比較簡單,基本只須要對朝前的Walk/Run/Sprint動畫作BlendSpace融合便可。以鏡頭方向轉身的移動動畫則要作八方向移動動畫,簡單的八方向動畫(前/後/左/右/左前/左後/右前/右後方向移動)其實用一個BlendSpace就能夠實現,但插件作了更復雜的八方向動畫。左右移動進一步細分出了左移姿式前進,左移姿式後退,右移姿式前進,右移姿式後退等四個動做,用了兩個BlendSpace來實現這種八方向移動。3d

八方向移動前進BlendSpace

八方向移動後退BlendSpace

狀態機根據人物移動方向切換使用兩個BlendSpace,當鏡頭與速度方向夾角處於[-90,90]範圍內用前進BlendSpace,不然用後退BlendSpace。上圖紅框部分是兩個BlendSpace實際採用區域。orm

該狀態機還有個分支用於輸出下蹲移動動做,移動速度是恆定的,因此用了1D BlendSpace作輸出,比較簡單,不展開細說。blog

另外整個狀態機不少分支都有RF變量身影,該變量意思是移動動畫是以左腳仍是右腳在前,所以以RF變量能夠分出了兩種BlendSpace。

移動傾斜

跑動轉向的身體傾斜效果

根據Lean Gounded X/Lean Gounded Y變量能夠BlendSpace出一個身體向左右,先後傾斜必定角度的Pose,將其與移動動畫作融合,就能表現出角色傾斜奔跑的效果。這個融合主要是爲了體現角色速度感。角色速度,每幀速度角度變化值決定左右傾斜度,每幀角色速度變化值決定先後傾斜度。

Lean融合

Lean Gounded X計算邏輯

Lean Grounded Y計算邏輯

正常中止移動動畫

從Moving到NotMoving有兩種過渡,一種是正常中止移動的Stop動畫,一種是奔跑急停的Pivot動畫。Stop動畫細分了多種狀態下的Stop動畫,這裏只看普通跑動下的Stop動畫。

Stop動畫狀態機

能夠看到Stop動畫是由2個BlendSpace輸出的,根據左腳在前,仍是右腳在前,決定使用哪個BlendSpace。兩個BlendSpace都接收Feet Position X和Feet Position Y做爲輸入。

Feet Position X:表示Foot Direction,Foot Direction的範圍是[-90,90],表示移動方向。
Feet Position Y:表示Foot Position。Foot Position的範圍爲[-1,1],其中左腳邁到最前時爲-1,右腳邁到最前時爲1,兩腿恰好交叉時爲0。看上圖可知當Foot Position>0時,即右腳邁在前面時,用ALS_N_Stop_RF BlendSpace,不然用ALS_N_Stop_LF BlendSpace。

Feet Position X、Feet Position Y兩個變量值的更新很巧妙:全部的移動Animation Sequence上,都添加了名爲FootDirection,FootPosition的Curve,記錄了每一幀的腳步位置和移動方向。當進入Stop狀態時,經過GetCurveValue接口獲取FootDirection,FootPosition的Curve值,再設置給Feet Position X、Feet Position Y。

Stop的BlendSpace基本就是採樣了人物在左移,右移,前行3個方向下,左腳或右腳在前的腳步回收動畫,可讓人物在中止移動時,有一個明顯收住腳部,回撤站立的表現,加強人物運動真實感。

人物停下沒有Stop過渡

人物停下增長Stop過渡

奔跑急停動畫

增長奔跑急停的Pivot動畫用於人物跑動中大幅度轉向的過渡,進一步強化運動速度感。判斷移動輸入方向與人物移動方向的Yaw角度大於100(基本就是反向移動)時,人物在地面上且速度處於必定範圍內,即進入Pivot過渡。

Pivot過渡條件

Pivot動畫

原地轉身動畫

90度轉身和180度轉身動畫

插件沒有在AnimGraph裏播放原地轉身動畫,而是在EventGraph裏調用Play Montage接口播放TurnInPlace的Montage動畫,在AnimGraph裏添加TurnInPlace Slot輸出轉身動畫。

TurnInPlace Slot輸出轉身動畫

看下動畫樹的EventGraph裏調用轉身動畫的接口:

轉身動畫調用接口

決定是否播放轉身動畫主要靠如下3個變量:

Turning In Place:當前是否正在轉身
Turning Right:當前是否正在向右側轉身
Aim Yaw Delta:當前幀鏡頭朝向與人物朝向的Yaw角變化值

基本邏輯是轉動鏡頭Yaw角大於90度轉身或180度轉身閾值時,且當前沒有在轉身,則播放轉身動畫;當前已在轉身中,只能夠打斷往相反方向轉身。這樣避免持續往一側轉動鏡頭時,播轉身動畫過程當中,出現打斷動畫,重頭播轉身動畫的狀況。

轉身動畫不帶人物旋轉

轉身動畫只有腿部動做,不帶人物轉向,人物轉向經過TurnInPlace_AnimNotifyState動畫事件每幀設置。

TurnInPlace_AnimNotifyState動畫事件每幀回調

左側轉身180度曲線

每幀設置轉向用一個EaseInOut曲線來控制,獲取上一幀跟當前幀的曲線差值,即爲當前幀人物轉向Yaw角偏移值。

最後,TurnInPlace_AnimNotifyState動畫事件還需每幀判斷當前人物是否有移動,移動則打斷轉身動畫。

空中動做

起跳動做

起跳動做用了基礎起跳動做,融合BlendSpace,讓起跳呈必定程度的Lean傾斜,表現出人物往對應方向起跳的感受。其中Lean In Air值由跳躍Z軸速度和移動速度決定,Direction爲移動速度方向。

下落動做

下落動做有兩個階段動做,一開始是正常騰空下落,隨着降低速度變大,逐漸Blend爲手腳胡亂擺動的動做,用一個EaseInOut曲線控制Blend速度。

下落動做狀態機

下落動做Blend曲線

下落動做

下落動做一樣融合BlendSapce作Lean傾斜,而且會計算着地時機,在快着地前融合一我的物手臂上揚再下落的動做,強化落地衝擊感。該融合靠Land Prediction Alpha變量控制。該變量在人物下落過程當中,每幀以腳部爲圓心作球形檢測,得出球形與地面的相交最短距離,歸一化到[0,1]的範圍值來作動畫融合。

紅色爲Blend前,綠色爲Blend後動畫

落地動畫

人物跳躍着地後播放一個着地過渡動畫,固然若是在此期間人物移動則打斷過渡動畫。

頭部AO

頭部AO處理

頭部AO比較簡單,在MainStateMachine動畫輸出後,根據人物朝向和攝像機朝向計算出AimOffset值,作一個[-180,180] Yaw角,[-90,90] Pitch角範圍的AO處理。

Ragdoll系統

人物死亡後會切換爲Ragdoll狀態,動畫狀態機比較簡單,根據人物是否處於奔跑,播放手腳亂擺或者身體蜷縮的動畫。Ragdoll系統更多在於藍圖裏的邏輯處理。

Ragdoll動畫狀態機

切換Ragdoll狀態

進入Ragdoll狀態,作如下處理:

  1. 角色骨骼運動改由Skeletal Mesh,pelvis節點下的骨骼自行進行模擬物理
  2. 角色MovementMode切爲None,讓MovementComponents再也不更新角色位置邏輯
  3. 開啓角色網格碰撞,禁用角色膠囊體碰撞

每幀Update作如下處理:

  1. 判斷人物Z軸速度小於-4000時,關閉重力模擬,防止下落速度過快致使剛體穿透
  2. 更新Ragdoll的速度,更新pelvis bone的位置和旋轉
  3. 更新Actor的位置和旋轉。由於Ragdoll狀態下MovementComponent再也不更新角色位置邏輯了,得根據pelvis bone的位置和旋轉計算並設置Actor的位置和旋轉,不然攝像機就不能正確跟隨角色Ragdoll了。

Ragdoll沒有更新Actor位置致使攝像機脫離

這裏還要注意一些細節,不能直接以Pelvis Bone來設置Actor位置,若是直接設置,當角色Ragdoll倒地後,膠囊體其實有一半嵌入了地面。當退出Ragdoll時,膠囊體會瞬間彈出地面,致使人物抖動。解決辦法是從Pelvis Bone往Z軸負方向(地面)作SapsuleHalfHeight距離的射線檢測,SapsuleHalfHeight減去射線碰撞距離得出Z軸補償值,再取Pelvis Bone位置做爲Actor位置,目的就是保證膠囊體不嵌入地面。
直接以Pelvis Bone設置Actor位置

Pelvis Bone+Z軸補償值設置Actor位置

角色膠囊體始終只旋轉Yaw角,Roll、Pitch角爲0,所以Actor旋轉只取Pelvis旋轉的Yaw角,這裏注意角色正面/背面倒地後,起身的朝向恰好是相反的,經過判斷Pelvis的Roll角是否大於0,翻轉Yaw角180度便可。

退出Ragdoll狀態

退出Ragdoll則要恢復進入Ragdoll時所做的改動,而且播放起身動畫:

  1. 取消骨骼模擬物理
  2. 視乎角色是在地面仍是空中,將Movement Mode切換爲Walking/Falling
  3. 開啓角色膠囊體碰撞,禁用角色網格碰撞
  4. 設置角色Movement當前速度爲Ragdoll速度
  5. 調用Anim Instance的Save Pose Snapshot接口,給當前角色動畫保存快照,在動畫機的退出Ragdoll狀態裏,輸出這個快照
  6. 判斷角色面部朝上/朝下,播放對應起身動畫,角色以快照Pose開始起身站立

保存動畫快照並播放起身動畫

退出Ragdoll動畫狀態機裏輸出快照Pose

腿部IK

插件的腿部IK實現也挺不錯,單獨用了一個後處理動畫樹來實現,跟前面其餘功能解耦,實現邏輯很清晰,也設計了一些變量來控制調整腿部IK效果。

插件的腿部IK實現了兩個基本功能:

  1. 左右腿自適應不一樣地面高度。站立在凹凸不平的地表上,左右腿能貼着地面站立,避免出現腿部懸空問題。
  2. 左右腳掌自適應不一樣地面角度。站立在斜坡上,人物腳掌要轉至與斜坡保持平行,緊貼地表。

腿部IK效果

簡單介紹下IK(Inverse Kinematics,逆向運動學)原理,它是與FK(Forawrd kinematics,正向運動學)
截然相反的一種骨骼定位技術。FK經過自頂向下肯定每根骨骼的位置和旋轉,肯定整個骨架形態。IK則是給某根骨骼指定位置旋轉,並自動計算其父骨骼的位置旋轉,從而肯定骨架形態。

FK和IK的計算原理

IK計算須要兩個參數,Joint Target和Effector。簡單理解,Effector其實就是咱們想要修改的骨骼的目標點,由此引起的其父骨骼到Base骨骼之間的位置變更,則由IK自動計算出來。已知Base骨骼位置不變,若是隻有Effector參數,IK計算出來的骨骼位置,在三維空間是有無數解的。所以還須要Joint Target參數,它至關因而一個參考點,讓IK計算得出的各骨骼位置儘可能靠近這個參考點。

UE4的Anim Graph提供了Two Bone IK節點用於處理IK,須要設置進行IK的目標骨骼、Effector、Joint Target。

  • 目標骨骼天然是兩條腿部骨骼:foot_l,foot_r。

IK目標骨骼:foot_l,foot_r

  • Effector以兩條腿部IK骨骼做爲參考:ik_foot_l,ik_foot_r,這是官方骨架自己自帶的IK骨骼。除了腿部IK骨骼,官方骨架還自帶了手部IK骨骼,ik_hand_l,ik_hand_r。IK骨骼只是用於定位IK目標點的,並無綁定動畫。

IK目標點:ik_foot_l,ik_foot_r

  • 因爲腳部屈伸時,膝蓋確定是朝前彎曲的,因此插件給Skeleton的左右腳各添加了從thigh(大腿)到calf(小腿肚)的虛擬骨骼:VB thigh_l_calf_l,VB thigh_r_calf_r,並將骨骼設置在膝蓋正前方30個單位的位置,做爲Joint Target。

設置虛擬骨骼做爲Joint Target

下圖就是Two Bone IK節點的對應設置:
Two Bone IK節點設置詳情

遊戲裏隨着人物的運動,腿部IK Effector是一直在變的。所以須要每幀計算Effector值,動畫藍圖的計算過程以下:

  1. 首先雙腿分別向Z軸負方向(地面)作射線檢測,得出雙腿距離地面距離,看哪條腿距離地面更遠,將其距離值做爲Pelvis Offset,把Pelvis(盆骨)骨骼向下移動Pelvis Offset單位,實際上也就是將總體人物骨骼下移,這樣靠下面的那條腿就站立在地面上了
  2. 接着計算兩條腿的Effector座標,從而讓腿擡到地面位置。雙腿距離地面的距離,分別設爲兩根IK骨骼的Z軸值,便可得出兩條腿Effector點的座標
  3. 接着計算兩條腿的Effector旋轉,從而讓腳掌旋轉到適合角度,緊貼地面站立。根據射線與地面的碰撞點法線,可計算出碰撞地面的朝向,只取地面朝向的Roll角,Pitch角份量設給IK骨骼(Yaw角不用調整,讓腳掌始終朝前)。

腳部IK怎麼作?
先把人物骨骼移到下面那條腿的位置,再把另外一條腿擡起來

得出以上關鍵數值後,Anim Graph裏經過Transform(Modify)Bone節點修改各個關鍵骨骼數據,最後再經過Two Bone IK節點作IK計算:
Anim Graph的Foot IK處理節點

這裏還有個細節,每幀計算得出的數值與上一幀的數值進行插值後,再設置給骨骼,不作插值的結果就是人物上下樓梯會明顯抖動,就像下圖同樣:

結語

插件自己的功能已經挺豐富了,拿來作簡單的FPS、ACT遊戲已經足夠。插件自己的設計架構也比較清晰合理,適合在此基礎上作重構,增長諸如持槍、匍匐等動做。就算不直接使用插件,插件諸如原地轉身、腳部IK的實現也是值得參考借鑑的。

相關文章
相關標籤/搜索