Custom Nodes

Learn how to write custom nodes.

Adding custom nodes to schematics, formulas or battle AI doesn’t require implementing them in a plugin or ORK/Makinom’s source code – you can just add them in a script file in your Unity project.

For base information on custom nodes and writing custom nodes for schematics and formulas, please see the Makinom custom nodes documentation.

Battle AI Nodes #

You can create custom nodes by deriving from the BaseAINode or BaseAICheckNode classes. For examples it’s best to check out the available node implementations.

Deriving from BaseAINode will make it a node with a single Next slot, the connection to the next node is stored in the int field next.

public class NewAINode : BaseAINode

Deriving from BaseAICheckNode (which descends from BaseAINode) will make a node with a Success and a Failed slot – the Success connection is stored in the int field next, the Failed connection is stored in the int field nextFail.

public class NewAINode : BaseAICheckNode

You can also create multi-slot nodes, please see the Makinom custom nodes documentation for details.

Using battle AI nodes should use the battle AI node namespace.

using GamingIsLove.ORKFramework.AI.Nodes;

Or, implement the node in the namespace (not required).

namespace GamingIsLove.ORKFramework.AI.Nodes

Node Execution #

The most crucial part of the node is the Execute function, which will be used when the node is executed by the battle AI. This function will handle whatever you want to do with your node – and it must set which node (index) will be executed next and either return an action that was found or null if none was found.

public override BaseAction Execute(ref int currentNode, BattleAICall call)
{
    currentNode = this.next;
    return null;
}

The currentNode parameter will hold the node that is executed next, so set it to what slot of the node should be used next (e.g. via the next or nextFail fields).

The function returns a BaseAction – the base implementation of a battle action. Returning an action can end the battle AI (depending on the combatant’s AI setup), so return null if no action is found.

The call also has access to user of the battle AI, found targets and other information of the battle AI call, as well as local variables and selected data.

Example #

In total, a node class can look like this:

using UnityEngine;
using System.Collections.Generic;
using GamingIsLove.Makinom;

namespace GamingIsLove.ORKFramework.AI.Nodes
{
    // INFO: The 'EditorHelp' attribute manages the name and description of the node.
    [EditorHelp("Node Name", "The description of your node.", "")]
    // INFO: The 'NodeInfo' attribute manages in which section the node can be found in the add node selection.
    [NodeInfo("Section")]
    public class NewAINode : BaseAINode
    {
        // INFO: Place your settings here.

        public NewAINode()
        {

        }

        // INFO: This code will be executed when the node is executed.
        public override BaseAction Execute(ref int currentNode, BattleAICall call)
        {
            currentNode = this.next;
            return null;
        }

        // INFO: This returns the text displayed in the node's info area.
        public override string GetNodeDetails()
        {
            return "Node info text";
        }

        // INFO: This property handles the color of your node in the node editor.
        public override Color EditorColor
        {
            get
            {
                return Maki.EditorSettings.baseNodeColor;
            }
        }
    }
}

This node doesn’t do much, though. You can add your settings in the class and do whatever needs to be done in the Execute function.

Please note that your custom node doesn’t need to be in the GamingIsLove.ORKFramework.AI.Nodes namespace, it can be placed in any namespace (or none at all).