人物骨骼的引用綁定,如果是要一個個手動設置,大概是相當讓人頭痛的事情吧。
using UnityEngine;
using System.Collections;
using UnityEditor;
using System.Reflection;
using System.IO;
using System;
public class SetRagdoll : EditorWindow
{
private GUIStyle m_HeaderLabelStyle;
// public Animator animator;
public static GameObject Character;
[MenuItem("Tool/SetRagdoll", false, 11)]
public static void SetRagdollWindow()
{
var window = EditorWindow.GetWindow<SetRagdoll>(true, "SetRagdoll");
window.minSize = new Vector2(500, 100);
}
private void OnEnable()
{
if(m_HeaderLabelStyle == null)
{
m_HeaderLabelStyle = new GUIStyle(EditorStyles.label);
m_HeaderLabelStyle.wordWrap = true;
}
}
private void OnGUI()
{
var description = "This is set Ragdoll for a character";
EditorGUILayout.LabelField(description, m_HeaderLabelStyle);
GUILayout.Space(5);
Character = EditorGUILayout.ObjectField("character", Character, typeof(GameObject), true) as GameObject;
GUILayout.Space(20);
if (GUILayout.Button("Build")) {
AddRagdoll();
Close();
}
}
private void AddRagdoll()
{
// AddAbility(controller, typeof(Opsive.ThirdPersonController.Wrappers.Abilities.Die), string.Empty, Abilities.Ability.AbilityStartType.Manual, Abilities.Ability.AbilityStopType.Manual);
var ragdollBuilderType = Type.GetType("UnityEditor.RagdollBuilder, UnityEditor");
var windows = Resources.FindObjectsOfTypeAll(ragdollBuilderType);
// Open the Ragdoll Builder if it isn't already opened.
if(windows == null || windows.Length == 0)
{
EditorApplication.ExecuteMenuItem("GameObject/3D Object/Ragdoll...");
windows = Resources.FindObjectsOfTypeAll(ragdollBuilderType);
}
if(windows != null && windows.Length > 0)
{
var ragdollWindow = windows[0] as ScriptableWizard;
var animator = Character.GetComponentInChildren<Animator>();
#if UNITY_4_6 || UNITY_4_7
SetFieldValue(ragdollWindow, "root", animator.GetBoneTransform(HumanBodyBones.Hips));
#else
SetFieldValue(ragdollWindow, "pelvis", animator.GetBoneTransform(HumanBodyBones.Hips));
#endif
SetFieldValue(ragdollWindow, "leftHips", animator.GetBoneTransform(HumanBodyBones.LeftUpperLeg));
SetFieldValue(ragdollWindow, "leftKnee", animator.GetBoneTransform(HumanBodyBones.LeftLowerLeg));
SetFieldValue(ragdollWindow, "leftFoot", animator.GetBoneTransform(HumanBodyBones.LeftFoot));
SetFieldValue(ragdollWindow, "rightHips", animator.GetBoneTransform(HumanBodyBones.RightUpperLeg));
SetFieldValue(ragdollWindow, "rightKnee", animator.GetBoneTransform(HumanBodyBones.RightLowerLeg));
SetFieldValue(ragdollWindow, "rightFoot", animator.GetBoneTransform(HumanBodyBones.RightFoot));
SetFieldValue(ragdollWindow, "leftArm", animator.GetBoneTransform(HumanBodyBones.LeftUpperArm));
SetFieldValue(ragdollWindow, "leftElbow", animator.GetBoneTransform(HumanBodyBones.LeftLowerArm));
SetFieldValue(ragdollWindow, "rightArm", animator.GetBoneTransform(HumanBodyBones.RightUpperArm));
SetFieldValue(ragdollWindow, "rightElbow", animator.GetBoneTransform(HumanBodyBones.RightLowerArm));
SetFieldValue(ragdollWindow, "middleSpine", animator.GetBoneTransform(HumanBodyBones.Spine));
SetFieldValue(ragdollWindow, "head", animator.GetBoneTransform(HumanBodyBones.Head));
var method = ragdollWindow.GetType().GetMethod("CheckConsistency", BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance);
if(method != null)
{
ragdollWindow.errorString = (string)method.Invoke(ragdollWindow, null);
ragdollWindow.isValid = string.IsNullOrEmpty(ragdollWindow.errorString);
}
}
}
/// <summary>
/// Use reflection to set the value of the field.
/// </summary>
private void SetFieldValue(ScriptableWizard obj, string name, object value)
{
if(value == null)
{
return;
}
var field = obj.GetType().GetField(name);
if(field != null)
{
field.SetValue(obj, value);
}
}
}