Exemple #1
0
        protected override void OnSPInspectorGUI()
        {
            this.serializedObject.Update();

            this.DrawPropertyField(EditorHelper.PROP_SCRIPT);



            var cache = SPGUI.DisableIfPlaying();

            this.DrawPropertyField(PROP_NOTIFTYPE);

            var useGlobalProp = this.serializedObject.FindProperty(PROP_USEGLOBAL);
            var targetProp    = this.serializedObject.FindProperty(PROP_TARGET);

            SPEditorGUILayout.PropertyField(useGlobalProp);
            if (useGlobalProp.boolValue)
            {
                targetProp.objectReferenceValue = null;
            }
            else
            {
                SPEditorGUILayout.PropertyField(targetProp);
            }

            cache.Reset();



            this.DrawDefaultInspectorExcept(EditorHelper.PROP_SCRIPT, PROP_NOTIFTYPE, PROP_USEGLOBAL, PROP_TARGET);

            this.serializedObject.ApplyModifiedProperties();
        }
        public override void OnGUI(Rect position, SerializedProperty property, GUIContent label)
        {
            var cache = SPGUI.DisableIfPlaying();

            /*
             * Component[] states = null;
             * var src = GameObjectUtil.GetGameObjectFromSource(property.serializedObject.targetObject);
             * if (src != null) states = ParentComponentStateSupplier<IAIState>.GetComponentsOnTarg(src, false).Cast<Component>().ToArray();
             * else states = new Component[] { };
             *
             * var componentLabels = (from c in states select EditorHelper.TempContent(string.Format("{0} ({1})", c.name, c.GetType().Name))).ToArray();
             * property.objectReferenceValue = SPEditorGUI.SelectComponentField(position, label, states, componentLabels, property.objectReferenceValue as Component);
             *
             * cache.Reset();
             */

            Component[] states = null;
            var         src    = GameObjectUtil.GetGameObjectFromSource(property.serializedObject.targetObject);

            if (src != null)
            {
                states = ParentComponentStateSupplier <IAIState> .GetComponentsOnTarg(src, false).Cast <Component>().Prepend(null).ToArray();
            }
            else
            {
                states = new Component[] { }
            };

            var componentLabels = (from c in states select(c != null) ? EditorHelper.TempContent(string.Format("{0} ({1})", c.name, c.GetType().Name)) : EditorHelper.TempContent("...Nothing")).ToArray();

            property.objectReferenceValue = SPEditorGUI.SelectComponentField(position, label, states, componentLabels, property.objectReferenceValue as Component);

            cache.Reset();
        }
    }
        private void OnGUI()
        {
            //draw header
            if (Application.isPlaying)
            {
                var cache = SPGUI.Disable();
                EditorGUILayout.ObjectField("Current Target: ", _ai, typeof(AITreeController), true);
                cache.Reset();
            }
            else
            {
                var         rect = EditorGUILayout.GetControlRect();
                Rect        r1, r2;
                const float BTN_WIDTH = 150f;
                if (rect.width > BTN_WIDTH * 2f)
                {
                    r1 = new Rect(rect.xMin, rect.yMin, rect.width - BTN_WIDTH, rect.height);
                    r2 = new Rect(r1.xMax, rect.yMin, BTN_WIDTH, rect.height);
                }
                else
                {
                    var w = rect.width / 2f;
                    r1 = new Rect(rect.xMin, rect.yMin, w, rect.height);
                    r2 = new Rect(r1.xMax, rect.yMin, w, rect.height);
                }

                var cache = SPGUI.Disable();
                EditorGUI.ObjectField(r1, "Current Target: ", _ai, typeof(AITreeController), true);
                cache.Reset();

                if (GUI.Button(r2, "Sync Actions"))
                {
                    this.SyncActions();
                }
            }

            //if we're not configured correctly, stop
            if (_ai == null)
            {
                return;
            }
            if (_currentTable == null)
            {
                this.CleanCurrentState();
            }

            //draw actions
            _scrollPosition = EditorGUILayout.BeginScrollView(_scrollPosition);
            try
            {
                this.DrawNode(_ai);
                //this.DrawActionGroup(_ai);
            }
            catch (System.Exception ex)
            {
                Debug.LogException(ex);
            }
            EditorGUILayout.EndScrollView();
        }
        public override void OnGUI(Rect position, SerializedProperty property, GUIContent label)
        {
            if (EditorHelper.AssertMultiObjectEditingNotSupported(position, property, label))
            {
                return;
            }

            this.Init(property, label);

            var cache = SPGUI.DisableIfPlaying();

            _maskList.DoList(position);

            cache.Reset();
        }
Exemple #5
0
        private void DrawReadOnlyInspector(Singleton.ConfigAttribute attrib)
        {
            this.DrawPropertyField(EditorHelper.PROP_SCRIPT);

            var prop = this.serializedObject.FindProperty("_maintainer._lifeCycle");

            if (prop.GetEnumValue <SingletonLifeCycleRule>() != attrib.DefaultLifeCycle)
            {
                prop.SetEnumValue(attrib.DefaultLifeCycle);
            }

            var cache = SPGUI.Disable();

            EditorGUILayout.EnumPopup("Life Cycle", prop.GetEnumValue <SingletonLifeCycleRule>());
            cache.Reset();

            this.DrawDefaultInspectorExcept(EditorHelper.PROP_SCRIPT, "_maintainer");
        }
Exemple #6
0
        protected void DrawSPAnimationControllerProps()
        {
            if (Application.isPlaying)
            {
                var targ = this.target as SPAnimationController;
                if (targ == null)
                {
                    return;
                }

                EditorGUI.BeginChangeCheck();
                var b1 = EditorGUILayout.Toggle("Animate Physics", targ.AnimatePhysics);
                if (EditorGUI.EndChangeCheck())
                {
                    targ.AnimatePhysics = b1;
                }


                EditorGUI.BeginChangeCheck();
                var ectp = (AnimationCullingType)EditorGUILayout.EnumPopup("Culling Type", targ.CullingType);
                if (EditorGUI.EndChangeCheck())
                {
                    targ.CullingType = ectp;
                }

                var cache = SPGUI.Disable();
                this.DrawPropertyField(PROP_TIMESUPPLIER);
                this.DrawPropertyField(PROP_SPEED);
                this.DrawPropertyField(PROP_MASK);
                cache.Reset();
                this.DrawPropertyField(PROP_STATES);
            }
            else
            {
                this.DrawPropertyField(PROP_ANIMATEPHYSICS, "Animate Physics", false);
                this.DrawPropertyField(PROP_ANIMCULLING, "Culling Type", false);
                this.DrawPropertyField(PROP_TIMESUPPLIER);
                this.DrawPropertyField(PROP_SPEED);
                this.DrawPropertyField(PROP_MASK);
                this.DrawPropertyField(PROP_STATES);
            }
        }
