From ce73a13f28e5a947df8f1f87f1f1be20010952ec Mon Sep 17 00:00:00 2001 From: chai Date: Mon, 2 Aug 2021 08:35:26 +0800 Subject: =?UTF-8?q?*=20=E6=B5=8B=E8=AF=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- Assets/Scripts/Unit/Action.meta | 8 ++ .../Scripts/Unit/Action/WaitForActionReachEnd.cs | 26 ++++ .../Unit/Action/WaitForActionReachEnd.cs.meta | 11 ++ Assets/Scripts/Unit/Component/UnitAnimation.cs | 69 ++++++++- Assets/Scripts/Unit/Component/UnitComponent.cs | 4 + Assets/Scripts/Unit/Component/UnitState.cs | 157 +++++++++++++++------ Assets/Scripts/Unit/Controller/PCController.cs | 13 ++ Assets/Scripts/Unit/Controller/UnitController.cs | 24 +++- .../Unit/RootMotion/Editor/RootMotionEditor.cs | 4 +- Assets/Scripts/Unit/RootMotionProxy.cs | 12 ++ Assets/Scripts/Unit/RootMotionProxy.cs.meta | 11 ++ Assets/Scripts/Unit/UnitActionData.cs | 2 +- Assets/Scripts/Unit/UnitRootMotion.cs | 81 +++++++++-- 13 files changed, 358 insertions(+), 64 deletions(-) create mode 100644 Assets/Scripts/Unit/Action.meta create mode 100644 Assets/Scripts/Unit/Action/WaitForActionReachEnd.cs create mode 100644 Assets/Scripts/Unit/Action/WaitForActionReachEnd.cs.meta create mode 100644 Assets/Scripts/Unit/RootMotionProxy.cs create mode 100644 Assets/Scripts/Unit/RootMotionProxy.cs.meta (limited to 'Assets/Scripts/Unit') diff --git a/Assets/Scripts/Unit/Action.meta b/Assets/Scripts/Unit/Action.meta new file mode 100644 index 00000000..0efb2bf1 --- /dev/null +++ b/Assets/Scripts/Unit/Action.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: 5350e9767900c074d87314281414977b +folderAsset: yes +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/Scripts/Unit/Action/WaitForActionReachEnd.cs b/Assets/Scripts/Unit/Action/WaitForActionReachEnd.cs new file mode 100644 index 00000000..28ab8177 --- /dev/null +++ b/Assets/Scripts/Unit/Action/WaitForActionReachEnd.cs @@ -0,0 +1,26 @@ +using System; +using System.Collections; +using System.Collections.Generic; +using UnityEngine; + +public class WaitForActionReachEnd : IEnumerator +{ + UnitAnimation m_UnitAnimation; + + public WaitForActionReachEnd(UnitAnimation unitAnim) + { + m_UnitAnimation = unitAnim; + } + + public object Current => null; + + public bool MoveNext() + { + float normalTime = m_UnitAnimation.stateInfo.normalizedTime; + return normalTime < 1f; + } + + public void Reset() + { + } +} diff --git a/Assets/Scripts/Unit/Action/WaitForActionReachEnd.cs.meta b/Assets/Scripts/Unit/Action/WaitForActionReachEnd.cs.meta new file mode 100644 index 00000000..d687ea23 --- /dev/null +++ b/Assets/Scripts/Unit/Action/WaitForActionReachEnd.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: b4bf8dd0e94ed6543a91f6d3563d6dcb +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/Scripts/Unit/Component/UnitAnimation.cs b/Assets/Scripts/Unit/Component/UnitAnimation.cs index d30dffe0..7ebd780c 100644 --- a/Assets/Scripts/Unit/Component/UnitAnimation.cs +++ b/Assets/Scripts/Unit/Component/UnitAnimation.cs @@ -22,14 +22,60 @@ public class UnitAnimation : UnitComponent ToHitKnockDown, ToJump, - ToWalk, + ToWalk, + + ToAttack, + + ToRise, + + ToStinger, + + ToTurn, } + // animator状态 + public enum EAnimState + { + Idle, + Move, + Jump, + Hit, + Attack, + Rise, + Stinger, + Turn, + } + + public Dictionary triggers = new Dictionary() { + { EAnimState.Idle, ETrigger.ToIdle}, + { EAnimState.Move, ETrigger.ToMove}, + { EAnimState.Jump, ETrigger.ToJump}, + { EAnimState.Attack, ETrigger.ToAttack}, + { EAnimState.Rise, ETrigger.ToRise}, + { EAnimState.Stinger, ETrigger.ToStinger}, + { EAnimState.Turn , ETrigger.ToTurn}, + }; + + public Animator animator { get { return m_Animator; } } private Animator m_Animator; private TimelineEvent m_Timeline; private UnitActionData m_ActionData; + public AnimatorStateInfo stateInfo + { + get + { + return m_Animator.GetCurrentAnimatorStateInfo(0); + } + } + + public EAnimState curState { get { return m_CurState; } } + private EAnimState m_CurState; + + public float playbackTime { get { return m_PlaybackTime; } } + private float m_PlaybackTime; + public override void Initialize() { base.Initialize(); @@ -43,10 +89,29 @@ public class UnitAnimation : UnitComponent } } - public void Play(ETrigger trigger) + public void Play(EAnimState state) { + m_CurState = state; + ETrigger trigger = triggers[state]; string toAnim = trigger.ToString(); m_Animator.SetTrigger(toAnim); + m_Animator.speed = 0; + m_PlaybackTime = 0; + m_Owner.unitRootMotion.Reset(); + } + + public override void OnUpdate() + { + base.OnUpdate(); + + m_PlaybackTime += Time.deltaTime; + + m_Animator.speed = 1; + m_Animator.Update(Time.deltaTime); + m_Animator.speed = 0; + + m_Owner.unitRootMotion.UpdateRootMotion(); + } } diff --git a/Assets/Scripts/Unit/Component/UnitComponent.cs b/Assets/Scripts/Unit/Component/UnitComponent.cs index 28f49eda..6c8dc916 100644 --- a/Assets/Scripts/Unit/Component/UnitComponent.cs +++ b/Assets/Scripts/Unit/Component/UnitComponent.cs @@ -25,4 +25,8 @@ public class UnitComponent : MonoBehaviour StopAllCoroutines(); } + public virtual void OnUpdate() { } + + private void Update() { } + } diff --git a/Assets/Scripts/Unit/Component/UnitState.cs b/Assets/Scripts/Unit/Component/UnitState.cs index 3832c933..500096d3 100644 --- a/Assets/Scripts/Unit/Component/UnitState.cs +++ b/Assets/Scripts/Unit/Component/UnitState.cs @@ -8,20 +8,26 @@ public class UnitState : UnitComponent { public enum EUnitState { - Idle = 1, - Move = 1 << 2, - Spawn = 1 << 3, - Die = 1 << 4, - Dead = 1 << 5, - Skill = 1 << 6, - // - HitAir = 1 << 7, - HitAirHit = 1 << 8, - Knockdown = 1 << 9, - // - HitGuard = 1 << 10, - // - Walk = 1 << 11, + Idle , + Move , + Spawn , + Die , + Dead , + Skill , + // + HitAir , + HitAirHit , + Knockdown , + // + HitGuard , + // + Walk , + // + Rise , + // + Jump , + // 转身 + Turn , } [SerializeField] private EUnitState m_State; @@ -31,47 +37,66 @@ public class UnitState : UnitComponent private delegate void EnterStateHandler(EUnitState prevState); private Dictionary m_ExitStateHandlerDic = new Dictionary(); - private Dictionary m_EnterStateHandlerDic = new Dictionary(); - #region state param - public struct IdleParam {} + public override void Initialize() + { + base.Initialize(); + + InitState(); + } + + #region state param + public struct IdleParam {} public struct MoveParam { + public bool isRight; + public string key; } public struct SkillParam { } + + public struct JumpParam + { } + + public struct TurnParam + { + EUnitState nextState; + } + #endregion void InitState() { - m_EnterStateHandlerDic.Add(EUnitState.Idle, OnIdleEnter); - m_EnterStateHandlerDic.Add(EUnitState.Move, OnMoveEnter); - m_ExitStateHandlerDic.Add(EUnitState.Idle, OnIdleExit); m_ExitStateHandlerDic.Add(EUnitState.Move, OnMoveExit); - } + m_ExitStateHandlerDic.Add(EUnitState.Skill, OnSkillExit); + m_ExitStateHandlerDic.Add(EUnitState.Jump, OnJumpExit); + } - public void ChangeState(EUnitState nextState, T param, bool bForce = false) + public void ChangeState(EUnitState nextState, T param = default, bool bForce = false) { if (!IsChange(nextState, bForce)) return; - StopAllCoroutines(); + LogHelper.Log("UnitState: " + m_State.ToString() + " -> " + nextState.ToString()); - m_ExitStateHandlerDic[m_State](nextState); + StopAllCoroutines(); - EUnitState prevState = m_State; - m_State = nextState; - m_EnterStateHandlerDic[m_State](prevState); + EUnitState prevState = m_State; + if (m_ExitStateHandlerDic.ContainsKey(m_State)) + { + m_ExitStateHandlerDic[m_State](nextState); + } + m_State = nextState; - StartCoroutine(m_State.ToString(), param); - } + StartCoroutine(m_State.ToString(), param); + } - bool IsChange(EUnitState newState, bool bForce) + bool IsChange(EUnitState newState, bool bForce) { if (newState != m_State || bForce) return true; @@ -79,15 +104,13 @@ public class UnitState : UnitComponent } #region Idle - void OnIdleEnter(EUnitState prevState) - { - } - IEnumerator Idle(IdleParam param) + IEnumerator Idle(IdleParam param) { - //m_Owner.unitAnimation.Play(); - yield return null; - } + m_Owner.unitAnimation.Play(UnitAnimation.EAnimState.Idle); + yield return null; + } + void OnIdleExit(EUnitState nextState) { @@ -95,14 +118,26 @@ public class UnitState : UnitComponent #endregion #region Move - void OnMoveEnter(EUnitState prevState) - { - - } - - IEnumerator Move(MoveParam param) + IEnumerator Move(MoveParam param) { - yield return null; + if (m_Owner.isTowardRight && !param.isRight + || !m_Owner.isTowardRight && param.isRight) + { + //m_Owner.unitAnimation.Play(UnitAnimation.EAnimState.Turn); + //yield return new WaitForActionReachEnd(m_Owner.unitAnimation); + //if (param.isRight) + // m_Owner.transform.rotation = Quaternion.Euler(0, 0, 0); + //else + // m_Owner.transform.rotation = Quaternion.Euler(0, 180, 0); + m_Owner.transform.rotation = Quaternion.Euler(0, param.isRight ? 0 : 180, 0); + } + if(Input.GetKey(param.key)) + m_Owner.unitAnimation.Play(UnitAnimation.EAnimState.Move); + while (Input.GetKey(param.key)) + { + yield return null; + } + ChangeState(EUnitState.Idle, new IdleParam()); } void OnMoveExit(EUnitState nextState) @@ -110,6 +145,38 @@ public class UnitState : UnitComponent } - #endregion + #endregion + + #region Skill + + IEnumerator Skill(SkillParam param) + { + m_Owner.unitAnimation.Play(UnitAnimation.EAnimState.Attack); + yield return new WaitForActionReachEnd(m_Owner.unitAnimation); + ChangeState(EUnitState.Idle, new IdleParam()); + } + + void OnSkillExit(EUnitState next) + { + + } + + #endregion + + #region Jump + + IEnumerator Jump(JumpParam param) + { + m_Owner.unitAnimation.Play(UnitAnimation.EAnimState.Jump); + yield return new WaitForActionReachEnd(m_Owner.unitAnimation); + ChangeState(EUnitState.Idle); + } + + void OnJumpExit(EUnitState next) + { + + } + + #endregion } diff --git a/Assets/Scripts/Unit/Controller/PCController.cs b/Assets/Scripts/Unit/Controller/PCController.cs index 58745311..ed472cdb 100644 --- a/Assets/Scripts/Unit/Controller/PCController.cs +++ b/Assets/Scripts/Unit/Controller/PCController.cs @@ -6,6 +6,12 @@ using UnityEngine; [DisallowMultipleComponent] public class PCController : UnitController { + public static PCController instance; + + private void Awake() + { + instance = this; + } public override void Initialize(GameObject obj) { @@ -16,4 +22,11 @@ public class PCController : UnitController } + public override void Update() + { + base.Update(); + + + } + } diff --git a/Assets/Scripts/Unit/Controller/UnitController.cs b/Assets/Scripts/Unit/Controller/UnitController.cs index 066aad58..c39e82f4 100644 --- a/Assets/Scripts/Unit/Controller/UnitController.cs +++ b/Assets/Scripts/Unit/Controller/UnitController.cs @@ -14,8 +14,18 @@ public class UnitController : MonoBehaviour public UnitSkill unitSkill; + public UnitRootMotion unitRootMotion; + public GameObject unitObj; // 角色模型 + public bool isTowardRight + { + get + { + return transform.rotation.eulerAngles.y == 0 ? true : false; + } + } + public virtual void Initialize( GameObject obj ) { unitObj = obj; @@ -32,6 +42,18 @@ public class UnitController : MonoBehaviour unitSkill = gameObject.GetOrAddComponent(); unitSkill.Initialize(); - } + unitRootMotion = gameObject.GetOrAddComponent(); + unitRootMotion.Initialize(); + + } + + public virtual void Update() + { + unitRender.OnUpdate(); + unitState.OnUpdate(); + unitAnimation.OnUpdate(); + unitSkill.OnUpdate(); + unitRootMotion.OnUpdate(); + } } diff --git a/Assets/Scripts/Unit/RootMotion/Editor/RootMotionEditor.cs b/Assets/Scripts/Unit/RootMotion/Editor/RootMotionEditor.cs index 61c60306..f2a31bba 100644 --- a/Assets/Scripts/Unit/RootMotion/Editor/RootMotionEditor.cs +++ b/Assets/Scripts/Unit/RootMotion/Editor/RootMotionEditor.cs @@ -32,7 +32,7 @@ public class RootMotionEditor : EditorWindow const string kEmptyClipName = "Empty"; const string kStateName = "Action"; - [MenuItem("Custom/RootMotion/Create")] + [MenuItem("Erika/RootMotion/Create")] static void OpenTool() { RootMotionEditor editor = GetWindow(); @@ -257,7 +257,7 @@ public class RootMotionEditor : EditorWindow { Vector3 pos = m_Transform.position; pos.x = 0; - pos.y = pos.y < 0 ? 0 : pos.y; + //pos.y = pos.y < 0 ? 0 : pos.y; rootmotion.positionList.Add(pos); sampleTime = sampleTime - sampleDuration; diff --git a/Assets/Scripts/Unit/RootMotionProxy.cs b/Assets/Scripts/Unit/RootMotionProxy.cs new file mode 100644 index 00000000..96bba7ca --- /dev/null +++ b/Assets/Scripts/Unit/RootMotionProxy.cs @@ -0,0 +1,12 @@ +using System.Collections; +using System.Collections.Generic; +using UnityEngine; + +public class RootMotionProxy : MonoBehaviour +{ + + private void OnAnimatorMove() + { + } + +} diff --git a/Assets/Scripts/Unit/RootMotionProxy.cs.meta b/Assets/Scripts/Unit/RootMotionProxy.cs.meta new file mode 100644 index 00000000..159e22b9 --- /dev/null +++ b/Assets/Scripts/Unit/RootMotionProxy.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: a446cc0f3964e6248b0411882c74ceab +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Assets/Scripts/Unit/UnitActionData.cs b/Assets/Scripts/Unit/UnitActionData.cs index dab76696..8e45ca76 100644 --- a/Assets/Scripts/Unit/UnitActionData.cs +++ b/Assets/Scripts/Unit/UnitActionData.cs @@ -4,7 +4,7 @@ using System.Collections.Generic; using UnityEngine; [Serializable] -public class TriggerAnimationDictionary : SerializableDictionary { } +public class TriggerAnimationDictionary : SerializableDictionary { } // 配置角色的动画 diff --git a/Assets/Scripts/Unit/UnitRootMotion.cs b/Assets/Scripts/Unit/UnitRootMotion.cs index a2607700..18e0093f 100644 --- a/Assets/Scripts/Unit/UnitRootMotion.cs +++ b/Assets/Scripts/Unit/UnitRootMotion.cs @@ -1,24 +1,79 @@ using System.Collections; using System.Collections.Generic; using UnityEngine; +#if UNITY_EDITOR +using UnityEditor; +#endif // 同步root motion到角色根节点 [DisallowMultipleComponent] -public class UnitRootMotion : MonoBehaviour +public class UnitRootMotion : UnitComponent { - Transform m_Root; - Animator m_Animator; - - private void Awake() - { - m_Root = transform.parent; - m_Animator = GetComponent(); - } - - public Vector3 UpdateRootMotion() + RootMotionData m_RootMotionData; + + Dictionary m_RootMotionDic = new Dictionary(); + + private float m_PrevNormalTime; + + public override void Initialize() { - - return Vector3.zero; + base.Initialize(); + } + + public void Reset() + { + m_PrevNormalTime = 0; + } + +#if false // 用自定义root motion + public override void OnUpdate() + { + base.OnUpdate(); + + var state = m_Owner.unitAnimation.curState; + float playbackTime = m_Owner.unitAnimation.playbackTime; + + var rootMotion = m_RootMotionDic[state]; + float normalTime = (playbackTime % rootMotion.animationLength) / rootMotion.animationLength; + + if (m_PrevNormalTime > normalTime) + m_PrevNormalTime = 0; + + m_Owner.transform.position += rootMotion.GetRootMotionDistance(m_PrevNormalTime, normalTime); + m_PrevNormalTime = normalTime; } + public void SetUpRootMotion(string unitFolder, UnitActionData actions) + { + if (actions == null) + return; + + foreach (var action in actions.actions) + { +#if UNITY_EDITOR + AnimationClip clip = action.Value; + string name = clip.name; + string path = unitFolder + "RootMotion/" + name + ".asset"; + RootMotionData data = AssetDatabase.LoadAssetAtPath(path); + m_RootMotionDic.Add(action.Key, data); +#endif + } + } + +#else + + public override void OnUpdate() + { + base.OnUpdate(); + } + + public void UpdateRootMotion() + { + Vector3 dest = m_Owner.unitAnimation.animator.deltaPosition; + dest.x = 0; + m_Owner.transform.position += dest; + } + +#endif + } -- cgit v1.1-26-g67d0