128 lines
4.9 KiB
C#
128 lines
4.9 KiB
C#
using System;
|
|
using System.Collections.Generic;
|
|
using Cysharp.Threading.Tasks;
|
|
using Sirenix.OdinInspector;
|
|
using UnityEngine;
|
|
using XNode;
|
|
|
|
namespace Stary.Evo.StoryEditor
|
|
{
|
|
[Serializable,CreateNodeMenu("")]
|
|
public class FlowNode : NodeBase
|
|
{
|
|
[HorizontalGroup("Port", order:0)]
|
|
[Input]
|
|
public Enter enter;
|
|
[HorizontalGroup("Port")]
|
|
[Output]
|
|
public Exit exit;
|
|
|
|
/// <summary>
|
|
/// Exit端口连接的节点的执行类型
|
|
/// </summary>
|
|
[BoxGroup("Config", order:5, showLabel:false)]
|
|
[LabelText("后续执行")]
|
|
public NodeExecuteType exitNodeExecuteType = NodeExecuteType.Async;
|
|
|
|
/// <summary>
|
|
/// 创建新的流程节点
|
|
/// </summary>
|
|
/// <param name="graph">所在的块</param>
|
|
/// <param name="name">节点名称</param>
|
|
/// <param name="position">节点位置</param>
|
|
/// <param name="prePorts">节点前部连接</param>
|
|
/// <param name="nextPorts">节点后部连接</param>
|
|
public static T Create<T>(NodeGraph graph, string name = null, Vector2 position = default,
|
|
List<NodePort> prePorts = null, List<NodePort> nextPorts = null) where T:FlowNode
|
|
{
|
|
// 创建节点
|
|
var node = NodeBase.Create<T>(graph, name, position);
|
|
if (node == null)
|
|
return null;
|
|
|
|
// 将剧本与前部节点和后部节点相连
|
|
var enterPort = node.GetInputPort("enter");
|
|
if (enterPort != null && prePorts != null)
|
|
prePorts.ForEach(port => port.Connect(enterPort));
|
|
var exitPort = node.GetInputPort("exit");
|
|
if (exitPort != null && nextPorts != null)
|
|
nextPorts.ForEach(port => port.Connect(exitPort));
|
|
|
|
return node;
|
|
}
|
|
|
|
#region 工具方法
|
|
|
|
/// <summary>
|
|
/// 将自身的入口连接传递给指定端口
|
|
/// </summary>
|
|
/// <param name="otherPort">指定端口</param>
|
|
/// <param name="deleteSelf">传递后删除自身连接</param>
|
|
public void GiveEnterPortToOtherPort(NodePort otherPort, bool deleteSelf)
|
|
=> GiveConnectionToOtherPort(GetInputPort("enter"), otherPort, deleteSelf);
|
|
|
|
/// <summary>
|
|
/// 将自身的出口连接传递给指定端口
|
|
/// </summary>
|
|
/// <param name="otherPort">指定端口</param>
|
|
/// <param name="deleteSelf">传递后删除自身连接</param>
|
|
public void GiveExitPortToOtherPort(NodePort otherPort, bool deleteSelf = false)
|
|
=> GiveConnectionToOtherPort(GetOutputPort("exit"), otherPort, deleteSelf);
|
|
|
|
#endregion
|
|
|
|
#region 节点操作
|
|
|
|
/// <summary>
|
|
/// 向前插入节点
|
|
/// </summary>
|
|
[HorizontalGroup("Insert", order:1)]
|
|
[Button("(←)插入节点")]
|
|
public void InsertForward()
|
|
{
|
|
// 生成新的空节点
|
|
var newNode = SelectionNode.Create(graph);
|
|
// 将本节点的Enter连接给到新的节点的Enter
|
|
GiveEnterPortToOtherPort(newNode.GetInputPort("enter"), true);
|
|
// 将新的节点的Exit连接到本节点的Enter
|
|
GetInputPort("enter").Connect(newNode.GetOutputPort("exit"));
|
|
// 将新节点设定为本节点位置
|
|
newNode.position = position;
|
|
|
|
// 将包括自身在内的所有后续节点向后移动一个默认间隔
|
|
newNode.DoActionToAllNodesAfter((thisNode, otherNode) => otherNode.position = thisNode.position + new Vector2(DefaultNodeXInterval, DefaultNodeYInterval));
|
|
}
|
|
|
|
/// <summary>
|
|
/// 向后插入节点
|
|
/// </summary>
|
|
[HorizontalGroup("Insert")]
|
|
[Button("插入节点(→)")]
|
|
public void InsertBackward()
|
|
{
|
|
// 生成新的空节点
|
|
var newNode = SelectionNode.Create(graph);
|
|
// 将本节点的Exit连接给到新的节点的Exit
|
|
GiveExitPortToOtherPort(newNode.GetOutputPort("exit"), true);
|
|
// 将新的节点的Enter连接到本节点的Exit
|
|
GetOutputPort("exit").Connect(newNode.GetInputPort("enter"));
|
|
// 将新节点设置为本节点位置后移一格
|
|
newNode.position = position + new Vector2(DefaultNodeXInterval, DefaultNodeYInterval);
|
|
|
|
// 将所有后续节点向后移动一个默认间隔
|
|
newNode.DoActionToAllNodesAfter((thisNode, otherNode) => otherNode.position = thisNode.position + new Vector2(DefaultNodeXInterval, DefaultNodeYInterval));
|
|
}
|
|
|
|
#endregion
|
|
|
|
/// <summary>
|
|
/// 导出
|
|
/// </summary>
|
|
public new async UniTask<FlowNodeData> Export()
|
|
{
|
|
FlowNodeData node = new(await base.Export());
|
|
node.executeType = exitNodeExecuteType;
|
|
return node;
|
|
}
|
|
}
|
|
} |