Exemple #7
0
        public override void OnGUI(Rect position, SerializedProperty property, GUIContent label)
        {
            var  e    = (ParallelPassOptions)property.intValue;
            bool both = ((e & BOTH_ANY) == BOTH_ANY);

            bool failAny   = e.HasFlag(ParallelPassOptions.FailOnAny);
            bool passAny   = e.HasFlag(ParallelPassOptions.SucceedOnAny);
            bool passOnTie = e.HasFlag(ParallelPassOptions.SucceedOnTie);

            var r1 = new Rect(position.xMin, position.yMin, position.width, EditorGUIUtility.singleLineHeight);
            var r2 = new Rect(position.xMin, r1.yMax, position.width, EditorGUIUtility.singleLineHeight);
            var r3 = new Rect(position.xMin, r2.yMax, position.width, EditorGUIUtility.singleLineHeight);

            EditorGUI.BeginChangeCheck();

            failAny = EditorGUI.Popup(r1, "Fail", (failAny) ? 1 : 0, new string[] { "All", "Any" }) == 1;
            passAny = EditorGUI.Popup(r2, "Succeed", (passAny) ? 1 : 0, new string[] { "All", "Any" }) == 1;

            var cache = SPGUI.DisableIf(both);

            passOnTie = EditorGUI.Popup(r3, "Tie Breaker", (passOnTie) ? 1 : 0, new string[] { "Fail", "Succeed" }) == 1;
            cache.Reset();

            if (EditorGUI.EndChangeCheck())
            {
                e = 0;
                if (failAny)
                {
                    e |= ParallelPassOptions.FailOnAny;
                }
                if (passAny)
                {
                    e |= ParallelPassOptions.SucceedOnAny;
                }
                if (passOnTie)
                {
                    e |= ParallelPassOptions.SucceedOnTie;
                }
                property.intValue = (int)e;
            }
        }
        public override void OnGUI(Rect position, SerializedProperty property, GUIContent label)
        {
            if (EditorHelper.AssertMultiObjectEditingNotSupported(position, property, label))
            {
                return;
            }

            var cache = SPGUI.DisableIfPlaying();

            _property = property;

            GUI.Box(position, GUIContent.none);

            var r0 = new Rect(position.xMin, position.yMin, position.width, EditorGUIUtility.singleLineHeight);

            _matPropRefDrawer.OnGUI(r0, property, label); //because we mirror the properties of MaterialPropertyReference, this works
            position = new Rect(position.xMin, r0.yMax, position.width, position.height - r0.height);

            EditorGUI.indentLevel++;

            _valuesProp = property.FindPropertyRelative(PROP_VALUES);
            var lst = CachedReorderableList.GetListDrawer(_valuesProp, _valuesList_DrawHeader, _valuesList_DrawElement);

            lst.headerHeight  = 0f;
            lst.elementHeight = EditorGUIUtility.singleLineHeight;

            var r2 = new Rect(position.xMin, position.yMin, position.width, lst.GetHeight());
            var r3 = new Rect(position.xMin, position.yMax - EditorGUIUtility.singleLineHeight * 1.25f, position.width, EditorGUIUtility.singleLineHeight);

            //lst.DoList(EditorGUI.IndentedRect(r2));
            lst.DoList(r2);
            EditorGUI.PropertyField(r3, property.FindPropertyRelative(PROP_POSITION));

            EditorGUI.indentLevel--;

            _property   = null;
            _valuesProp = null;

            cache.Reset();
        }
Exemple #9
0
        protected override void OnSPInspectorGUI()
        {
            this.serializedObject.Update();

            var targ = this.target as AIController;

            if (targ == null)
            {
                return;
            }

            this.DrawPropertyField(EditorHelper.PROP_SCRIPT);

            var sourceProp = this.serializedObject.FindProperty(PROP_STATESOURCE);

            SPEditorGUILayout.PropertyField(sourceProp);

            var cache     = SPGUI.DisableIfPlaying();
            var stateProp = this.serializedObject.FindProperty(PROP_DEFAULTSTATE);

            switch (sourceProp.GetEnumValue <AIStateMachineSourceMode>())
            {
            case AIStateMachineSourceMode.SelfSourced:
            {
                var states = ComponentStateSupplier <IAIState> .GetComponentsOnTarg(targ.gameObject).Cast <Component>().ToArray();

                stateProp.objectReferenceValue = SPEditorGUILayout.SelectComponentField(stateProp.displayName, states, stateProp.objectReferenceValue as Component);
            }
            break;

            case AIStateMachineSourceMode.ChildSourced:
            {
                var states = ParentComponentStateSupplier <IAIState> .GetComponentsOnTarg(targ.gameObject, false);

                var names = (from s in states select EditorHelper.TempContent(GameObjectUtil.GetGameObjectFromSource(s).name + " (" + s.GetType().Name + ")")).ToArray();
                int i     = states.IndexOf(stateProp.objectReferenceValue);
                i = EditorGUILayout.Popup(EditorHelper.TempContent(stateProp.displayName), i, names);
                stateProp.objectReferenceValue = (i >= 0) ? states[i] as UnityEngine.Object : null;
            }
            break;

            default:
            {
                var states = ArrayUtil.Empty <Component>();
                stateProp.objectReferenceValue = SPEditorGUILayout.SelectComponentField(stateProp.displayName, states, stateProp.objectReferenceValue as Component);
            }
            break;
            }

            cache.Reset();


            this.DrawDefaultInspectorExcept(EditorHelper.PROP_SCRIPT, PROP_STATESOURCE, PROP_DEFAULTSTATE);

            this.serializedObject.ApplyModifiedProperties();


            if (Application.isPlaying)
            {
                if (targ.States != null && targ.States.Current != null)
                {
                    var c   = targ.States.Current;
                    var msg = string.Format("Currently active state is {0} ({1}).", c.DisplayName, c.GetType().Name);
                    EditorGUILayout.HelpBox(msg, MessageType.Info);
                }
                else
                {
                    EditorGUILayout.HelpBox("Currently active state is null.", MessageType.Info);
                }
            }
        }
        public static Rect DrawTimeSupplier(Rect position, SerializedProperty property, float desiredWidth, string[] availableNames)
        {
            if (position.width <= 0f)
            {
                return(position);
            }

            var r = new Rect(position.xMin, position.yMin, Mathf.Min(position.width, desiredWidth), position.height);

            var tsTypeProp = property.FindPropertyRelative(PROP_TIMESUPPLIERTYPE);
            var tsNameProp = property.FindPropertyRelative(PROP_TIMESUPPLIERNAME);

            int index = -1;

            using (var lst = TempCollection.GetList <string>())
            {
                lst.Add("Normal");
                lst.Add("Real");
                lst.Add("Smooth");

                foreach (var nm in CustomTimeLayersData.Layers)
                {
                    if (!lst.Contains(nm))
                    {
                        lst.Add(nm);
                    }
                }

                if (availableNames != null)
                {
                    foreach (var nm in availableNames)
                    {
                        if (!lst.Contains(nm))
                        {
                            lst.Add(nm);
                        }
                    }
                }

                var e = tsTypeProp.GetEnumValue <DeltaTimeType>();
                if (e == DeltaTimeType.Custom)
                {
                    index = lst.IndexOf(tsNameProp.stringValue);
                    if (index < 0)
                    {
                        tsTypeProp.SetEnumValue(DeltaTimeType.Normal);
                        tsNameProp.stringValue = null;
                        index = 0;
                    }
                }
                else
                {
                    index = (int)e;
                }

                var cache = SPGUI.DisableIfPlaying();
                EditorGUI.BeginChangeCheck();
                index = Mathf.Max(EditorGUI.Popup(position, index, lst.ToArray()), 0);
                if (EditorGUI.EndChangeCheck())
                {
                    if (index < 3)
                    {
                        tsTypeProp.SetEnumValue((DeltaTimeType)index);
                        tsNameProp.stringValue = null;
                    }
                    else
                    {
                        tsTypeProp.SetEnumValue(DeltaTimeType.Custom);
                        tsNameProp.stringValue = lst[index];
                    }
                }
                cache.Reset();
            }

            return(new Rect(r.xMax, position.yMin, Mathf.Max(position.width - r.width, 0f), position.height));
        }
