using UnityEditor; using UnityEngine; using UnityEditor.SceneManagement; using System; using System.Collections; using System.Collections.Generic; namespace Obi{ /** * Custom inspector for ObiBone components. * Allows particle selection and constraint edition. */ [CustomEditor(typeof(ObiBone)), CanEditMultipleObjects] public class ObiBoneEditor : ObiParticleActorEditor { public class BoneParticleProperty : ParticleProperty { public const int Frozen = 3; public BoneParticleProperty (int value) : base (value){} } ObiBone bone; public override void OnEnable(){ base.OnEnable(); bone = (ObiBone)target; particlePropertyNames.AddRange(new string[]{"Frozen"}); } public override void OnDisable(){ base.OnDisable(); EditorUtility.ClearProgressBar(); } public override void UpdateParticleEditorInformation(){ for(int i = 0; i < bone.positions.Length; i++) { wsPositions[i] = bone.GetParticlePosition(i); facingCamera[i] = true; } } protected override void SetPropertyValue(ParticleProperty property,int index, float value){ if (index >= 0 && index < bone.invMasses.Length){ switch(property){ case ParticleProperty.Mass: bone.invMasses[index] = 1.0f / Mathf.Max(value,0.00001f); break; case ParticleProperty.Radius: bone.solidRadii[index] = value; break; case BoneParticleProperty.Frozen: bone.frozen[index] = value >= 1; break; } } } protected override float GetPropertyValue(ParticleProperty property, int index){ if (index >= 0 && index < bone.invMasses.Length){ switch(property){ case ParticleProperty.Mass: return 1.0f/bone.invMasses[index]; case ParticleProperty.Radius: return bone.solidRadii[index]; case BoneParticleProperty.Frozen: return bone.frozen[index] ? 1 : 0; } } return 0; } public override void OnInspectorGUI() { serializedObject.Update(); GUI.enabled = bone.Initialized; EditorGUI.BeginChangeCheck(); editMode = GUILayout.Toggle(editMode,new GUIContent("Edit particles",Resources.Load("EditParticles")),"LargeButton"); if (EditorGUI.EndChangeCheck()){ SceneView.RepaintAll(); } GUI.enabled = true; EditorGUILayout.LabelField("Status: "+ (bone.Initialized ? "Initialized":"Not initialized")); if (GUILayout.Button("Initialize")){ if (!bone.Initialized){ CoroutineJob job = new CoroutineJob(); routine = EditorCoroutine.StartCoroutine(job.Start(bone.GeneratePhysicRepresentationForBones())); EditorSceneManager.MarkSceneDirty(EditorSceneManager.GetActiveScene()); }else{ if (EditorUtility.DisplayDialog("Actor initialization","Are you sure you want to re-initialize this actor?","Ok","Cancel")){ CoroutineJob job = new CoroutineJob(); routine = EditorCoroutine.StartCoroutine(job.Start(bone.GeneratePhysicRepresentationForBones())); EditorSceneManager.MarkSceneDirty(EditorSceneManager.GetActiveScene()); } } } EditorGUI.BeginChangeCheck(); ObiSolver solver = EditorGUILayout.ObjectField("Solver",bone.Solver, typeof(ObiSolver), true) as ObiSolver; if (EditorGUI.EndChangeCheck()){ Undo.RecordObject(bone, "Set solver"); bone.Solver = solver; } bool newSelfCollisions = EditorGUILayout.Toggle(new GUIContent("Self collisions","Enabling this allows particles generated by this actor to interact with each other."),bone.SelfCollisions); if (bone.SelfCollisions != newSelfCollisions){ Undo.RecordObject(bone, "Set self collisions"); bone.SelfCollisions = newSelfCollisions; } Editor.DrawPropertiesExcluding(serializedObject,"m_Script","chainLinks"); // Progress bar: EditorCoroutine.ShowCoroutineProgressBar("Generating physical representation...",routine); // Apply changes to the serializedProperty if (GUI.changed){ serializedObject.ApplyModifiedProperties(); } } } }