From 561b6d764f48f5756d697915be4b779301c5f432 Mon Sep 17 00:00:00 2001
From: fengjiayi <12821976+ning_xi@user.noreply.gitee.com>
Date: Mon, 28 Oct 2024 15:21:08 +0800
Subject: [PATCH] =?UTF-8?q?=E4=BC=98=E5=8C=96=E4=BA=86=E8=8A=82=E7=82=B9?=
=?UTF-8?q?=E8=BF=9E=E6=8E=A5?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
Library/Api/IFlowEnvironment.cs | 7 +-
Library/FlowNode/MethodDetails.cs | 35 ++++++---
Library/FlowNode/MethodDetailsInfo.cs | 2 +-
Library/FlowNode/NodeDebugSetting.cs | 17 ++--
Library/FlowNode/NodeModelBaseData.cs | 1 -
Library/FlowNode/NodeModelBaseFunc.cs | 2 +-
Library/FlowNode/ParameterDetails.cs | 15 +++-
.../WebSocket/Handle/WebSocketHandleModule.cs | 5 +-
.../WebSocket/Handle/WebSocketMsgContext.cs | 11 ++-
.../Handle/WebSocketMsgHandleHelper.cs | 9 ++-
Library/Network/WebSocket/TestExtension.cs | 62 ++++++++++-----
Library/Network/WebSocket/WebSocketClient.cs | 21 ++---
Library/Network/WebSocket/WebSocketServer.cs | 25 +++---
Library/NodeAttribute.cs | 4 +-
NodeFlow/Env/FlowEnvironment.cs | 77 ++++++++++++-------
NodeFlow/Env/FlowEnvironmentDecorator.cs | 17 +++-
NodeFlow/Env/FlowFunc.cs | 2 +-
NodeFlow/Env/MsgControllerOfServer.cs | 3 +
NodeFlow/Env/RemoteFlowEnvironment.cs | 29 ++++---
NodeFlow/Model/CompositeConditionNode.cs | 2 +-
NodeFlow/Tool/NodeMethodDetailsHelper.cs | 8 +-
.../ParameterDetailsPropertyGenerator.cs | 34 +++++---
WorkBench/MainWindow.xaml | 17 ++--
WorkBench/MainWindow.xaml.cs | 35 ++++++---
WorkBench/Node/View/ActionNodeControl.xaml | 4 +-
WorkBench/Node/View/DllControlControl.xaml.cs | 6 +-
WorkBench/Node/View/FlipflopNodeControl.xaml | 4 +-
.../Themes/NodeTreeItemViewControl.xaml.cs | 6 +-
28 files changed, 295 insertions(+), 165 deletions(-)
diff --git a/Library/Api/IFlowEnvironment.cs b/Library/Api/IFlowEnvironment.cs
index 64017da..5b50ab8 100644
--- a/Library/Api/IFlowEnvironment.cs
+++ b/Library/Api/IFlowEnvironment.cs
@@ -517,13 +517,12 @@ namespace Serein.Library.Api
/// 表示是否正在控制远程
/// Local control remote env
///
- bool IsLcR { get; }
+ bool IsControlRemoteEnv { get; }
///
- /// 表示是否受到远程控制
- /// Remote control local env
+ /// 是否运行在控制台上
///
- bool IsRcL { get; }
+ // bool IsRuningOnConsole { get; }
///
/// 流程运行状态
diff --git a/Library/FlowNode/MethodDetails.cs b/Library/FlowNode/MethodDetails.cs
index a329bcc..67b26e4 100644
--- a/Library/FlowNode/MethodDetails.cs
+++ b/Library/FlowNode/MethodDetails.cs
@@ -2,6 +2,7 @@
using Serein.Library.Utils;
using System;
using System.Linq;
+using System.Text;
namespace Serein.Library
{
@@ -12,7 +13,7 @@ namespace Serein.Library
[NodeProperty(ValuePath = NodeValuePath.Method)]
public partial class MethodDetails
{
- private readonly IFlowEnvironment env;
+ // private readonly IFlowEnvironment env;
///
/// 对应的节点
@@ -58,10 +59,10 @@ namespace Serein.Library
///
- /// 方法说明
+ /// 方法别名
///
[PropertyInfo]
- private string _methodTips;
+ private string _methodAnotherName;
///
@@ -109,7 +110,7 @@ namespace Serein.Library
throw new ArgumentException("无效的节点类型");
}
MethodName = Info.MethodName;
- MethodTips = Info.MethodTips;
+ MethodAnotherName = Info.MethodAnotherName;
MethodDynamicType = nodeType;
ReturnType = Type.GetType(Info.ReturnTypeFullName);
ParameterDetailss = Info.ParameterDetailsInfos.Select(pinfo => new ParameterDetails(pinfo)).ToArray();
@@ -121,10 +122,12 @@ namespace Serein.Library
///
public MethodDetailsInfo ToInfo()
{
+
+
return new MethodDetailsInfo
{
MethodName = MethodName,
- MethodTips = MethodTips,
+ MethodAnotherName = MethodAnotherName,
NodeType = MethodDynamicType.ToString(),
ParameterDetailsInfos = ParameterDetailss.Select(p => p.ToInfo()).ToArray(),
ReturnTypeFullName = ReturnType.FullName,
@@ -142,7 +145,7 @@ namespace Serein.Library
ActingInstance = this.ActingInstance,
ActingInstanceType = this.ActingInstanceType,
MethodDynamicType = this.MethodDynamicType,
- MethodTips = this.MethodTips,
+ MethodAnotherName = this.MethodAnotherName,
ReturnType = this.ReturnType,
MethodName = this.MethodName,
MethodLockName = this.MethodLockName,
@@ -152,9 +155,23 @@ namespace Serein.Library
return md;
}
-
-
-
+ public override string ToString()
+ {
+ StringBuilder sb = new StringBuilder();
+ sb.AppendLine($"方法别名:{this.MethodAnotherName}");
+ sb.AppendLine($"方法名称:{this.MethodName}");
+ sb.AppendLine($"需要实例:{this.ActingInstanceType.FullName}");
+ sb.AppendLine($"");
+ sb.AppendLine($"入参参数信息:");
+ foreach (var arg in this.ParameterDetailss)
+ {
+ sb.AppendLine($" {arg.ToString()}");
+ }
+ sb.AppendLine($"");
+ sb.AppendLine($"返回值信息:");
+ sb.AppendLine($" {this.ReturnType.FullName}");
+ return sb.ToString();
+ }
/////
///// 每个节点有独自的MethodDetails实例
diff --git a/Library/FlowNode/MethodDetailsInfo.cs b/Library/FlowNode/MethodDetailsInfo.cs
index c7a228a..8e0383f 100644
--- a/Library/FlowNode/MethodDetailsInfo.cs
+++ b/Library/FlowNode/MethodDetailsInfo.cs
@@ -29,7 +29,7 @@ namespace Serein.Library
///
/// 方法说明
///
- public string MethodTips { get; set; }
+ public string MethodAnotherName { get; set; }
///
/// 参数内容
diff --git a/Library/FlowNode/NodeDebugSetting.cs b/Library/FlowNode/NodeDebugSetting.cs
index 2395651..b3e7cac 100644
--- a/Library/FlowNode/NodeDebugSetting.cs
+++ b/Library/FlowNode/NodeDebugSetting.cs
@@ -12,12 +12,6 @@ namespace Serein.Library
[NodeProperty(ValuePath = NodeValuePath.DebugSetting)]
public partial class NodeDebugSetting
{
- ///
- /// 对应的节点
- ///
- [PropertyInfo(IsProtection = true)]
- private NodeModelBase _nodeModel;
-
///
/// 创建属于某个节点的调试设置
///
@@ -26,6 +20,13 @@ namespace Serein.Library
{
NodeModel = nodeModel;
}
+
+ ///
+ /// 对应的节点
+ ///
+ [PropertyInfo(IsProtection = true)]
+ private NodeModelBase _nodeModel;
+
///
/// 是否使能
///
@@ -41,11 +42,9 @@ namespace Serein.Library
///
/// 中断级别,暂时停止继续执行后继分支。
///
- [PropertyInfo(IsNotification = true, CustomCode = "NodeModel?.Env?.SetNodeInterruptAsync(NodeModel?.Guid, value);")]
+ [PropertyInfo(IsNotification = true)] // CustomCode = "NodeModel?.Env?.SetNodeInterruptAsync(NodeModel?.Guid, value);"
private bool _isInterrupt = false;
- //private const string MyInteruptCode = "NodeModel?.Env?.SetNodeInterruptAsync(NodeModel?.Guid, value);"; // 添加到中断的自定义代码
-
///
/// 取消中断的回调函数
///
diff --git a/Library/FlowNode/NodeModelBaseData.cs b/Library/FlowNode/NodeModelBaseData.cs
index 7d51e8e..545e89b 100644
--- a/Library/FlowNode/NodeModelBaseData.cs
+++ b/Library/FlowNode/NodeModelBaseData.cs
@@ -81,7 +81,6 @@ namespace Serein.Library
[PropertyInfo]
private Exception _runingException ;
-
}
diff --git a/Library/FlowNode/NodeModelBaseFunc.cs b/Library/FlowNode/NodeModelBaseFunc.cs
index f743537..32facce 100644
--- a/Library/FlowNode/NodeModelBaseFunc.cs
+++ b/Library/FlowNode/NodeModelBaseFunc.cs
@@ -53,7 +53,7 @@ namespace Serein.Library
{
Guid = Guid,
MethodName = MethodDetails?.MethodName,
- Label = DisplayName ?? "",
+ Label = MethodDetails?.MethodAnotherName,
Type = this.GetType().ToString(),
TrueNodes = trueNodes.ToArray(),
FalseNodes = falseNodes.ToArray(),
diff --git a/Library/FlowNode/ParameterDetails.cs b/Library/FlowNode/ParameterDetails.cs
index 683edc5..30fa744 100644
--- a/Library/FlowNode/ParameterDetails.cs
+++ b/Library/FlowNode/ParameterDetails.cs
@@ -68,7 +68,6 @@ namespace Serein.Library
[PropertyInfo]
private string _argDataSourceNodeGuid;
-
///
/// 方法入参需要的类型。
///
@@ -128,7 +127,6 @@ namespace Serein.Library
ExplicitType = Type.GetType(info.ExplicitTypeFullName);
ExplicitTypeName = info.ExplicitTypeName;
Items = info.Items;
-
}
///
@@ -171,6 +169,19 @@ namespace Serein.Library
};
return pd;
}
+
+ public override string ToString()
+ {
+ if(_convertor is null)
+ {
+ return $"[{this.Index}] {this.Name} : {this.DataType.FullName}";
+ }
+ else
+ {
+
+ }
+ return $"[{this.Index}] {this.Name} : {this.ExplicitType.FullName} -> {this.DataType.FullName}";
+ }
}
diff --git a/Library/Network/WebSocket/Handle/WebSocketHandleModule.cs b/Library/Network/WebSocket/Handle/WebSocketHandleModule.cs
index d374f16..acfd58d 100644
--- a/Library/Network/WebSocket/Handle/WebSocketHandleModule.cs
+++ b/Library/Network/WebSocket/Handle/WebSocketHandleModule.cs
@@ -123,7 +123,10 @@ namespace Serein.Library.Network.WebSocketCommunication.Handle
catch (Exception ex)
{
Console.WriteLine($"error in ws : {ex.Message}{Environment.NewLine}json value:{jsonObject}");
- return;
+ }
+ finally
+ {
+ context.Handle = true;
}
}
diff --git a/Library/Network/WebSocket/Handle/WebSocketMsgContext.cs b/Library/Network/WebSocket/Handle/WebSocketMsgContext.cs
index bdc7101..acbd5a4 100644
--- a/Library/Network/WebSocket/Handle/WebSocketMsgContext.cs
+++ b/Library/Network/WebSocket/Handle/WebSocketMsgContext.cs
@@ -11,7 +11,7 @@ namespace Serein.Library.Network.WebSocketCommunication.Handle
///
/// 消息处理上下文
///
- public class WebSocketMsgContext : IDisposable
+ public class WebSocketMsgContext /*: IDisposable*/
{
public WebSocketMsgContext(Func sendAsync)
{
@@ -31,7 +31,14 @@ namespace Serein.Library.Network.WebSocketCommunication.Handle
///
/// 标记是否已经处理,如果是,则提前退出
///
- public bool Handle { get; set; }
+ public bool Handle { get => _handle; set{
+ if(value)
+ {
+ Dispose();
+ _handle = value;
+ }
+ } }
+ public bool _handle = false;
///
/// 消息本体(JObject)
diff --git a/Library/Network/WebSocket/Handle/WebSocketMsgHandleHelper.cs b/Library/Network/WebSocket/Handle/WebSocketMsgHandleHelper.cs
index c957de4..c54c379 100644
--- a/Library/Network/WebSocket/Handle/WebSocketMsgHandleHelper.cs
+++ b/Library/Network/WebSocket/Handle/WebSocketMsgHandleHelper.cs
@@ -201,13 +201,18 @@ namespace Serein.Library.Network.WebSocketCommunication.Handle
///
/// 此次请求的上下文
///
- public async Task HandleAsync(WebSocketMsgContext context)
+ public void Handle(WebSocketMsgContext context)
{
foreach (var module in MyHandleModuleDict.Values)
{
- await module.HandleAsync(context);
+ if (context.Handle)
+ {
+ return;
+ }
+ _ = module.HandleAsync(context);
}
+
}
diff --git a/Library/Network/WebSocket/TestExtension.cs b/Library/Network/WebSocket/TestExtension.cs
index 02acb67..1434b48 100644
--- a/Library/Network/WebSocket/TestExtension.cs
+++ b/Library/Network/WebSocket/TestExtension.cs
@@ -11,23 +11,25 @@ using System.Threading.Tasks;
namespace Serein.Library.Network.WebSocketCommunication
{
- public class MsgQueueUtil
+ ///
+ /// 消息处理工具
+ ///
+ public class MsgHandleUtil
{
- public ConcurrentQueue Msgs = new ConcurrentQueue();
-
private readonly Channel _msgChannel;
- public MsgQueueUtil()
- {
- _msgChannel = CreateChannel();
- }
- private Channel CreateChannel()
+ ///
+ /// 初始化优先容器
+ ///
+ ///
+ public MsgHandleUtil(int capacity = 100)
{
- return Channel.CreateBounded(new BoundedChannelOptions(100)
+ _msgChannel = Channel.CreateBounded(new BoundedChannelOptions(capacity)
{
FullMode = BoundedChannelFullMode.Wait
});
}
+
///
/// 等待消息
@@ -35,27 +37,45 @@ namespace Serein.Library.Network.WebSocketCommunication
///
public async Task WaitMsgAsync()
{
- var state = await _msgChannel.Reader.ReadAsync();
- return state;
- }
-
- public void WriteMsg(string msg)
- {
- //Msgs.Enqueue(msg);
- Console.WriteLine($"{DateTime.Now}{msg}{Environment.NewLine}");
- _ = _msgChannel.Writer.WriteAsync(msg);
+ // 检查是否可以读取消息
+ if (await _msgChannel.Reader.WaitToReadAsync())
+ {
+ return await _msgChannel.Reader.ReadAsync();
+ }
+ return null; // 若通道关闭,则返回null
}
- public bool TryGetMsg(out string msg)
+ ///
+ /// 写入消息
+ ///
+ /// 消息内容
+ /// 是否写入成功
+ public async Task WriteMsgAsync(string msg)
{
- return Msgs.TryDequeue(out msg);
+ try
+ {
+ await _msgChannel.Writer.WriteAsync(msg);
+ return true;
+ }
+ catch (ChannelClosedException)
+ {
+ // Channel 已关闭
+ return false;
+ }
}
-
+ ///
+ /// 尝试关闭通道,停止写入消息
+ ///
+ public void CloseChannel()
+ {
+ _msgChannel.Writer.Complete();
+ }
}
+
public class SocketExtension
{
///
diff --git a/Library/Network/WebSocket/WebSocketClient.cs b/Library/Network/WebSocket/WebSocketClient.cs
index 94234be..8d0c22e 100644
--- a/Library/Network/WebSocket/WebSocketClient.cs
+++ b/Library/Network/WebSocket/WebSocketClient.cs
@@ -76,7 +76,7 @@ namespace Serein.Library.Network.WebSocketCommunication
private async Task ReceiveAsync()
{
- var msgQueueUtil = new MsgQueueUtil();
+ var msgQueueUtil = new MsgHandleUtil();
_ = Task.Run(async () =>
{
await HandleMsgAsync(_client, msgQueueUtil);
@@ -102,7 +102,7 @@ namespace Serein.Library.Network.WebSocketCommunication
} while (!result.EndOfMessage); // 判断是否已经收到完整消息
var message = receivedMessage.ToString();
- msgQueueUtil.WriteMsg(message);
+ await msgQueueUtil.WriteMsgAsync(message);
receivedMessage.Clear(); // 清空 StringBuilder 为下一条消息做准备
// 处理收到的完整消息
if (result.MessageType == WebSocketMessageType.Close)
@@ -126,8 +126,7 @@ namespace Serein.Library.Network.WebSocketCommunication
}
- public async Task HandleMsgAsync(WebSocket webSocket,
- MsgQueueUtil msgQueueUtil)
+ public async Task HandleMsgAsync(WebSocket webSocket, MsgHandleUtil msgQueueUtil)
{
async Task sendasync(string text)
{
@@ -136,11 +135,15 @@ namespace Serein.Library.Network.WebSocketCommunication
while (true)
{
var message = await msgQueueUtil.WaitMsgAsync(); // 有消息时通知
- using (var context = new WebSocketMsgContext(sendasync))
- {
- context.JsonObject = JObject.Parse(message);
- await MsgHandleHelper.HandleAsync(context); // 处理消息
- }
+ var context = new WebSocketMsgContext(sendasync);
+ context.JsonObject = JObject.Parse(message);
+ MsgHandleHelper.Handle(context); // 处理消息
+
+ //using (var context = new WebSocketMsgContext(sendasync))
+ //{
+ // context.JsonObject = JObject.Parse(message);
+ // await MsgHandleHelper.HandleAsync(context); // 处理消息
+ //}
//_ = Task.Run(() => {
// JObject json = JObject.Parse(message);
diff --git a/Library/Network/WebSocket/WebSocketServer.cs b/Library/Network/WebSocket/WebSocketServer.cs
index 240727f..dca9ee3 100644
--- a/Library/Network/WebSocket/WebSocketServer.cs
+++ b/Library/Network/WebSocket/WebSocketServer.cs
@@ -180,7 +180,7 @@ namespace Serein.Library.Network.WebSocketCommunication
return;
}
- var msgQueueUtil = new MsgQueueUtil();
+ var msgQueueUtil = new MsgHandleUtil();
_ = Task.Run(async () =>
{
await HandleMsgAsync(webSocket,msgQueueUtil, authorizedHelper);
@@ -219,7 +219,7 @@ namespace Serein.Library.Network.WebSocketCommunication
// 完整消息已经接收到,准备处理
var message = receivedMessage.ToString(); // 获取消息文本
receivedMessage.Clear(); // 清空 StringBuilder 为下一条消息做准备
- msgQueueUtil.WriteMsg(message); // 处理消息
+ await msgQueueUtil.WriteMsgAsync(message); // 处理消息
}
catch (Exception ex)
{
@@ -231,7 +231,7 @@ namespace Serein.Library.Network.WebSocketCommunication
public async Task HandleMsgAsync(WebSocket webSocket,
- MsgQueueUtil msgQueueUtil,
+ MsgHandleUtil msgQueueUtil,
WebSocketAuthorizedHelper authorizedHelper)
{
async Task sendasync(string text)
@@ -254,18 +254,21 @@ namespace Serein.Library.Network.WebSocketCommunication
return;
}
}
+ var context = new WebSocketMsgContext(sendasync);
+ context.JsonObject = JObject.Parse(message);
+ MsgHandleHelper.Handle(context); // 处理消息
- using (var context = new WebSocketMsgContext(sendasync))
- {
- context.JsonObject = JObject.Parse(message);
- await MsgHandleHelper.HandleAsync(context); // 处理消息
- }
+ //using (var context = new WebSocketMsgContext(sendasync))
+ //{
+ // context.JsonObject = JObject.Parse(message);
+ // await MsgHandleHelper.Handle(context); // 处理消息
+ //}
//_ = Task.Run(() => {
-
-
- //});
+ //});
+
+
}
}
diff --git a/Library/NodeAttribute.cs b/Library/NodeAttribute.cs
index 750308a..8101672 100644
--- a/Library/NodeAttribute.cs
+++ b/Library/NodeAttribute.cs
@@ -91,7 +91,7 @@ namespace Serein.Library
{
Scan = scan;
MethodDynamicType = methodDynamicType;
- MethodTips = methodTips;
+ AnotherName = methodTips;
LockName = lockName;
}
///
@@ -101,7 +101,7 @@ namespace Serein.Library
///
/// 类似于注释的效果
///
- public string MethodTips;
+ public string AnotherName;
///
/// 标记节点行为
///
diff --git a/NodeFlow/Env/FlowEnvironment.cs b/NodeFlow/Env/FlowEnvironment.cs
index 4037dba..618b6b5 100644
--- a/NodeFlow/Env/FlowEnvironment.cs
+++ b/NodeFlow/Env/FlowEnvironment.cs
@@ -63,13 +63,7 @@ namespace Serein.NodeFlow.Env
/// 表示是否正在控制远程
/// Local control remote env
///
- public bool IsLcR { get; set; }
- ///
- /// 表示是否受到远程控制
- /// Remote control local env
- ///
- public bool IsRcL { get; set; }
-
+ public bool IsControlRemoteEnv { get; set; }
///
@@ -81,6 +75,7 @@ namespace Serein.NodeFlow.Env
if (clientMsgManage is null)
{
clientMsgManage = new MsgControllerOfServer(this);
+ //clientMsgManage = new MsgControllerOfServer(this,"123456");
}
_ = clientMsgManage.StartRemoteServerAsync(port);
}
@@ -657,7 +652,7 @@ namespace Serein.NodeFlow.Env
&& NodeModels.TryGetValue(pd.ArgDataSourceNodeGuid, out var fromNode))
{
- ConnectGerResultOfNode(fromNode, toNode, pd.ArgDataSourceType, pd.Index);
+ await ConnectArgSourceOfNodeAsync(fromNode, toNode, pd.ArgDataSourceType, pd.Index);
}
}
}
@@ -678,7 +673,7 @@ namespace Serein.NodeFlow.Env
/// 密码
public async Task<(bool, RemoteMsgUtil)> ConnectRemoteEnv(string addres, int port, string token)
{
- if (IsLcR)
+ if (IsControlRemoteEnv)
{
await Console.Out.WriteLineAsync($"当前已经连接远程环境");
return (false, null);
@@ -702,7 +697,7 @@ namespace Serein.NodeFlow.Env
return (false, null);
}
await Console.Out.WriteLineAsync("连接成功,开始验证Token");
- IsLcR = true;
+ IsControlRemoteEnv = true;
return (true, remoteMsgUtil);
}
@@ -711,7 +706,7 @@ namespace Serein.NodeFlow.Env
///
public void ExitRemoteEnv()
{
- IsLcR = false;
+ IsControlRemoteEnv = false;
}
///
@@ -916,7 +911,7 @@ namespace Serein.NodeFlow.Env
var fromNode = GuidToModel(fromNodeGuid);
var toNode = GuidToModel(toNodeGuid);
if (fromNode is null || toNode is null) return false;
- (var type,var state) = CheckConnect(fromNode, toNode, fromNodeJunctionType, toNodeJunctionType);
+ (var type, var state) = CheckConnect(fromNode, toNode, fromNodeJunctionType, toNodeJunctionType);
if (!state)
{
Console.WriteLine("出现非预期的连接行为");
@@ -977,7 +972,7 @@ namespace Serein.NodeFlow.Env
}
// 确定方法入参关系
- state = ConnectGerResultOfNode(fromNode, toNode, connectionArgSourceType, argIndex); // 本地环境进行连接
+ state = await ConnectArgSourceOfNodeAsync(fromNode, toNode, connectionArgSourceType, argIndex); // 本地环境进行连接
}
return state;
@@ -1291,21 +1286,36 @@ namespace Serein.NodeFlow.Env
{
var nodeModel = GuidToModel(nodeGuid);
if (nodeModel is null) return;
- if (NodeValueChangeLogger.Remove((nodeGuid, path, value)))
- {
- // 说明存在过重复的修改
- return;
- }
- NodeValueChangeLogger.Add((nodeGuid, path, value));
- var setExp = $"@Set .{path} = {value}"; // 生成 set 表达式
- //var getExp = $"@Get .{path}";
- SerinExpressionEvaluator.Evaluate(setExp, nodeModel, out _); // 更改对应的数据
- //var getResult = SerinExpressionEvaluator.Evaluate(getExp, nodeModel, out _);
- //Console.WriteLine($"Set表达式:{setExp},result : {getResult}");
-
+ SerinExpressionEvaluator.Evaluate($"@Set .{path} = {value}", nodeModel, out _); // 更改对应的数据
+
+ //if (NodeValueChangeLogger.Remove((nodeGuid, path, value)))
+ //{
+ // // 说明存在过重复的修改
+ // return;
+ //}
+ //NodeValueChangeLogger.Add((nodeGuid, path, value));
+
+ //lock (NodeValueChangeLogger)
+ //{
+
+ // Interlocked.Add(ref i, 1);
+ // Console.WriteLine(i);
+ // var getExp = $"@Get .{path}";
+ // var setExp = $"@Set .{path} = {value}"; // 生成 set 表达式
+ // var oldValue = SerinExpressionEvaluator.Evaluate(getExp, nodeModel, out _);
+ // if(oldValue != value)
+ // {
+ // Console.WriteLine($"旧值:{getExp},result : {oldValue}");
+ // SerinExpressionEvaluator.Evaluate(setExp, nodeModel, out _); // 更改对应的数据
+ // Console.WriteLine($"新值:{getExp},result : {SerinExpressionEvaluator.Evaluate(getExp, nodeModel, out _)}");
+ // }
+
+ //}
+
+
}
-
+
@@ -1487,7 +1497,7 @@ namespace Serein.NodeFlow.Env
Console.WriteLine($"无法加载方法信息:{assemblyName}-{type}-{method}");
continue;
}
- md.MethodTips = flowName + md.MethodTips;
+ md.MethodAnotherName = flowName + md.MethodAnotherName;
if (MethodDelegates.TryAdd(md.MethodName, del))
{
methodDetails.Add(md);
@@ -1702,14 +1712,23 @@ namespace Serein.NodeFlow.Env
///
///
///
- private bool ConnectGerResultOfNode(NodeModelBase fromNode,
+ private async Task ConnectArgSourceOfNodeAsync(NodeModelBase fromNode,
NodeModelBase toNode,
ConnectionArgSourceType connectionArgSourceType,
int argIndex)
{
+
+ if (!string.IsNullOrEmpty(toNode.MethodDetails.ParameterDetailss[argIndex].ArgDataSourceNodeGuid))
+ {
+ //if(toNode.MethodDetails.ParameterDetailss[argIndex].ArgDataSourceType == connectionArgSourceType)
+ //{
+ // return ;
+ //}
+ await RemoteConnectAsync(fromNode,toNode,argIndex); // 已经存在连接,将其移除
+ }
toNode.MethodDetails.ParameterDetailss[argIndex].ArgDataSourceNodeGuid = fromNode.Guid;
toNode.MethodDetails.ParameterDetailss[argIndex].ArgDataSourceType = connectionArgSourceType;
- UIContextOperation?.Invoke(() =>
+ await UIContextOperation.InvokeAsync(() =>
OnNodeConnectChange?.Invoke(
new NodeConnectChangeEventArgs(
fromNode.Guid, // 从哪个节点开始
diff --git a/NodeFlow/Env/FlowEnvironmentDecorator.cs b/NodeFlow/Env/FlowEnvironmentDecorator.cs
index e5b0280..9feddf1 100644
--- a/NodeFlow/Env/FlowEnvironmentDecorator.cs
+++ b/NodeFlow/Env/FlowEnvironmentDecorator.cs
@@ -34,6 +34,7 @@ namespace Serein.NodeFlow.Env
private IFlowEnvironment currentFlowEnvironment;
+
private int _loadingProjectFlag = 0; // 使用原子自增代替锁
///
/// 传入false时,将停止数据通知。传入true时,
@@ -68,9 +69,8 @@ namespace Serein.NodeFlow.Env
public bool IsGlobalInterrupt => currentFlowEnvironment.IsGlobalInterrupt;
- public bool IsLcR => currentFlowEnvironment.IsLcR;
+ public bool IsControlRemoteEnv => currentFlowEnvironment.IsControlRemoteEnv;
- public bool IsRcL => currentFlowEnvironment.IsRcL;
public RunState FlowState { get => currentFlowEnvironment.FlowState; set => currentFlowEnvironment.FlowState = value; }
public RunState FlipFlopState { get => currentFlowEnvironment.FlipFlopState; set => currentFlowEnvironment.FlipFlopState = value; }
@@ -404,14 +404,23 @@ namespace Serein.NodeFlow.Env
currentFlowEnvironment.WriteLineObjToJson(obj);
}
-
+ ///
+ /// (用于远程)通知节点属性变更
+ ///
+ /// 节点Guid
+ /// 属性路径
+ /// 属性值
+ ///
public async Task NotificationNodeValueChangeAsync(string nodeGuid, string path, object value)
{
if (!IsLoadingProject())
{
return;
}
- await currentFlowEnvironment.NotificationNodeValueChangeAsync(nodeGuid, path, value);
+ if (currentFlowEnvironment.IsControlRemoteEnv)
+ {
+ await currentFlowEnvironment.NotificationNodeValueChangeAsync(nodeGuid, path, value);
+ }
}
diff --git a/NodeFlow/Env/FlowFunc.cs b/NodeFlow/Env/FlowFunc.cs
index b8423d2..1152329 100644
--- a/NodeFlow/Env/FlowFunc.cs
+++ b/NodeFlow/Env/FlowFunc.cs
@@ -53,7 +53,7 @@ namespace Serein.NodeFlow.Env
methodDetails = new MethodDetails();
}
var md = methodDetails.CloneOfNode(nodeModel.Env, nodeModel);
- nodeModel.DisplayName = md.MethodTips;
+ nodeModel.DisplayName = md.MethodAnotherName;
nodeModel.MethodDetails = md;
diff --git a/NodeFlow/Env/MsgControllerOfServer.cs b/NodeFlow/Env/MsgControllerOfServer.cs
index 064d6b0..a87163e 100644
--- a/NodeFlow/Env/MsgControllerOfServer.cs
+++ b/NodeFlow/Env/MsgControllerOfServer.cs
@@ -55,6 +55,7 @@ namespace Serein.NodeFlow.Env
///
/// 启动带token验证的远程服务
///
+ ///
///
public MsgControllerOfServer(IFlowEnvironment environment, string token)
{
@@ -567,6 +568,7 @@ namespace Serein.NodeFlow.Env
environment.SetMonitorObjState(key, isMonitor);
}
+
///
/// 节点数据更改
///
@@ -576,6 +578,7 @@ namespace Serein.NodeFlow.Env
[AutoSocketHandle(ThemeValue = EnvMsgTheme.ValueNotification)]
public async Task ValueNotification(string nodeGuid, string path, string value)
{
+
await environment.NotificationNodeValueChangeAsync(nodeGuid, path, value);
}
diff --git a/NodeFlow/Env/RemoteFlowEnvironment.cs b/NodeFlow/Env/RemoteFlowEnvironment.cs
index 601029f..673d653 100644
--- a/NodeFlow/Env/RemoteFlowEnvironment.cs
+++ b/NodeFlow/Env/RemoteFlowEnvironment.cs
@@ -64,9 +64,8 @@ namespace Serein.NodeFlow.Env
public bool IsGlobalInterrupt => false;
- public bool IsLcR => true;
+ public bool IsControlRemoteEnv => true;
- public bool IsRcL => false;
public RunState FlowState { get => throw new NotImplementedException(); set => throw new NotImplementedException(); }
public RunState FlipFlopState { get => throw new NotImplementedException(); set => throw new NotImplementedException(); }
@@ -78,6 +77,10 @@ namespace Serein.NodeFlow.Env
/// 标示是否正在加载项目
///
private bool IsLoadingProject = false;
+ ///
+ /// 表示是否正在加载节点
+ ///
+ private bool IsLoadingNode = false;
public void SetConsoleOut()
{
@@ -666,13 +669,14 @@ namespace Serein.NodeFlow.Env
/// 节点绑定的方法说明
public async Task CreateNodeAsync(NodeControlType nodeControlType, PositionOfUI position, MethodDetailsInfo methodDetailsInfo = null)
{
+ IsLoadingNode = true;
var nodeInfo = await msgClient.SendAndWaitDataAsync(EnvMsgTheme.CreateNode, new
{
nodeType = nodeControlType.ToString(),
position = position,
mdInfo = methodDetailsInfo,
});
-
+
MethodDetails? methodDetails = null;
if (!string.IsNullOrEmpty(nodeInfo.MethodName))
{
@@ -683,6 +687,7 @@ namespace Serein.NodeFlow.Env
var nodeModel = FlowFunc.CreateNode(this, nodeControlType, methodDetails); // 远程环境下加载节点
nodeModel.LoadInfo(nodeInfo);
TryAddNode(nodeModel);
+ IsLoadingNode = false;
// 通知UI更改
UIContextOperation.Invoke(() =>
@@ -816,14 +821,18 @@ namespace Serein.NodeFlow.Env
public async Task NotificationNodeValueChangeAsync(string nodeGuid, string path, object value)
{
- //Console.WriteLine($"通知远程环境修改节点数据:{nodeGuid},name:{path},value:{value}");
+ if(IsLoadingProject || IsLoadingNode)
+ {
+ return;
+ }
+ Console.WriteLine($"通知远程环境修改节点数据:{nodeGuid},name:{path},value:{value}");
- //_ = msgClient.SendAsync(EnvMsgTheme.ValueNotification, new
- //{
- // nodeGuid = nodeGuid,
- // path = path,
- // value = value.ToString(),
- //});
+ _ = msgClient.SendAsync(EnvMsgTheme.ValueNotification, new
+ {
+ nodeGuid = nodeGuid,
+ path = path,
+ value = value.ToString(),
+ });
}
}
diff --git a/NodeFlow/Model/CompositeConditionNode.cs b/NodeFlow/Model/CompositeConditionNode.cs
index af32f8b..eff7428 100644
--- a/NodeFlow/Model/CompositeConditionNode.cs
+++ b/NodeFlow/Model/CompositeConditionNode.cs
@@ -104,7 +104,7 @@ namespace Serein.NodeFlow.Model
{
Guid = Guid,
MethodName = MethodDetails?.MethodName,
- Label = DisplayName ?? "",
+ Label = MethodDetails?.MethodAnotherName,
Type = this.GetType().ToString(),
TrueNodes = trueNodes.ToArray(),
FalseNodes = falseNodes.ToArray(),
diff --git a/NodeFlow/Tool/NodeMethodDetailsHelper.cs b/NodeFlow/Tool/NodeMethodDetailsHelper.cs
index 31cb4af..3d5e324 100644
--- a/NodeFlow/Tool/NodeMethodDetailsHelper.cs
+++ b/NodeFlow/Tool/NodeMethodDetailsHelper.cs
@@ -83,14 +83,14 @@ public static class NodeMethodDetailsHelper
returnType = method.ReturnType;
}
- if (string.IsNullOrEmpty(attribute.MethodTips)){
- attribute.MethodTips = method.Name;
+ if (string.IsNullOrEmpty(attribute.AnotherName)){
+ attribute.AnotherName = method.Name;
}
var asyncPrefix = "[异步]"; // IsGenericTask(returnType) ? "[async]" : ;
- var methodTips = isTask ? asyncPrefix + attribute.MethodTips : attribute.MethodTips;
+ var methodMethodAnotherName = isTask ? asyncPrefix + attribute.AnotherName : attribute.AnotherName;
@@ -101,7 +101,7 @@ public static class NodeMethodDetailsHelper
MethodName = dllTypeMethodName,
MethodDynamicType = attribute.MethodDynamicType,
MethodLockName = attribute.LockName,
- MethodTips = methodTips,
+ MethodAnotherName = methodMethodAnotherName,
ParameterDetailss = explicitDataOfParameters,
ReturnType = returnType,
};
diff --git a/Serein.Library.MyGenerator/ParameterDetailsPropertyGenerator.cs b/Serein.Library.MyGenerator/ParameterDetailsPropertyGenerator.cs
index 14f723b..afdf017 100644
--- a/Serein.Library.MyGenerator/ParameterDetailsPropertyGenerator.cs
+++ b/Serein.Library.MyGenerator/ParameterDetailsPropertyGenerator.cs
@@ -183,20 +183,32 @@ namespace Serein.Library.NodeGenerator
{
if (classInfo.ExitsPath(nameof(NodeValuePath.Node))) // 节点 or 自定义节点
{
- sb.AddCode(5, $"((NodeModelBase)this).Env?.NotificationNodeValueChangeAsync(this.Guid, nameof({propertyName}), value); // 通知远程环境属性发生改变了");
+ sb.AddCode(5, $"if (this?.Env?.IsControlRemoteEnv == true) // 正在控制远程环境时才触发");
+ sb.AddCode(5, $"{{");
+ sb.AddCode(6, $"this.Env?.NotificationNodeValueChangeAsync(this.Guid, nameof({propertyName}), value); // 通知远程环境属性发生改变了");
+ sb.AddCode(5, $"}}");
}
- else if (classInfo.ExitsPath(nameof(NodeValuePath.Method))) // 节点方法详情
+ else
{
- sb.AddCode(5, $"NodeModel?.Env?.NotificationNodeValueChangeAsync(NodeModel.Guid, \"MethodDetails.\"+nameof({propertyName}), value); // 通知远程环境属性发生改变了");
- }
- else if (classInfo.ExitsPath(nameof(NodeValuePath.Parameter))) // 节点方法入参参数描述
- {
- sb.AddCode(5, "NodeModel?.Env?.NotificationNodeValueChangeAsync(NodeModel.Guid, \"MethodDetails.ParameterDetailss[\"+$\"{Index}\"+\"]." + $"\"+nameof({propertyName}),value); // 通知远程环境属性发生改变了");
- }
- else if (classInfo.ExitsPath(nameof(NodeValuePath.DebugSetting))) // 节点的调试信息
- {
- sb.AddCode(5, $"NodeModel?.Env?.NotificationNodeValueChangeAsync(NodeModel.Guid, \"DebugSetting.\"+nameof({propertyName}), value); // 通知远程环境属性发生改变了");
+ sb.AddCode(5, $"if (NodeModel?.Env?.IsControlRemoteEnv == true) // 正在控制远程环境时才触发");
+ sb.AddCode(5, $"{{");
+ if (classInfo.ExitsPath(nameof(NodeValuePath.Method))) // 节点方法详情
+ {
+ sb.AddCode(6, $"NodeModel?.Env?.NotificationNodeValueChangeAsync(NodeModel.Guid, \"MethodDetails.\"+nameof({propertyName}), value); // 通知远程环境属性发生改变了");
+ }
+ else if (classInfo.ExitsPath(nameof(NodeValuePath.Parameter))) // 节点方法入参参数描述
+ {
+ sb.AddCode(6, "NodeModel?.Env?.NotificationNodeValueChangeAsync(NodeModel.Guid, \"MethodDetails.ParameterDetailss[\"+$\"{Index}\"+\"]." + $"\"+nameof({propertyName}),value); // 通知远程环境属性发生改变了");
+ }
+ else if (classInfo.ExitsPath(nameof(NodeValuePath.DebugSetting))) // 节点的调试信息
+ {
+
+ sb.AddCode(6, $"NodeModel?.Env?.NotificationNodeValueChangeAsync(NodeModel.Guid, \"DebugSetting.\"+nameof({propertyName}), value); // 通知远程环境属性发生改变了");
+
+ }
+ sb.AddCode(5, $"}}");
}
+
}
if (attributeInfo.Search(nameof(PropertyInfo), nameof(PropertyInfo.CustomCode), value => !string.IsNullOrEmpty(value))) // 是否打印
{
diff --git a/WorkBench/MainWindow.xaml b/WorkBench/MainWindow.xaml
index a5c1efe..de96d14 100644
--- a/WorkBench/MainWindow.xaml
+++ b/WorkBench/MainWindow.xaml
@@ -89,14 +89,15 @@
-
+
+
-
+
@@ -209,21 +210,21 @@ Canvas.Top="{Binding ActualHeight, ElementName=FlowChartCanvas, Mode=OneWay, Con
-
+
-
-
-
-
+
+
+
diff --git a/WorkBench/MainWindow.xaml.cs b/WorkBench/MainWindow.xaml.cs
index 920a628..e212519 100644
--- a/WorkBench/MainWindow.xaml.cs
+++ b/WorkBench/MainWindow.xaml.cs
@@ -368,8 +368,9 @@ namespace Serein.Workbench
if (eventArgs.JunctionOfConnectionType == JunctionOfConnectionType.Invoke)
{
- #region 创建/删除节点之间的调用关系
ConnectionInvokeType connectionType = eventArgs.ConnectionInvokeType;
+ #region 创建/删除节点之间的调用关系
+ #region 创建连接
if (eventArgs.ChangeType == NodeConnectChangeEventArgs.ConnectChangeType.Create) // 添加连接
{
if (fromNodeControl is not INodeJunction IFormJunction || toNodeControl is not INodeJunction IToJunction)
@@ -383,10 +384,10 @@ namespace Serein.Workbench
// 添加连接
var connection = new ConnectionControl(
- FlowChartCanvas,
+ FlowChartCanvas,
connectionType,
startJunction,
- endJunction,
+ endJunction,
() => EnvDecorator.RemoveConnectInvokeAsync(fromNodeGuid, toNodeGuid, connectionType)
);
@@ -403,11 +404,16 @@ namespace Serein.Workbench
}
+ #endregion
+ #region 移除连接
else if (eventArgs.ChangeType == NodeConnectChangeEventArgs.ConnectChangeType.Remote) // 移除连接
{
// 需要移除连接
- var removeConnections = Connections.Where(c => c.Start.MyNode.Guid.Equals(fromNodeGuid)
- && c.End.MyNode.Guid.Equals(toNodeGuid))
+ var removeConnections = Connections.Where(c =>
+ c.Start.MyNode.Guid.Equals(fromNodeGuid)
+ && c.End.MyNode.Guid.Equals(toNodeGuid)
+ && (c.Start.JunctionType.ToConnectyionType() == JunctionOfConnectionType.Invoke
+ || c.End.JunctionType.ToConnectyionType() == JunctionOfConnectionType.Invoke))
.ToList();
@@ -417,18 +423,20 @@ namespace Serein.Workbench
Connections.Remove(connection);
fromNodeControl.RemoveCnnection(connection);
toNodeControl.RemoveCnnection(connection);
- if(NodeControls.TryGetValue(connection.End.MyNode.Guid, out var control))
+ if (NodeControls.TryGetValue(connection.End.MyNode.Guid, out var control))
{
JudgmentFlipFlopNode(control); // 连接关系变更时判断
}
}
- }
+ }
+ #endregion
#endregion
}
else
{
- #region 创建/删除节点之间的参数传递关系
ConnectionArgSourceType connectionArgSourceType = eventArgs.ConnectionArgSourceType;
+ #region 创建/删除节点之间的参数传递关系
+ #region 创建连接
if (eventArgs.ChangeType == NodeConnectChangeEventArgs.ConnectChangeType.Create) // 添加连接
{
if (fromNodeControl is not INodeJunction IFormJunction || toNodeControl is not INodeJunction IToJunction)
@@ -471,6 +479,8 @@ namespace Serein.Workbench
}
+ #endregion
+ #region 移除连接
else if (eventArgs.ChangeType == NodeConnectChangeEventArgs.ConnectChangeType.Remote) // 移除连接
{
// 需要移除连接
@@ -478,11 +488,11 @@ namespace Serein.Workbench
&& c.End.MyNode.Guid.Equals(toNodeGuid))
.ToList(); // 获取这两个节点之间的所有连接关系
-
+
foreach (var connection in removeConnections)
{
- if(connection.End is ArgJunctionControl junctionControl && junctionControl.ArgIndex == eventArgs.ArgIndex)
+ if (connection.End is ArgJunctionControl junctionControl && junctionControl.ArgIndex == eventArgs.ArgIndex)
{
// 找到符合删除条件的连接线
connection.DeleteConnection(); // 从UI层面上移除
@@ -491,13 +501,14 @@ namespace Serein.Workbench
toNodeControl.RemoveCnnection(connection); // 从节点持有的记录移除
}
-
+
//if (NodeControls.TryGetValue(connection.End.MyNode.Guid, out var control))
//{
// JudgmentFlipFlopNode(control); // 连接关系变更时判断
//}
}
- }
+ }
+ #endregion
#endregion
}
diff --git a/WorkBench/Node/View/ActionNodeControl.xaml b/WorkBench/Node/View/ActionNodeControl.xaml
index bd25f67..7baaddf 100644
--- a/WorkBench/Node/View/ActionNodeControl.xaml
+++ b/WorkBench/Node/View/ActionNodeControl.xaml
@@ -20,7 +20,7 @@
-
+
@@ -66,7 +66,7 @@
-
+
diff --git a/WorkBench/Node/View/DllControlControl.xaml.cs b/WorkBench/Node/View/DllControlControl.xaml.cs
index 8eb72ef..cb01118 100644
--- a/WorkBench/Node/View/DllControlControl.xaml.cs
+++ b/WorkBench/Node/View/DllControlControl.xaml.cs
@@ -66,14 +66,14 @@ namespace Serein.Workbench.Node.View
///
/// 向指定面板添加类型的文本块
///
- /// 要添加的类型
- /// 要添加到的面板
+ /// 要添加的方法信息
+ /// 要添加到的面板
private void AddTypeToListBox(MethodDetailsInfo mdInfo, ListBox listBox)
{
// 创建一个新的 TextBlock 并设置其属性
TextBlock typeText = new TextBlock
{
- Text = $"{mdInfo.MethodTips}",
+ Text = $"{mdInfo.MethodAnotherName} - {mdInfo.MethodName}",
Margin = new Thickness(10, 2, 0, 0),
Tag = mdInfo
};
diff --git a/WorkBench/Node/View/FlipflopNodeControl.xaml b/WorkBench/Node/View/FlipflopNodeControl.xaml
index d6e89e0..5715eb2 100644
--- a/WorkBench/Node/View/FlipflopNodeControl.xaml
+++ b/WorkBench/Node/View/FlipflopNodeControl.xaml
@@ -22,7 +22,7 @@
-
+
@@ -47,7 +47,7 @@
-
+
diff --git a/WorkBench/Themes/NodeTreeItemViewControl.xaml.cs b/WorkBench/Themes/NodeTreeItemViewControl.xaml.cs
index 113344d..4f77fb8 100644
--- a/WorkBench/Themes/NodeTreeItemViewControl.xaml.cs
+++ b/WorkBench/Themes/NodeTreeItemViewControl.xaml.cs
@@ -56,7 +56,7 @@ namespace Serein.Workbench.Themes
{ConnectionInvokeType.IsError, []},
}
};
- string? itemName = rootNodeModel.MethodDetails?.MethodTips;
+ string? itemName = rootNodeModel.MethodDetails?.MethodAnotherName;
if (string.IsNullOrEmpty(itemName))
{
itemName = rootNodeModel.ControlType.ToString();
@@ -123,7 +123,7 @@ namespace Serein.Workbench.Themes
RootNode = child,
ChildNodes = child.SuccessorNodes,
};
- string? itemName = child?.MethodDetails?.MethodTips;
+ string? itemName = child?.MethodDetails?.MethodAnotherName;
if (string.IsNullOrEmpty(itemName))
{
itemName = child?.ControlType.ToString();
@@ -186,7 +186,7 @@ namespace Serein.Workbench.Themes
ChildNodes = childNodeModel.SuccessorNodes,
};
- string? itemName = childNodeModel?.MethodDetails?.MethodTips;
+ string? itemName = childNodeModel?.MethodDetails?.MethodAnotherName;
if (string.IsNullOrEmpty(itemName))
{
itemName = childNodeModel?.ControlType.ToString();