Exemple #11
0
        protected override void OnSPInspectorGUI()
        {
            this.serializedObject.Update();

            this.DrawDefaultInspectorExcept("_target", "_memberName", "_value", "_mode");
            this.DrawPropertyField("_target"); //uses the SelectableComponent PropertyDrawer

            var targProp   = this.serializedObject.FindProperty("_target");
            var memberProp = this.serializedObject.FindProperty("_memberName");
            var valueProp  = this.serializedObject.FindProperty("_value");
            var modeProp   = this.serializedObject.FindProperty("_mode");

            //SELECT MEMBER
            System.Reflection.MemberInfo selectedMember;
            memberProp.stringValue = SPEditorGUILayout.ReflectedRecursingPropertyField(EditorHelper.TempContent("Property", "The property on the target to set."),
                                                                                       targProp.objectReferenceValue,
                                                                                       memberProp.stringValue,
                                                                                       com.spacepuppy.Dynamic.DynamicMemberAccess.ReadWrite,
                                                                                       out selectedMember);
            this.serializedObject.ApplyModifiedProperties();


            //MEMBER VALUE TO SET TO
            if (selectedMember != null)
            {
                var propType = com.spacepuppy.Dynamic.DynamicUtil.GetInputType(selectedMember);
                var emode    = modeProp.GetEnumValue <i_SetValue.SetMode>();
                if (emode == i_SetValue.SetMode.Toggle)
                {
                    //EditorGUILayout.LabelField(EditorHelper.TempContent(valueProp.displayName), EditorHelper.TempContent(propType.Name));
                    var evtp  = VariantReference.GetVariantType(propType);
                    var cache = SPGUI.Disable();
                    EditorGUILayout.EnumPopup(EditorHelper.TempContent(valueProp.displayName), evtp);
                    cache.Reset();
                }
                else
                {
                    if (DynamicUtil.TypeIsVariantSupported(propType))
                    {
                        //draw the default variant as the method accepts anything
                        _variantDrawer.RestrictVariantType = false;
                        _variantDrawer.ForcedObjectType    = null;
                        var label = EditorHelper.TempContent("Value", "The value to set to.");
                        _variantDrawer.OnGUI(EditorGUILayout.GetControlRect(true, _variantDrawer.GetPropertyHeight(valueProp, label)), valueProp, label);
                    }
                    else
                    {
                        _variantDrawer.RestrictVariantType = true;
                        _variantDrawer.TypeRestrictedTo    = propType;
                        _variantDrawer.ForcedObjectType    = (TypeUtil.IsType(propType, typeof(UnityEngine.Object))) ? propType : null;
                        var label = EditorHelper.TempContent("Value", "The value to set to.");
                        _variantDrawer.OnGUI(EditorGUILayout.GetControlRect(true, _variantDrawer.GetPropertyHeight(valueProp, label)), valueProp, label);
                    }
                }

                if (com.spacepuppy.Dynamic.Evaluator.WillArithmeticallyCompute(propType))
                {
                    EditorGUILayout.PropertyField(modeProp);
                }
                else
                {
                    //modeProp.SetEnumValue(i_SetValue.SetMode.Set);
                    EditorGUI.BeginChangeCheck();
                    emode = (i_SetValue.SetMode)SPEditorGUILayout.EnumPopupExcluding(EditorHelper.TempContent(modeProp.displayName), emode, i_SetValue.SetMode.Decrement, i_SetValue.SetMode.Increment);
                    if (EditorGUI.EndChangeCheck())
                    {
                        modeProp.SetEnumValue(emode);
                    }
                }
            }
            else
            {
                modeProp.SetEnumValue(i_SetValue.SetMode.Set);
            }

            this.serializedObject.ApplyModifiedProperties();
        }
Exemple #12
0
        public void DrawDetails(Rect position, SerializedProperty property)
        {
            var cache = SPGUI.DisableIfPlaying();

            //draw basic details
            var yMin = position.yMin;

            for (int i = 0; i < _detailProps.Length; i++)
            {
                //var r = new Rect(position.xMin, yMin + i * EditorGUIUtility.singleLineHeight, position.width, EditorGUIUtility.singleLineHeight);
                switch (_detailProps[i])
                {
                case SPAnimClip.PROP_WRAPMODE:
                {
                    var r = new Rect(position.xMin, position.yMin, position.width, EditorGUIUtility.singleLineHeight);
                    position = new Rect(position.xMin, r.yMax, position.width, Mathf.Max(position.height - r.height, 0f));

                    var wrapModeProp = property.FindPropertyRelative(SPAnimClip.PROP_WRAPMODE);
                    wrapModeProp.SetEnumValue(SPEditorGUI.WrapModeField(r, wrapModeProp.displayName, wrapModeProp.GetEnumValue <WrapMode>(), true));
                }
                break;

                case "ScaledDuration":
                {
                    var r = new Rect(position.xMin, position.yMin, position.width, EditorGUIUtility.singleLineHeight);
                    position = new Rect(position.xMin, r.yMax, position.width, Mathf.Max(position.height - r.height, 0f));

                    var label = EditorHelper.TempContent("Scaled Duration", "The duration of the clip with the speed applied. Modifying this alters the 'speed' property.");
                    var clip  = property.FindPropertyRelative(PROP_CLIP).objectReferenceValue as AnimationClip;
                    if (clip == null)
                    {
                        EditorGUI.FloatField(r, label, 0f);
                        continue;
                    }

                    var   speedProp = property.FindPropertyRelative(SPAnimClip.PROP_SPEED);
                    float dur       = (speedProp.floatValue == 0f) ? float.PositiveInfinity : Mathf.Abs(clip.length / speedProp.floatValue);
                    EditorGUI.BeginChangeCheck();

                    dur = EditorGUI.FloatField(r, label, dur);

                    if (EditorGUI.EndChangeCheck())
                    {
                        speedProp.floatValue = (dur <= 0f) ? 0f : clip.length / dur;
                    }
                }
                break;

                default:
                {
                    var r = new Rect(position.xMin, position.yMin, position.width, EditorGUIUtility.singleLineHeight);
                    position = new Rect(position.xMin, r.yMax, position.width, Mathf.Max(position.height - r.height, 0f));

                    EditorGUI.PropertyField(r, property.FindPropertyRelative(_detailProps[i]));
                }
                break;
                }
            }

            cache.Reset();
        }
