// Stickman rigidbody configuration // // 0 : pelvis // 1 : spine 2 // 2 : spine 3 // 3 : UpperArm Left // 4 : LowerArm Left // 5 : UpperArm Right // 6 : LowerArm Right // 7 : Head // 8 : Thigh Left // 9 : Calf Left // 10 : Thigh Right // 11 : Calf Right RagdollProfile SetRagdollProfile(Profile prof) { RagdollProfile thisProf = new RagdollProfile(); if (slaveRigidbodies.Length != 12) { Debug.LogError("There are not 12 rigidboides in ragdoll. You must assign Profiles manually.."); return(thisProf); } switch (prof) { case Profile.Default: case Profile.Dundee: // The ranges are not set in stone. Feel free to extend the ranges thisProf.maxTorque = 100f; // Limits the world space torque thisProf.maxForce = 10f; // Limits the force thisProf.maxJointTorque = 700f; // Limits the force //thisProf.maxTorqueProfile = new List<float> { 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f }; // Individual limits per limb //thisProf.maxForceProfile = new List<float> { 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f }; thisProf.maxJointTorqueProfile = new List <float> { 1f, 1f, 1f, .3f, .3f, .3f, .3f, 1f, 1f, 1f, 1f, 1f }; thisProf.PTorque = 0.3f; // For all limbs Torque strength thisProf.PForce = 20f; thisProf.DTorque = 0.002f; // Derivative multiplier to PD controller thisProf.DForce = 0.02f; // public float[] PTorqueProfile = {20f, 30f, 10f, 30f, 10f, 30f, 30f, 30f, 10f, 30f, 10f}; // Per limb world space torque strength thisProf.PTorqueProfile = new List <float> { 20f, 30f, 10f, 30f, 10f, 30f, 30f, 30f, 30f, 10f, 30f, 10f }; // Per limb world space torque strength //thisProf.PForceProfile = new List<float> { 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f, 0.5f, 0.3f, 0.5f, 0.3f }; thisProf.PForceProfile = new List <float> { 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f }; thisProf.followRateProfile = new List <float> { 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f }; // The ranges are not set in stone. Feel free to extend the ranges thisProf.angularDrag = 50f; // Rigidbodies angular drag. Unitys parameter thisProf.drag = 0.2f; // Rigidbodies drag. Unitys parameter break; case Profile.Manual: break; } return(thisProf); }
[Range(0f, 1f)] public float ragdollToFollower = 1f; //RagdollMovement script will change this value when player is airborne or falls collide etc. in order to go full ragdoll or animation follower #endregion //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// /// <summary> /// AWAKE /// Assign profiles /// rigidbodies /// local and world transforms /// if something is not right set needToAssignStuff to false and return /// /// </summary> private void Awake() { reciprocalFixedDeltaTime = 1f / Time.fixedDeltaTime; // Cache the reciprocal if (!master) { UnityEngine.Debug.LogWarning("master not assigned in AnimFollow script on " + this.name + "\n"); //Try to assign manually bool found = false; foreach (Transform tmpMaster in this.transform.parent.GetComponentInChildren <Transform>()) { if (tmpMaster.name.ToLower().Contains("master")) { master = tmpMaster.gameObject; found = true; break; } } if (!found) { UnityEngine.Debug.LogError("Could not found master in " + this.name + "\n"); } else { UnityEngine.Debug.LogWarning("master " + master.name + "assigned manually in " + this.name + " could be wrong\n"); } } else if (hideMaster) //master needed some time for debugging { SkinnedMeshRenderer visible; MeshRenderer visible2; if (visible = master.GetComponentInChildren <SkinnedMeshRenderer>()) { visible.enabled = false; SkinnedMeshRenderer[] visibles; visibles = master.GetComponentsInChildren <SkinnedMeshRenderer>(); foreach (SkinnedMeshRenderer visiblen in visibles) { visiblen.enabled = false; } } if (visible2 = master.GetComponentInChildren <MeshRenderer>()) { visible2.enabled = false; MeshRenderer[] visibles2; visibles2 = master.GetComponentsInChildren <MeshRenderer>(); foreach (MeshRenderer visiblen2 in visibles2) { visiblen2.enabled = false; } } } slaveTransforms = GetComponentsInChildren <Transform>(); // Get all transforms in ragdoll. THE NUMBER OF TRANSFORMS MUST BE EQUAL IN RAGDOLL AS IN MASTER! masterTransforms = master.GetComponentsInChildren <Transform>(); // Get all transforms in master. if (!(masterTransforms.Length == slaveTransforms.Length)) { UnityEngine.Debug.LogError(this.name + " does not have a valid master.\nMaster transform count does not equal slave transform count." + "\n"); } slaveRigidbodies = GetComponentsInChildren <Rigidbody>(); int rigidCount = slaveRigidbodies.Length; myProfile = SetRagdollProfile(ragdollProfile); System.Array.Resize(ref masterRigidbodies, rigidCount); System.Array.Resize(ref forceErrorWeightProfile, rigidCount); System.Array.Resize(ref torqueLastError, rigidCount); System.Array.Resize(ref forceLastError, rigidCount); System.Array.Resize(ref startLocalRotation, rigidCount); System.Array.Resize(ref configurableJoints, rigidCount); System.Array.Resize(ref localToJointSpace, rigidCount); System.Array.Resize(ref rigidbodiesPosToCOM, rigidCount); System.Array.Resize(ref lastRigibbodyPositions, rigidCount); int currentJoint = 0; int configurableCount = 0; int currentTransform = 0; foreach (Transform slaveTransform in slaveTransforms) // Sort the transform arrays { if (slaveTransform.GetComponent <Rigidbody>()) { masterRigidbodies[currentJoint] = masterTransforms[currentTransform]; lastRigibbodyPositions[currentJoint] = slaveTransform.GetComponent <Rigidbody>().worldCenterOfMass; if (slaveTransform.GetComponent <ConfigurableJoint>()) { configurableJoints[currentJoint] = slaveTransform.GetComponent <ConfigurableJoint>(); Vector3 forward = Vector3.Cross(configurableJoints[currentJoint].axis, configurableJoints[currentJoint].secondaryAxis); Vector3 up = configurableJoints[currentJoint].secondaryAxis; localToJointSpace[currentJoint] = Quaternion.LookRotation(forward, up); startLocalRotation[currentJoint] = slaveTransform.localRotation * localToJointSpace[currentJoint]; jointDrive = configurableJoints[currentJoint].slerpDrive; //jointDrive.mode = JointDriveMode.Position; configurableJoints[currentJoint].slerpDrive = jointDrive; configurableCount++; } else if (currentJoint > 0) { UnityEngine.Debug.LogWarning("Rigidbody " + slaveTransform.name + " on " + this.name + " is not connected to a configurable joint" + "\n"); } Quaternion rot = slaveTransform.rotation; rot.eulerAngles = new Vector3(rot.eulerAngles.x * 1, rot.eulerAngles.y * -1, rot.eulerAngles.z * -1); if (slaveTransform.name.ToLower().Contains("thigh") || slaveTransform.name.ToLower().Contains("calf")) { rigidbodiesPosToCOM[currentJoint] = Quaternion.Inverse(rot) * (slaveRigidbodies[currentJoint].worldCenterOfMass - slaveTransform.position); //* (slaveTransform.position - slaveRigidbodies[currentJoint].worldCenterOfMass); } else { rigidbodiesPosToCOM[currentJoint] = Quaternion.Inverse(slaveTransform.rotation) * (slaveRigidbodies[currentJoint].worldCenterOfMass - slaveTransform.position); } currentJoint++; } currentTransform++; } if (slaveRigidbodies.Length == 0) { UnityEngine.Debug.LogError("There are no rigid body components on the ragdoll " + this.name + "\n"); } else if (configurableCount == 0) { UnityEngine.Debug.LogError("There are no configurable joints on the ragdoll " + this.name + "\nDrag and drop the ReplaceJoints script on the ragdoll." + "\n"); } else { SetJointTorque(myProfile.maxJointTorque); JointsLimited(false); } }