コード例 #1
0
ファイル: GoapAgent.cs プロジェクト: Over42/uGOAP
    private void CreatePerformActionState()
    {
        performActionState = (fsm, gameObj) =>
        {
            // perform the action
            if (!HasActionPlan())
            {
                // no actions to perform
                Debug.Log("<color=red>Done actions</color>");
                fsm.PopState();
                fsm.PushState(idleState);
                dataProvider.ActionsFinished();
                return;
            }

            GoapAction action = currentActions.Peek();
            if (action.IsDone())
            {
                // the action is done. Remove it so we can perform the next one
                currentActions.Dequeue();
            }

            if (HasActionPlan())
            {
                // perform the next action
                action = currentActions.Peek();
                bool inRange = action.RequiresInRange() ? action.IsInRange() : true;

                if (inRange)
                {
                    // we are in range, so perform the action
                    bool success = action.Perform(gameObj, dataProvider.GetMemory());

                    if (!success)
                    {
                        // action failed, we need to plan again
                        fsm.PopState();
                        fsm.PushState(idleState);
                        dataProvider.PlanAborted(action);
                    }
                }
                else
                {
                    // we need to move there first
                    // push moveTo state
                    fsm.PushState(moveToState);
                }
            }
            else
            {
                // no actions left, move to Plan state
                fsm.PopState();
                fsm.PushState(idleState);
                dataProvider.ActionsFinished();
            }
        };
    }
コード例 #2
0
ファイル: GoapPlanner.cs プロジェクト: Over42/uGOAP
    /**
     * Plan what sequence of actions can fulfill the goal.
     * Returns null if a plan could not be found, or a list of the actions
     * that must be performed, in order, to fulfill the goal.
     */
    public Queue <GoapAction> Plan(GameObject agent,
                                   HashSet <GoapAction> availableActions,
                                   Dictionary <string, object> worldState,
                                   KeyValuePair <string, object> goal,
                                   IGoap goap)
    {
        // reset the actions so we can start fresh with them
        foreach (GoapAction a in availableActions)
        {
            a.DoReset();
        }

        // check what actions can run using their checkProceduralPrecondition
        HashSet <GoapAction> usableActions = NodeManager.GetFreeActionSet();

        foreach (GoapAction a in availableActions)
        {
            if (a.CheckProceduralPrecondition(agent, goap.GetMemory()))
            {
                usableActions.Add(a);
            }
        }

        // we now have all actions that can run, stored in usableActions

        // build up the tree and record the leaf nodes that provide a solution to the goal.
        List <GoapNode> leaves = new List <GoapNode>();

        // build graph
        GoapNode start   = NodeManager.GetFreeNode(null, 0, worldState, null);
        bool     success = BuildGraph(start, leaves, usableActions, goal);

        if (!success)
        {
            // oh no, we didn't get a plan
            Debug.Log("[" + agent.name + "] " + "NO PLAN");
            return(null);
        }

        // get the cheapest leaf
        GoapNode cheapest = null;

        foreach (GoapNode leaf in leaves)
        {
            if (cheapest == null)
            {
                cheapest = leaf;
            }
            else
            {
                if (leaf.BetterThen(cheapest))
                {
                    cheapest = leaf;
                }
            }
        }

        // get its node and work back through the parents
        List <GoapAction> result = new List <GoapAction>();
        GoapNode          n      = cheapest;

        while (n != null)
        {
            if (n.action != null)
            {
                result.Insert(0, n.action); // insert the action in the front
            }
            n = n.parent;
        }
        NodeManager.Release();
        // we now have this action list in correct order

        Queue <GoapAction> queue = new Queue <GoapAction>();

        foreach (GoapAction a in result)
        {
            queue.Enqueue(a);
        }

        // Builds a shortest way for many actions
        //for (int i = 1; i < result.Count; i++)
        //{
        //    GoapAction a = result[i];
        //    a.CheckDistance(result[i-1].target, goap.GetMemory());
        //}

        // hooray we have a plan!
        return(queue);
    }