Exemple #13
0
        public void DrawClip(Rect area, SerializedProperty property, GUIContent label, float labelWidth, GUIStyle labelStyle, bool nameIsReadonly)
        {
            //Draw Name
            var nameProp = property.FindPropertyRelative(PROP_NAME);

            var labelRect = new Rect(area.xMin, area.yMin, labelWidth, EditorGUIUtility.singleLineHeight);
            var textRect  = new Rect(labelRect.xMax, area.yMin, (area.width - labelWidth) * 0.4f, EditorGUIUtility.singleLineHeight);

            EditorGUI.BeginProperty(area, label, nameProp);
            //EditorGUI.LabelField(labelRect, label, labelStyle);
            GUI.Label(labelRect, label, labelStyle);
            if (nameIsReadonly || _nameIsReadOnly || Application.isPlaying)
            {
                //EditorGUI.LabelField(textRect, nameProp.stringValue, GUI.skin.textField);
                GUI.Label(textRect, nameProp.stringValue, GUI.skin.textField);
            }
            else
            {
                //nameProp.stringValue = EditorGUI.TextField(textRect, nameProp.stringValue);
                nameProp.stringValue = GUI.TextField(textRect, nameProp.stringValue);
            }
            //EditorGUI.EndProperty();

            var cache = SPGUI.DisableIfPlaying();

            //Draw Animation Clip Reference
            var clipProp  = property.FindPropertyRelative(PROP_CLIP);
            var xmin      = textRect.xMax + 2f;
            var clipRect  = new Rect(xmin, area.yMin, area.xMax - xmin, EditorGUIUtility.singleLineHeight);
            var clipLabel = GUIContent.none;
            //EditorGUI.BeginProperty(clipRect, clipLabel, clipProp);
            //clipProp.objectReferenceValue = EditorGUI.ObjectField(clipRect, clipProp.objectReferenceValue, typeof(AnimationClip), false);
            var obj = clipProp.objectReferenceValue;

            if (GameObjectUtil.IsGameObjectSource(obj))
            {
                if (_selectComponentDrawer == null)
                {
                    _selectComponentDrawer = new SelectableComponentPropertyDrawer();
                    _selectComponentDrawer.RestrictionType = typeof(IScriptableAnimationClip);
                    _selectComponentDrawer.ShowXButton     = true;
                }
                _selectComponentDrawer.OnGUI(clipRect, clipProp, GUIContent.none);
            }
            else
            {
                obj = EditorGUI.ObjectField(clipRect, obj, typeof(UnityEngine.Object), true);
                if (obj == null || obj is AnimationClip || obj is IScriptableAnimationClip)
                {
                    clipProp.objectReferenceValue = obj;
                }
                else if (GameObjectUtil.IsGameObjectSource(obj))
                {
                    clipProp.objectReferenceValue = ObjUtil.GetAsFromSource <IScriptableAnimationClip>(obj) as UnityEngine.Object;
                }
            }
            EditorGUI.EndProperty();

            cache.Reset();



            if (Application.isPlaying && !property.hasMultipleDifferentValues && property.serializedObject.targetObject is SPLegacyAnimController)
            {
                if (GUI.Button(new Rect(area.xMin, area.yMin, 20f, EditorGUIUtility.singleLineHeight), ">"))
                {
                    var targ = property.serializedObject.targetObject as SPLegacyAnimController;
                    targ.Play(nameProp.stringValue);
                }
            }
        }
