Beispiel #1
0
    private void OnEnable()
    {
        questCache  = Resources.LoadAll <Quest>("Configuration");
        quest       = target as Quest;
        talkerCache = Resources.LoadAll <TalkerInformation>("Configuration").Where(x => x.Enable).ToArray();
        holder      = talkerCache.FirstOrDefault(x => x.QuestsStored.Contains(quest));
        itemCache   = Resources.LoadAll <ItemBase>("Configuration");

        lineHeight            = EditorGUIUtility.singleLineHeight;
        lineHeightSpace       = lineHeight + 2;
        _ID                   = serializedObject.FindProperty("_ID");
        title                 = serializedObject.FindProperty("title");
        description           = serializedObject.FindProperty("description");
        abandonable           = serializedObject.FindProperty("abandonable");
        group                 = serializedObject.FindProperty("group");
        questType             = serializedObject.FindProperty("questType");
        repeatFrequancy       = serializedObject.FindProperty("repeatFrequancy");
        timeUnit              = serializedObject.FindProperty("timeUnit");
        acceptCondition       = serializedObject.FindProperty("acceptCondition");
        beginDialogue         = serializedObject.FindProperty("beginDialogue");
        ongoingDialogue       = serializedObject.FindProperty("ongoingDialogue");
        completeDialogue      = serializedObject.FindProperty("completeDialogue");
        rewardItems           = serializedObject.FindProperty("rewardItems");
        _NPCToSubmit          = serializedObject.FindProperty("_NPCToSubmit");
        cmpltObjctvInOrder    = serializedObject.FindProperty("cmpltObjctvInOrder");
        objectives            = serializedObject.FindProperty("objectives");
        groupSelector         = new ObjectSelectionDrawer <QuestGroup>(group, "_name", "", "归属组", "无");
        npcSelector           = new ObjectSelectionDrawer <TalkerInformation>(_NPCToSubmit, "_name", talkerCache, "在此NPC处提交", "接取处NPC");
        acceptConditionDrawer = new ConditionGroupDrawer(serializedObject, acceptCondition, lineHeight, lineHeightSpace, "接取条件列表");
        rewardDrawer          = new ItemAmountListDrawer(serializedObject, rewardItems, lineHeight, lineHeightSpace, "奖励列表");
        HandlingObjectiveList();
        showState = new AnimBool(objectives.isExpanded);
        AddAnimaListener(OnAnima);
    }
Beispiel #2
0
 private void OnEnable()
 {
     globalVariables = serializedObject.FindProperty("globalVariables");
     presetVariables = serializedObject.FindProperty("presetVariables");
     globalDrawer    = new ObjectSelectionDrawer <GlobalVariables>(globalVariables, string.Empty, string.Empty, "全局变量");
     InitGlobal();
 }
