美文网首页Unity3D游戏开发
Unity2018.4.16 布娃娃系统 RagDoll

Unity2018.4.16 布娃娃系统 RagDoll

作者: xzhuan | 来源:发表于2021-04-13 14:52 被阅读0次

    xzhuan原创稿件,转载请注明出处!

    一些游戏中的角色死亡时,死亡的肢体动作十分逼真,受重力和物理模拟。Unity3D物理引擎中的Ragdoll系统,可以用来创建这种效果


    如何给模型添加布娃娃系统

    官方文档:https://docs.unity3d.com/Manual/wizard-RagdollWizard.html
    布娃娃系统只能用在具有Rigging(骨骼)的模型上,添加方法是:GameObject—>3D Object—>Ragdoll



    把需要附加Ragdoll的模型拖到Hierarchy视图中,接下来就很简单也很麻烦了,需要把模型骨骼对应的游戏体拖到Ragdoll面板一一对应,建立好引用,一个都不要错,会导致刚体和碰撞体附加到错误的游戏体上。感觉不准切可以提前看下骨骼界面:

    全部拖好以后,根据需求修改一下质量(TotalMass)和力(Strength),点击create就OK了,可以看到模型中拖到Ragdoll面板的游戏体添加了如图下组件:

    布娃娃系统是以Create Ragdoll窗口中的骨骼映射信息为基础,以各关节为单位,添加Capsule Collider和Rigidbody组件,关节与关节之间以Character Joint组件连接。若产生的Collider不符合要求,可在骨骼结构中调整radius的大小。

    怎样控制布娃娃系统

    布娃娃系统的核心是由物理引擎实现的,所以在角色死亡或需要时,通过勾选和取消关节添加的Rigidbody组件的Is Kinematic选项来激活和关闭布娃娃系统。 因此我们可以通过获取模型的某个节点的Rigidbody组件来控制特定的运动。要注意的是在打开布娃娃系统时,模型最好不要播放动画。同时,不要在场景中大量使用布娃娃系统,毕竟是用物理引擎实现的比较耗性能。
    C#代码如下

    using System.Collections;
    using System.Collections.Generic;
    using UnityEngine;
    
    /// <summary>
    /// 布娃娃管理器
    /// </summary>
    public class RagdollMgr : MonoBehaviour
    {
        public List<Rigidbody> rigidbodys = new List<Rigidbody>();
        public List<Collider> colliders = new List<Collider>();
    
        static public RagdollMgr instance = null;
        void Awake()
        {
            instance = this;
        }
    
        void Start()
        {
            Rigidbody[] _rigidbodys = GetComponentsInChildren<Rigidbody>();
    
            for (int i = 0; i < _rigidbodys.Length; i++)
            {
                //排除玩家身上的Rigidbody组件
                if (_rigidbodys[i] == Player.instance.mRigidbody)
                    continue;
    
                rigidbodys.Add(_rigidbodys[i]);
                _rigidbodys[i].isKinematic = true;
                _rigidbodys[i].mass = 0;
    
                Collider _collider = _rigidbodys[i].gameObject.GetComponent<Collider>();
                _collider.isTrigger = true;
                colliders.Add(_collider);
            }
        }
    
        /// <summary>
        /// 开启 布娃娃系统
        /// </summary>
        public void EnableRagdoll()
        {
            for (int i = 0; i < rigidbodys.Count; i++)
            {
                rigidbodys[i].constraints = RigidbodyConstraints.None;
                rigidbodys[i].useGravity = true;
                rigidbodys[i].isKinematic = false;
                colliders[i].isTrigger = false;
            }
            //设置 玩家身上的isKinematic选项
            Player.instance.mRigidbody.isKinematic = true;
    
            StartCoroutine(CloseAnimator());
        }
    
        IEnumerator CloseAnimator()
        {
            yield return new WaitForEndOfFrame();
            //注意: 开启布娃娃系统 一定要将Animator enabled设为false,不然 布娃娃系统不生效
            Player.instance.mAnimator.enabled = false;
        }
    
        /// <summary>
        /// 关闭 布娃娃系统
        /// </summary>
        public void DisableRagdoll()
        {
            for (int i = 0; i < rigidbodys.Count; i++)
            {
                rigidbodys[i].constraints = RigidbodyConstraints.FreezeAll;
                rigidbodys[i].useGravity = false;
                rigidbodys[i].isKinematic = true;
                colliders[i].isTrigger = true;
            }
            //还原 玩家身上的设置
            Player.instance.mRigidbody.isKinematic = false;
            Player.instance.mAnimator.enabled = true;
        }
    
    }
    

    注意事项:

    1.播放布娃娃的时候要把Animator勾掉,不然不生效
    2.部位穿插拉伸,要把部位Character Joint组件上面的Enable Projection勾上
    3.激活布娃娃弹得很高,就是刚体的速度,把rigidbody的速度置为0
    4.如果布娃娃动作僵硬,肯定用错骨骼来绑定布娃娃导致的
    5.布娃娃穿透场景碰撞的问题,其实这个由于速度太快引起的,可以设置rigidbody的碰撞检测模式collisionDetectionMode
    6.受力不要全部部位都给力,一般都是给一个部位就够了,不然各种力作用引起怪异表现
    7.关于倒地之后抖动问题,这个只能加个检测,如果所有刚体速度小于某个数则关闭刚体功能
    8.布娃娃系统的碰撞 可能会影响触发OnCollisionEnter、OnCollisionStay、OnCollisionExit等函数,建议使用ParentConstraint约束,外置碰撞检测等处理

    相关文章

      网友评论

        本文标题:Unity2018.4.16 布娃娃系统 RagDoll

        本文链接:https://www.haomeiwen.com/subject/udfclltx.html