Exemple #14
0
        public override void OnGUI(Rect position, SerializedProperty property, GUIContent label)
        {
            this.Init(property);

            EditorGUI.BeginProperty(position, label, property);

            //################################
            //FIRST LINE
            var rect = new Rect(position.xMin, position.yMin, position.width, EditorGUIUtility.singleLineHeight);

            var configProp = property.FindPropertyRelative(PROP_CONFIGURED);
            var targetProp = property.FindPropertyRelative(PROP_TARGET);
            var findProp   = property.FindPropertyRelative(PROP_FIND);

            //var r0 = new Rect(rect.xMin, rect.yMin, EditorGUIUtility.labelWidth, rect.height);
            //rect = new Rect(r0.xMax, rect.yMin, rect.width - r0.width, rect.height);
            //property.isExpanded = EditorGUI.Foldout(r0, property.isExpanded, label);
            if (!this.AlwaysExpanded)
            {
                property.isExpanded = SPEditorGUI.PrefixFoldoutLabel(ref rect, property.isExpanded, label);
            }
            else
            {
                rect = EditorGUI.PrefixLabel(rect, label);
            }

            var r0 = new Rect(rect.xMin, rect.yMin, Mathf.Min(rect.width * 0.25f, 50f), rect.height);
            var e  = (configProp.boolValue) ? TargetSource.Config : TargetSource.Arg;

            EditorGUI.BeginChangeCheck();
            e = (TargetSource)EditorGUI.EnumPopup(r0, e);
            if (EditorGUI.EndChangeCheck())
            {
                UpdateTargetFromSource(targetProp, e);
                configProp.boolValue = (e != TargetSource.Arg);
                if (e != TargetSource.Arg)
                {
                    findProp.SetEnumValue(TriggerableTargetObject.FindCommand.Direct);
                }
            }
            else if (e == TargetSource.Config && !_defaultSet && targetProp.objectReferenceValue == null)
            {
                UpdateTargetFromSource(targetProp, e);
                _defaultSet = true;
            }
            else
            {
                _defaultSet = true;
            }

            var r1 = new Rect(rect.xMin + r0.width, rect.yMin, rect.width - r0.width, rect.height);

            if (!configProp.boolValue)
            {
                var e0 = findProp.GetEnumValue <TriggerableTargetObject.FindCommand>();
                switch (e0)
                {
                case TriggerableTargetObject.FindCommand.Direct:
                    EditorGUI.LabelField(r1, "Target determined by activating trigger.");
                    break;

                case TriggerableTargetObject.FindCommand.FindParent:
                case TriggerableTargetObject.FindCommand.FindInChildren:
                case TriggerableTargetObject.FindCommand.FindInEntity:
                    EditorGUI.LabelField(r1, e0.ToString() + " of activating trigger arg.");
                    break;

                case TriggerableTargetObject.FindCommand.FindInScene:
                case TriggerableTargetObject.FindCommand.FindEntityInScene:
                default:
                    configProp.boolValue            = false;
                    targetProp.objectReferenceValue = null;
                    EditorGUI.LabelField(r1, e0.ToString());
                    break;
                }

                targetProp.objectReferenceValue = null;
            }
            else
            {
                _objectDrawer.OnGUI(r1, targetProp, GUIContent.none);
            }


            //################################
            //SECOND LINE
            if (this.AlwaysExpanded || property.isExpanded)
            {
                var indent = EditorGUIUtility.labelWidth * 0.5f;
                rect = new Rect(position.xMin + indent, position.yMin + EditorGUIUtility.singleLineHeight, Mathf.Max(0f, position.width - indent), EditorGUIUtility.singleLineHeight);

                var w0 = Mathf.Min(rect.width * 0.3f, 120f);
                var w1 = Mathf.Min(rect.width * 0.3f, 80f);
                var w2 = rect.width - w0 - w1;
                r0 = new Rect(rect.xMin, rect.yMin, w0, rect.height);
                r1 = new Rect(r0.xMax, rect.yMin, w1, rect.height);
                var r2 = new Rect(r1.xMax, rect.yMin, w2, rect.height);

                var resolveProp = property.FindPropertyRelative(PROP_RESOLVEBY);
                var queryProp   = property.FindPropertyRelative(PROP_QUERY);

                var e0 = findProp.GetEnumValue <TriggerableTargetObject.FindCommand>();
                EditorGUI.BeginChangeCheck();
                e0 = (TriggerableTargetObject.FindCommand)EditorGUI.EnumPopup(r0, e0);
                if (EditorGUI.EndChangeCheck())
                {
                    findProp.SetEnumValue(e0);
                }
                switch (e0)
                {
                case TriggerableTargetObject.FindCommand.FindInScene:
                case TriggerableTargetObject.FindCommand.FindEntityInScene:
                    configProp.boolValue            = false;
                    targetProp.objectReferenceValue = null;
                    break;
                }

                var e1 = resolveProp.GetEnumValue <TriggerableTargetObject.ResolveByCommand>();
                EditorGUI.BeginChangeCheck();
                e1 = (TriggerableTargetObject.ResolveByCommand)EditorGUI.EnumPopup(r1, e1);
                if (EditorGUI.EndChangeCheck())
                {
                    resolveProp.SetEnumValue(e1);
                }

                switch (e1)
                {
                case TriggerableTargetObject.ResolveByCommand.Nothing:
                {
                    var cache = SPGUI.Disable();
                    EditorGUI.TextField(r2, string.Empty);
                    queryProp.stringValue = string.Empty;
                    cache.Reset();
                }
                break;

                case TriggerableTargetObject.ResolveByCommand.WithTag:
                {
                    queryProp.stringValue = EditorGUI.TagField(r2, queryProp.stringValue);
                }
                break;

                case TriggerableTargetObject.ResolveByCommand.WithName:
                {
                    queryProp.stringValue = EditorGUI.TextField(r2, queryProp.stringValue);
                }
                break;

                case TriggerableTargetObject.ResolveByCommand.WithType:
                {
                    var tp = TypeUtil.FindType(queryProp.stringValue);
                    if (!TypeUtil.IsType(tp, typeof(UnityEngine.Object)))
                    {
                        tp = null;
                    }
                    tp = SPEditorGUI.TypeDropDown(r2, GUIContent.none, typeof(UnityEngine.Object), tp);
                    queryProp.stringValue = (tp != null) ? tp.FullName : null;
                }
                break;
                }
            }

            EditorGUI.EndProperty();
        }
        private void DrawValueFieldInValueMode(Rect position, SerializedProperty property, VariantReference.EditorHelper helper)
        {
            if (helper.Target == null)
            {
                return;
            }
            var variant = helper.Target;

            if (this.RestrictVariantType && helper._type != this.VariantTypeRestrictedTo)
            {
                helper.PrepareForValueTypeChange(this.VariantTypeRestrictedTo);
                GUI.changed = true; //force change
            }

            var r0 = new Rect(position.xMin, position.yMin, 90.0f, EditorGUIUtility.singleLineHeight);
            var r1 = new Rect(r0.xMax, position.yMin, position.xMax - r0.xMax, EditorGUIUtility.singleLineHeight);

            var cache = SPGUI.DisableIf(this.RestrictVariantType);

            EditorGUI.BeginChangeCheck();
            var valueType = (VariantType)EditorGUI.EnumPopup(r0, GUIContent.none, variant.ValueType);

            if (EditorGUI.EndChangeCheck())
            {
                helper.PrepareForValueTypeChange(valueType);
            }
            cache.Reset();

            if (_typeRestrictedTo.IsEnum)
            {
                variant.IntValue = ConvertUtil.ToInt(EditorGUI.EnumPopup(r1, ConvertUtil.ToEnumOfType(_typeRestrictedTo, variant.IntValue)));
            }
            else
            {
                switch (valueType)
                {
                case VariantType.Null:
                    cache = SPGUI.Disable();
                    EditorGUI.TextField(r1, "Null");
                    cache.Reset();
                    break;

                case VariantType.String:
                    variant.StringValue = EditorGUI.TextField(r1, variant.StringValue);
                    break;

                case VariantType.Boolean:
                    variant.BoolValue = EditorGUI.Toggle(r1, variant.BoolValue);
                    break;

                case VariantType.Integer:
                    variant.IntValue = EditorGUI.IntField(r1, variant.IntValue);
                    break;

                case VariantType.Float:
                    variant.FloatValue = EditorGUI.FloatField(r1, variant.FloatValue);
                    break;

                case VariantType.Double:
                    variant.DoubleValue = ConvertUtil.ToDouble(EditorGUI.TextField(r1, variant.DoubleValue.ToString()));
                    break;

                case VariantType.Vector2:
                    variant.Vector2Value = EditorGUI.Vector2Field(r1, GUIContent.none, variant.Vector2Value);
                    break;

                case VariantType.Vector3:
                    variant.Vector3Value = EditorGUI.Vector3Field(r1, GUIContent.none, variant.Vector3Value);
                    break;

                case VariantType.Vector4:
                    variant.Vector4Value = EditorGUI.Vector4Field(r1, (string)null, variant.Vector4Value);
                    break;

                case VariantType.Quaternion:
                    variant.QuaternionValue = SPEditorGUI.QuaternionField(r1, GUIContent.none, variant.QuaternionValue);
                    break;

                case VariantType.Color:
                    variant.ColorValue = EditorGUI.ColorField(r1, variant.ColorValue);
                    break;

                case VariantType.DateTime:
                    variant.DateValue = ConvertUtil.ToDate(EditorGUI.TextField(r1, variant.DateValue.ToString()));
                    break;

                case VariantType.GameObject:
                    variant.GameObjectValue = EditorGUI.ObjectField(r1, variant.GameObjectValue, typeof(GameObject), true) as GameObject;
                    break;

                case VariantType.Component:
                {
                    _selectComponentDrawer.AllowNonComponents = false;
                    _selectComponentDrawer.RestrictionType    = _forcedObjectType;
                    _selectComponentDrawer.ShowXButton        = true;
                    var targProp = property.FindPropertyRelative("_unityObjectReference");
                    EditorGUI.BeginChangeCheck();
                    _selectComponentDrawer.OnGUI(r1, targProp);
                    if (EditorGUI.EndChangeCheck())
                    {
                        variant.ComponentValue = targProp.objectReferenceValue as Component;
                    }
                }
                break;

                case VariantType.Object:
                {
                    var obj = variant.ObjectValue;
                    if (ComponentUtil.IsAcceptableComponentType(_forcedObjectType))
                    {
                        if (obj is GameObject || obj is Component)
                        {
                            _selectComponentDrawer.AllowNonComponents = false;
                            _selectComponentDrawer.RestrictionType    = _forcedObjectType;
                            _selectComponentDrawer.ShowXButton        = true;
                            var targProp = property.FindPropertyRelative("_unityObjectReference");
                            EditorGUI.BeginChangeCheck();
                            _selectComponentDrawer.OnGUI(r1, targProp);
                            if (EditorGUI.EndChangeCheck())
                            {
                                variant.ObjectValue = targProp.objectReferenceValue as Component;
                            }
                        }
                        else
                        {
                            EditorGUI.BeginChangeCheck();
                            obj = EditorGUI.ObjectField(r1, obj, typeof(UnityEngine.Object), true);
                            if (EditorGUI.EndChangeCheck())
                            {
                                if (obj == null)
                                {
                                    variant.ObjectValue = null;
                                }
                                else if (TypeUtil.IsType(obj.GetType(), _forcedObjectType))
                                {
                                    variant.ObjectValue = obj;
                                }
                                else
                                {
                                    var go = GameObjectUtil.GetGameObjectFromSource(obj);
                                    if (go != null)
                                    {
                                        variant.ObjectValue = go.GetComponent(_forcedObjectType);
                                    }
                                    else
                                    {
                                        variant.ObjectValue = null;
                                    }
                                }
                            }
                        }
                    }
                    else
                    {
                        variant.ObjectValue = EditorGUI.ObjectField(r1, obj, _forcedObjectType, true);
                    }
                }
                break;

                case VariantType.LayerMask:
                {
                    variant.LayerMaskValue = SPEditorGUI.LayerMaskField(r1, GUIContent.none, (int)variant.LayerMaskValue);
                }
                break;

                case VariantType.Rect:
                {
                    variant.RectValue = EditorGUI.RectField(r1, variant.RectValue);
                }
                break;
                }
            }
        }
        protected Rect DrawPrimaryPortionOfInspector(Rect position, SerializedProperty property)
        {
            var r0 = new Rect(position.xMin, position.yMin, position.width, EditorGUIUtility.singleLineHeight);
            var r1 = new Rect(position.xMin, r0.yMax, position.width, EditorGUIUtility.singleLineHeight);
            var r2 = new Rect(position.xMin, r1.yMax, position.width, EditorGUIUtility.singleLineHeight);

            EditorGUI.PropertyField(r0, property.FindPropertyRelative(PROP_REPEAT));
            EditorGUI.PropertyField(r1, property.FindPropertyRelative(PROP_ALWAYSSUCEED));

            var eloop = property.FindPropertyRelative(PROP_MODE).GetEnumValue <ActionGroupType>();

            EditorGUI.PropertyField(r2, property.FindPropertyRelative(PROP_MODE), EditorHelper.TempContent("Loop Mode"));

            if (eloop == ActionGroupType.Parrallel)
            {
                EditorGUI.indentLevel++;

                var  propOptions = property.FindPropertyRelative(PROP_OPTIONS);
                var  e           = (ParallelPassOptions)propOptions.intValue;
                bool both        = ((e & BOTH_ANY) == BOTH_ANY);

                bool failAny   = e.HasFlag(ParallelPassOptions.FailOnAny);
                bool passAny   = e.HasFlag(ParallelPassOptions.SucceedOnAny);
                bool passOnTie = e.HasFlag(ParallelPassOptions.SucceedOnTie);

                var r3 = new Rect(position.xMin, r2.yMax, position.width, EditorGUIUtility.singleLineHeight);
                var r4 = new Rect(position.xMin, r3.yMax, position.width, EditorGUIUtility.singleLineHeight);
                var r5 = new Rect(position.xMin, r4.yMax, position.width, EditorGUIUtility.singleLineHeight);

                EditorGUI.BeginChangeCheck();

                failAny = EditorGUI.Popup(r3, "Fail", (failAny) ? 1 : 0, new string[] { "All", "Any" }) == 1;
                passAny = EditorGUI.Popup(r4, "Succeed", (passAny) ? 1 : 0, new string[] { "All", "Any" }) == 1;

                var cache = SPGUI.DisableIf(both);
                passOnTie = EditorGUI.Popup(r5, "Tie Breaker", (passOnTie) ? 1 : 0, new string[] { "Fail", "Succeed" }) == 1;
                cache.Reset();

                if (EditorGUI.EndChangeCheck())
                {
                    e = 0;
                    if (failAny)
                    {
                        e |= ParallelPassOptions.FailOnAny;
                    }
                    if (passAny)
                    {
                        e |= ParallelPassOptions.SucceedOnAny;
                    }
                    if (passOnTie)
                    {
                        e |= ParallelPassOptions.SucceedOnTie;
                    }
                    propOptions.intValue = (int)e;
                }

                EditorGUI.indentLevel--;

                return(new Rect(position.xMin, r5.yMax, position.width, position.yMax - r5.yMax));
            }
            else
            {
                return(new Rect(position.xMin, r2.yMax, position.width, position.yMax - r2.yMax));
            }
        }
        protected override void OnSPInspectorGUI()
        {
            this.serializedObject.Update();

            this.DrawDefaultInspectorExcept("_target", "_restrictedType", "_memberName", "_values", "_mode");
            this.DrawPropertyField("_target"); //uses the SelectableComponent PropertyDrawer
            this.DrawPropertyField("_restrictedType");
            this.serializedObject.ApplyModifiedProperties();

            var targProp         = this.serializedObject.FindProperty("_target");
            var restrictTypeProp = this.serializedObject.FindProperty("_restrictedType");
            var memberProp       = this.serializedObject.FindProperty("_memberName");
            var valuesArrProp    = this.serializedObject.FindProperty("_values");
            var modeProp         = this.serializedObject.FindProperty("_mode");

            var targetRef = EditorHelper.GetTargetObjectOfProperty(targProp) as TriggerableTargetObject;

            if (targetRef == null)
            {
                return;
            }

            //SELECT MEMBER
            System.Reflection.MemberInfo selectedMember = null;
            var restrictType = TypeReferencePropertyDrawer.GetTypeFromTypeReference(restrictTypeProp);

            if (restrictType == null && !targetRef.TargetsTriggerArg && targetRef.Target != null &&
                targetRef.Find == TriggerableTargetObject.FindCommand.Direct && targetRef.ResolveBy != TriggerableTargetObject.ResolveByCommand.WithType &&
                targetRef.Target.GetType() != restrictType)
            {
                memberProp.stringValue = SPEditorGUILayout.ReflectedPropertyField(EditorHelper.TempContent("Property", "The property on the target to set."),
                                                                                  targetRef.Target,
                                                                                  memberProp.stringValue,
                                                                                  com.spacepuppy.Dynamic.DynamicMemberAccess.ReadWrite,
                                                                                  out selectedMember,
                                                                                  true);
            }
            else
            {
                if (restrictType == null)
                {
                    if (targetRef.ResolveBy == TriggerableTargetObject.ResolveByCommand.WithType)
                    {
                        restrictType = TypeUtil.FindType(targetRef.ResolveByQuery);
                    }
                    if (restrictType == null)
                    {
                        restrictType = typeof(object);
                    }
                    else
                    {
                        TypeReferencePropertyDrawer.SetTypeToTypeReference(restrictTypeProp, restrictType);
                    }
                }
                memberProp.stringValue = SPEditorGUILayout.ReflectedPropertyField(EditorHelper.TempContent("Property", "The property on the target to set."),
                                                                                  restrictType,
                                                                                  memberProp.stringValue,
                                                                                  out selectedMember,
                                                                                  true);
            }
            this.serializedObject.ApplyModifiedProperties();


            //MEMBER VALUE TO SET TO
            if (selectedMember != null && selectedMember.MemberType == System.Reflection.MemberTypes.Method)
            {
                var methodInfo = selectedMember as System.Reflection.MethodInfo;
                if (methodInfo == null)
                {
                    return;
                }

                var parameters = methodInfo.GetParameters();
                valuesArrProp.arraySize = parameters.Length;

                for (int i = 0; i < parameters.Length; i++)
                {
                    var p         = parameters[i];
                    var valueProp = valuesArrProp.GetArrayElementAtIndex(i);
                    var propType  = p.ParameterType;

                    if (DynamicUtil.TypeIsVariantSupported(propType))
                    {
                        //draw the default variant as the method accepts anything
                        _variantDrawer.RestrictVariantType = false;
                        _variantDrawer.ForcedObjectType    = null;
                        var label = EditorHelper.TempContent("Parameter " + i.ToString(), "The value to set to.");
                        _variantDrawer.OnGUI(EditorGUILayout.GetControlRect(true, _variantDrawer.GetPropertyHeight(valueProp, label)), valueProp, label);
                    }
                    else
                    {
                        _variantDrawer.RestrictVariantType = true;
                        _variantDrawer.TypeRestrictedTo    = propType;
                        _variantDrawer.ForcedObjectType    = (TypeUtil.IsType(propType, typeof(UnityEngine.Object))) ? propType : null;
                        var label = EditorHelper.TempContent("Parameter " + i.ToString(), "The value to set to.");
                        _variantDrawer.OnGUI(EditorGUILayout.GetControlRect(true, _variantDrawer.GetPropertyHeight(valueProp, label)), valueProp, label);
                    }
                }

                modeProp.SetEnumValue(i_SetValueOnTarget.SetMode.Set);
            }
            else if (selectedMember != null)
            {
                var propType = com.spacepuppy.Dynamic.DynamicUtil.GetInputType(selectedMember);
                var emode    = modeProp.GetEnumValue <i_SetValueOnTarget.SetMode>();
                if (emode == i_SetValueOnTarget.SetMode.Toggle)
                {
                    //EditorGUILayout.LabelField(EditorHelper.TempContent(valueProp.displayName), EditorHelper.TempContent(propType.Name));
                    valuesArrProp.arraySize = 0;
                    var evtp  = VariantReference.GetVariantType(propType);
                    var cache = SPGUI.Disable();
                    EditorGUILayout.EnumPopup(EditorHelper.TempContent("Value"), evtp);
                    cache.Reset();
                }
                else
                {
                    valuesArrProp.arraySize = 1;
                    var valueProp = valuesArrProp.GetArrayElementAtIndex(0);
                    if (DynamicUtil.TypeIsVariantSupported(propType))
                    {
                        //draw the default variant as the method accepts anything
                        _variantDrawer.RestrictVariantType = false;
                        _variantDrawer.ForcedObjectType    = null;
                        var label = EditorHelper.TempContent("Value", "The value to set to.");
                        _variantDrawer.OnGUI(EditorGUILayout.GetControlRect(true, _variantDrawer.GetPropertyHeight(valueProp, label)), valueProp, label);
                    }
                    else
                    {
                        _variantDrawer.RestrictVariantType = true;
                        _variantDrawer.TypeRestrictedTo    = propType;
                        _variantDrawer.ForcedObjectType    = (TypeUtil.IsType(propType, typeof(UnityEngine.Object))) ? propType : null;
                        var label = EditorHelper.TempContent("Value", "The value to set to.");
                        _variantDrawer.OnGUI(EditorGUILayout.GetControlRect(true, _variantDrawer.GetPropertyHeight(valueProp, label)), valueProp, label);
                    }
                }

                if (com.spacepuppy.Dynamic.Evaluator.WillArithmeticallyCompute(propType))
                {
                    EditorGUILayout.PropertyField(modeProp);
                }
                else
                {
                    //modeProp.SetEnumValue(i_SetValueOnTarget.SetMode.Set);
                    EditorGUI.BeginChangeCheck();
                    emode = (i_SetValueOnTarget.SetMode)SPEditorGUILayout.EnumPopupExcluding(EditorHelper.TempContent(modeProp.displayName), emode, i_SetValueOnTarget.SetMode.Decrement, i_SetValueOnTarget.SetMode.Increment);
                    if (EditorGUI.EndChangeCheck())
                    {
                        modeProp.SetEnumValue(emode);
                    }
                }
            }
            else
            {
                modeProp.SetEnumValue(i_SetValueOnTarget.SetMode.Set);
            }

            this.serializedObject.ApplyModifiedProperties();
        }