Beispiel #3
0
 private void OnEnable()
 {
     behaviour         = serializedObject.FindProperty("behaviour");
     frequency         = serializedObject.FindProperty("frequency");
     interval          = serializedObject.FindProperty("interval");
     startOnStart      = serializedObject.FindProperty("startOnStart");
     restartOnComplete = serializedObject.FindProperty("restartOnComplete");
     resetOnRestart    = serializedObject.FindProperty("resetOnRestart");
     gizmos            = serializedObject.FindProperty("gizmos");
     presetVariables   = serializedObject.FindProperty("presetVariables");
     treeDrawer        = new ObjectSelectionDrawer <BehaviourTree>(behaviour, string.Empty, string.Empty, "行为树");
     InitTree();
 }
    public ConditionGroupDrawer(SerializedObject owner, SerializedProperty property, float lineHeight, float lineHeightSpace, string listTitle = "条件列表")
    {
        this.owner           = owner;
        this.property        = property;
        this.lineHeightSpace = lineHeightSpace;
        SerializedProperty conditions = property.FindPropertyRelative("conditions");

        npcSelectors = new Dictionary <int, ObjectSelectionDrawer <TalkerInformation> >();
        var talkers = Resources.LoadAll <TalkerInformation>("").Where(x => x.Enable).ToArray();
        var quests  = Resources.LoadAll <Quest>("").Where(x => x != (owner.targetObject as Quest)).ToArray();

        List = new ReorderableList(property.serializedObject, conditions, true, true, true, true)
        {
            drawElementCallback = (Rect rect, int index, bool isActive, bool isFocused) =>
            {
                owner.UpdateIfRequiredOrScript();
                SerializedProperty condition     = conditions.GetArrayElementAtIndex(index);
                SerializedProperty type          = condition.FindPropertyRelative("type");
                ConditionType      conditionType = (ConditionType)type.enumValueIndex;
                EditorGUI.PropertyField(new Rect(rect.x + 8, rect.y, rect.width * 0.2f, lineHeight), condition, new GUIContent("条件[" + index + "]"), false);
                EditorGUI.BeginChangeCheck();
                EditorGUI.PropertyField(new Rect(rect.x + rect.width * 0.2f + 8, rect.y, rect.width * 0.8f - 8, lineHeight),
                                        type, new GUIContent(string.Empty), true);
                if (condition.isExpanded)
                {
                    switch (conditionType)
                    {
                    case ConditionType.CompleteQuest:
                    case ConditionType.AcceptQuest:
                        SerializedProperty day          = condition.FindPropertyRelative("intValue");
                        SerializedProperty relatedQuest = condition.FindPropertyRelative("relatedQuest");
                        new ObjectSelectionDrawer <Quest>(relatedQuest, "title", quests, "对应任务").DoDraw(new Rect(rect.x, rect.y + lineHeightSpace * 1, rect.width, lineHeight));
                        if (relatedQuest.objectReferenceValue == owner.targetObject as Quest)
                        {
                            relatedQuest.objectReferenceValue = null;
                        }
                        day.intValue = EditorGUI.IntSlider(new Rect(rect.x, rect.y + lineHeightSpace * 2, rect.width, lineHeight), "后第几天", day.intValue, 0, 30);
                        break;

                    case ConditionType.HasItem:
                        SerializedProperty relatedItem = condition.FindPropertyRelative("relatedItem");
                        new ObjectSelectionDrawer <ItemBase>(relatedItem, "_name", i => ZetanUtility.GetInspectorName(i.ItemType), "",
                                                             "对应道具").DoDraw(new Rect(new Rect(rect.x, rect.y + lineHeightSpace, rect.width, lineHeight)));
                        break;

                    case ConditionType.Level:
                        SerializedProperty level       = condition.FindPropertyRelative("intValue");
                        SerializedProperty compareType = condition.FindPropertyRelative("compareType");
                        EditorGUI.PropertyField(new Rect(rect.x, rect.y + lineHeightSpace * 1, rect.width, lineHeight), compareType, new GUIContent("比较方式"));
                        EditorGUI.PropertyField(new Rect(rect.x, rect.y + lineHeightSpace * 2, rect.width, lineHeight), level, new GUIContent("对应等级"));
                        if (level.intValue < 1)
                        {
                            level.intValue = 1;
                        }
                        break;

                    case ConditionType.TriggerSet:
                    case ConditionType.TriggerReset:
                        EditorGUI.PropertyField(new Rect(rect.x, rect.y + lineHeightSpace, rect.width, lineHeight),
                                                condition.FindPropertyRelative("triggerName"), new GUIContent("触发器名称"));
                        break;

                    case ConditionType.NPCIntimacy:
                        int lineCount               = 1;
                        SerializedProperty npc      = condition.FindPropertyRelative("relatedCharInfo");
                        SerializedProperty intimacy = condition.FindPropertyRelative("intValue");
                        compareType = condition.FindPropertyRelative("compareType");
                        if (!npcSelectors.TryGetValue(index, out var selector))
                        {
                            selector = new ObjectSelectionDrawer <TalkerInformation>(npc, "_name", talkers, "条件对象");
                            npcSelectors.Add(index, selector);
                        }
                        selector.DoDraw(new Rect(rect.x, rect.y + lineHeightSpace * lineCount, rect.width, lineHeight));
                        lineCount++;
                        EditorGUI.PropertyField(new Rect(rect.x, rect.y + lineHeightSpace * lineCount, rect.width, lineHeight), npc, new GUIContent("对象引用"), false);
                        lineCount++;
                        EditorGUI.PropertyField(new Rect(rect.x, rect.y + lineHeightSpace * lineCount, rect.width, lineHeight), intimacy, new GUIContent("亲密度"));
                        lineCount++;
                        EditorGUI.PropertyField(new Rect(rect.x, rect.y + lineHeightSpace * lineCount, rect.width, lineHeight), compareType, new GUIContent("比较方式"));
                        lineCount++;
                        break;

                    default: break;
                    }
                }
                if (EditorGUI.EndChangeCheck())
                {
                    owner.ApplyModifiedProperties();
                }
            },

            elementHeightCallback = (int index) =>
            {
                if (index < 0 || index > conditions.arraySize - 1)
                {
                    return(0);
                }
                SerializedProperty condition     = conditions.GetArrayElementAtIndex(index);
                SerializedProperty type          = condition.FindPropertyRelative("type");
                ConditionType      conditionType = (ConditionType)type.enumValueIndex;
                if (condition.isExpanded)
                {
                    switch (conditionType)
                    {
                    case ConditionType.CompleteQuest:
                    case ConditionType.AcceptQuest:
                    case ConditionType.Level:
                        return(3 * lineHeightSpace);

                    case ConditionType.NPCIntimacy:
                        return(5 * lineHeightSpace);

                    case ConditionType.HasItem:
                    case ConditionType.TriggerSet:
                    case ConditionType.TriggerReset:
                        return(2 * lineHeightSpace);

                    default: return(lineHeightSpace);
                    }
                }
                else
                {
                    return(lineHeightSpace);
                }
            },

            onRemoveCallback = (list) =>
            {
                owner.UpdateIfRequiredOrScript();
                EditorGUI.BeginChangeCheck();
                if (EditorUtility.DisplayDialog("删除", "确定删除这个条件吗?", "确定", "取消"))
                {
                    list.Deselect(list.index);
                    conditions.DeleteArrayElementAtIndex(list.index);
                    npcSelectors.Clear();
                }
                if (EditorGUI.EndChangeCheck())
                {
                    owner.ApplyModifiedProperties();
                }
            },

            onCanRemoveCallback = (list) =>
            {
                return(list.IsSelected(list.index));
            },

            drawHeaderCallback = (rect) =>
            {
                int notCmpltCount = 0;
                for (int i = 0; i < conditions.arraySize; i++)
                {
                    SerializedProperty condition     = conditions.GetArrayElementAtIndex(i);
                    SerializedProperty type          = condition.FindPropertyRelative("type");
                    ConditionType      conditionType = (ConditionType)type.enumValueIndex;
                    switch (conditionType)
                    {
                    case ConditionType.CompleteQuest:
                    case ConditionType.AcceptQuest:
                        if (condition.FindPropertyRelative("relatedQuest").objectReferenceValue == null)
                        {
                            notCmpltCount++;
                        }
                        break;

                    case ConditionType.HasItem:
                        if (condition.FindPropertyRelative("relatedItem").objectReferenceValue == null)
                        {
                            notCmpltCount++;
                        }
                        break;

                    case ConditionType.Level:
                        if (condition.FindPropertyRelative("intValue").intValue < 1)
                        {
                            notCmpltCount++;
                        }
                        break;

                    case ConditionType.TriggerSet:
                    case ConditionType.TriggerReset:
                        if (!string.IsNullOrEmpty(condition.FindPropertyRelative("triggerName").stringValue))
                        {
                            notCmpltCount++;
                        }
                        break;

                    default: break;
                    }
                }
                EditorGUI.LabelField(rect, listTitle, "数量:" + conditions.arraySize + (notCmpltCount > 0 ? "\t未补全:" + notCmpltCount : string.Empty));
            },

            drawNoneElementCallback = (rect) =>
            {
                EditorGUI.LabelField(rect, "空列表");
            }
        };
    }
Beispiel #5
0
        public override void OnInspectorGUI()
        {
            if (target is RuntimeBehaviourExecutor exe)
            {
                if (PrefabUtility.IsPartOfAnyPrefab(exe))
                {
                    EditorGUILayout.HelpBox("不能在预制件使用RuntimeBehaviourExecutor", MessageType.Error);
                    return;
                }
                else
                {
                    EditorGUILayout.HelpBox("只在本场景生效,若要制作预制件,请使用BehaviourExecutor", MessageType.Info);
                }
            }
            serializedObject.UpdateIfRequiredOrScript();
            EditorGUI.BeginChangeCheck();
            var hasTreeBef = behaviour.objectReferenceValue;

            if (target is not RuntimeBehaviourExecutor)
            {
                bool shouldDisable = Application.isPlaying && !PrefabUtility.IsPartOfAnyPrefab(target);
                EditorGUI.BeginDisabledGroup(shouldDisable);
                if (shouldDisable)
                {
                    EditorGUILayout.PropertyField(behaviour, new GUIContent("行为树"));
                }
                else
                {
                    treeDrawer.DoLayoutDraw();
                }
                EditorGUI.EndDisabledGroup();
            }
            if (behaviour.objectReferenceValue != hasTreeBef)
            {
                InitTree();
            }
            if (behaviour.objectReferenceValue)
            {
                if (GUILayout.Button("编辑"))
                {
                    BehaviourTreeEditor.CreateWindow(target as BehaviourExecutor);
                }
                serializedTree.UpdateIfRequiredOrScript();
                EditorGUI.BeginChangeCheck();
                EditorGUILayout.PropertyField(serializedTree.FindProperty("_name"));
                EditorGUILayout.PropertyField(serializedTree.FindProperty("description"));
                if (EditorGUI.EndChangeCheck())
                {
                    serializedTree.ApplyModifiedProperties();
                }
            }
            else
            {
                if (GUILayout.Button("新建"))
                {
                    BehaviourTree tree = ZetanUtility.Editor.SaveFilePanel(CreateInstance <BehaviourTree>, "new behaviour tree");
                    if (tree)
                    {
                        behaviour.objectReferenceValue = tree;
                        InitTree();
                        treeDrawer = new ObjectSelectionDrawer <BehaviourTree>(behaviour, string.Empty, string.Empty, "行为树");
                        EditorApplication.delayCall += delegate { BehaviourTreeEditor.CreateWindow(target as BehaviourExecutor); };
                    }
                }
            }
            EditorGUILayout.PropertyField(frequency, new GUIContent("执行频率"));
            if (frequency.enumValueIndex == (int)BehaviourExecutor.Frequency.FixedTime)
            {
                EditorGUILayout.PropertyField(interval, new GUIContent("间隔(秒)"));
            }
            EditorGUILayout.BeginHorizontal();
            EditorGUILayout.PropertyField(startOnStart, new GUIContent("开始时执行"));
            EditorGUILayout.PropertyField(restartOnComplete, new GUIContent("完成时重启"));
            EditorGUILayout.EndHorizontal();
            EditorGUILayout.BeginHorizontal();
            EditorGUILayout.PropertyField(resetOnRestart, new GUIContent("重启时重置"));
            EditorGUILayout.PropertyField(gizmos, new GUIContent("显示Gizmos"));
            EditorGUILayout.EndHorizontal();
            if (EditorGUI.EndChangeCheck())
            {
                serializedObject.ApplyModifiedProperties();
            }
            if (behaviour.objectReferenceValue)
            {
                serializedTree.UpdateIfRequiredOrScript();
                showList.target = EditorGUILayout.Foldout(serializedVariables.isExpanded, "行为树共享变量", true);
                if (EditorGUILayout.BeginFadeGroup(showList.faded))
                {
                    variableList.DoLayoutList();
                }
                EditorGUILayout.EndFadeGroup();
                if (target is not RuntimeBehaviourExecutor && !Application.isPlaying && !ZetanUtility.IsPrefab((target as BehaviourExecutor).gameObject))
                {
                    showPreset.target = EditorGUILayout.Foldout(presetVariables.isExpanded, "变量预设列表", true);
                    if (EditorGUILayout.BeginFadeGroup(showPreset.faded))
                    {
                        presetVariableList.DoLayoutList();
                    }
                    EditorGUILayout.EndFadeGroup();
                }
                serializedTree.ApplyModifiedProperties();
            }
        }