Exemple #18
0
        protected override void OnSPInspectorGUI()
        {
            this.serializedObject.Update();
            var targ = this.target as ArmatureRig;

            this.DrawDefaultInspectorExcept("Joints");

            var cache = SPGUI.Disable();

            EditorGUILayout.FloatField("Mass", targ.CalculateMass());
            cache.Reset();

            EditorGUI.BeginChangeCheck();
            Rigidbody rootJoint = EditorGUILayout.ObjectField("Root Joint", targ.RootJoint, typeof(Rigidbody), true) as Rigidbody;

            if (EditorGUI.EndChangeCheck())
            {
                if (rootJoint != null)
                {
                    if (targ.JointCount == 0)
                    {
                        targ.SetJoints(new Rigidbody[] { rootJoint });
                    }
                    else
                    {
                        using (var lst = TempCollection.GetList <Rigidbody>(targ.Joints))
                        {
                            lst.Remove(rootJoint);
                            lst.Insert(0, rootJoint);
                            targ.SetJoints(lst);
                        }
                    }

                    this.serializedObject.Update();
                }
            }

            this.DrawPropertyField("Joints", true);

            //TODO - implement a button that allows removing and setting the bones of the rig

            EditorGUILayout.Separator();

            if (GUILayout.Button("Build Ragdoll Rig"))
            {
                //EditorApplication.ExecuteMenuItem("GameObject/Create Other/Ragdoll...");
                com.spacepuppyeditor.Base.SPCreateRagdollWizard.StartWizard();
            }

            if (GUILayout.Button("Generate Joint List"))
            {
                targ.ReloadJointList();
                targ.LoadJointListOnStart = false;
                this.serializedObject.Update();
            }

            bool bIsKinematic = false;

            if (targ.Joints.Count() > 0)
            {
                bIsKinematic = targ.Joints.First().isKinematic;
            }
            string msg = (bIsKinematic) ? "Set Joints Not Kinematic" : "Set Joints Kinematic";

            if (GUILayout.Button(msg))
            {
                targ.SetJointsKinematic(!bIsKinematic);
            }

            if (GUILayout.Button("Try Clear Ragdoll Rig"))
            {
                if (EditorUtility.DisplayDialog("WARNING!", "Are you sure you want to clear rig?", "Yes", "No"))
                {
                    //foreach (var t in targ.GetAllChildrenAndSelf())
                    //{
                    //    if (t.HasComponent<CharacterJoint>())
                    //    {
                    //        DestroyImmediate(t.GetComponent<CharacterJoint>());
                    //        DestroyImmediate(t.GetComponent<Collider>());
                    //        DestroyImmediate(t.GetComponent<Rigidbody>());
                    //    }
                    //}
                    targ.ReloadJointList();
                    foreach (var j in targ.Joints)
                    {
                        if (j.HasComponent <CharacterJoint>())
                        {
                            DestroyImmediate(j.GetComponent <CharacterJoint>());
                        }
                        DestroyImmediate(j.GetComponent <Collider>());
                        DestroyImmediate(j);
                    }
                    targ.SetJoints(null);
                    this.serializedObject.Update();
                }
            }

            if (GUILayout.Button("Clear Defined Joints"))
            {
                if (targ.Joints.Count() > 0)
                {
                    if (EditorUtility.DisplayDialog("WARNING!", "Are you sure you want to clear all defined joints?", "Yes", "No"))
                    {
                        foreach (var j in targ.Joints)
                        {
                            var go = j.gameObject;
                            DestroyImmediate(go.GetComponent <CharacterJoint>());
                            DestroyImmediate(go.GetComponent <Collider>());
                            DestroyImmediate(go.GetComponent <Rigidbody>());
                        }
                    }

                    targ.SetJoints(null);
                    this.serializedObject.Update();
                }
            }

            if (Application.isPlaying)
            {
                GUILayout.Space(10);

                if (!targ.Ragdolled)
                {
                    if (GUILayout.Button("Ragdoll..."))
                    {
                        targ.Ragdoll();
                    }
                }
                else
                {
                    if (GUILayout.Button("Undo Ragdoll..."))
                    {
                        targ.UndoRagdoll();
                    }
                }
            }
        }
        private void DrawAdvanced_CallMethodOnSelected(Rect area, SerializedProperty property)
        {
            //Draw Target
            var targRect  = new Rect(area.xMin, area.yMin, area.width, EditorGUIUtility.singleLineHeight);
            var targProp  = property.FindPropertyRelative(TriggerTargetProps.PROP_TRIGGERABLETARG);
            var targLabel = new GUIContent("Triggerable Target");
            var targGo    = GameObjectUtil.GetGameObjectFromSource(targProp.objectReferenceValue);
            var newTargGo = EditorGUI.ObjectField(targRect, targLabel, targGo, typeof(GameObject), true) as GameObject;

            if (newTargGo != targGo)
            {
                targGo = newTargGo;
                targProp.objectReferenceValue = (targGo != null) ? targGo.transform : null;
            }

            var targCompPopupRect = new Rect(area.xMin, targRect.yMax, area.width, EditorGUIUtility.singleLineHeight);

            if (targGo != null)
            {
                EditorGUI.BeginChangeCheck();
                var selectedComp = SPEditorGUI.SelectComponentFromSourceField(targCompPopupRect, "Target Component", targGo, targProp.objectReferenceValue as Component);
                if (EditorGUI.EndChangeCheck())
                {
                    targProp.objectReferenceValue = selectedComp;
                }
            }
            else
            {
                EditorGUI.LabelField(targCompPopupRect, "Target Component", "(First Select a Target)");
            }

            //Draw Method Name
            var methNameRect = new Rect(area.xMin, targCompPopupRect.yMax, area.width, EditorGUIUtility.singleLineHeight);

            System.Reflection.MemberInfo selectedMember = null;
            if (targProp.objectReferenceValue != null)
            {
                var methProp = property.FindPropertyRelative(TriggerTargetProps.PROP_METHODNAME);

                //var tp = targProp.objectReferenceValue.GetType();
                //var members = GetAvailableMethods(tp).ToArray();

                //var members = com.spacepuppy.Dynamic.DynamicUtil.GetEasilySerializedMembers(targProp.objectReferenceValue, System.Reflection.MemberTypes.Method).ToArray();
                var members = com.spacepuppy.Dynamic.DynamicUtil.GetEasilySerializedMembers(targProp.objectReferenceValue, System.Reflection.MemberTypes.All, spacepuppy.Dynamic.DynamicMemberAccess.Write).ToArray();
                System.Array.Sort(members, (a, b) => string.Compare(a.Name, b.Name, true));
                var memberNames = members.Select((m) => m.Name).ToArray();

                int index = System.Array.IndexOf(memberNames, methProp.stringValue);
                index = EditorGUI.Popup(methNameRect, new GUIContent("Method", "The method/prop on the target to call."), index, (from n in memberNames select new GUIContent(n)).ToArray());
                methProp.stringValue = (index >= 0) ? memberNames[index] : null;
                selectedMember       = (index >= 0) ? members[index] : null;
            }
            else
            {
                EditorGUI.Popup(methNameRect, new GUIContent("Method", "The method/prop on the target to call."), -1, new GUIContent[0]);
            }

            property.serializedObject.ApplyModifiedProperties();

            //Draw Triggerable Arg
            var parr = (selectedMember != null) ? com.spacepuppy.Dynamic.DynamicUtil.GetDynamicParameterInfo(selectedMember) : null;

            if (parr == null || parr.Length == 0)
            {
                //NO PARAMETERS
                _callMethodModeExtraLines = 1;

                var argRect      = new Rect(area.xMin, methNameRect.yMax, area.width, EditorGUIUtility.singleLineHeight);
                var argArrayProp = property.FindPropertyRelative(TriggerTargetProps.PROP_TRIGGERABLEARGS);
                if (argArrayProp.arraySize > 0)
                {
                    argArrayProp.arraySize = 0;
                    argArrayProp.serializedObject.ApplyModifiedProperties();
                }

                var cache = SPGUI.Disable();
                EditorGUI.LabelField(argRect, GUIContent.none, new GUIContent("*Zero Parameter Count*"));
                cache.Reset();
            }
            else
            {
                //MULTIPLE PARAMETERS - special case, does not support trigger event arg
                _callMethodModeExtraLines = parr.Length;

                var argArrayProp = property.FindPropertyRelative(TriggerTargetProps.PROP_TRIGGERABLEARGS);

                if (argArrayProp.arraySize != parr.Length)
                {
                    argArrayProp.arraySize = parr.Length;
                    argArrayProp.serializedObject.ApplyModifiedProperties();
                }

                EditorGUI.indentLevel++;
                for (int i = 0; i < parr.Length; i++)
                {
                    var paramType = parr[i].ParameterType;
                    var argRect   = new Rect(area.xMin, methNameRect.yMax + i * EditorGUIUtility.singleLineHeight, area.width, EditorGUIUtility.singleLineHeight);
                    var argProp   = argArrayProp.GetArrayElementAtIndex(i);

                    if (paramType == typeof(object))
                    {
                        //draw the default variant as the method accepts anything
                        _variantDrawer.RestrictVariantType = false;
                        _variantDrawer.ForcedObjectType    = null;
                        _variantDrawer.OnGUI(argRect, argProp, EditorHelper.TempContent("Arg " + i.ToString() + ": " + parr[i].ParameterName, "A parameter to be passed to the method if needed."));
                    }
                    else
                    {
                        var argType = VariantReference.GetVariantType(paramType);
                        _variantDrawer.RestrictVariantType     = true;
                        _variantDrawer.VariantTypeRestrictedTo = argType;
                        _variantDrawer.ForcedObjectType        = (paramType.IsInterface || TypeUtil.IsType(paramType, typeof(Component))) ? paramType : null;
                        _variantDrawer.OnGUI(argRect, argProp, EditorHelper.TempContent("Arg " + i.ToString() + ": " + parr[i].ParameterName, "A parameter to be passed to the method if needed."));
                    }
                }
                EditorGUI.indentLevel--;
            }
        }
        protected void DrawDefaultMaterialSourceInspector()
        {
            var prop   = this.serializedObject.FindProperty(PROP_RENDERER);
            var source = this.target as RendererMaterialSource;
            var go     = GameObjectUtil.GetGameObjectFromSource(source);

            if (go == null)
            {
                EditorGUILayout.HelpBox("MaterialSource can not find target GameObject it's attached to.", MessageType.Error);
                return;
            }

            if (Application.isPlaying)
            {
                var cache = SPGUI.Disable();
                this.DrawPropertyField(PROP_RENDERER);
                this.DrawPropertyField(PROP_MAKEUNIQUEONSTART);
                EditorGUILayout.Toggle("Is Unique", source.IsUnique);
                cache.Reset();
            }
            else
            {
                if (prop.objectReferenceValue != null && prop.objectReferenceValue is Renderer)
                {
                    var renderer = prop.objectReferenceValue as Renderer;
                    if (renderer.gameObject != go)
                    {
                        prop.objectReferenceValue = null;
                    }
                }

                var renderers = go.GetComponents <Renderer>();
                if (renderers.Length == 0)
                {
                    EditorGUILayout.HelpBox("MaterialSource can not find a Renderer on that GameObject it's attached to.", MessageType.Error);
                    return;
                }
                else
                {
                    var sources = go.GetComponents <RendererMaterialSource>();
                    if (sources.Length > renderers.Length)
                    {
                        Debug.LogWarning("There are too many MaterialSources attached to this GameObject. Removing extra.", go);
                        UnityEngine.Object.DestroyImmediate(this.target);
                        return;
                    }

                    renderers = renderers.Except((from s in sources where s.Renderer != null && s.Renderer != source.Renderer select s.Renderer)).ToArray();
                    var names = (from r in renderers select EditorHelper.TempContent(r.GetType().Name)).ToArray();
                    int index = renderers.IndexOf(source.Renderer);

                    index = EditorGUILayout.Popup(EditorHelper.TempContent("Renderer"), index, names);
                    if (index >= 0)
                    {
                        prop.objectReferenceValue = renderers[index];
                    }
                    else
                    {
                        prop.objectReferenceValue = null;
                    }
                }

                this.DrawPropertyField(PROP_MAKEUNIQUEONSTART);
            }
        }