mirror of
https://gitee.com/akwkevin/aistudio.-wpf.-diagram
synced 2026-04-06 17:26:35 +08:00
sfc界面处理完成,还差顺序逻辑控制过程
This commit is contained in:
@@ -56,12 +56,13 @@ namespace AIStudio.Wpf.ADiagram.Models
|
||||
public class SFCToolBoxData : ToolBoxData
|
||||
{
|
||||
public SFCNodeKinds Kind { get; set; }
|
||||
public SFCToolBoxData(SFCNodeKinds kind, Type type, double width = 32, double height = 32) : base(kind.GetDescription(), null, type, width, height)
|
||||
public SFCToolBoxData(SFCNodeKinds kind, Type type, double width = 32, double height = 32) : base(null, null, type, width, height)
|
||||
{
|
||||
Kind = kind;
|
||||
ColorViewModel.LineColor.Color = Colors.Black;
|
||||
}
|
||||
ColorViewModel.FillColor.Color = Colors.Blue;
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
public class DesignerItemToolBoxData : ToolBoxData
|
||||
|
||||
@@ -772,7 +772,7 @@ namespace AIStudio.Wpf.ADiagram.ViewModels
|
||||
}
|
||||
}
|
||||
|
||||
public void CenterExecuted(object para)
|
||||
public void CenterMoveExecuted(object para)
|
||||
{
|
||||
foreach (var item in DiagramViewModel.SelectedItems.OfType<DesignerItemViewModelBase>())
|
||||
{
|
||||
@@ -781,6 +781,38 @@ namespace AIStudio.Wpf.ADiagram.ViewModels
|
||||
}
|
||||
}
|
||||
|
||||
public void LeftMoveExecuted(object para)
|
||||
{
|
||||
foreach (var item in DiagramViewModel.SelectedItems.OfType<DesignerItemViewModelBase>())
|
||||
{
|
||||
item.Left -= 0.5;
|
||||
}
|
||||
}
|
||||
|
||||
public void RightMoveExecuted(object para)
|
||||
{
|
||||
foreach (var item in DiagramViewModel.SelectedItems.OfType<DesignerItemViewModelBase>())
|
||||
{
|
||||
item.Left += 0.5;
|
||||
}
|
||||
}
|
||||
|
||||
public void UpMoveExecuted(object para)
|
||||
{
|
||||
foreach (var item in DiagramViewModel.SelectedItems.OfType<DesignerItemViewModelBase>())
|
||||
{
|
||||
item.Top -= 0.5;
|
||||
}
|
||||
}
|
||||
|
||||
public void DownMoveExecuted(object para)
|
||||
{
|
||||
foreach (var item in DiagramViewModel.SelectedItems.OfType<DesignerItemViewModelBase>())
|
||||
{
|
||||
item.Top += 0.5;
|
||||
}
|
||||
}
|
||||
|
||||
public void SameWidthExecuted(object para)
|
||||
{
|
||||
if (para is DesignerItemViewModelBase designerItem)
|
||||
|
||||
@@ -98,7 +98,7 @@ namespace AIStudio.Wpf.Flowchart
|
||||
|
||||
DiagramViewModel.ClearSelectedItems();
|
||||
|
||||
FlowchartService.InitOAData(DiagramViewModel.Items.OfType<FlowNode>().ToList(), DiagramViewModel.Items.OfType<ConnectorViewModel>().ToList());
|
||||
FlowchartService.InitData(DiagramViewModel.Items.OfType<FlowNode>().ToList(), DiagramViewModel.Items.OfType<ConnectorViewModel>().ToList());
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -461,7 +461,7 @@ namespace AIStudio.Wpf.ADiagram.ViewModels
|
||||
{
|
||||
get
|
||||
{
|
||||
return this._centerCommand ?? (this._centerCommand = new DelegateCommand<object>(para => this.CenterExecuted(para)));
|
||||
return this._centerCommand ?? (this._centerCommand = new DelegateCommand<object>(para => this.CenterMoveExecuted(para)));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -706,8 +706,9 @@ namespace AIStudio.Wpf.ADiagram.ViewModels
|
||||
}
|
||||
|
||||
|
||||
private void KeyExecuted(string para)
|
||||
public bool KeyExecuted(string para)
|
||||
{
|
||||
bool executed = true;
|
||||
switch (para)
|
||||
{
|
||||
case "Control+A": SelectedAllExecuted(); break;
|
||||
@@ -719,8 +720,15 @@ namespace AIStudio.Wpf.ADiagram.ViewModels
|
||||
case "Control+S": SaveExecuted(); break;
|
||||
case "Control+Z": UnDoExecuted(); break;
|
||||
case "Control+Y": ReDoExecuted(); break;
|
||||
case "None+Delete": DeleteExecuted(); break;
|
||||
case "Delete": DeleteExecuted(); break;
|
||||
case "Left": LeftMoveExecuted(); break;
|
||||
case "Right": RightMoveExecuted(); break;
|
||||
case "Up": UpMoveExecuted(); break;
|
||||
case "Down": DownMoveExecuted(); break;
|
||||
default: executed = false; break;
|
||||
}
|
||||
|
||||
return executed;
|
||||
}
|
||||
|
||||
private void UnDoExecuted()
|
||||
@@ -889,6 +897,10 @@ namespace AIStudio.Wpf.ADiagram.ViewModels
|
||||
{
|
||||
DiagramsViewModel = new LogicalViewModel(NewNameHelper.GetNewName(DiagramsViewModels.Select(p => p.Title), "新建-"), "*", (DiagramType)Enum.Parse(typeof(DiagramType), type));
|
||||
}
|
||||
else if (type == DiagramType.SFC.ToString())
|
||||
{
|
||||
DiagramsViewModel = new SFCViewModel(NewNameHelper.GetNewName(DiagramsViewModels.Select(p => p.Title), "新建-"), "*", (DiagramType)Enum.Parse(typeof(DiagramType), type));
|
||||
}
|
||||
else
|
||||
{
|
||||
DiagramsViewModel = new DiagramsViewModel(NewNameHelper.GetNewName(DiagramsViewModels.Select(p => p.Title), "新建-"), "*", (DiagramType)Enum.Parse(typeof(DiagramType), type));
|
||||
@@ -993,11 +1005,39 @@ namespace AIStudio.Wpf.ADiagram.ViewModels
|
||||
}
|
||||
#endregion
|
||||
|
||||
private void CenterExecuted(object para)
|
||||
private void CenterMoveExecuted(object para)
|
||||
{
|
||||
if (DiagramsViewModel == null) return;
|
||||
|
||||
DiagramsViewModel.CenterExecuted(para);
|
||||
DiagramsViewModel.CenterMoveExecuted(para);
|
||||
}
|
||||
|
||||
private void LeftMoveExecuted(object para = null)
|
||||
{
|
||||
if (DiagramsViewModel == null) return;
|
||||
|
||||
DiagramsViewModel.LeftMoveExecuted(para);
|
||||
}
|
||||
|
||||
private void RightMoveExecuted(object para = null)
|
||||
{
|
||||
if (DiagramsViewModel == null) return;
|
||||
|
||||
DiagramsViewModel.RightMoveExecuted(para);
|
||||
}
|
||||
|
||||
private void UpMoveExecuted(object para = null)
|
||||
{
|
||||
if (DiagramsViewModel == null) return;
|
||||
|
||||
DiagramsViewModel.UpMoveExecuted(para);
|
||||
}
|
||||
|
||||
private void DownMoveExecuted(object para = null)
|
||||
{
|
||||
if (DiagramsViewModel == null) return;
|
||||
|
||||
DiagramsViewModel.DownMoveExecuted(para);
|
||||
}
|
||||
|
||||
private void SameWidthExecuted(object para)
|
||||
|
||||
247
AIStudio.Wpf.ADiagram/ViewModels/SFCViewModel.cs
Normal file
247
AIStudio.Wpf.ADiagram/ViewModels/SFCViewModel.cs
Normal file
@@ -0,0 +1,247 @@
|
||||
using AIStudio.Wpf.ADiagram.ViewModels;
|
||||
using AIStudio.Wpf.Flowchart.ViewModels;
|
||||
using AIStudio.Wpf.SFC;
|
||||
using AIStudio.Wpf.SFC.ViewModels;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Collections.ObjectModel;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
using System.Windows;
|
||||
using System.Windows.Media;
|
||||
using Util.DiagramDesigner;
|
||||
|
||||
namespace AIStudio.Wpf.Flowchart
|
||||
{
|
||||
public class SFCViewModel : DiagramsViewModel
|
||||
{
|
||||
public SFCViewModel(string title, string status, DiagramType diagramType) : base(title, status, diagramType)
|
||||
{
|
||||
|
||||
}
|
||||
public SFCViewModel(string filename) : base(filename)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
protected override void InitDiagramViewModel()
|
||||
{
|
||||
base.InitDiagramViewModel();
|
||||
|
||||
DiagramViewModel.ShowGrid = true;
|
||||
DiagramViewModel.GridCellSize = new Size(100, 60);
|
||||
DiagramViewModel.CellHorizontalAlignment = CellHorizontalAlignment.Center;
|
||||
DiagramViewModel.CellVerticalAlignment = CellVerticalAlignment.Center;
|
||||
}
|
||||
|
||||
protected override void Init()
|
||||
{
|
||||
base.Init();
|
||||
|
||||
SFCStartNode start = new SFCStartNode() { Left = 0, Top = 60, Text = "S0" };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(start);
|
||||
|
||||
SFCConditionNode condition1 = new SFCConditionNode() { Left = 0, Top = 120, Text = "X0" };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(condition1);
|
||||
|
||||
SFCNodeNode step1 = new SFCNodeNode() { Left = 0, Top = 180, Text = "S1" };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(step1);
|
||||
|
||||
SFCActionNode action11 = new SFCActionNode() { Left = 100, Top = 180, Text = "SET_V1" };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(action11);
|
||||
|
||||
SFCActionNode action12 = new SFCActionNode() { Left = 200, Top = 180, Text = "SET_V2" };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(action12);
|
||||
|
||||
SFCActionNode action13 = new SFCActionNode() { Left = 300, Top = 180, Text = "SET_V3" };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(action13);
|
||||
|
||||
SFCActionNode action14 = new SFCActionNode() { Left = 400, Top = 180, Text = "RES_V4" };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(action14);
|
||||
|
||||
SFCConditionNode condition2 = new SFCConditionNode() { Left = 0, Top = 240, Text = "X1" };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(condition2);
|
||||
|
||||
SFCNodeNode step2 = new SFCNodeNode() { Left = 0, Top = 300, Text = "S2" };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(step2);
|
||||
|
||||
SFCActionNode action2 = new SFCActionNode() { Left = 100, Top = 300, Text = "SET_V4" };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(action2);
|
||||
|
||||
SFCConditionNode condition3 = new SFCConditionNode() { Left = 0, Top = 360, Text = "X2" };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(condition3);
|
||||
|
||||
SFCNodeNode step3 = new SFCNodeNode() { Left = 0, Top = 420, Text = "S3" };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(step3);
|
||||
|
||||
SFCActionNode action3 = new SFCActionNode() { Left = 100, Top = 420, Text = "RES_V1" };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(action3);
|
||||
|
||||
SFCConditionNode condition4 = new SFCConditionNode() { Left = 0, Top = 480, Text = "X4" };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(condition4);
|
||||
|
||||
SFCCOBeginNode cobegin = new SFCCOBeginNode() { Left = 38, Top = 540, Text = "" };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(cobegin);
|
||||
|
||||
SFCNodeNode step4 = new SFCNodeNode() { Left = 0, Top = 600, Text = "S4" };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(step4);
|
||||
|
||||
SFCActionNode action4 = new SFCActionNode() { Left = 100, Top = 600, Text = "RES_V2" };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(action4);
|
||||
|
||||
SFCNodeNode step5 = new SFCNodeNode() { Left = 200, Top = 600, Text = "S5" };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(step5);
|
||||
|
||||
SFCActionNode action5 = new SFCActionNode() { Left = 300, Top = 600, Text = "RES_V3" };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(action5);
|
||||
|
||||
SFCCOEndNode coend = new SFCCOEndNode() { Left = 38, Top = 660, Text = "" };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(coend);
|
||||
|
||||
ConnectorViewModel connector1 = new ConnectorViewModel(start.Output[0], condition1.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector1);
|
||||
|
||||
ConnectorViewModel connector2 = new ConnectorViewModel(condition1.Output[0], step1.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector2);
|
||||
|
||||
ConnectorViewModel connector31 = new ConnectorViewModel(step1.Action[0], action11.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector31);
|
||||
|
||||
ConnectorViewModel connector32 = new ConnectorViewModel(step1.Action[0], action12.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector32);
|
||||
|
||||
ConnectorViewModel connector33 = new ConnectorViewModel(step1.Action[0], action13.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector33);
|
||||
|
||||
ConnectorViewModel connector34 = new ConnectorViewModel(step1.Action[0], action14.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector34);
|
||||
|
||||
ConnectorViewModel connector4 = new ConnectorViewModel(step1.Output[0], condition2.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector4);
|
||||
|
||||
ConnectorViewModel connector5 = new ConnectorViewModel(condition2.Output[0], step2.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector5);
|
||||
|
||||
ConnectorViewModel connector6 = new ConnectorViewModel(step2.Action[0], action2.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector6);
|
||||
|
||||
ConnectorViewModel connector7 = new ConnectorViewModel(step2.Output[0], condition3.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector7);
|
||||
|
||||
ConnectorViewModel connector8 = new ConnectorViewModel(condition3.Output[0], step3.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector8);
|
||||
|
||||
ConnectorViewModel connector9 = new ConnectorViewModel(step3.Action[0], action3.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector9);
|
||||
|
||||
ConnectorViewModel connector10 = new ConnectorViewModel(step3.Output[0], condition4.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector10);
|
||||
|
||||
ConnectorViewModel connector11 = new ConnectorViewModel(condition4.Output[0], cobegin.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector11);
|
||||
|
||||
ConnectorViewModel connector12 = new ConnectorViewModel(cobegin.Output[0], step4.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector12);
|
||||
|
||||
ConnectorViewModel connector13 = new ConnectorViewModel(step4.Action[0], action4.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector13);
|
||||
|
||||
ConnectorViewModel connector14 = new ConnectorViewModel(cobegin.Output[1], step5.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector14);
|
||||
|
||||
ConnectorViewModel connector15 = new ConnectorViewModel(step5.Action[0], action5.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector15);
|
||||
|
||||
ConnectorViewModel connector16 = new ConnectorViewModel(step4.Output[0], coend.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector16);
|
||||
|
||||
ConnectorViewModel connector17 = new ConnectorViewModel(step5.Output[0], coend.Input[1]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector17);
|
||||
|
||||
ConnectorViewModel connector18 = new ConnectorViewModel(coend.Output[0], start.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(connector18);
|
||||
|
||||
#region 模拟部分
|
||||
TextDesignerItemViewModel despcription = new TextDesignerItemViewModel()
|
||||
{
|
||||
Left = 230,
|
||||
Top = 270,
|
||||
ItemWidth = 300,
|
||||
ItemHeight = 120,
|
||||
Text = @"模拟一个容器的高低液位控制方法
|
||||
1.按下启动按钮, 程序启动
|
||||
2.当液位低于20%的时候, V1,V2,V3打开, V4关闭
|
||||
3.当液位高于50%的时候, V4打开
|
||||
4.当液位高于70%的时侯, V1关闭
|
||||
5.当液位高于80%的时候, V2,V3并行关闭"
|
||||
};
|
||||
despcription.FontViewModel.HorizontalAlignment = HorizontalAlignment.Left;
|
||||
despcription.FontViewModel.VerticalAlignment = VerticalAlignment.Top;
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(despcription);
|
||||
|
||||
Simulate_ListViewModel list = new Simulate_ListViewModel()
|
||||
{
|
||||
Left = 410,
|
||||
Top = 390,
|
||||
};
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(list);
|
||||
|
||||
Simulate_StartViewModel btnstart = new Simulate_StartViewModel() { Left = 0, Top = 0, LinkPoint = SFCService.LinkPoint.FirstOrDefault(p => p.Name == "S0"), };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(btnstart);
|
||||
|
||||
Simulate_TankViewModel tank1 = new Simulate_TankViewModel() { Left = 100, Top = 43, ItemWidth = 48, ItemHeight = 60, Text = "T1", LinkPoint = SFCService.LinkPoint.FirstOrDefault(p => p.Name == "T1") };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(tank1);
|
||||
|
||||
Simulate_SolenoidViewModel k1 = new Simulate_SolenoidViewModel() { Left = 200, Top = 0, Text = "K1", DILinkPoint = SFCService.LinkPoint.FirstOrDefault(p => p.Name == "K1_DI"), DOLinkPoint = SFCService.LinkPoint.FirstOrDefault(p => p.Name == "K1_DO") };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(k1);
|
||||
|
||||
Simulate_SolenoidViewModel k2 = new Simulate_SolenoidViewModel() { Left = 200, Top = 60, Text = "K2", DILinkPoint = SFCService.LinkPoint.FirstOrDefault(p => p.Name == "K2_DI"), DOLinkPoint = SFCService.LinkPoint.FirstOrDefault(p => p.Name == "K2_DO") };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(k2);
|
||||
|
||||
Simulate_SolenoidViewModel k3 = new Simulate_SolenoidViewModel() { Left = 200, Top = 120, Text = "K3", DILinkPoint = SFCService.LinkPoint.FirstOrDefault(p => p.Name == "K3_DI"), DOLinkPoint = SFCService.LinkPoint.FirstOrDefault(p => p.Name == "K3_DO") };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(k3);
|
||||
|
||||
Simulate_TankViewModel tank2 = new Simulate_TankViewModel() { Left = 300, Top = 28, Text = "T2", LinkPoint = SFCService.LinkPoint.FirstOrDefault(p => p.Name == "T2") };
|
||||
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(tank2);
|
||||
|
||||
Simulate_SolenoidViewModel k4 = new Simulate_SolenoidViewModel() { Left = 400, Top = 60, Text = "K4", DILinkPoint = SFCService.LinkPoint.FirstOrDefault(p => p.Name == "K4_DI"), DOLinkPoint = SFCService.LinkPoint.FirstOrDefault(p => p.Name == "K4_DO") };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(k4);
|
||||
|
||||
Simulate_TankViewModel tank3 = new Simulate_TankViewModel() { Left = 500, Top = 103, ItemWidth = 48, ItemHeight = 60, Text = "T3", LinkPoint = SFCService.LinkPoint.FirstOrDefault(p => p.Name == "T3") };
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(tank3);
|
||||
|
||||
ConnectorViewModel conn1 = new ConnectorViewModel(tank1.Output[0], k1.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(conn1);
|
||||
|
||||
ConnectorViewModel conn2 = new ConnectorViewModel(tank1.Output[0], k2.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(conn2);
|
||||
|
||||
ConnectorViewModel conn3 = new ConnectorViewModel(tank1.Output[0], k3.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(conn3);
|
||||
|
||||
ConnectorViewModel conn4 = new ConnectorViewModel(k1.Output[0], tank2.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(conn4);
|
||||
|
||||
ConnectorViewModel conn5 = new ConnectorViewModel(k2.Output[0], tank2.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(conn5);
|
||||
|
||||
ConnectorViewModel conn6 = new ConnectorViewModel(k3.Output[0], tank2.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(conn6);
|
||||
|
||||
ConnectorViewModel conn7 = new ConnectorViewModel(tank2.Output[1], k4.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(conn7);
|
||||
|
||||
ConnectorViewModel conn8 = new ConnectorViewModel(k4.Output[0], tank3.Input[0]);
|
||||
DiagramViewModel.DirectAddItemCommand.Execute(conn8);
|
||||
#endregion
|
||||
|
||||
DiagramViewModel.ClearSelectedItems();
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
@@ -15,6 +15,7 @@ using Util.DiagramDesigner;
|
||||
using Util.DiagramDesigner.Helpers;
|
||||
using AIStudio.Wpf.SFC;
|
||||
using AIStudio.Wpf.SFC.ViewModels;
|
||||
using System.Windows.Media;
|
||||
|
||||
namespace AIStudio.Wpf.ADiagram.ViewModels
|
||||
{
|
||||
@@ -186,7 +187,9 @@ namespace AIStudio.Wpf.ADiagram.ViewModels
|
||||
sfcToolBoxItems.Add(new SFCToolBoxData(SFCNodeKinds.Action, typeof(SFCActionNode), 32, 28));
|
||||
sfcToolBoxItems.Add(new SFCToolBoxData(SFCNodeKinds.COBegin, typeof(SFCCOBeginNode), 32, 10));
|
||||
sfcToolBoxItems.Add(new SFCToolBoxData(SFCNodeKinds.COEnd, typeof(SFCCOEndNode), 32, 10));
|
||||
|
||||
sfcToolBoxItems.Add(new SFCToolBoxData(SFCNodeKinds.Simulate_Tank, typeof(Simulate_TankViewModel), 32, 32));
|
||||
sfcToolBoxItems.Add(new SFCToolBoxData(SFCNodeKinds.Simulate_Solenoid, typeof(Simulate_SolenoidViewModel)));
|
||||
sfcToolBoxItems.Add(new SFCToolBoxData(SFCNodeKinds.Simulate_Start, typeof(Simulate_StartViewModel)));
|
||||
ToolBoxCategory.Add(new ToolBoxCategory() { Header = "SFC顺序控制图", ToolBoxItems = new ObservableCollection<ToolBoxData>(sfcToolBoxItems) });
|
||||
|
||||
LoadMyItems();
|
||||
|
||||
@@ -91,6 +91,9 @@
|
||||
<Button Margin="5" ToolTip="逻辑图" Command="{Binding NewCommand}" CommandParameter="Logical" Width="80" Height="80" Foreground="{DynamicResource BlackBrush}" Background="{DynamicResource WhiteBrush}" BorderBrush="{DynamicResource BlackBrush}">
|
||||
<Path Stretch="Fill" Margin="20" Fill="{DynamicResource GrayBrush2}" Data="M 23.6584,49.0333L 23.5634,46.9483L 22.5134,47.9133C 22.1467,48.2067 21.7434,48.4608 21.3034,48.6758C 20.8634,48.8908 20.3851,49.0575 19.8684,49.1758C 19.3517,49.2942 18.7851,49.3533 18.1684,49.3533C 17.3517,49.3533 16.6351,49.2317 16.0184,48.9883C 15.4017,48.745 14.8842,48.4067 14.4659,47.9733C 14.0476,47.54 13.7309,47.0167 13.5159,46.4033C 13.3009,45.79 13.1934,45.115 13.1934,44.3783C 13.1934,43.615 13.3526,42.9108 13.6709,42.2658C 13.9892,41.6208 14.4759,41.0667 15.1309,40.6033C 15.7859,40.14 16.6026,39.7758 17.5809,39.5108C 18.5592,39.2458 19.7067,39.1133 21.0234,39.1133L 23.1134,39.1133L 23.1134,38.1833C 23.1134,37.7867 23.0559,37.4283 22.9409,37.1083C 22.8259,36.7883 22.6409,36.5167 22.3859,36.2933C 22.1309,36.07 21.8001,35.8975 21.3934,35.7758C 20.9867,35.6542 20.4867,35.5933 19.8934,35.5933C 18.9567,35.5933 18.0326,35.7058 17.1209,35.9308C 16.2092,36.1558 15.3267,36.47 14.4734,36.8733L 14.4734,33.6733C 15.2367,33.3967 16.1167,33.1675 17.1134,32.9858C 18.1101,32.8042 19.1451,32.7133 20.2184,32.7133C 21.3984,32.7133 22.4117,32.8258 23.2584,33.0508C 24.1051,33.2758 24.8017,33.6142 25.3484,34.0658C 25.8951,34.5175 26.2992,35.0808 26.5609,35.7558C 26.8226,36.4308 26.9534,37.22 26.9534,38.1233L 26.9534,49.0333L 23.6584,49.0333 Z M 23.1134,41.9934L 20.8284,41.9934C 20.1984,41.9934 19.6634,42.0575 19.2234,42.1859C 18.7834,42.3142 18.4259,42.4909 18.1509,42.7159C 17.8759,42.9409 17.6742,43.2009 17.5459,43.4959C 17.4176,43.7909 17.3534,44.1033 17.3534,44.4333C 17.3534,45.0967 17.5576,45.6025 17.9659,45.9509C 18.3742,46.2992 18.9317,46.4734 19.6384,46.4734C 20.1584,46.4734 20.6992,46.275 21.2609,45.8783C 21.8226,45.4817 22.4401,44.915 23.1134,44.1784L 23.1134,41.9934 Z M 40.0334,49.0333L 40.0334,38.5584C 40.0334,36.795 39.3751,35.9134 38.0584,35.9134C 37.4017,35.9134 36.7734,36.1775 36.1734,36.7059C 35.5734,37.2342 34.9401,37.9517 34.2734,38.8583L 34.2734,49.0333L 30.4334,49.0334L 30.4334,33.0334L 33.7584,33.0334L 33.8534,35.3934L 34.8734,34.2859C 35.2267,33.9542 35.6092,33.6717 36.0209,33.4384C 36.4326,33.205 36.8759,33.0259 37.3509,32.9009C 37.8259,32.7759 38.3584,32.7134 38.9484,32.7134C 39.7717,32.7134 40.4901,32.8467 41.1034,33.1134C 41.7167,33.38 42.2292,33.7575 42.6409,34.2459C 43.0526,34.7342 43.3609,35.3217 43.5659,36.0084C 43.7709,36.695 43.8734,37.4617 43.8734,38.3084L 43.8734,49.0333L 40.0334,49.0333 Z M 57.6534,49.0333L 57.5584,46.6883L 56.5159,47.7808C 56.1576,48.1092 55.7734,48.3892 55.3634,48.6208C 54.9534,48.8525 54.5142,49.0325 54.0459,49.1609C 53.5776,49.2892 53.0601,49.3533 52.4934,49.3533C 51.5467,49.3533 50.7051,49.1642 49.9684,48.7859C 49.2317,48.4075 48.6134,47.87 48.1134,47.1733C 47.6134,46.4767 47.2317,45.6292 46.9684,44.6309C 46.7051,43.6325 46.5734,42.52 46.5734,41.2933C 46.5734,39.8233 46.7809,38.5508 47.1959,37.4758C 47.6109,36.4008 48.1867,35.5092 48.9234,34.8008C 49.6601,34.0925 50.5342,33.5675 51.5459,33.2259C 52.5576,32.8842 53.6567,32.7134 54.8434,32.7134L 56.0509,32.7909L 57.1334,32.9934L 57.1334,26.9534L 60.9734,26.9534L 60.9734,49.0333L 57.6534,49.0333 Z M 50.7334,41.0983C 50.7334,42.0017 50.7926,42.7725 50.9109,43.4108C 51.0292,44.0492 51.2051,44.5717 51.4384,44.9783C 51.6717,45.385 51.9584,45.6825 52.2984,45.8708C 52.6384,46.0592 53.0251,46.1534 53.4584,46.1534C 54.1017,46.1534 54.7126,45.885 55.2909,45.3484C 55.8692,44.8117 56.4834,44.0767 57.1334,43.1433L 57.1334,35.9933L 56.0259,35.7059L 54.6984,35.5933C 54.0917,35.5933 53.5451,35.7225 53.0584,35.9809C 52.5717,36.2392 52.1559,36.6042 51.8109,37.0758C 51.4659,37.5475 51.2001,38.1242 51.0134,38.8059C 50.8267,39.4875 50.7334,40.2517 50.7334,41.0983 Z M 36,60L 36,63L 33,63L 33,67L 36,67L 36,70L 40,70L 40,67L 43,67L 43,63L 40,63L 40,60L 36,60 Z M 38,73C 25.6744,73 14.8369,66.6288 8.60116,57L 67.3988,57C 61.1631,66.6288 50.3256,73 38,73 Z " ></Path>
|
||||
</Button>
|
||||
<Button Margin="5" ToolTip="顺序控制图" Command="{Binding NewCommand}" CommandParameter="SFC" Width="80" Height="80" Foreground="{DynamicResource BlackBrush}" Background="{DynamicResource WhiteBrush}" BorderBrush="{DynamicResource BlackBrush}">
|
||||
<Path Stretch="Fill" Margin="20" Fill="{DynamicResource GrayBrush2}" Data="M10.984 13.836a.5.5 0 0 1-.353-.146l-.745-.743a.5.5 0 1 1 .706-.708l.392.391 1.181-1.18a.5.5 0 0 1 .708.707l-1.535 1.533a.504.504 0 0 1-.354.146zm9.353-.147l1.534-1.532a.5.5 0 0 0-.707-.707l-1.181 1.18-.392-.391a.5.5 0 1 0-.706.708l.746.743a.497.497 0 0 0 .706-.001zM4.527 7.452l2.557-1.585A1 1 0 0 0 7.09 4.17L4.533 2.56A1 1 0 0 0 3 3.406v3.196a1.001 1.001 0 0 0 1.527.85zm2.03-2.436L4 6.602V3.406l2.557 1.61zM24 12.5c0 1.93-1.57 3.5-3.5 3.5a3.503 3.503 0 0 1-3.46-3h-2.08a3.503 3.503 0 0 1-3.46 3 3.502 3.502 0 0 1-3.46-3h-.558c-.972 0-1.85-.399-2.482-1.042V17c0 1.654 1.346 3 3 3h.04c.244-1.693 1.7-3 3.46-3 1.93 0 3.5 1.57 3.5 3.5S13.43 24 11.5 24a3.502 3.502 0 0 1-3.46-3H8c-2.206 0-4-1.794-4-4V9.899A5.008 5.008 0 0 1 0 5c0-2.757 2.243-5 5-5s5 2.243 5 5a5.005 5.005 0 0 1-4.952 4.998A2.482 2.482 0 0 0 7.482 12h.558c.244-1.693 1.7-3 3.46-3a3.502 3.502 0 0 1 3.46 3h2.08a3.503 3.503 0 0 1 3.46-3c1.93 0 3.5 1.57 3.5 3.5zm-15 8c0 1.378 1.122 2.5 2.5 2.5s2.5-1.122 2.5-2.5-1.122-2.5-2.5-2.5S9 19.122 9 20.5zM5 9c2.206 0 4-1.794 4-4S7.206 1 5 1 1 2.794 1 5s1.794 4 4 4zm9 3.5c0-1.378-1.122-2.5-2.5-2.5S9 11.122 9 12.5s1.122 2.5 2.5 2.5 2.5-1.122 2.5-2.5zm9 0c0-1.378-1.122-2.5-2.5-2.5S18 11.122 18 12.5s1.122 2.5 2.5 2.5 2.5-1.122 2.5-2.5zm-13 8a.5.5 0 1 0 1 0 .5.5 0 0 0-1 0zm2 0a.5.5 0 1 0 1 0 .5.5 0 0 0-1 0zm12 0c0 1.93-1.57 3.5-3.5 3.5a3.503 3.503 0 0 1-3.46-3.002c-.007.001-.013.005-.021.005l-.506.017h-.017a.5.5 0 0 1-.016-.999l.506-.017c.018-.002.035.006.052.007A3.503 3.503 0 0 1 20.5 17c1.93 0 3.5 1.57 3.5 3.5zm-1 0c0-1.378-1.122-2.5-2.5-2.5S18 19.122 18 20.5s1.122 2.5 2.5 2.5 2.5-1.122 2.5-2.5z" ></Path>
|
||||
</Button>
|
||||
</WrapPanel>
|
||||
</TabItem>
|
||||
<TabItem Header="待续" />
|
||||
|
||||
@@ -40,10 +40,8 @@ namespace AIStudio.Wpf.ADiagram
|
||||
|
||||
protected override void OnPreviewKeyDown(KeyEventArgs e)
|
||||
{
|
||||
base.OnPreviewKeyDown(e);
|
||||
|
||||
MainWindowViewModel.KeyCommand.Execute(e.KeyboardDevice.Modifiers.ToString() + "+" + e.Key.ToString());
|
||||
}
|
||||
e.Handled = MainWindowViewModel.KeyExecuted(e.KeyboardDevice.Modifiers == ModifierKeys.None ? e.Key.ToString() : e.KeyboardDevice.Modifiers.ToString() + "+" + e.Key.ToString());
|
||||
}
|
||||
|
||||
private void HookEvents()
|
||||
{
|
||||
|
||||
@@ -16,8 +16,10 @@
|
||||
<ResourceDictionary>
|
||||
<conventer:StringPathConverter x:Key="stringPathConverter"/>
|
||||
<conventer:IntVisibilityConverter x:Key="IntVisibilityConverter"/>
|
||||
<dd:EnumDescriptionConverter x:Key="EnumDescriptionConverter"/>
|
||||
<command:CommandReference x:Key="DeleteItemCommandReference" Command="{Binding DeleteItemCommand}"/>
|
||||
|
||||
|
||||
<DataTemplate DataType="{x:Type model:ImageToolBoxData}">
|
||||
<Grid Width="{Binding Width}" Height="{Binding Height}">
|
||||
<Rectangle Name="Border"
|
||||
@@ -165,7 +167,7 @@
|
||||
Fill="Transparent"
|
||||
SnapsToDevicePixels="true"/>
|
||||
<Viewbox Stretch="Fill">
|
||||
<Grid>
|
||||
<Grid IsHitTestVisible="False">
|
||||
<ContentControl Style="{StaticResource CustomFlowNodeStyle}" Margin="2"/>
|
||||
<TextBlock Text="{Binding Text}" Margin="5" Foreground="{Binding ColorViewModel.LineColor,Converter={StaticResource ColorBrushConverter}}" HorizontalAlignment="Left" />
|
||||
</Grid>
|
||||
@@ -178,14 +180,14 @@
|
||||
</DataTemplate.Triggers>
|
||||
</DataTemplate>
|
||||
<DataTemplate DataType="{x:Type model:SFCToolBoxData}">
|
||||
<Grid Width="{Binding Width}" Height="{Binding Height}">
|
||||
<Grid Width="{Binding Width}" Height="{Binding Height}" ToolTip="{Binding Kind,Converter={StaticResource EnumDescriptionConverter}}">
|
||||
<Rectangle Name="Border"
|
||||
StrokeThickness="1"
|
||||
StrokeDashArray="2"
|
||||
Fill="Transparent"
|
||||
SnapsToDevicePixels="true"/>
|
||||
<Grid ToolTip="{Binding Text}">
|
||||
<ContentControl Style="{StaticResource CustomSFCNodeStyle}" Margin="2"/>
|
||||
<Grid IsHitTestVisible="False">
|
||||
<ContentControl Style="{StaticResource CustomSFCNodeStyle}" Margin="2" />
|
||||
</Grid>
|
||||
</Grid>
|
||||
<DataTemplate.Triggers>
|
||||
|
||||
176
AIStudio.Wpf.BaseDiagram/Converters/Converters.cs
Normal file
176
AIStudio.Wpf.BaseDiagram/Converters/Converters.cs
Normal file
@@ -0,0 +1,176 @@
|
||||
using System;
|
||||
using System.ComponentModel;
|
||||
using System.Globalization;
|
||||
using System.Windows;
|
||||
using System.Windows.Data;
|
||||
|
||||
namespace AIStudio.Wpf.BaseDiagram.Converters
|
||||
{
|
||||
#region Half
|
||||
public class HalfConverter : IValueConverter
|
||||
{
|
||||
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
|
||||
{
|
||||
var doubleValue = (value as double?).GetValueOrDefault();
|
||||
|
||||
return doubleValue / 2;
|
||||
}
|
||||
|
||||
public object ConvertBack(object value, Type targetTypes, object parameter, CultureInfo culture)
|
||||
{
|
||||
return DependencyProperty.UnsetValue;
|
||||
}
|
||||
}
|
||||
#endregion
|
||||
|
||||
#region String IsNullOrEmpty
|
||||
public class IsNullOrEmptyConverter : IValueConverter
|
||||
{
|
||||
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
|
||||
{
|
||||
return string.IsNullOrEmpty((string)value);
|
||||
}
|
||||
|
||||
public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
|
||||
{
|
||||
return DependencyProperty.UnsetValue;
|
||||
}
|
||||
}
|
||||
#endregion
|
||||
|
||||
#region True -> False
|
||||
public class BoolInverseConverter : IValueConverter
|
||||
{
|
||||
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
|
||||
{
|
||||
return !(bool)value;
|
||||
}
|
||||
|
||||
public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
|
||||
{
|
||||
return DependencyProperty.UnsetValue;
|
||||
}
|
||||
}
|
||||
#endregion
|
||||
|
||||
#region True -> Visible Or Collpased
|
||||
public class BoolToVisibleConverter : IValueConverter
|
||||
{
|
||||
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
|
||||
{
|
||||
return (bool)value ? Visibility.Visible : Visibility.Collapsed;
|
||||
}
|
||||
|
||||
public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
|
||||
{
|
||||
return DependencyProperty.UnsetValue;
|
||||
}
|
||||
}
|
||||
|
||||
public class BoolToInvisibleConverter : IValueConverter
|
||||
{
|
||||
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
|
||||
{
|
||||
return (bool)value ? Visibility.Collapsed : Visibility.Visible;
|
||||
}
|
||||
|
||||
public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
|
||||
{
|
||||
return DependencyProperty.UnsetValue;
|
||||
}
|
||||
}
|
||||
#endregion
|
||||
|
||||
#region object try to convert to image (if is uri)
|
||||
public class IconConverter : IValueConverter
|
||||
{
|
||||
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
|
||||
{
|
||||
if (value == null || !(value.GetType() == typeof(string)))
|
||||
return value;
|
||||
|
||||
var iconString = value as string;
|
||||
|
||||
if (!string.IsNullOrEmpty(iconString) && Uri.IsWellFormedUriString(iconString, UriKind.RelativeOrAbsolute))
|
||||
{
|
||||
var image = new System.Windows.Controls.Image()
|
||||
{
|
||||
Source = new System.Windows.Media.Imaging.BitmapImage(new Uri(iconString, UriKind.RelativeOrAbsolute)),
|
||||
};
|
||||
System.Windows.Media.RenderOptions.SetBitmapScalingMode(image, System.Windows.Media.BitmapScalingMode.HighQuality);
|
||||
return image;
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
|
||||
{
|
||||
return DependencyProperty.UnsetValue;
|
||||
}
|
||||
}
|
||||
#endregion
|
||||
|
||||
#region Double -> GridLength
|
||||
public class GridLengthConverter : IValueConverter
|
||||
{
|
||||
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
|
||||
{
|
||||
var length = value?.ToString();
|
||||
try
|
||||
{
|
||||
return (GridLength)TypeDescriptor.GetConverter(typeof(GridLength)).ConvertFromString(length);
|
||||
}
|
||||
catch
|
||||
{
|
||||
return new GridLength(1, GridUnitType.Auto);
|
||||
}
|
||||
}
|
||||
|
||||
public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
|
||||
{
|
||||
return DependencyProperty.UnsetValue;
|
||||
}
|
||||
}
|
||||
#endregion
|
||||
|
||||
#region Combiner
|
||||
public class MultiCombinerConverter : IMultiValueConverter
|
||||
{
|
||||
public object Convert(object[] values, Type targetType, object parameter, CultureInfo culture)
|
||||
{
|
||||
return values.Clone();
|
||||
}
|
||||
|
||||
public object[] ConvertBack(object value, Type[] targetTypes, object parameter, CultureInfo culture)
|
||||
{
|
||||
return new object[] { DependencyProperty.UnsetValue, DependencyProperty.UnsetValue };
|
||||
}
|
||||
}
|
||||
#endregion
|
||||
|
||||
#region NotAlignmentCenter
|
||||
public class NotAlignmentCenterConverter : IValueConverter
|
||||
{
|
||||
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
|
||||
{
|
||||
if (value is HorizontalAlignment)
|
||||
{
|
||||
var alignment = (HorizontalAlignment)value;
|
||||
return alignment != HorizontalAlignment.Center;
|
||||
}
|
||||
else if (value is VerticalAlignment)
|
||||
{
|
||||
var alignment = (VerticalAlignment)value;
|
||||
return alignment != VerticalAlignment.Center;
|
||||
}
|
||||
else
|
||||
return true;
|
||||
}
|
||||
|
||||
public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
|
||||
{
|
||||
return DependencyProperty.UnsetValue;
|
||||
}
|
||||
}
|
||||
#endregion
|
||||
}
|
||||
24
AIStudio.Wpf.BaseDiagram/Converters/IntToBoolConverter.cs
Normal file
24
AIStudio.Wpf.BaseDiagram/Converters/IntToBoolConverter.cs
Normal file
@@ -0,0 +1,24 @@
|
||||
using System;
|
||||
using System.Windows.Data;
|
||||
|
||||
namespace AIStudio.Wpf.BaseDiagram.Converters
|
||||
{
|
||||
public class IntToBoolConverter : IValueConverter
|
||||
{
|
||||
public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
|
||||
{
|
||||
if (object.Equals(value, 0d))
|
||||
return false;
|
||||
else
|
||||
return true;
|
||||
}
|
||||
|
||||
public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
|
||||
{
|
||||
if (object.Equals(value, false))
|
||||
return 0d;
|
||||
else
|
||||
return 1d;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -31,7 +31,6 @@ namespace AIStudio.Wpf.BaseDiagram.Extensions.ViewModels
|
||||
base.LoadDesignerItemViewModel(parent, designerbase);
|
||||
|
||||
Format = (BarcodeFormat)Enum.Parse(typeof(BarcodeFormat), (designerbase as DesignerItemBase).Reserve.ToString());
|
||||
ShowText = false;
|
||||
}
|
||||
|
||||
public void AutoSize()
|
||||
@@ -54,6 +53,19 @@ namespace AIStudio.Wpf.BaseDiagram.Extensions.ViewModels
|
||||
|
||||
public BarcodeFormat Format { get; set; } = BarcodeFormat.QR_CODE;
|
||||
|
||||
private bool _showText;
|
||||
public override bool ShowText
|
||||
{
|
||||
get
|
||||
{
|
||||
return false;
|
||||
}
|
||||
set
|
||||
{
|
||||
SetProperty(ref _showText, value);
|
||||
}
|
||||
}
|
||||
|
||||
public override bool EditData()
|
||||
{
|
||||
if (IsReadOnly == true) return false;
|
||||
@@ -63,7 +75,6 @@ namespace AIStudio.Wpf.BaseDiagram.Extensions.ViewModels
|
||||
{
|
||||
bool needauto = Text == null;
|
||||
Text = data.Text;
|
||||
ShowText = false;
|
||||
Icon = data.Icon;
|
||||
Margin = data.Margin;
|
||||
if (needauto)
|
||||
|
||||
@@ -48,7 +48,7 @@
|
||||
<Grid>
|
||||
<Image IsHitTestVisible="False"
|
||||
Stretch="Fill"
|
||||
Source="/AIStudio.Wpf.BaseDiagram;component/Images/Persist.png"
|
||||
Source="/AIStudio.Wpf.ADiagram;component/Images/Persist.png"
|
||||
Tag="setting" />
|
||||
<Button x:Name="btnSetting" HorizontalAlignment="Right"
|
||||
VerticalAlignment="Bottom"
|
||||
|
||||
@@ -48,7 +48,7 @@
|
||||
<Grid>
|
||||
<Image IsHitTestVisible="False"
|
||||
Stretch="Fill"
|
||||
Source="/AIStudio.Wpf.BaseDiagram;component/Images/Setting.png"
|
||||
Source="/AIStudio.Wpf.ADiagram;component/Images/Setting.png"
|
||||
Tag="setting" />
|
||||
<Button HorizontalAlignment="Right"
|
||||
VerticalAlignment="Bottom"
|
||||
|
||||
@@ -60,7 +60,7 @@ namespace AIStudio.Wpf.Flowchart
|
||||
/// <param name="json"></param>
|
||||
/// <param name="id"></param>
|
||||
/// <returns></returns>
|
||||
public static void InitOAData(List<FlowNode> oASteps, List<ConnectorViewModel> connectors)
|
||||
public static void InitData(List<FlowNode> oASteps, List<ConnectorViewModel> connectors)
|
||||
{
|
||||
foreach (var edge in connectors)
|
||||
{
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
<Project Sdk="Microsoft.NET.Sdk.WindowsDesktop">
|
||||
<Project Sdk="Microsoft.NET.Sdk.WindowsDesktop">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFramework>netcoreapp3.1</TargetFramework>
|
||||
@@ -9,6 +9,10 @@
|
||||
<Folder Include="Models\" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="MathParser.org-mXparser" Version="4.4.2" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\AIStudio.Wpf.BaseDiagram\AIStudio.Wpf.BaseDiagram.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
31
AIStudio.Wpf.SFC/LinkPoint.cs
Normal file
31
AIStudio.Wpf.SFC/LinkPoint.cs
Normal file
@@ -0,0 +1,31 @@
|
||||
using System;
|
||||
using Util.DiagramDesigner;
|
||||
|
||||
namespace AIStudio.Wpf.SFC
|
||||
{
|
||||
public class LinkPoint: BindableBase
|
||||
{
|
||||
public Guid Id { get; set; }
|
||||
|
||||
private string _name;
|
||||
public string Name
|
||||
{
|
||||
get { return _name; }
|
||||
set
|
||||
{
|
||||
SetProperty(ref _name, value);
|
||||
}
|
||||
}
|
||||
public string Despcription { get; set; }
|
||||
|
||||
private double _value;
|
||||
public double Value
|
||||
{
|
||||
get { return _value; }
|
||||
set
|
||||
{
|
||||
SetProperty(ref _value, value);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
908
AIStudio.Wpf.SFC/README.txt
Normal file
908
AIStudio.Wpf.SFC/README.txt
Normal file
@@ -0,0 +1,908 @@
|
||||
mXparser - Math Parser Java Android C# .NET (CLS) Library
|
||||
A flexible mathematical expressions parser for JAVA and C# .NET (CLS)
|
||||
|
||||
*** Donation through PayPal ***
|
||||
*** Did you find the software useful? Please consider donation :-) ***
|
||||
Developing and maintaining MathParser.org-mXparser takes a lot of time,
|
||||
mainly my free time. I hope it saved some of your time. If yes, then
|
||||
buy me a cup coffee :-)
|
||||
*** http://mathparser.org/donate/ ***
|
||||
|
||||
*** Scalar Scientific Calculator, Charts & Scripts ***
|
||||
*** https://play.google.com/store/apps/details?id=org.mathparser.scalar.lite ***
|
||||
*** https://play.google.com/store/apps/details?id=org.mathparser.scalar.pro ***
|
||||
*** http://scalarmath.org/ ***
|
||||
|
||||
v.4.4.2 (2020-01-25): Gemoni - bugs fixing
|
||||
|
||||
* #200 System.OutOfMemoryException: Array dimensions exceeded supported range (https://github.com/mariuszgromada/MathParser.org-mXparser/issues/200)
|
||||
* #199 cancelCurrentCalculation does not stop for some expressions (https://github.com/mariuszgromada/MathParser.org-mXparser/issues/199)
|
||||
|
||||
v.4.4.0 (2020-01-14): Gemoni - API improvement
|
||||
|
||||
* Canonical rounding: Bye bye floating point arithmetic artifacts
|
||||
|
||||
ULP rounding is switched of as a default setting (can be enabled / disabled). As a default canonical rounding is switched on (can be disabled / enabled). New methods:
|
||||
|
||||
- mXparser.enableCanonicalRounding()
|
||||
- mXparser.disableCanonicalRounding()
|
||||
- mXparser.setCanonicalRounding(boolean)
|
||||
- mXparser.checkIfCanonicalRounding
|
||||
|
||||
Example 1
|
||||
|
||||
Expression e = new Expression("0.1 + 0.1 + 0.1");
|
||||
System.out.println("Pure Java : 0.1 + 0.1 + 0.1 = " + (0.1 + 0.1 + 0.1));
|
||||
System.out.println("mXparser : 0.1 + 0.1 + 0.1 = " + e.calculate());
|
||||
mXparser.disableCanonicalRounding();
|
||||
System.out.println("mXparser canonical off: 0.1 + 0.1 + 0.1 = " + e.calculate());
|
||||
===========
|
||||
Pure Java : 0.1 + 0.1 + 0.1 = 0.30000000000000004
|
||||
mXparser : 0.1 + 0.1 + 0.1 = 0.3
|
||||
mXparser canonical off: 0.1 + 0.1 + 0.1 = 0.30000000000000004
|
||||
|
||||
Example 2
|
||||
|
||||
Expression e = new Expression("(-1/6.2)^(-3)");
|
||||
System.out.println("Pure Java : (-1/6.2)^(-3) = " + Math.pow(-1/6.2, -3));
|
||||
System.out.println("mXparser : (-1/6.2)^(-3) = " + e.calculate());
|
||||
mXparser.disableCanonicalRounding();
|
||||
System.out.println("mXparser canonical off: (-1/6.2)^(-3) = " + e.calculate());
|
||||
===========
|
||||
Pure Java : (-1/6.2)^(-3) = -238.32800000000003
|
||||
mXparser : (-1/6.2)^(-3) = -238.328
|
||||
mXparser canonical off: (-1/6.2)^(-3) = -238.32800000000003
|
||||
|
||||
* Argument extension - analogy to Function Extension
|
||||
|
||||
Now you can define user arguments implementing your own algorithm in source code.
|
||||
|
||||
Example
|
||||
|
||||
class PiMultArgExt implements ArgumentExtension {
|
||||
private int multiple = 0;
|
||||
public double getArgumentValue() {
|
||||
multiple++;
|
||||
return MathConstants.PI * multiple;
|
||||
}
|
||||
public PiMultArgExt clone() {
|
||||
return new PiMultArgExt();
|
||||
}
|
||||
}
|
||||
|
||||
Argument x = new Argument("x", new PiMultArgExt());
|
||||
Expression e = new Expression("x/pi", x);
|
||||
System.out.println("1st calc exec: " + e.calculate());
|
||||
System.out.println("2nd calc exec: " + e.calculate());
|
||||
System.out.println("3rd calc exec: " + e.calculate());
|
||||
===========
|
||||
1st calc exec: 1.0
|
||||
2nd calc exec: 2.0
|
||||
3rd calc exec: 3.0
|
||||
|
||||
* Bugs fixed
|
||||
|
||||
- #168, #18 Exact special trigonometric values
|
||||
- #192, #178 Logical operators precedence
|
||||
- #172 "x + 4 * - 2"
|
||||
|
||||
v.4.3.3 (2019-01-27): Bug fix
|
||||
|
||||
* No Operator between Argumant and Parentheses #170 https://github.com/mariuszgromada/MathParser.org-mXparser/issues/170
|
||||
|
||||
v.4.3.2 (2019-01-25): Nuget package fix
|
||||
|
||||
* Could not load file or assembly MathParser.org-mXparser #171 https://github.com/mariuszgromada/MathParser.org-mXparser/issues/171
|
||||
|
||||
v.4.3.0 (2019-01-19): Caprica - API improvement
|
||||
|
||||
* Cancel ongoing calculation
|
||||
- mXparser.cancelCurrentCalculation()
|
||||
- mXparser.resetCancelCurrentCalculationFlag();
|
||||
|
||||
* Set default options
|
||||
- mXparser.setDefaultOptions()
|
||||
|
||||
* User defined constants / units
|
||||
- constant name can be surrounded by square bracket, i.e. [const]
|
||||
- Expression.getMissingUserDefinedUnits()
|
||||
|
||||
* Bug fixing
|
||||
- #153, #162 Endless Loop
|
||||
- #164 PrimeCache out of memory - handling error / exception
|
||||
|
||||
v.4.2.0 (2018-07-15): Aquaria - Major release
|
||||
|
||||
* Broader types of decimal number literals
|
||||
|
||||
- No leading zero, i.e.: .2, .312, -.21
|
||||
|
||||
* Fraction as number literals
|
||||
|
||||
- 1_2 is recognized as 1/2
|
||||
- 2_3_4 is recognized as 2 + 3/4
|
||||
- 17_5 is recognized as 17/5
|
||||
- Just use Expression e = new Expression("2_3_2 + 1_2")
|
||||
|
||||
* Double to fraction conversion
|
||||
|
||||
- mXparser.toFraction(double value) - double[]
|
||||
- mXparser.toMixedFraction(double value) - double[]
|
||||
- mXparser.fractionToString(double[] fraction) - String
|
||||
- mXparser.toFractionString(double value) - String
|
||||
- mXparser.toMixedFractionString(double value) - String
|
||||
|
||||
* Disable / enable almost int rounding
|
||||
|
||||
- mXparser.enableAlmostIntRounding()
|
||||
- mXparser.disableAlmostIntRounding()
|
||||
- mXparser.checkIfAlmostIntRounding()
|
||||
- mXparser.getEpsilon()
|
||||
- mXparser.setEpsilon()
|
||||
|
||||
* Variadic user defined functions
|
||||
|
||||
- Function f = new Function("f(...) = sum(i, 1, [npar], par(i)^2 )");
|
||||
- [npar] - number of available parameters
|
||||
- par(i) - parameter value
|
||||
- body extended is supported
|
||||
|
||||
* New special functions
|
||||
|
||||
- Gamma(x) - Gamma special function Γ(s)
|
||||
- LambW0(x) - Lambert-W special function, principal branch 0, also called the omega function or product logarithm
|
||||
- LambW1(x) - Lambert-W special function, branch -1, also called the omega function or product logarithm
|
||||
- sgnGamma(x) - Signum of Gamma special function, Γ(s)
|
||||
- logGamma(x) - Log Gamma special function, lnΓ(s)
|
||||
- diGamma(x) - Digamma function as the logarithmic derivative of the Gamma special function, ψ(x)
|
||||
- GammaL(s,x) - Lower incomplete gamma special function, γ(s,x)
|
||||
- GammaU(s,x) - Upper incomplete Gamma special function, Γ(s,x)
|
||||
- GammaP(s,x), GammaRegL(s,x) - Lower regularized P gamma special function, P(s,x)
|
||||
- GammaQ(s,x), GammaRegU(s,x) - Upper regularized Q Gamma special function, Q(s,x)
|
||||
- Beta(x,y) - The Beta special function B(x,y), also called the Euler integral of the first kind
|
||||
- logBeta(x,y) - The Log Beta special function ln B(x,y), also called the Log Euler integral of the first kind, ln B(x,y)
|
||||
- BetaInc(x,a,b) - The incomplete beta special function B(x; a, b), also called the incomplete Euler integral of the first kind
|
||||
- BetaI(x,a,b), BetaReg(x,a,b) - The regularized incomplete beta (or regularized beta) special function I(x; a, b), also called the regularized incomplete Euler integral of the first kind
|
||||
|
||||
* Degrees / Radians mode for trigonometrix
|
||||
|
||||
- mXparser.setDegreesMode()
|
||||
- mXparser.setRadiansMode()
|
||||
- mXparser.checkIfDegreesMode()
|
||||
- mXparser.checkIfRadiansMode()
|
||||
|
||||
* New operator - Tetration
|
||||
|
||||
- a^^n is recognized as a^a^a...^a - n times
|
||||
|
||||
* Bugs fixed
|
||||
|
||||
- Argument.checkSyntax() https://github.com/mariuszgromada/MathParser.org-mXparser/issues/145
|
||||
- Endless loop with factorial https://github.com/mariuszgromada/MathParser.org-mXparser/issues/136
|
||||
- StringIndexOutOfBoundsException asking for tokens of empty expression https://github.com/mariuszgromada/MathParser.org-mXparser/issues/135
|
||||
- Function.checkSyntax() always returns true https://github.com/mariuszgromada/MathParser.org-mXparser/issues/111
|
||||
- Syntax for unary complement https://github.com/mariuszgromada/MathParser.org-mXparser/issues/114
|
||||
- Iterative operators descending sequence https://github.com/mariuszgromada/MathParser.org-mXparser/issues/119
|
||||
- checkSyntax() bug https://github.com/mariuszgromada/MathParser.org-mXparser/issues/80
|
||||
- Very very very long processing time of gcd https://github.com/mariuszgromada/MathParser.org-mXparser/issues/91
|
||||
- Priorities of "if", "iff" and other calculus operations https://github.com/mariuszgromada/MathParser.org-mXparser/issues/82
|
||||
|
||||
* Other framework support (binaries)
|
||||
|
||||
- .NET Core: 2.0, 2.1
|
||||
- .NET Standard: 2.0
|
||||
- .NET Framework: 4.7, 4.7.2
|
||||
- JAVA: 1.9, 1.10
|
||||
|
||||
* New regression tests - current tests coverage:
|
||||
|
||||
- 1155 expression related tests
|
||||
- 245 syntax related tests
|
||||
- 65 API related tests
|
||||
- 20 performance tests
|
||||
|
||||
https://github.com/mariuszgromada/MathParser.org-mXparser/milestone/2
|
||||
|
||||
v.4.1.1 (2017-07-28): Aeries - checkSyntax() bug fixing
|
||||
|
||||
* Fixed: checkSyntax() returns true "already checked no errors" #75
|
||||
https://github.com/mariuszgromada/MathParser.org-mXparser/issues/75
|
||||
|
||||
v.4.1.0 (2017-06-30): Aeries
|
||||
|
||||
* Various numeral systems
|
||||
|
||||
- Binary numbers literals
|
||||
- Octal numbers literals
|
||||
- Hexadecimal numbers literals
|
||||
- Number literals with base between 1 and 36
|
||||
- base(b, digit1, ..., digitn) function to generate numbers in any given base
|
||||
|
||||
* Leading zeros support
|
||||
|
||||
- 0001
|
||||
- 0001.12e10
|
||||
- ...
|
||||
|
||||
* Working with digits
|
||||
|
||||
- ndig(number, targetBase) function - number of digits - specified numeral system base
|
||||
- ndig10(number) function - number of digits - base 10
|
||||
- dig(number, targetBase, position) - digit at position - specified numeral system base
|
||||
- dig10(number, position) - digit at position - base 10
|
||||
|
||||
* Prime factorization
|
||||
|
||||
- nfact(number) - number of prime factors
|
||||
- factval(number, factorId) - factor value
|
||||
- factexp(number, factorId) - factor exponent
|
||||
|
||||
* Not-a-Number
|
||||
|
||||
- [NaN] symbol
|
||||
- isNaN(x) function
|
||||
- coalesce(a1,...,an) function - first non-NaN value
|
||||
|
||||
* Statistics
|
||||
|
||||
- med(a1, a2, ..., an) - sample median
|
||||
- mode(a1, a2, ..., an) - sample mode
|
||||
|
||||
* Boolean logic
|
||||
|
||||
- [true] symbol
|
||||
- [false] symbol
|
||||
- or(a1,...an) - variadic or
|
||||
- and(a1,...an) - variadic and
|
||||
- xor(a1,...an) - variadic xor
|
||||
|
||||
* Other functions
|
||||
|
||||
- root(order, number) - root + support for negative numbers and odd-order
|
||||
- arcsec(x) - inverse trigonometric secant
|
||||
- arccsc(x) - inverse trigonometric cosecant
|
||||
- ndist(v1, v2, ... vn) - number of distinct values
|
||||
- argmin(v1, v2, ... vn) - index of minimum
|
||||
- argmax(v1, v2, ... vn) - index of maximum
|
||||
|
||||
* New operator
|
||||
|
||||
- % support (i.e. 2%, x%)
|
||||
|
||||
* Calculus
|
||||
|
||||
- der( f(x), x, x0 ) - alternative syntax for derivative (no need to define x as argument)
|
||||
|
||||
* Built-in tokens
|
||||
|
||||
- Option to override built-in tokens
|
||||
- Possibility to remove built-in tokens
|
||||
- Possibility to change built-in token
|
||||
- Key words: syntax + since
|
||||
- Get key words list
|
||||
|
||||
* Working with expression tokens
|
||||
|
||||
- Get missing user defined arguments
|
||||
- Get missing user defined functions
|
||||
|
||||
* Bugs fixed
|
||||
|
||||
- Dependent arguments and StackOverflowError #35 (introduction of recursion calls counter)
|
||||
- FunctionExtension.calculate #32
|
||||
|
||||
* New regression tests - current tests coverage:
|
||||
|
||||
- 829 expression related tests
|
||||
- 207 syntax related tests
|
||||
- 51 api related tests
|
||||
- 20 performance tests
|
||||
|
||||
https://github.com/mariuszgromada/MathParser.org-mXparser/milestone/1
|
||||
|
||||
|
||||
v.4.0.0.2 (2017-04-17): Port to various .NET frameworks
|
||||
- .NET Core
|
||||
- .NET Standard
|
||||
- .NET PCL
|
||||
- Xamarin.Android
|
||||
- Xamarin.iOS
|
||||
|
||||
v.4.0.0 (2017-03-27): Major update
|
||||
- Bitwise Operators
|
||||
- Numbers in scientific notation
|
||||
- Units, Physical & Astronomical Constants,
|
||||
- Equations solving via finding function root
|
||||
- Better tokens handling
|
||||
- Function Extensions - possibility of using your own implementation
|
||||
- Bugs fixed
|
||||
|
||||
* Bitwise Operators
|
||||
|
||||
- @~ Bitwise unary complement
|
||||
- @& Bitwise AND
|
||||
- @^ Bitwise exclusive OR
|
||||
- @| Bitwise inclusive OR
|
||||
- @<< Signed left shift
|
||||
- @>> Signed right shift
|
||||
|
||||
* Numbers in scientific notation
|
||||
|
||||
- 1.2e10
|
||||
- 1.2e-10
|
||||
- 1.2e+10
|
||||
- 1.2E10
|
||||
- 1.2E-10
|
||||
- 1.2E+10
|
||||
- ...
|
||||
|
||||
* Units
|
||||
|
||||
- [%] <Ratio, Fraction> Percentage = 0.01
|
||||
- [%%] <Ratio, Fraction> Promil, Per mille = 0.001
|
||||
- [Y] <Metric prefix> Septillion / Yotta = 10^24
|
||||
- [sept] <Metric prefix> Septillion / Yotta = 10^24
|
||||
- [Z] <Metric prefix> Sextillion / Zetta = 10^21
|
||||
- [sext] <Metric prefix> Sextillion / Zetta = 10^21
|
||||
- [E] <Metric prefix> Quintillion / Exa = 10^18
|
||||
- [quint] <Metric prefix> Quintillion / Exa = 10^18
|
||||
- [P] <Metric prefix> Quadrillion / Peta = 10^15
|
||||
- [quad] <Metric prefix> Quadrillion / Peta = 10^15
|
||||
- [T] <Metric prefix> Trillion / Tera = 10^12
|
||||
- [tril] <Metric prefix> Trillion / Tera = 10^12
|
||||
- [G] <Metric prefix> Billion / Giga = 10^9
|
||||
- [bil] <Metric prefix> Billion / Giga = 10^9
|
||||
- [M] <Metric prefix> Million / Mega = 10^6
|
||||
- [mil] <Metric prefix> Million / Mega = 10^6
|
||||
- [k] <Metric prefix> Thousand / Kilo = 10^3
|
||||
- [th] <Metric prefix> Thousand / Kilo = 10^3
|
||||
- [hecto] <Metric prefix> Hundred / Hecto = 10^2
|
||||
- [hund] <Metric prefix> Hundred / Hecto = 10^2
|
||||
- [deca] <Metric prefix> Ten / Deca = 10
|
||||
- [ten] <Metric prefix> Ten / Deca = 10
|
||||
- [deci] <Metric prefix> Tenth / Deci = 0.1
|
||||
- [centi] <Metric prefix> Hundredth / Centi = 0.01
|
||||
- [milli] <Metric prefix> Thousandth / Milli = 0.001
|
||||
- [mic] <Metric prefix> Millionth / Micro = 10^-6
|
||||
- [n] <Metric prefix> Billionth / Nano = 10^-9
|
||||
- [p] <Metric prefix> Trillionth / Pico = 10^-12
|
||||
- [f] <Metric prefix> Quadrillionth / Femto = 10^-15
|
||||
- [a] <Metric prefix> Quintillionth / Atoo = 10^-18
|
||||
- [z] <Metric prefix> Sextillionth / Zepto = 10^-21
|
||||
- [y] <Metric prefix> Septillionth / Yocto = 10^-24
|
||||
- [m] <Unit of length> Metre / Meter (m=1)
|
||||
- [km] <Unit of length> Kilometre / Kilometer (m=1)
|
||||
- [cm] <Unit of length> Centimetre / Centimeter (m=1)
|
||||
- [mm] <Unit of length> Millimetre / Millimeter (m=1)
|
||||
- [inch] <Unit of length> Inch (m=1)
|
||||
- [yd] <Unit of length> Yard (m=1)
|
||||
- [ft] <Unit of length> Feet (m=1)
|
||||
- [mile] <Unit of length> Mile (m=1)
|
||||
- [nmi] <Unit of length> Nautical mile (m=1)
|
||||
- [m2] <Unit of area> Square metre / Square meter (m=
|
||||
- [cm2] <Unit of area> Square centimetre / Square cent
|
||||
- [mm2] <Unit of area> Square millimetre / Square mill
|
||||
- [are] <Unit of area> Are (m=1)
|
||||
- [ha] <Unit of area> Hectare (m=1)
|
||||
- [acre] <Unit of area> Acre (m=1)
|
||||
- [km2] <Unit of area> Square kilometre / Square kilom
|
||||
- [mm3] <Unit of volume> Cubic millimetre / Cubic mill
|
||||
- [cm3] <Unit of volume> Cubic centimetre / Cubic cent
|
||||
- [m3] <Unit of volume> Cubic metre / Cubic meter (m=
|
||||
- [km3] <Unit of volume> Cubic kilometre / Cubic kilom
|
||||
- [ml] <Unit of volume> Millilitre / Milliliter (m=1)
|
||||
- [l] <Unit of volume> Litre / Liter (m=1)
|
||||
- [gall] <Unit of volume> Gallon (m=1)
|
||||
- [pint] <Unit of volume> Pint (m=1)
|
||||
- [s] <Unit of time> Second (s=1)
|
||||
- [ms] <Unit of time> Millisecond (s=1)
|
||||
- [min] <Unit of time> Minute (s=1)
|
||||
- [h] <Unit of time> Hour (s=1)
|
||||
- [day] <Unit of time> Day (s=1)
|
||||
- [week] <Unit of time> Week (s=1)
|
||||
- [yearj] <Unit of time> Julian year = 365.25 days (s=1)
|
||||
- [kg] <Unit of mass> Kilogram (kg=1)
|
||||
- [gr] <Unit of mass> Gram (kg=1)
|
||||
- [mg] <Unit of mass> Milligram (kg=1)
|
||||
- [dag] <Unit of mass> Decagram (kg=1)
|
||||
- [t] <Unit of mass> Tonne (kg=1)
|
||||
- [oz] <Unit of mass> Ounce (kg=1)
|
||||
- [lb] <Unit of mass> Pound (kg=1)
|
||||
- [b] <Unit of information> Bit (bit=1)
|
||||
- [kb] <Unit of information> Kilobit (bit=1)
|
||||
- [Mb] <Unit of information> Megabit (bit=1)
|
||||
- [Gb] <Unit of information> Gigabit (bit=1)
|
||||
- [Tb] <Unit of information> Terabit (bit=1)
|
||||
- [Pb] <Unit of information> Petabit (bit=1)
|
||||
- [Eb] <Unit of information> Exabit (bit=1)
|
||||
- [Zb] <Unit of information> Zettabit (bit=1)
|
||||
- [Yb] <Unit of information> Yottabit (bit=1)
|
||||
- [B] <Unit of information> Byte (bit=1)
|
||||
- [kB] <Unit of information> Kilobyte (bit=1)
|
||||
- [MB] <Unit of information> Megabyte (bit=1)
|
||||
- [GB] <Unit of information> Gigabyte (bit=1)
|
||||
- [TB] <Unit of information> Terabyte (bit=1)
|
||||
- [PB] <Unit of information> Petabyte (bit=1)
|
||||
- [EB] <Unit of information> Exabyte (bit=1)
|
||||
- [ZB] <Unit of information> Zettabyte (bit=1)
|
||||
- [YB] <Unit of information> Yottabyte (bit=1)
|
||||
- [J] <Unit of energy> Joule (m=1, kg=1, s=1)
|
||||
- [eV] <Unit of energy> Electronovolt (m=1, kg=1, s=1
|
||||
- [keV] <Unit of energy> Kiloelectronovolt (m=1, kg=1,
|
||||
- [MeV] <Unit of energy> Megaelectronovolt (m=1, kg=1,
|
||||
- [GeV] <Unit of energy> Gigaelectronovolt (m=1, kg=1,
|
||||
- [TeV] <Unit of energy> Teraelectronovolt (m=1, kg=1,
|
||||
- [m/s] <Unit of speed> Metre / Meter per second (m=1,
|
||||
- [km/h] <Unit of speed> Kilometre / Kilometer per hour
|
||||
- [mi/h] <Unit of speed> Mile per hour (m=1, s=1)
|
||||
- [knot] <Unit of speed> Knot (m=1, s=1)
|
||||
- [m/s2] <Unit of acceleration> Metre / Meter per squar
|
||||
- [km/h2] <Unit of acceleration> Kilometre / Kilometer p
|
||||
- [mi/h2] <Unit of acceleration> Mile per square hour (m
|
||||
- [rad] <Unit of angle> Radian (rad=1)
|
||||
- [deg] <Unit of angle> Degree of arc (rad=1)
|
||||
- ['] <Unit of angle> Minute of arc (rad=1)
|
||||
- [''] <Unit of angle> Second of arc (rad=1)
|
||||
|
||||
* Physical Constants
|
||||
|
||||
- [c] Light speed in vacuum [m/s] (m=1, s=1)
|
||||
- [G.] Gravitational constant (m=1, kg=1, s=1)]
|
||||
- [g] Gravitational acceleration on Earth [m/s^2] (m=1, s=1)
|
||||
- [hP] Planck constant (m=1, kg=1, s=1)
|
||||
- [h-] Reduced Planck constant / Dirac constant (m=1, kg=1, s=1)]
|
||||
- [lP] Planck length [m] (m=1)
|
||||
- [mP] Planck mass [kg] (kg=1)
|
||||
- [tP] Planck time [s] (s=1)
|
||||
|
||||
* Astronomical Constants
|
||||
|
||||
- [ly] Light year [m] (m=1)
|
||||
- [au] Astronomical unit [m] (m=1)
|
||||
- [pc] Parsec [m] (m=1)
|
||||
- [kpc] Kiloparsec [m] (m=1)
|
||||
- [Earth-R-eq] Earth equatorial radius [m] (m=1)
|
||||
- [Earth-R-po] Earth polar radius [m] (m=1)
|
||||
- [Earth-R] Earth mean radius (m=1)
|
||||
- [Earth-M] Earth mass [kg] (kg=1)
|
||||
- [Earth-D] Earth-Sun distance - semi major axis [m] (m=1)
|
||||
- [Moon-R] Moon mean radius [m] (m=1)
|
||||
- [Moon-M] Moon mass [kg] (kg=1)
|
||||
- [Moon-D] Moon-Earth distance - semi major axis [m] (m=1)
|
||||
- [Solar-R] Solar mean radius [m] (m=1)
|
||||
- [Solar-M] Solar mass [kg] (kg=1)
|
||||
- [Mercury-R] Mercury mean radius [m] (m=1)
|
||||
- [Mercury-M] Mercury mass [kg] (kg=1)
|
||||
- [Mercury-D] Mercury-Sun distance - semi major axis [m] (m=1)
|
||||
- [Venus-R] Venus mean radius [m] (m=1)
|
||||
- [Venus-M] Venus mass [kg] (kg=1)
|
||||
- [Venus-D] Venus-Sun distance - semi major axis [m] (m=1)
|
||||
- [Mars-R] Mars mean radius [m] (m=1)
|
||||
- [Mars-M] Mars mass [kg] (kg=1)
|
||||
- [Mars-D] Mars-Sun distance - semi major axis [m] (m=1)
|
||||
- [Jupiter-R] Jupiter mean radius [m] (m=1)
|
||||
- [Jupiter-M] Jupiter mass [kg] (kg=1)
|
||||
- [Jupiter-D] Jupiter-Sun distance - semi major axis [m] (m=1)
|
||||
- [Saturn-R] Saturn mean radius [m] (m=1)
|
||||
- [Saturn-M] Saturn mass [kg] (kg=1)
|
||||
- [Saturn-D] Saturn-Sun distance - semi major axis [m] (m=1)
|
||||
- [Uranus-R] Uranus mean radius [m] (m=1)
|
||||
- [Uranus-M] Uranus mass [kg] (kg=1)
|
||||
- [Uranus-D] Uranus-Sun distance - semi major axis [m] (m=1)
|
||||
- [Neptune-R] Neptune mean radius [m] (m=1)
|
||||
- [Neptune-M] Neptune mass [kg] (kg=1)
|
||||
- [Neptune-D] Neptune-Sun distance - semi major axis [m] (m=1)
|
||||
|
||||
* Equations solving via finding function root
|
||||
|
||||
- solve( f(x), x, a, b ) - solving f(x) = 0
|
||||
|
||||
* Function Extensions
|
||||
|
||||
- FileExtension interface + new constructor in Function class
|
||||
|
||||
* Better tokens handling
|
||||
|
||||
- Better handling of invalid / not known tokens
|
||||
- Looks like functionality
|
||||
|
||||
* Bugs fixed
|
||||
|
||||
- Exception thrown by getCopyOfInitialTokens() #21
|
||||
- System.format.exception - system.IO.EndOfStreamException #20
|
||||
- Expression relating factorial "!" cause the application to hang #17
|
||||
- Negative sign missing when is right of operators #16
|
||||
- Negative in if statement #12
|
||||
- Speed when debugging #11
|
||||
- User defined arguments ending in e #10
|
||||
|
||||
* New regression tests - current tests coverage:
|
||||
|
||||
- 622 expression related tests
|
||||
- 114 syntax related tests
|
||||
- 30 api related tests
|
||||
- 20 performance tests
|
||||
|
||||
|
||||
v.3.0.0 (2016-05-16): Major update
|
||||
Random numbers, Probability distributions & Random variables
|
||||
Double precision rounding, ULP rounding, epsilon comparison
|
||||
New special functions
|
||||
|
||||
* .NET: since v.3.0.0 dll I started to use different private key for signing.
|
||||
|
||||
* Random numbers - new functions
|
||||
- rUni(a, b) - Random number from uniform continuous distribution U(a,b)
|
||||
- rUnid(a, b) - Random number from uniform discrete distribution U{a,b}
|
||||
- rNor(m, s) - Random number from normal distribution N(m,s)
|
||||
- rList(a1, a2, ..., an) - Random number from given list of numbers
|
||||
|
||||
* Probability distributions - new functions
|
||||
- pUni(x, a, b) - Probability distribution function - Uniform continuous distribution U(a,b)
|
||||
- cUni(x, a, b) - Cumulative distribution function - Uniform continuous distribution U(a,b)
|
||||
- qUni(q, a, b) - Quantile function (inverse cumulative distribution function) -
|
||||
Uniform continuous distribution U(a,b)
|
||||
- pNor(x, a, b) - Probability distribution function - Normal distribution N(m,s)
|
||||
- cNor(x, a, b) - Cumulative distribution function - Normal distribution N(m,s)
|
||||
- qNor(q, m, s) - Quantile function (inverse cumulative distribution function) -
|
||||
Normal distribution N(m,s)
|
||||
|
||||
* Random variables (predefined) - acting as random constant (no parameters)
|
||||
|
||||
- [Uni] - Random variable - Uniform continuous distribution U(0,1)
|
||||
|
||||
- [Int] - Random variable - random integer
|
||||
- [Int1] - Random variable - random integer - Uniform discrete distribution U{-10^1, 10^1}
|
||||
- [Int2] - Random variable - random integer - Uniform discrete distribution U{-10^2, 10^2}
|
||||
- [Int3] - Random variable - random integer - Uniform discrete distribution U{-10^3, 10^3}
|
||||
- [Int4] - Random variable - random integer - Uniform discrete distribution U{-10^4, 10^4}
|
||||
- [Int5] - Random variable - random integer - Uniform discrete distribution U{-10^5, 10^5}
|
||||
- [Int6] - Random variable - random integer - Uniform discrete distribution U{-10^6, 10^6}
|
||||
- [Int7] - Random variable - random integer - Uniform discrete distribution U{-10^7, 10^7}
|
||||
- [Int8] - Random variable - random integer - Uniform discrete distribution U{-10^8, 10^8}
|
||||
- [Int9] - Random variable - random integer - Uniform discrete distribution U{-10^9, 10^9}
|
||||
|
||||
- [nat] - Random variable - random natural number including 0
|
||||
|
||||
- [nat1] - Random variable - random natural number including 0 - Uniform discrete distribution U{0, 10^1}
|
||||
- [nat2] - Random variable - random natural number including 0 - Uniform discrete distribution U{0, 10^2}
|
||||
- [nat3] - Random variable - random natural number including 0 - Uniform discrete distribution U{0, 10^3}
|
||||
- [nat4] - Random variable - random natural number including 0 - Uniform discrete distribution U{0, 10^4}
|
||||
- [nat5] - Random variable - random natural number including 0 - Uniform discrete distribution U{0, 10^5}
|
||||
- [nat6] - Random variable - random natural number including 0 - Uniform discrete distribution U{0, 10^6}
|
||||
- [nat7] - Random variable - random natural number including 0 - Uniform discrete distribution U{0, 10^7}
|
||||
- [nat8] - Random variable - random natural number including 0 - Uniform discrete distribution U{0, 10^8}
|
||||
- [nat9] - Random variable - random natural number including 0 - Uniform discrete distribution U{0, 10^9}
|
||||
|
||||
- [Nat] - Random variable - random natural number
|
||||
|
||||
- [Nat1] - Random variable - random natural number - Uniform discrete distribution U{1, 10^1}
|
||||
- [Nat2] - Random variable - random natural number - Uniform discrete distribution U{1, 10^2}
|
||||
- [Nat3] - Random variable - random natural number - Uniform discrete distribution U{1, 10^3}
|
||||
- [Nat4] - Random variable - random natural number - Uniform discrete distribution U{1, 10^4}
|
||||
- [Nat5] - Random variable - random natural number - Uniform discrete distribution U{1, 10^5}
|
||||
- [Nat6] - Random variable - random natural number - Uniform discrete distribution U{1, 10^6}
|
||||
- [Nat7] - Random variable - random natural number - Uniform discrete distribution U{1, 10^7}
|
||||
- [Nat8] - Random variable - random natural number - Uniform discrete distribution U{1, 10^8}
|
||||
- [Nat9] - Random variable - random natural number - Uniform discrete distribution U{1, 10^9}
|
||||
|
||||
- [Nor] - Random variable - Normal distribution N(0,1)
|
||||
|
||||
* Double precision rounding
|
||||
- round(value, places) - decimal rounding (half-up)
|
||||
|
||||
* New special functions
|
||||
- erf(x) - Gauss error function
|
||||
- erfc(x) - Gauss complementary error function
|
||||
- erfInv(x) - Inverse Gauss error function
|
||||
- erfcInv(x) - Inverse Gauss complementary error function
|
||||
|
||||
* Other functions
|
||||
- ulp(x) - Unit in The Last Place
|
||||
|
||||
* Binary relations - epsilon+ulp comparison - enabled as default
|
||||
If a rel b then applied epsilon is maximum from epsilon and ulp(b)
|
||||
a eq b if a \in [b-eps; b+eps] inclusive
|
||||
- mXparser.setExactComparison()
|
||||
- mXparser.setEpsilonComparison()
|
||||
- mXparser.setEpsilon(double epsilon)
|
||||
- mXparser.setDefaultEpsilon()
|
||||
- mXparser.getEpsilon()
|
||||
- mXparser.checkIfEpsilonMode()
|
||||
- mXparser.checkIfExactMode()
|
||||
|
||||
* Intelligent automatic double ULP rounding - enabled as default
|
||||
Try 0.1 + 0.1 + 0.1 - it will give exact 0.3 :-)
|
||||
- mXparser.enableUlpRounding()
|
||||
- mXparser.disableUlpRounding()
|
||||
- mXparser.checkIfUlpRounding()
|
||||
|
||||
* Parser tokens definition now public in API
|
||||
- mxparser.parsertokens.*
|
||||
|
||||
* Expression after tokenization now public in API
|
||||
- Expression.getCopyOfInitialTokens()
|
||||
- mxparser.parsertokens.*
|
||||
- mXparser.consolePrintTokens()
|
||||
|
||||
* Significant reorganization of code
|
||||
- Mainly mathcollection & parser tokens
|
||||
|
||||
* Backwards compatibility
|
||||
- is preserved for String API, Expression, Function, Argument,
|
||||
Constnat, ...
|
||||
- other public API was reorganized (mainly mxparser.mathcollection)
|
||||
|
||||
* Bugs fixed
|
||||
- bugs related to iterated operators
|
||||
|
||||
* Other changes
|
||||
- Many new regression tests
|
||||
|
||||
v.2.4.0 (2016-02-28): Average, variance and standard deviation.
|
||||
|
||||
* New functions with variadic parameters:
|
||||
- mean(a1, a2, ... , an) - sample average
|
||||
- var(a1, a2, ... , an) - bias-corrected sample variance
|
||||
- std(a1, a2, ... , an) - bias-corrected sample standard deviation
|
||||
|
||||
* New iterative operators:
|
||||
- mini(i, from, to, f(i), <by>) - minimum from function values
|
||||
- maxi(i, from, to, f(i), <by>) - maximum from function values
|
||||
- avg(i, from, to, f(i), <by>) - average from function values
|
||||
- vari(i, from, to, f(i), <by>) - bias-corrected sample variance from
|
||||
function values
|
||||
- stdi(i, from, to, f(i), <by>) - bias-corrected sample standard deviation
|
||||
from function values
|
||||
|
||||
* New regression tests to cover new functions
|
||||
* Small code reorganization
|
||||
* Added manifest to jar files containg version information
|
||||
* .dll files were signed
|
||||
|
||||
v.2.3.1 (2016-01-29): Trailing letter 'e' bug fix + some minor changes in the code.
|
||||
|
||||
v.2.3.0 (2016-01-17): Prime numbers supported! Multithreading performance tests!
|
||||
New functions: Exponential/Offset/Logarithmic integral!
|
||||
|
||||
* Prime numbers supported:
|
||||
- new class PrimesCache in mathcollection
|
||||
- MathFunctions extended with prime testes
|
||||
- ispr(n) - Prime test function supported in expressions
|
||||
- Pi(n) - Prime Counting function supported in expressions
|
||||
- mXparser.initPrimesCache() methods (and others) to initialize prime numbers cache
|
||||
|
||||
* Some special functions supported
|
||||
- Ei(x) - Exponential integral function supported in expressions
|
||||
- li(x) - Logarithmic integral function supported in expressions
|
||||
- Li(x) - Offset logarithmic integral function supported in expressions
|
||||
|
||||
* New constants
|
||||
- [G] - Gompertz Constant OEIS A073003 supported in expressions
|
||||
- [li2] - li(2) A069284 - supported in expressions
|
||||
|
||||
* Multithreading performance tests
|
||||
- Default number of cores taken from the environment
|
||||
- Possibility to change number of default threads:
|
||||
- PerformanceTests.start(int threadsNum)
|
||||
- mXparser.setThreadsNumber(int threadsNumber)
|
||||
|
||||
* New regression tests to cover new functionalities
|
||||
|
||||
|
||||
v.2.2.0 (2016-01-10): Android is coming!
|
||||
* mXparser_jdk1.7.jar - tested with Android !!!
|
||||
- all regression tests passed
|
||||
|
||||
* New public methods in the mXparser class
|
||||
- static String getConsoleOutput() - returns as string output
|
||||
produced by mXparser.consolePrin/ln() methods. Using this method
|
||||
you can capture the output to the string variable.
|
||||
- static void resetConsoleOutput() - resets the string
|
||||
representing console output
|
||||
- Added CONSOLE/PREFIX & CONSOLUE_OUTPUT_STRING/PREFIX + configuration
|
||||
|
||||
* Method modified in mXparser class
|
||||
- consolePrintln()
|
||||
- consolePrintln(Object o)
|
||||
- consolePrint(Object o)
|
||||
Above methods are outputing also to string representing
|
||||
console output.
|
||||
|
||||
* New RunTest method in regressiontesting, method executes
|
||||
specified scenario according to below params:
|
||||
- reg - Expression regression tests
|
||||
- api - mXparser API regression tests
|
||||
- syn - Syntax checking regression tests
|
||||
- perf - Performance tests
|
||||
|
||||
* Code clean-up
|
||||
- blank lines
|
||||
- trailing white spaces
|
||||
- src folders structure for c-sharp is now the same as in java
|
||||
|
||||
v.2.1.1-1 (2016-01-07):
|
||||
* Binaries for java: 1.5, 1.6, 1.7, 1.8
|
||||
* Binaries for .NET: 2.0, 3.0, 3.5, 4.0, 4.5, 4.6
|
||||
|
||||
v.2.1.1 (2016-01-04):
|
||||
* fixed bug w min/max function
|
||||
|
||||
v.2.1.0 (2016-01-02):
|
||||
* New static methods in class mxparser
|
||||
- mXparser.numberToHexString(number) + overloads: int, long, double
|
||||
- mXparser.hexString2AsciiString(String hexString)
|
||||
- mXparser.numberToAsciiString(number) + overloads: int, long, double
|
||||
- additional regression tests for the above methods
|
||||
|
||||
* Hello World examples of how to use mXparser binary library (manual includes:
|
||||
projects, code, screenshots) for:
|
||||
- JAVA (project done in Eclipse Mars 1)
|
||||
- C# (project done in Visual Studio 2015)
|
||||
- Visual Basic (project done in Visual Studio 2015)
|
||||
- C++/CLI (project done in Visual Studio 2015)
|
||||
- F# (project done in Visual Studio 2015)
|
||||
|
||||
v.2.0.0 (2015-12-31): Major update of the library providing more intuitive and
|
||||
much simpler to use API, no changes to the MathCollection.
|
||||
|
||||
* Methods removed: setRecursiveMode(), disableRecursiveMode()
|
||||
- No need to manually mark recursive mode, mXparser is recognizing this
|
||||
mode automatically.
|
||||
- New handy and super easy (natural to use) constructors:
|
||||
|
||||
* Constructors for user defined arguments (Argument / RecursiveArgument
|
||||
classes), user defined constant (Constant class), user defined functions
|
||||
(Function class).
|
||||
|
||||
Sample code:
|
||||
|
||||
Constant c = new Constant("c=5");
|
||||
Constant c = new Constant("c=5+2");
|
||||
Argument x = new Argument("x=5");
|
||||
Constant c = new Constant("c=5+x", x);
|
||||
Argument y = new Argument("y=2*x", x);
|
||||
RecursiveArgument f = new RecursiveArgument("f(n)=n*f(n-1)");
|
||||
Function f = new Function("f(x,y)=sin(x)+y");
|
||||
Function f = new Function("f(n)=if( n>0, n*f(n-1), 1)");
|
||||
|
||||
|
||||
* New methods: addDefinitions(PrimitiveElement... elements),
|
||||
removeDefinitions(PrimitiveElement... elements)
|
||||
|
||||
* New class PrimitiveElement introduced only to simplify constructors of
|
||||
arguments, constants, functions and expressions.
|
||||
|
||||
* Classes Argument, RecursiveArgument, Constant, Functions inherits now
|
||||
from PrimitiveElement class, it means you can call one method for
|
||||
adding / removing definitions by passing comma separated list of elements
|
||||
that can be different type (supported types: Argument, RecursiveArgument,
|
||||
Constant, Function).
|
||||
|
||||
* Method addArguments(), addConstants(), addFunctions(),removeArguments(),
|
||||
removeConstants(), removeFunctions() are still public, but this will
|
||||
change in the future.
|
||||
|
||||
Sample code:
|
||||
|
||||
Constant c = new Constant("c=5");
|
||||
Argument x = new Argument("x=10/2");
|
||||
Expression e = new Expression("c+x");
|
||||
e.addDefinitions(x,c);
|
||||
|
||||
* Modified constructors for classes Argument, RecursiveArgument, Constant,
|
||||
Function
|
||||
|
||||
* Constructors relying on directly given argument / constant / function
|
||||
name are now checking given name according to the predefined regular
|
||||
expression (the name must start with letters, and then
|
||||
digits / underscores/ letters are allowed).
|
||||
|
||||
* Constructors removed – all constructors relying on ArrayList/List
|
||||
of arguments, constants, functions or on varidic type Argument, Constant,
|
||||
Function were substituted based on comma separated prams list of
|
||||
PrimitiveElement type, where Argument, Constant, Functions
|
||||
extend / inherit PrimitiveElement).
|
||||
|
||||
* C# library is now Common Language Specification Compliant, it means
|
||||
mXparser is available right now to many other .NET languages
|
||||
(providing exactly the same API), including:
|
||||
|
||||
- C#
|
||||
- Visual Basic .NET
|
||||
- C++/CLI
|
||||
- F#
|
||||
|
||||
* Other changes
|
||||
|
||||
- New extended list of regression tests (to cover new methods,
|
||||
constructors, etc...)
|
||||
- Implemented Performance Tests
|
||||
- Source code converted from cp150 to UTF-8
|
||||
- Source code reorganization (some part of package level code of the
|
||||
Expression class was moved to the mXparser class)
|
||||
- Some bugs fixed (for sure there are others)
|
||||
|
||||
v.1.0.3 (2015-12-15):
|
||||
* Fixed bug during indirect recursion (infinite loops while syntax checking)
|
||||
Some minor modification of code making it more portable across platforms
|
||||
|
||||
v.1.0.2 (2015-12-06):
|
||||
* Fixed bug in user defined function related to RecursiveArguments
|
||||
|
||||
v.1.0.1 (2010-04-17):
|
||||
* Fixed BAG BIG Problem with evaluation without parenthesis
|
||||
ID: 2985722http://sourceforge.net/tracker/index.php?func=detail&aid=2985722&group_id=300839&atid=1268726
|
||||
|
||||
v.1.0.0 (2010-02-01):
|
||||
* Initial release
|
||||
|
||||
You may use this software under the condition of Simplified BSD License:
|
||||
|
||||
Copyright 2010-2017 MARIUSZ GROMADA. All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are
|
||||
permitted provided that the following conditions are met:
|
||||
|
||||
1. Redistributions of source code must retain the above copyright notice, this list of
|
||||
conditions and the following disclaimer.
|
||||
|
||||
2. Redistributions in binary form must reproduce the above copyright notice, this list
|
||||
of conditions and the following disclaimer in the documentation and/or other materials
|
||||
provided with the distribution.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY MARIUSZ GROMADA ``AS IS'' AND ANY EXPRESS OR IMPLIED
|
||||
WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
|
||||
FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL MARIUSZ GROMADA OR
|
||||
CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
|
||||
NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
The views and conclusions contained in the software and documentation are those of the
|
||||
authors and should not be interpreted as representing official policies, either expressed
|
||||
or implied, of MARIUSZ GROMADA.
|
||||
|
||||
If you have any questions/bugs feel free to contact:
|
||||
|
||||
Mariusz Gromada
|
||||
mariuszgromada.org@gmail.com
|
||||
http://mathspace.pl/
|
||||
http://mathparser.org/
|
||||
http://github.com/mariuszgromada/MathParser.org-mXparser
|
||||
http://mariuszgromada.github.io/MathParser.org-mXparser/
|
||||
http://mxparser.sourceforge.net/
|
||||
http://bitbucket.org/mariuszgromada/mxparser/
|
||||
http://mxparser.codeplex.com/
|
||||
|
||||
mXparser tutorial:
|
||||
doc/tutorial.html
|
||||
|
||||
mXparser API:
|
||||
doc/index.html
|
||||
|
||||
If you would like to run some regression testing just hit commands listed below:
|
||||
|
||||
JAVA:
|
||||
java -cp mxparser.jar org.mariuszgromada.math.mxparser.Tutorial
|
||||
java -cp mxparser.jar org.mariuszgromada.math.mxparser.regressiontesting.RunTest reg
|
||||
java -cp mxparser.jar org.mariuszgromada.math.mxparser.regressiontesting.RunTest api
|
||||
java -cp mxparser.jar org.mariuszgromada.math.mxparser.regressiontesting.RunTest syn
|
||||
java -cp mxparser.jar org.mariuszgromada.math.mxparser.regressiontesting.RunTest perf
|
||||
java -cp mxparser.jar org.mariuszgromada.math.mxparser.regressiontesting.RunTest reg api syn perf
|
||||
|
||||
Setting number of threads in performance tests:
|
||||
java -cp mxparser.jar org.mariuszgromada.math.mxparser.regressiontesting.PerformanceTests 4
|
||||
|
||||
C# (using PowerShell):
|
||||
[Reflection.Assembly]::LoadFile("full\exact\path\to\mxparser.dll")
|
||||
[org.mariuszgromada.math.mxparser.Tutorial]::Start()
|
||||
[org.mariuszgromada.math.mxparser.regressiontesting.RunTest]::Start("reg")
|
||||
[org.mariuszgromada.math.mxparser.regressiontesting.RunTest]::Start("api")
|
||||
[org.mariuszgromada.math.mxparser.regressiontesting.RunTest]::Start("syn")
|
||||
[org.mariuszgromada.math.mxparser.regressiontesting.RunTest]::Start("perf")
|
||||
|
||||
Setting number of threads in performance tests:
|
||||
[org.mariuszgromada.math.mxparser.regressiontesting.PerformanceTests]::Start(4)
|
||||
@@ -19,5 +19,14 @@ namespace AIStudio.Wpf.SFC
|
||||
COBegin = 5,
|
||||
[Description("并行结束")]
|
||||
COEnd = 6,
|
||||
|
||||
[Description("容器")]
|
||||
Simulate_Tank = 100,
|
||||
[Description("阀门")]
|
||||
Simulate_Solenoid = 101,
|
||||
[Description("开始")]
|
||||
Simulate_Start= 102,
|
||||
[Description("测定清单")]
|
||||
Simulate_List =103,
|
||||
}
|
||||
}
|
||||
|
||||
41
AIStudio.Wpf.SFC/SFCService.cs
Normal file
41
AIStudio.Wpf.SFC/SFCService.cs
Normal file
@@ -0,0 +1,41 @@
|
||||
using AIStudio.Wpf.SFC.ViewModels;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using Util.DiagramDesigner;
|
||||
|
||||
namespace AIStudio.Wpf.SFC
|
||||
{
|
||||
public static class SFCService
|
||||
{
|
||||
public static List<LinkPoint> LinkPoint { get; set; }
|
||||
|
||||
static SFCService()
|
||||
{
|
||||
LinkPoint = new List<LinkPoint>();
|
||||
|
||||
LinkPoint.Add(new LinkPoint { Id = Guid.NewGuid(), Name = "S0", Despcription = "启动按钮", Value = 0 });
|
||||
LinkPoint.Add(new LinkPoint { Id = Guid.NewGuid(), Name = "K1_DI", Despcription = "阀门1输入", Value = 0 });
|
||||
LinkPoint.Add(new LinkPoint { Id = Guid.NewGuid(), Name = "K2_DI", Despcription = "阀门2输入", Value = 0 });
|
||||
LinkPoint.Add(new LinkPoint { Id = Guid.NewGuid(), Name = "K3_DI", Despcription = "阀门3输入", Value = 0 });
|
||||
LinkPoint.Add(new LinkPoint { Id = Guid.NewGuid(), Name = "K4_DI", Despcription = "阀门4输入", Value = 0 });
|
||||
LinkPoint.Add(new LinkPoint { Id = Guid.NewGuid(), Name = "K1_DO", Despcription = "阀门1反馈", Value = 0 });
|
||||
LinkPoint.Add(new LinkPoint { Id = Guid.NewGuid(), Name = "K2_DO", Despcription = "阀门2反馈", Value = 0 });
|
||||
LinkPoint.Add(new LinkPoint { Id = Guid.NewGuid(), Name = "K3_DO", Despcription = "阀门3反馈", Value = 0 });
|
||||
LinkPoint.Add(new LinkPoint { Id = Guid.NewGuid(), Name = "K4_DO", Despcription = "阀门4反馈", Value = 0 });
|
||||
LinkPoint.Add(new LinkPoint { Id = Guid.NewGuid(), Name = "T1", Despcription = "容器1液位", Value = 100, });
|
||||
LinkPoint.Add(new LinkPoint { Id = Guid.NewGuid(), Name = "T2", Despcription = "容器2液位", Value = 0 });
|
||||
LinkPoint.Add(new LinkPoint { Id = Guid.NewGuid(), Name = "T3", Despcription = "容器3液位", Value = 20 });
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 初始化数据
|
||||
/// </summary>
|
||||
/// <param name="json"></param>
|
||||
/// <param name="id"></param>
|
||||
/// <returns></returns>
|
||||
public static void InitData(List<SFCNode> oASteps, List<ConnectorViewModel> connectors)
|
||||
{
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -9,10 +9,52 @@ namespace AIStudio.Wpf.SFC.ViewModels
|
||||
{
|
||||
public SFCActionNode() : base(SFCNodeKinds.Action)
|
||||
{
|
||||
FontViewModel.FontSize = 10;
|
||||
ItemWidth = 60;
|
||||
ItemHeight = 48;
|
||||
|
||||
ExecuteAddLeftInput(null);
|
||||
}
|
||||
|
||||
public SFCActionNode(IDiagramViewModel parent, DesignerItemBase designer) : base(parent, designer)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
private string _expression;
|
||||
public string Expression
|
||||
{
|
||||
get
|
||||
{
|
||||
return _expression;
|
||||
}
|
||||
set
|
||||
{
|
||||
SetProperty(ref _expression, value);
|
||||
}
|
||||
}
|
||||
|
||||
private LinkPoint _linkPoint;
|
||||
public LinkPoint LinkPoint
|
||||
{
|
||||
get
|
||||
{
|
||||
return _linkPoint;
|
||||
}
|
||||
set
|
||||
{
|
||||
SetProperty(ref _linkPoint, value);
|
||||
}
|
||||
}
|
||||
|
||||
protected override void ExecuteEditCommand(object parameter)
|
||||
{
|
||||
SFCActionNodeData data = new SFCActionNodeData(LinkPoint, Expression);
|
||||
if (visualiserService.ShowDialog(data) == true)
|
||||
{
|
||||
this.LinkPoint = data.LinkPoint;
|
||||
this.Expression = data.Expression;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
53
AIStudio.Wpf.SFC/ViewModels/SFCActionNodeData.cs
Normal file
53
AIStudio.Wpf.SFC/ViewModels/SFCActionNodeData.cs
Normal file
@@ -0,0 +1,53 @@
|
||||
using AIStudio.Wpf.BaseDiagram.Commands;
|
||||
using AIStudio.Wpf.BaseDiagram.Models;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Collections.ObjectModel;
|
||||
using System.Windows.Input;
|
||||
using Util.DiagramDesigner;
|
||||
|
||||
namespace AIStudio.Wpf.SFC.ViewModels
|
||||
{
|
||||
/// <summary>
|
||||
/// This is passed to the PopupWindow.xaml window, where a DataTemplate is used to provide the
|
||||
/// ContentControl with the look for this data. This class is also used to allow
|
||||
/// the popup to be cancelled without applying any changes to the calling ViewModel
|
||||
/// whos data will be updated if the PopupWindow.xaml window is closed successfully
|
||||
/// </summary>
|
||||
public class SFCActionNodeData : TitleBindableBase
|
||||
{
|
||||
public SFCActionNodeData(LinkPoint linkPoint, string expression)
|
||||
{
|
||||
Title = "输出动作";
|
||||
|
||||
LinkPoint = linkPoint;
|
||||
Expression = expression;
|
||||
}
|
||||
|
||||
private string _expression;
|
||||
public string Expression
|
||||
{
|
||||
get
|
||||
{
|
||||
return _expression;
|
||||
}
|
||||
set
|
||||
{
|
||||
SetProperty(ref _expression, value);
|
||||
}
|
||||
}
|
||||
|
||||
private LinkPoint _linkPoint;
|
||||
public LinkPoint LinkPoint
|
||||
{
|
||||
get
|
||||
{
|
||||
return _linkPoint;
|
||||
}
|
||||
set
|
||||
{
|
||||
SetProperty(ref _linkPoint, value);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -9,10 +9,37 @@ namespace AIStudio.Wpf.SFC.ViewModels
|
||||
{
|
||||
public SFCCOBeginNode() : base(SFCNodeKinds.COBegin)
|
||||
{
|
||||
ItemWidth = 280;
|
||||
ItemHeight = 10;
|
||||
|
||||
ExecuteAddTopInput(null);
|
||||
ExecuteAddBottomOutput(null);
|
||||
ExecuteAddBottomOutput(null);
|
||||
}
|
||||
|
||||
public SFCCOBeginNode(IDiagramViewModel parent, DesignerItemBase designer) : base(parent, designer)
|
||||
{
|
||||
}
|
||||
|
||||
public override void ExecuteAddTopInput(object parameter)
|
||||
{
|
||||
FullyCreatedConnectorInfo connector = new FullyCreatedConnectorInfo(this, ConnectorOrientation.Top, true);
|
||||
connector.YRatio = 0;
|
||||
connector.XRatio = (40 + Input.Count * 200) / ItemWidth;
|
||||
Input.Add(Input.Count, connector);
|
||||
|
||||
AddConnector(connector);
|
||||
}
|
||||
|
||||
public override void ExecuteAddBottomOutput(object parameter)
|
||||
{
|
||||
FullyCreatedConnectorInfo connector = new FullyCreatedConnectorInfo(this, ConnectorOrientation.Bottom, true);
|
||||
connector.YRatio = 1;
|
||||
connector.XRatio = (40 + Output.Count * 200) / ItemWidth;
|
||||
Output.Add(Output.Count, connector);
|
||||
|
||||
|
||||
AddConnector(connector);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -9,10 +9,38 @@ namespace AIStudio.Wpf.SFC.ViewModels
|
||||
{
|
||||
public SFCCOEndNode() : base(SFCNodeKinds.COEnd)
|
||||
{
|
||||
ItemWidth = 280;
|
||||
ItemHeight = 10;
|
||||
|
||||
ExecuteAddBottomOutput(null);
|
||||
ExecuteAddTopInput(null);
|
||||
ExecuteAddTopInput(null);
|
||||
}
|
||||
|
||||
public SFCCOEndNode(IDiagramViewModel parent, DesignerItemBase designer) : base(parent, designer)
|
||||
{
|
||||
}
|
||||
|
||||
public override void ExecuteAddTopInput(object parameter)
|
||||
{
|
||||
FullyCreatedConnectorInfo connector = new FullyCreatedConnectorInfo(this, ConnectorOrientation.Top, true);
|
||||
connector.YRatio = 0;
|
||||
connector.XRatio = (40 + Input.Count * 200) / ItemWidth;
|
||||
Input.Add(Input.Count, connector);
|
||||
|
||||
AddConnector(connector);
|
||||
}
|
||||
|
||||
public override void ExecuteAddBottomOutput(object parameter)
|
||||
{
|
||||
FullyCreatedConnectorInfo connector = new FullyCreatedConnectorInfo(this, ConnectorOrientation.Bottom, true);
|
||||
connector.YRatio = 1;
|
||||
connector.XRatio = (40 + Output.Count * 200) / ItemWidth;
|
||||
Output.Add(Output.Count, connector);
|
||||
|
||||
|
||||
AddConnector(connector);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,6 +1,9 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Collections.ObjectModel;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Windows.Media;
|
||||
using Util.DiagramDesigner;
|
||||
|
||||
namespace AIStudio.Wpf.SFC.ViewModels
|
||||
@@ -9,10 +12,83 @@ namespace AIStudio.Wpf.SFC.ViewModels
|
||||
{
|
||||
public SFCConditionNode() : base(SFCNodeKinds.Condition)
|
||||
{
|
||||
ColorViewModel.LineColor.Color = Colors.Black;
|
||||
ItemWidth = 30;
|
||||
ItemHeight = 30;
|
||||
|
||||
ExecuteAddTopInput(null);
|
||||
ExecuteAddBottomOutput(null);
|
||||
}
|
||||
|
||||
public SFCConditionNode(IDiagramViewModel parent, DesignerItemBase designer) : base(parent, designer)
|
||||
{
|
||||
}
|
||||
|
||||
protected override void Init()
|
||||
{
|
||||
base.Init();
|
||||
}
|
||||
|
||||
private bool _showText;
|
||||
public override bool ShowText
|
||||
{
|
||||
get
|
||||
{
|
||||
return false;
|
||||
}
|
||||
set
|
||||
{
|
||||
SetProperty(ref _showText, value);
|
||||
}
|
||||
}
|
||||
|
||||
private string _expression;
|
||||
public string Expression
|
||||
{
|
||||
get
|
||||
{
|
||||
return _expression;
|
||||
}
|
||||
set
|
||||
{
|
||||
SetProperty(ref _expression, value);
|
||||
}
|
||||
}
|
||||
|
||||
private string _para;
|
||||
public string Para
|
||||
{
|
||||
get
|
||||
{
|
||||
return _para;
|
||||
}
|
||||
set
|
||||
{
|
||||
_para = value;
|
||||
}
|
||||
}
|
||||
|
||||
private ObservableCollection<LinkPoint> _linkPoint = new ObservableCollection<LinkPoint>();
|
||||
public ObservableCollection<LinkPoint> LinkPoint
|
||||
{
|
||||
get
|
||||
{
|
||||
return _linkPoint;
|
||||
}
|
||||
set
|
||||
{
|
||||
SetProperty(ref _linkPoint, value);
|
||||
}
|
||||
}
|
||||
|
||||
protected override void ExecuteEditCommand(object parameter)
|
||||
{
|
||||
SFCConditionNodeData data = new SFCConditionNodeData(LinkPoint, Expression);
|
||||
if (visualiserService.ShowDialog(data) == true)
|
||||
{
|
||||
this.LinkPoint = new ObservableCollection<LinkPoint>(data.LinkPoint.Select(p => SFCService.LinkPoint.FirstOrDefault(q => q.Name == p.Name)));
|
||||
this.Expression = data.Expression;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
82
AIStudio.Wpf.SFC/ViewModels/SFCConditionNodeData.cs
Normal file
82
AIStudio.Wpf.SFC/ViewModels/SFCConditionNodeData.cs
Normal file
@@ -0,0 +1,82 @@
|
||||
using AIStudio.Wpf.BaseDiagram.Commands;
|
||||
using AIStudio.Wpf.BaseDiagram.Models;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Collections.ObjectModel;
|
||||
using System.Windows.Input;
|
||||
using Util.DiagramDesigner;
|
||||
|
||||
namespace AIStudio.Wpf.SFC.ViewModels
|
||||
{
|
||||
/// <summary>
|
||||
/// This is passed to the PopupWindow.xaml window, where a DataTemplate is used to provide the
|
||||
/// ContentControl with the look for this data. This class is also used to allow
|
||||
/// the popup to be cancelled without applying any changes to the calling ViewModel
|
||||
/// whos data will be updated if the PopupWindow.xaml window is closed successfully
|
||||
/// </summary>
|
||||
public class SFCConditionNodeData : TitleBindableBase
|
||||
{
|
||||
public SFCConditionNodeData(IEnumerable<LinkPoint> linkPoint, string expression)
|
||||
{
|
||||
Title = "转移条件";
|
||||
LinkPoint = new ObservableCollection<LinkPoint>(linkPoint);
|
||||
Expression = expression;
|
||||
}
|
||||
|
||||
private string _expression;
|
||||
public string Expression
|
||||
{
|
||||
get
|
||||
{
|
||||
return _expression;
|
||||
}
|
||||
set
|
||||
{
|
||||
SetProperty(ref _expression, value);
|
||||
}
|
||||
}
|
||||
|
||||
private ObservableCollection<LinkPoint> _linkPoint;
|
||||
public ObservableCollection<LinkPoint> LinkPoint
|
||||
{
|
||||
get
|
||||
{
|
||||
return _linkPoint;
|
||||
}
|
||||
set
|
||||
{
|
||||
SetProperty(ref _linkPoint, value);
|
||||
}
|
||||
}
|
||||
|
||||
private ICommand _addCommand;
|
||||
public ICommand AddCommand
|
||||
{
|
||||
get
|
||||
{
|
||||
return this._addCommand ?? (this._addCommand = new DelegateCommand<object>(para => this.AddExecuted(para)));
|
||||
}
|
||||
}
|
||||
|
||||
private ICommand _deleteCommand;
|
||||
public ICommand DeleteCommand
|
||||
{
|
||||
get
|
||||
{
|
||||
return this._deleteCommand ?? (this._deleteCommand = new DelegateCommand<object>(para => this.DeleteExecuted(para)));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
private void AddExecuted(object para)
|
||||
{
|
||||
LinkPoint.Add(new SFC.LinkPoint());
|
||||
}
|
||||
|
||||
private void DeleteExecuted(object para)
|
||||
{
|
||||
LinkPoint.Remove(para as SFC.LinkPoint);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -4,6 +4,7 @@ using System;
|
||||
using System.Collections.Generic;
|
||||
using System.ComponentModel;
|
||||
using System.Text;
|
||||
using System.Windows.Media;
|
||||
using Util.DiagramDesigner;
|
||||
|
||||
namespace AIStudio.Wpf.SFC.ViewModels
|
||||
@@ -14,10 +15,10 @@ namespace AIStudio.Wpf.SFC.ViewModels
|
||||
|
||||
public SFCNode(SFCNodeKinds kind) : base()
|
||||
{
|
||||
ColorViewModel.FillColor.Color = Colors.Blue;
|
||||
Kind = kind;
|
||||
ItemWidth = 80;
|
||||
ItemHeight = 40;
|
||||
|
||||
ItemHeight = 40;
|
||||
}
|
||||
|
||||
public SFCNode(IDiagramViewModel parent, DesignerItemBase designer) : base(parent, designer)
|
||||
@@ -27,14 +28,16 @@ namespace AIStudio.Wpf.SFC.ViewModels
|
||||
|
||||
protected override void Init()
|
||||
{
|
||||
base.Init();
|
||||
|
||||
IsRatioConnector = true;
|
||||
ShowRotate = false;
|
||||
ShowArrow = false;
|
||||
ShowText = true;
|
||||
IsReadOnlyText = true;
|
||||
|
||||
base.Init();
|
||||
|
||||
visualiserService = ApplicationServicesProvider.Instance.Provider.VisualizerService;
|
||||
}
|
||||
}
|
||||
|
||||
protected override void LoadDesignerItemViewModel(IDiagramViewModel parent, SelectableDesignerItemBase designerbase)
|
||||
{
|
||||
@@ -42,7 +45,95 @@ namespace AIStudio.Wpf.SFC.ViewModels
|
||||
|
||||
}
|
||||
|
||||
protected override void InitConnector()
|
||||
{
|
||||
ClearConnectors();
|
||||
}
|
||||
|
||||
public Dictionary<int, FullyCreatedConnectorInfo> Input { get; set; } = new Dictionary<int, FullyCreatedConnectorInfo>();
|
||||
public Dictionary<int, FullyCreatedConnectorInfo> Output { get; set; } = new Dictionary<int, FullyCreatedConnectorInfo>();
|
||||
public Dictionary<int, FullyCreatedConnectorInfo> Action { get; set; } = new Dictionary<int, FullyCreatedConnectorInfo>();
|
||||
|
||||
public virtual void ExecuteAddLeftInput(object parameter)
|
||||
{
|
||||
FullyCreatedConnectorInfo connector = new FullyCreatedConnectorInfo(this, ConnectorOrientation.Left, true);
|
||||
connector.XRatio = 0;
|
||||
Input.Add(Input.Count, connector);
|
||||
for (int i = 0; i < Input.Values.Count; i++)
|
||||
{
|
||||
Input[i].YRatio = (i + 1.0) / (Input.Values.Count + 1.0);
|
||||
}
|
||||
AddConnector(connector);
|
||||
}
|
||||
|
||||
public virtual void ExecuteAddTopInput(object parameter)
|
||||
{
|
||||
FullyCreatedConnectorInfo connector = new FullyCreatedConnectorInfo(this, ConnectorOrientation.Top, true);
|
||||
connector.YRatio = 0;
|
||||
Input.Add(Input.Count, connector);
|
||||
for (int i = 0; i < Input.Values.Count; i++)
|
||||
{
|
||||
Input[i].XRatio = (i + 1.0) / (Input.Values.Count + 1.0);
|
||||
if (Output.ContainsKey(i))
|
||||
{
|
||||
Output[i].XRatio = Input[i].XRatio;
|
||||
}
|
||||
}
|
||||
AddConnector(connector);
|
||||
}
|
||||
|
||||
public virtual void ExecuteAddRightOutput(object parameter)
|
||||
{
|
||||
FullyCreatedConnectorInfo connector = new FullyCreatedConnectorInfo(this, ConnectorOrientation.Right, true);
|
||||
connector.XRatio = 1;
|
||||
Output.Add(Output.Count, connector);
|
||||
for (int i = 0; i < Output.Values.Count; i++)
|
||||
{
|
||||
Output[i].YRatio = (i + 1.0) / (Output.Values.Count + 1.0);
|
||||
}
|
||||
AddConnector(connector);
|
||||
}
|
||||
|
||||
public virtual void ExecuteAddBottomOutput(object parameter)
|
||||
{
|
||||
FullyCreatedConnectorInfo connector = new FullyCreatedConnectorInfo(this, ConnectorOrientation.Bottom, true);
|
||||
connector.YRatio = 1;
|
||||
Output.Add(Output.Count, connector);
|
||||
for (int i = 0; i < Output.Values.Count; i++)
|
||||
{
|
||||
Output[i].XRatio = (i + 1.0) / (Output.Values.Count + 1.0);
|
||||
if (Input.ContainsKey(i))
|
||||
{
|
||||
Input[i].XRatio = Output[i].XRatio;
|
||||
}
|
||||
}
|
||||
|
||||
AddConnector(connector);
|
||||
}
|
||||
|
||||
public virtual void ExecuteAddActionOutput(object parameter)
|
||||
{
|
||||
FullyCreatedConnectorInfo connector = new FullyCreatedConnectorInfo(this, ConnectorOrientation.Right, true);
|
||||
connector.XRatio = 1;
|
||||
Action.Add(Action.Count, connector);
|
||||
Action[Action.Count - 1].YRatio = 0.5;
|
||||
AddConnector(connector);
|
||||
}
|
||||
|
||||
[Browsable(false)]
|
||||
public SFCNodeKinds Kind { get; set; }
|
||||
|
||||
private double _value;
|
||||
public double Value
|
||||
{
|
||||
get
|
||||
{
|
||||
return _value;
|
||||
}
|
||||
set
|
||||
{
|
||||
SetProperty(ref _value, value);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2,12 +2,15 @@
|
||||
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
||||
xmlns:s="clr-namespace:Util.DiagramDesigner;assembly=Util.DiagramDesigner"
|
||||
xmlns:viewmodel="clr-namespace:AIStudio.Wpf.SFC.ViewModels"
|
||||
xmlns:local="clr-namespace:AIStudio.Wpf.SFC"
|
||||
xmlns:converter="clr-namespace:AIStudio.Wpf.BaseDiagram.Converters;assembly=AIStudio.Wpf.BaseDiagram">
|
||||
|
||||
<s:ColorBrushConverter x:Key="ColorBrushConverter"/>
|
||||
<converter:HalfConverter x:Key="HalfConverter"/>
|
||||
<converter:IntToBoolConverter x:Key="IntToBoolConverter"/>
|
||||
|
||||
<ControlTemplate x:Key="StartStyle" TargetType="{x:Type ContentControl}">
|
||||
<Grid>
|
||||
<Grid IsHitTestVisible="False">
|
||||
<Border BorderThickness="1" BorderBrush="{Binding ColorViewModel.LineColor,Converter={StaticResource ColorBrushConverter}}">
|
||||
<Border BorderThickness="1" Margin="3" BorderBrush="{Binding ColorViewModel.LineColor,Converter={StaticResource ColorBrushConverter}}" Background="{Binding ColorViewModel.FillColor,Converter={StaticResource ColorBrushConverter}}">
|
||||
<Grid>
|
||||
@@ -19,37 +22,38 @@
|
||||
</ControlTemplate>
|
||||
|
||||
<ControlTemplate x:Key="NodeStyle" TargetType="{x:Type ContentControl}">
|
||||
<Grid>
|
||||
<Grid IsHitTestVisible="False">
|
||||
<Border BorderThickness="4" BorderBrush="{Binding ColorViewModel.LineColor,Converter={StaticResource ColorBrushConverter}}" Background="{Binding ColorViewModel.FillColor,Converter={StaticResource ColorBrushConverter}}">
|
||||
<Grid>
|
||||
|
||||
</Grid>
|
||||
</Border>
|
||||
</Grid>
|
||||
</ControlTemplate>
|
||||
</ControlTemplate>
|
||||
|
||||
<ControlTemplate x:Key="ConditionStyle" TargetType="{x:Type ContentControl}">
|
||||
<Grid>
|
||||
<Grid IsHitTestVisible="False">
|
||||
<Border BorderThickness="1" HorizontalAlignment="Center" BorderBrush="{Binding ColorViewModel.LineColor,Converter={StaticResource ColorBrushConverter}}">
|
||||
</Border>
|
||||
<Border BorderThickness="1" VerticalAlignment="Center" BorderBrush="{Binding ColorViewModel.LineColor,Converter={StaticResource ColorBrushConverter}}">
|
||||
</Border>
|
||||
<TextBlock Text="{Binding Text}" RenderTransformOrigin="1,0.5" TextWrapping="Wrap" HorizontalAlignment="Left" VerticalAlignment="Center" Margin="2">
|
||||
<TextBlock.RenderTransform>
|
||||
<TranslateTransform X="{Binding ItemWidth}"/>
|
||||
</TextBlock.RenderTransform>
|
||||
</TextBlock>
|
||||
</Grid>
|
||||
</ControlTemplate>
|
||||
|
||||
<ControlTemplate x:Key="ActionStyle" TargetType="{x:Type ContentControl}">
|
||||
<Grid>
|
||||
<Border BorderThickness="1" BorderBrush="{Binding ColorViewModel.LineColor,Converter={StaticResource ColorBrushConverter}}" Background="{Binding ColorViewModel.FillColor,Converter={StaticResource ColorBrushConverter}}">
|
||||
<Grid>
|
||||
|
||||
</Grid>
|
||||
</Border>
|
||||
<Grid IsHitTestVisible="False">
|
||||
<Ellipse StrokeThickness="1" Stroke="{Binding ColorViewModel.LineColor,Converter={StaticResource ColorBrushConverter}}" Fill="{Binding ColorViewModel.FillColor,Converter={StaticResource ColorBrushConverter}}" />
|
||||
</Grid>
|
||||
</ControlTemplate>
|
||||
|
||||
<ControlTemplate x:Key="COBeginStyle" TargetType="{x:Type ContentControl}">
|
||||
<Grid>
|
||||
<Border BorderThickness="0,1,0,1" BorderBrush="{Binding ColorViewModel.LineColor,Converter={StaticResource ColorBrushConverter}}" Background="{Binding ColorViewModel.FillColor,Converter={StaticResource ColorBrushConverter}}">
|
||||
<Grid IsHitTestVisible="False">
|
||||
<Border BorderThickness="0,2,0,2" BorderBrush="{Binding ColorViewModel.LineColor,Converter={StaticResource ColorBrushConverter}}" Background="{Binding ColorViewModel.FillColor,Converter={StaticResource ColorBrushConverter}}">
|
||||
<Grid>
|
||||
|
||||
</Grid>
|
||||
@@ -58,8 +62,8 @@
|
||||
</ControlTemplate>
|
||||
|
||||
<ControlTemplate x:Key="COEndStyle" TargetType="{x:Type ContentControl}">
|
||||
<Grid>
|
||||
<Border BorderThickness="0,1,0,1" BorderBrush="{Binding ColorViewModel.LineColor,Converter={StaticResource ColorBrushConverter}}" Background="{Binding ColorViewModel.FillColor,Converter={StaticResource ColorBrushConverter}}">
|
||||
<Grid IsHitTestVisible="False">
|
||||
<Border BorderThickness="0,2,0,2" BorderBrush="{Binding ColorViewModel.LineColor,Converter={StaticResource ColorBrushConverter}}" Background="{Binding ColorViewModel.FillColor,Converter={StaticResource ColorBrushConverter}}">
|
||||
<Grid>
|
||||
|
||||
</Grid>
|
||||
@@ -67,6 +71,105 @@
|
||||
</Grid>
|
||||
</ControlTemplate>
|
||||
|
||||
<ControlTemplate x:Key="TankStyle" TargetType="{x:Type ContentControl}">
|
||||
<Grid IsHitTestVisible="False">
|
||||
<Rectangle RadiusX="5" RadiusY="5" StrokeThickness="1" Stroke="{Binding ColorViewModel.LineColor,Converter={StaticResource ColorBrushConverter}}" Fill="{Binding ColorViewModel.FillColor,Converter={StaticResource ColorBrushConverter}}" />
|
||||
<ProgressBar Orientation="Vertical" Foreground="Green" Background="Red" Value="{Binding LinkPoint.Value,FallbackValue=50}" Width="5" HorizontalAlignment="Right" Margin="5" Maximum="100" Minimum="0"/>
|
||||
</Grid>
|
||||
</ControlTemplate>
|
||||
|
||||
<Style TargetType="{x:Type ToggleButton}" x:Key="SolenoidToggleButtonStyle">
|
||||
<Setter Property="Background" Value="Red"/>
|
||||
<Setter Property="SnapsToDevicePixels" Value="True" />
|
||||
<Setter Property="Template">
|
||||
<Setter.Value>
|
||||
<ControlTemplate TargetType="{x:Type ToggleButton}">
|
||||
<Grid x:Name="Grid" Margin="{TemplateBinding Padding}">
|
||||
<Path x:Name="path1" Data="M192 128l128 128-128 128z" Fill="Red" Stroke="Black" Stretch="Fill" Width="{Binding Path=ActualWidth, RelativeSource={RelativeSource Mode=TemplatedParent}, Converter={StaticResource HalfConverter}}" HorizontalAlignment="Left"/>
|
||||
<Path x:Name="path2" Data="M450 600L650 800V400z" Fill="Red" Stroke="Black" Stretch="Fill" Width="{Binding Path=ActualWidth, RelativeSource={RelativeSource Mode=TemplatedParent}, Converter={StaticResource HalfConverter}}" HorizontalAlignment="Right"/>
|
||||
</Grid>
|
||||
<ControlTemplate.Triggers>
|
||||
<Trigger Property="IsMouseOver" Value="True">
|
||||
<Setter Property="Foreground" Value="{DynamicResource GrayBrush8}" />
|
||||
</Trigger>
|
||||
<Trigger Property="IsPressed" Value="True">
|
||||
<Setter Property="Foreground" Value="{DynamicResource Fluent.Ribbon.Brushes.HighlightBrush}" />
|
||||
</Trigger>
|
||||
<Trigger Property="IsChecked" Value="True">
|
||||
<Setter Property="Fill" TargetName="path1" Value="Green" />
|
||||
<Setter Property="Fill" TargetName="path2" Value="Green" />
|
||||
</Trigger>
|
||||
<Trigger Property="IsEnabled" Value="false">
|
||||
<Setter Property="Opacity" Value="0.6" TargetName="Grid"/>
|
||||
</Trigger>
|
||||
</ControlTemplate.Triggers>
|
||||
</ControlTemplate>
|
||||
</Setter.Value>
|
||||
</Setter>
|
||||
</Style>
|
||||
|
||||
<Style TargetType="{x:Type ToggleButton}" x:Key="StartToggleButtonStyle">
|
||||
<Setter Property="Background" Value="Red"/>
|
||||
<Setter Property="SnapsToDevicePixels" Value="True" />
|
||||
<Setter Property="Template">
|
||||
<Setter.Value>
|
||||
<ControlTemplate TargetType="{x:Type ToggleButton}">
|
||||
<Grid x:Name="Grid" Margin="{TemplateBinding Padding}" Background="{TemplateBinding Background}">
|
||||
<TextBlock x:Name="txt" Text="开始" VerticalAlignment="Center" HorizontalAlignment="Center"/>
|
||||
</Grid>
|
||||
<ControlTemplate.Triggers>
|
||||
<Trigger Property="IsMouseOver" Value="True">
|
||||
<Setter Property="Foreground" Value="{DynamicResource GrayBrush8}" />
|
||||
</Trigger>
|
||||
<Trigger Property="IsPressed" Value="True">
|
||||
<Setter Property="Foreground" Value="{DynamicResource Fluent.Ribbon.Brushes.HighlightBrush}" />
|
||||
</Trigger>
|
||||
<Trigger Property="IsChecked" Value="True">
|
||||
<Setter Property="Background" TargetName="Grid" Value="Green" />
|
||||
<Setter Property="Text" TargetName="txt" Value="停止" />
|
||||
</Trigger>
|
||||
<Trigger Property="IsEnabled" Value="false">
|
||||
<Setter Property="Opacity" Value="0.6" TargetName="Grid"/>
|
||||
</Trigger>
|
||||
</ControlTemplate.Triggers>
|
||||
</ControlTemplate>
|
||||
</Setter.Value>
|
||||
</Setter>
|
||||
</Style>
|
||||
|
||||
<ControlTemplate x:Key="SolenoidStyle" TargetType="{x:Type ContentControl}">
|
||||
<Grid Margin="0,5">
|
||||
<ToggleButton Style="{StaticResource SolenoidToggleButtonStyle}" IsChecked="{Binding DOLinkPoint.Value, Converter={StaticResource IntToBoolConverter}}"/>
|
||||
<TextBlock Text="{Binding Text}" RenderTransformOrigin="0.5,1" TextWrapping="Wrap" HorizontalAlignment="Center" VerticalAlignment="Top" Margin="2">
|
||||
<TextBlock.RenderTransform>
|
||||
<TranslateTransform Y="16"/>
|
||||
</TextBlock.RenderTransform>
|
||||
</TextBlock>
|
||||
</Grid>
|
||||
</ControlTemplate>
|
||||
|
||||
<ControlTemplate x:Key="StartBtnStyle" TargetType="{x:Type ContentControl}">
|
||||
<Grid Margin="0,5">
|
||||
<ToggleButton Style="{StaticResource StartToggleButtonStyle}" IsChecked="{Binding LinkPoint.Value, Converter={StaticResource IntToBoolConverter}}"/>
|
||||
</Grid>
|
||||
</ControlTemplate>
|
||||
|
||||
<ControlTemplate x:Key="ListStyle" TargetType="{x:Type ContentControl}">
|
||||
<Grid Margin="2">
|
||||
<ItemsControl ItemsSource="{x:Static local:SFCService.LinkPoint}">
|
||||
<ItemsControl.ItemTemplate>
|
||||
<DataTemplate>
|
||||
<StackPanel Orientation="Horizontal" Margin="2">
|
||||
<TextBlock Text="{Binding Name}" Width="45" VerticalAlignment="Center" />
|
||||
<TextBlock Text="{Binding Despcription}" Width="60" VerticalAlignment="Center" />
|
||||
<TextBox Text="{Binding Value,Mode=TwoWay}" Width="50" VerticalAlignment="Center"/>
|
||||
</StackPanel>
|
||||
</DataTemplate>
|
||||
</ItemsControl.ItemTemplate>
|
||||
</ItemsControl>
|
||||
</Grid>
|
||||
</ControlTemplate>
|
||||
|
||||
<Style x:Key="CustomSFCNodeStyle" TargetType="{x:Type ContentControl}">
|
||||
<Setter Property="Template" Value="{StaticResource StartStyle}" />
|
||||
<Style.Triggers>
|
||||
@@ -88,12 +191,140 @@
|
||||
<DataTrigger Binding="{Binding Kind}" Value="COEnd">
|
||||
<Setter Property="Template" Value="{StaticResource COEndStyle}" />
|
||||
</DataTrigger>
|
||||
<DataTrigger Binding="{Binding Kind}" Value="Simulate_Tank">
|
||||
<Setter Property="Template" Value="{StaticResource TankStyle}" />
|
||||
</DataTrigger>
|
||||
<DataTrigger Binding="{Binding Kind}" Value="Simulate_Solenoid">
|
||||
<Setter Property="Template" Value="{StaticResource SolenoidStyle}" />
|
||||
</DataTrigger>
|
||||
<DataTrigger Binding="{Binding Kind}" Value="Simulate_Start">
|
||||
<Setter Property="Template" Value="{StaticResource StartBtnStyle}" />
|
||||
</DataTrigger>
|
||||
<DataTrigger Binding="{Binding Kind}" Value="Simulate_List">
|
||||
<Setter Property="Template" Value="{StaticResource ListStyle}" />
|
||||
</DataTrigger>
|
||||
</Style.Triggers>
|
||||
</Style>
|
||||
|
||||
<DataTemplate DataType="{x:Type viewmodel:SFCNode}">
|
||||
<Grid IsHitTestVisible="False">
|
||||
<Grid>
|
||||
<ContentControl Style="{StaticResource CustomSFCNodeStyle}"/>
|
||||
</Grid>
|
||||
</DataTemplate>
|
||||
|
||||
<DataTemplate DataType="{x:Type viewmodel:SFCConditionNodeData}">
|
||||
<Grid Background="{DynamicResource Fluent.Ribbon.Brushes.AccentBaseColorBrush}">
|
||||
<Grid.RowDefinitions>
|
||||
<RowDefinition Height="Auto"/>
|
||||
<RowDefinition Height="Auto"/>
|
||||
</Grid.RowDefinitions>
|
||||
<Grid.ColumnDefinitions>
|
||||
<ColumnDefinition Width="Auto" />
|
||||
<ColumnDefinition Width="*" />
|
||||
</Grid.ColumnDefinitions>
|
||||
<Label Grid.Column="0"
|
||||
Content="条件"
|
||||
Margin="5" />
|
||||
<TextBox Grid.Column="1"
|
||||
Text="{Binding Expression}" VerticalAlignment="Center"
|
||||
Margin="2"
|
||||
FontSize="12"/>
|
||||
<StackPanel Grid.Column="0" Grid.Row="1" Orientation="Horizontal" VerticalAlignment="Top">
|
||||
<Label
|
||||
Content="绑定"
|
||||
Margin="5,5,0,5" />
|
||||
<Button Command="{Binding AddCommand}" Width="16" Height="16">
|
||||
<Path Stretch="Fill" Fill="Black" Data="M938.666667 426.666667h-341.333334V85.333333c0-46.933333-38.4-85.333333-85.333333-85.333333s-85.333333 38.4-85.333333 85.333333v341.333334H85.333333c-46.933333 0-85.333333 38.4-85.333333 85.333333s38.4 85.333333 85.333333 85.333333h341.333334v341.333334c0 46.933333 38.4 85.333333 85.333333 85.333333s85.333333-38.4 85.333333-85.333333v-341.333334h341.333334c46.933333 0 85.333333-38.4 85.333333-85.333333s-38.4-85.333333-85.333333-85.333333z"/>
|
||||
</Button>
|
||||
</StackPanel>
|
||||
<StackPanel Orientation="Vertical" Grid.Column="1" Grid.Row="1" Margin="2">
|
||||
<ItemsControl
|
||||
ItemsSource="{Binding LinkPoint}" AlternationCount="{Binding LinkPoint.Count}" Background="{DynamicResource Fluent.Ribbon.Brushes.AccentBaseColorBrush}">
|
||||
<ItemsControl.ItemTemplate>
|
||||
<DataTemplate>
|
||||
<DockPanel Margin="2">
|
||||
<Button DockPanel.Dock="Right" Command="{Binding DataContext.DeleteCommand, RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type ItemsControl}}}" CommandParameter="{Binding .}" Width="16" Height="16">
|
||||
<Path Stretch="Fill" Fill="Black" Data="M512 620.544l253.3376 253.3376a76.6976 76.6976 0 1 0 108.544-108.544L620.6464 512l253.2352-253.3376a76.6976 76.6976 0 1 0-108.544-108.544L512 403.3536 258.6624 150.1184a76.6976 76.6976 0 1 0-108.544 108.544L403.3536 512 150.1184 765.3376a76.6976 76.6976 0 1 0 108.544 108.544L512 620.6464z"/>
|
||||
</Button>
|
||||
<ComboBox SelectedValue="{Binding Name}" ItemsSource="{x:Static local:SFCService.LinkPoint}" VerticalAlignment="Center" SelectedValuePath="Name" DisplayMemberPath="Name" FontSize="12"/>
|
||||
</DockPanel>
|
||||
</DataTemplate>
|
||||
</ItemsControl.ItemTemplate>
|
||||
</ItemsControl>
|
||||
</StackPanel>
|
||||
</Grid>
|
||||
</DataTemplate>
|
||||
|
||||
<DataTemplate DataType="{x:Type viewmodel:SFCActionNodeData}">
|
||||
<Grid Background="{DynamicResource Fluent.Ribbon.Brushes.AccentBaseColorBrush}">
|
||||
<Grid.RowDefinitions>
|
||||
<RowDefinition Height="Auto"/>
|
||||
<RowDefinition Height="Auto"/>
|
||||
</Grid.RowDefinitions>
|
||||
<Grid.ColumnDefinitions>
|
||||
<ColumnDefinition Width="Auto" />
|
||||
<ColumnDefinition Width="*" />
|
||||
</Grid.ColumnDefinitions>
|
||||
<Label Grid.Column="0"
|
||||
Content="结果"
|
||||
Margin="5" />
|
||||
<TextBox Grid.Column="1"
|
||||
Text="{Binding Expression}" VerticalAlignment="Center"
|
||||
Margin="2"
|
||||
FontSize="12"/>
|
||||
<Label Grid.Column="0" Grid.Row="1"
|
||||
Content="测点"
|
||||
Margin="5" />
|
||||
<ComboBox Grid.Column="1" Grid.Row="1"
|
||||
SelectedItem="{Binding LinkPoint}" ItemsSource="{x:Static local:SFCService.LinkPoint}" VerticalAlignment="Center" DisplayMemberPath="Name"
|
||||
Margin="5"
|
||||
FontSize="12"/>
|
||||
</Grid>
|
||||
</DataTemplate>
|
||||
|
||||
<DataTemplate DataType="{x:Type viewmodel:Simulate_SolenoidViewModelData}">
|
||||
<Grid Background="{DynamicResource Fluent.Ribbon.Brushes.AccentBaseColorBrush}">
|
||||
<Grid.RowDefinitions>
|
||||
<RowDefinition Height="Auto"/>
|
||||
<RowDefinition Height="Auto"/>
|
||||
</Grid.RowDefinitions>
|
||||
<Grid.ColumnDefinitions>
|
||||
<ColumnDefinition Width="Auto" />
|
||||
<ColumnDefinition Width="*" />
|
||||
</Grid.ColumnDefinitions>
|
||||
<Label Grid.Column="0"
|
||||
Content="输入"
|
||||
Margin="5" />
|
||||
<ComboBox Grid.Column="1" Grid.Row="0"
|
||||
SelectedItem="{Binding DILinkPoint}" ItemsSource="{x:Static local:SFCService.LinkPoint}" VerticalAlignment="Center" DisplayMemberPath="Name"
|
||||
Margin="5"
|
||||
FontSize="12"/>
|
||||
<Label Grid.Column="0"
|
||||
Grid.Row="1"
|
||||
Content="反馈"
|
||||
Margin="5" />
|
||||
<ComboBox Grid.Column="1" Grid.Row="1"
|
||||
SelectedItem="{Binding DOLinkPoint}" ItemsSource="{x:Static local:SFCService.LinkPoint}" VerticalAlignment="Center" DisplayMemberPath="Name"
|
||||
Margin="5"
|
||||
FontSize="12"/>
|
||||
|
||||
</Grid>
|
||||
</DataTemplate>
|
||||
|
||||
<DataTemplate DataType="{x:Type viewmodel:Simulate_TankViewModelData}">
|
||||
<Grid Background="{DynamicResource Fluent.Ribbon.Brushes.AccentBaseColorBrush}">
|
||||
<Grid.ColumnDefinitions>
|
||||
<ColumnDefinition Width="Auto" />
|
||||
<ColumnDefinition Width="*" />
|
||||
</Grid.ColumnDefinitions>
|
||||
<Label Grid.Column="0"
|
||||
Content="液位"
|
||||
Margin="5" />
|
||||
<ComboBox Grid.Column="1" Grid.Row="0"
|
||||
SelectedItem="{Binding LinkPoint}" ItemsSource="{x:Static local:SFCService.LinkPoint}" VerticalAlignment="Center" DisplayMemberPath="Name"
|
||||
Margin="5"
|
||||
FontSize="12"/>
|
||||
</Grid>
|
||||
</DataTemplate>
|
||||
|
||||
</ResourceDictionary>
|
||||
@@ -9,10 +9,14 @@ namespace AIStudio.Wpf.SFC.ViewModels
|
||||
{
|
||||
public SFCNodeNode() : base(SFCNodeKinds.Node)
|
||||
{
|
||||
ExecuteAddTopInput(null);
|
||||
ExecuteAddBottomOutput(null);
|
||||
ExecuteAddActionOutput(null);
|
||||
}
|
||||
|
||||
public SFCNodeNode(IDiagramViewModel parent, DesignerItemBase designer) : base(parent, designer)
|
||||
{
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@@ -9,6 +9,8 @@ namespace AIStudio.Wpf.SFC.ViewModels
|
||||
{
|
||||
public SFCStartNode() : base(SFCNodeKinds.Start)
|
||||
{
|
||||
ExecuteAddTopInput(null);
|
||||
ExecuteAddBottomOutput(null);
|
||||
}
|
||||
|
||||
public SFCStartNode(IDiagramViewModel parent, DesignerItemBase designer) : base(parent, designer)
|
||||
|
||||
22
AIStudio.Wpf.SFC/ViewModels/Simulate_ListViewModel.cs
Normal file
22
AIStudio.Wpf.SFC/ViewModels/Simulate_ListViewModel.cs
Normal file
@@ -0,0 +1,22 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Collections.ObjectModel;
|
||||
using System.Text;
|
||||
using Util.DiagramDesigner;
|
||||
|
||||
namespace AIStudio.Wpf.SFC.ViewModels
|
||||
{
|
||||
public class Simulate_ListViewModel : SFCNode
|
||||
{
|
||||
public Simulate_ListViewModel() : base(SFCNodeKinds.Simulate_List)
|
||||
{
|
||||
ItemWidth = 170;
|
||||
ItemHeight = 260;
|
||||
}
|
||||
|
||||
public Simulate_ListViewModel(IDiagramViewModel parent, DesignerItemBase designer) : base(parent, designer)
|
||||
{
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
80
AIStudio.Wpf.SFC/ViewModels/Simulate_SolenoidViewModel.cs
Normal file
80
AIStudio.Wpf.SFC/ViewModels/Simulate_SolenoidViewModel.cs
Normal file
@@ -0,0 +1,80 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Collections.ObjectModel;
|
||||
using System.Text;
|
||||
using Util.DiagramDesigner;
|
||||
|
||||
namespace AIStudio.Wpf.SFC.ViewModels
|
||||
{
|
||||
public class Simulate_SolenoidViewModel : SFCNode
|
||||
{
|
||||
public Simulate_SolenoidViewModel() : base(SFCNodeKinds.Simulate_Solenoid)
|
||||
{
|
||||
ItemWidth = 32;
|
||||
ItemHeight = 32;
|
||||
|
||||
ExecuteAddLeftInput(null);
|
||||
ExecuteAddRightOutput(null);
|
||||
}
|
||||
|
||||
public Simulate_SolenoidViewModel(IDiagramViewModel parent, DesignerItemBase designer) : base(parent, designer)
|
||||
{
|
||||
}
|
||||
|
||||
private bool _showText;
|
||||
public override bool ShowText
|
||||
{
|
||||
get
|
||||
{
|
||||
return false;
|
||||
}
|
||||
set
|
||||
{
|
||||
SetProperty(ref _showText, value);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 输入
|
||||
/// </summary>
|
||||
private LinkPoint _dILinkPoint;
|
||||
public LinkPoint DILinkPoint
|
||||
{
|
||||
get
|
||||
{
|
||||
return _dILinkPoint;
|
||||
}
|
||||
set
|
||||
{
|
||||
SetProperty(ref _dILinkPoint, value);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 反馈
|
||||
/// </summary>
|
||||
private LinkPoint _dOLinkPoint;
|
||||
public LinkPoint DOLinkPoint
|
||||
{
|
||||
get
|
||||
{
|
||||
return _dOLinkPoint;
|
||||
}
|
||||
set
|
||||
{
|
||||
SetProperty(ref _dOLinkPoint, value);
|
||||
}
|
||||
}
|
||||
|
||||
protected override void ExecuteEditCommand(object parameter)
|
||||
{
|
||||
Simulate_SolenoidViewModelData data = new Simulate_SolenoidViewModelData(DILinkPoint, DOLinkPoint);
|
||||
if (visualiserService.ShowDialog(data) == true)
|
||||
{
|
||||
this.DILinkPoint = data.DILinkPoint;
|
||||
this.DOLinkPoint = data.DOLinkPoint;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,51 @@
|
||||
using AIStudio.Wpf.BaseDiagram.Models;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
using Util.DiagramDesigner;
|
||||
|
||||
namespace AIStudio.Wpf.SFC.ViewModels
|
||||
{
|
||||
public class Simulate_SolenoidViewModelData : TitleBindableBase
|
||||
{
|
||||
public Simulate_SolenoidViewModelData(LinkPoint dILinkPoint, LinkPoint dOLinkPoint)
|
||||
{
|
||||
Title = "阀门";
|
||||
DILinkPoint = dILinkPoint;
|
||||
DOLinkPoint = dOLinkPoint;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 输入
|
||||
/// </summary>
|
||||
private LinkPoint _dILinkPoint;
|
||||
public LinkPoint DILinkPoint
|
||||
{
|
||||
get
|
||||
{
|
||||
return _dILinkPoint;
|
||||
}
|
||||
set
|
||||
{
|
||||
SetProperty(ref _dILinkPoint, value);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 反馈
|
||||
/// </summary>
|
||||
private LinkPoint _dOLinkPoint;
|
||||
public LinkPoint DOLinkPoint
|
||||
{
|
||||
get
|
||||
{
|
||||
return _dOLinkPoint;
|
||||
}
|
||||
set
|
||||
{
|
||||
SetProperty(ref _dOLinkPoint, value);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
37
AIStudio.Wpf.SFC/ViewModels/Simulate_StartViewModel.cs
Normal file
37
AIStudio.Wpf.SFC/ViewModels/Simulate_StartViewModel.cs
Normal file
@@ -0,0 +1,37 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
using Util.DiagramDesigner;
|
||||
|
||||
namespace AIStudio.Wpf.SFC.ViewModels
|
||||
{
|
||||
public class Simulate_StartViewModel : SFCNode
|
||||
{
|
||||
public Simulate_StartViewModel() : base(SFCNodeKinds.Simulate_Start)
|
||||
{
|
||||
ItemWidth = 32;
|
||||
ItemHeight = 32;
|
||||
|
||||
ExecuteAddLeftInput(null);
|
||||
ExecuteAddRightOutput(null);
|
||||
}
|
||||
|
||||
public Simulate_StartViewModel(IDiagramViewModel parent, DesignerItemBase designer) : base(parent, designer)
|
||||
{
|
||||
}
|
||||
|
||||
private LinkPoint linkPoint;
|
||||
public LinkPoint LinkPoint
|
||||
{
|
||||
get
|
||||
{
|
||||
return linkPoint;
|
||||
}
|
||||
set
|
||||
{
|
||||
SetProperty(ref linkPoint, value);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
72
AIStudio.Wpf.SFC/ViewModels/Simulate_TankViewModel.cs
Normal file
72
AIStudio.Wpf.SFC/ViewModels/Simulate_TankViewModel.cs
Normal file
@@ -0,0 +1,72 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
using Util.DiagramDesigner;
|
||||
|
||||
namespace AIStudio.Wpf.SFC.ViewModels
|
||||
{
|
||||
public class Simulate_TankViewModel : SFCNode
|
||||
{
|
||||
public Simulate_TankViewModel() : base(SFCNodeKinds.Simulate_Tank)
|
||||
{
|
||||
ItemWidth = 50;
|
||||
ItemHeight = 120;
|
||||
|
||||
ExecuteAddLeftInput(null);
|
||||
ExecuteAddLeftInput(null);
|
||||
ExecuteAddRightOutput(null);
|
||||
ExecuteAddRightOutput(null);
|
||||
}
|
||||
|
||||
public Simulate_TankViewModel(IDiagramViewModel parent, DesignerItemBase designer) : base(parent, designer)
|
||||
{
|
||||
}
|
||||
|
||||
public override void ExecuteAddLeftInput(object parameter)
|
||||
{
|
||||
FullyCreatedConnectorInfo connector = new FullyCreatedConnectorInfo(this, ConnectorOrientation.Left, true);
|
||||
connector.XRatio = 0;
|
||||
connector.YRatio = (30 + Input.Count * 60) / ItemHeight;
|
||||
Input.Add(Input.Count, connector);
|
||||
|
||||
AddConnector(connector);
|
||||
}
|
||||
|
||||
public override void ExecuteAddRightOutput(object parameter)
|
||||
{
|
||||
FullyCreatedConnectorInfo connector = new FullyCreatedConnectorInfo(this, ConnectorOrientation.Right, true);
|
||||
connector.XRatio = 1;
|
||||
connector.YRatio = (30 + Output.Count * 60) / ItemHeight;
|
||||
Output.Add(Output.Count, connector);
|
||||
|
||||
|
||||
AddConnector(connector);
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// 液位
|
||||
/// </summary>
|
||||
private LinkPoint linkPoint;
|
||||
public LinkPoint LinkPoint
|
||||
{
|
||||
get
|
||||
{
|
||||
return linkPoint;
|
||||
}
|
||||
set
|
||||
{
|
||||
SetProperty(ref linkPoint, value);
|
||||
}
|
||||
}
|
||||
|
||||
protected override void ExecuteEditCommand(object parameter)
|
||||
{
|
||||
Simulate_TankViewModelData data = new Simulate_TankViewModelData(LinkPoint);
|
||||
if (visualiserService.ShowDialog(data) == true)
|
||||
{
|
||||
this.LinkPoint = data.LinkPoint;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
34
AIStudio.Wpf.SFC/ViewModels/Simulate_TankViewModelData.cs
Normal file
34
AIStudio.Wpf.SFC/ViewModels/Simulate_TankViewModelData.cs
Normal file
@@ -0,0 +1,34 @@
|
||||
using AIStudio.Wpf.BaseDiagram.Models;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
using Util.DiagramDesigner;
|
||||
|
||||
namespace AIStudio.Wpf.SFC.ViewModels
|
||||
{
|
||||
public class Simulate_TankViewModelData : TitleBindableBase
|
||||
{
|
||||
public Simulate_TankViewModelData(LinkPoint linkPoint)
|
||||
{
|
||||
Title = "容器";
|
||||
LinkPoint = linkPoint;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 液位
|
||||
/// </summary>
|
||||
private LinkPoint linkPoint;
|
||||
public LinkPoint LinkPoint
|
||||
{
|
||||
get
|
||||
{
|
||||
return linkPoint;
|
||||
}
|
||||
set
|
||||
{
|
||||
SetProperty(ref linkPoint, value);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
@@ -376,6 +376,52 @@ namespace Util.DiagramDesigner
|
||||
_service.DrawModeViewModel.ResetDrawMode();
|
||||
}
|
||||
|
||||
protected override void OnPreviewKeyDown(KeyEventArgs e)
|
||||
{
|
||||
base.OnPreviewKeyDown(e);
|
||||
|
||||
if (e.Key == Key.Left)
|
||||
{
|
||||
if (_viewModel.SelectedItems != null)
|
||||
{
|
||||
foreach(var item in _viewModel.SelectedItems.OfType<DesignerItemViewModelBase>())
|
||||
{
|
||||
item.Left -= 0.1;
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (e.Key == Key.Right)
|
||||
{
|
||||
if (_viewModel.SelectedItems != null)
|
||||
{
|
||||
foreach (var item in _viewModel.SelectedItems.OfType<DesignerItemViewModelBase>())
|
||||
{
|
||||
item.Left += 0.1;
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (e.Key == Key.Up)
|
||||
{
|
||||
if (_viewModel.SelectedItems != null)
|
||||
{
|
||||
foreach (var item in _viewModel.SelectedItems.OfType<DesignerItemViewModelBase>())
|
||||
{
|
||||
item.Top -= 0.1;
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (e.Key == Key.Down)
|
||||
{
|
||||
if (_viewModel.SelectedItems != null)
|
||||
{
|
||||
foreach (var item in _viewModel.SelectedItems.OfType<DesignerItemViewModelBase>())
|
||||
{
|
||||
item.Top += 0.1;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
protected override Size MeasureOverride(Size constraint)
|
||||
{
|
||||
Size size = new Size();
|
||||
|
||||
@@ -99,7 +99,6 @@ namespace Util.DiagramDesigner.Controls
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private DesignerCanvas GetDesignerCanvas(DependencyObject element)
|
||||
{
|
||||
while (element != null && !(element is DesignerCanvas))
|
||||
|
||||
@@ -8,6 +8,7 @@ namespace Util.DiagramDesigner
|
||||
{
|
||||
Normal,
|
||||
FlowChart,
|
||||
Logical
|
||||
Logical,
|
||||
SFC,
|
||||
}
|
||||
}
|
||||
|
||||
@@ -16,6 +16,7 @@ namespace Util.DiagramDesigner
|
||||
{
|
||||
//如果是字符串或值类型则直接返回
|
||||
if (obj == null || obj is string || obj.GetType().IsValueType) return obj;
|
||||
|
||||
object retval = Activator.CreateInstance(obj.GetType());
|
||||
FieldInfo[] fields = obj.GetType().GetFields(BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static);
|
||||
foreach (FieldInfo field in fields)
|
||||
@@ -45,6 +46,9 @@ namespace Util.DiagramDesigner
|
||||
|
||||
public static T AutoCopy<T>(T source) where T : new()
|
||||
{
|
||||
//如果是字符串或值类型则直接返回
|
||||
if (source == null || source is string || source.GetType().IsValueType) return source;
|
||||
|
||||
T target = new T();
|
||||
var Properties = typeof(T).GetProperties();
|
||||
foreach (var Propertie in Properties)
|
||||
@@ -61,7 +65,8 @@ namespace Util.DiagramDesigner
|
||||
|
||||
public static T DeepCopy<T>(T obj)
|
||||
{
|
||||
if (obj == null) return obj;
|
||||
//如果是字符串或值类型则直接返回
|
||||
if (obj == null || obj is string || obj.GetType().IsValueType) return obj;
|
||||
|
||||
object retval;
|
||||
using (MemoryStream ms = new MemoryStream())
|
||||
|
||||
@@ -17,30 +17,8 @@ namespace Util.DiagramDesigner
|
||||
Point point = new Point();
|
||||
if (connector.IsInnerPoint)
|
||||
{
|
||||
switch (connector.Orientation)
|
||||
{
|
||||
case ConnectorOrientation.Top:
|
||||
point = new Point(connector.DataItem.Left + connector.DataItem.ItemWidth * connector.XRatio + connector.ConnectorWidth / 2,
|
||||
connector.DataItem.Top + connector.DataItem.ItemHeight * connector.YRatio);
|
||||
break;
|
||||
case ConnectorOrientation.Bottom:
|
||||
point = new Point(connector.DataItem.Left + connector.DataItem.ItemWidth * connector.XRatio + connector.ConnectorWidth / 2,
|
||||
connector.DataItem.Top + connector.DataItem.ItemHeight * connector.YRatio + connector.ConnectorHeight / 2); ;
|
||||
break;
|
||||
case ConnectorOrientation.Right:
|
||||
point = new Point(connector.DataItem.Left + connector.DataItem.ItemWidth * connector.XRatio,
|
||||
connector.DataItem.Top + connector.DataItem.ItemHeight * connector.YRatio + connector.ConnectorHeight / 2);
|
||||
break;
|
||||
case ConnectorOrientation.Left:
|
||||
point = new Point(connector.DataItem.Left + connector.DataItem.ItemWidth * connector.XRatio,
|
||||
connector.DataItem.Top + connector.DataItem.ItemHeight * connector.YRatio + connector.ConnectorHeight / 2);
|
||||
break;
|
||||
default:
|
||||
point = new Point(connector.DataItem.Left + connector.DataItem.ItemWidth * connector.XRatio + connector.ConnectorWidth / 2,
|
||||
connector.DataItem.Top + connector.DataItem.ItemHeight * connector.YRatio + connector.ConnectorHeight / 2);
|
||||
break;
|
||||
}
|
||||
|
||||
point = new Point(connector.DataItem.Left + connector.DataItem.ItemWidth * connector.XRatio,
|
||||
connector.DataItem.Top + connector.DataItem.ItemHeight * connector.YRatio);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
@@ -37,10 +37,10 @@ namespace Util.DiagramDesigner
|
||||
FullyCreatedConnectorInfo vm = item as FullyCreatedConnectorInfo;
|
||||
var connector = ItemContainerGenerator.ContainerFromItem(item) as ContentPresenter;
|
||||
|
||||
Canvas.SetLeft(connector, vm.DataItem.ItemWidth * vm.XRatio);
|
||||
Canvas.SetTop(connector, vm.DataItem.ItemHeight * vm.YRatio);
|
||||
Canvas.SetLeft(connector, vm.DataItem.ItemWidth * vm.XRatio - vm.ConnectorWidth / 2);
|
||||
Canvas.SetTop(connector, vm.DataItem.ItemHeight * vm.YRatio - vm.ConnectorHeight / 2);
|
||||
}
|
||||
SetConnectorLocation();
|
||||
//SetConnectorLocation();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -63,8 +63,8 @@ namespace Util.DiagramDesigner
|
||||
var vm = connector.DataContext as FullyCreatedConnectorInfo;
|
||||
if (vm != null)
|
||||
{
|
||||
Canvas.SetLeft(connector, vm.DataItem.ItemWidth * vm.XRatio);
|
||||
Canvas.SetTop(connector, vm.DataItem.ItemHeight * vm.YRatio);
|
||||
Canvas.SetLeft(connector, vm.DataItem.ItemWidth * vm.XRatio - vm.ConnectorWidth / 2);
|
||||
Canvas.SetTop(connector, vm.DataItem.ItemHeight * vm.YRatio - vm.ConnectorHeight / 2);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -23,7 +23,7 @@
|
||||
<s:LineDashConverter x:Key="LineDashConverter"/>
|
||||
<s:ClipConverter x:Key="ClipConverter"/>
|
||||
<s:InvertBoolConverter x:Key="InvertBoolConverter"/>
|
||||
|
||||
|
||||
<!-- ResizeDecorator Default Template -->
|
||||
<!--
|
||||
<ControlTemplate x:Key="ResizeDecoratorTemplate" TargetType="{x:Type Control}">
|
||||
@@ -307,6 +307,45 @@
|
||||
</Setter>
|
||||
</Style>
|
||||
|
||||
<ControlTemplate x:Key="ConnectorDecoratorTemplate"
|
||||
TargetType="{x:Type Control}">
|
||||
<Grid Margin="-5">
|
||||
<s:Connector DataContext="{Binding LeftConnector}" Style="{StaticResource normalConnector}"
|
||||
Orientation="Left"
|
||||
VerticalAlignment="Center"
|
||||
HorizontalAlignment="Left"
|
||||
Visibility="{Binding Path=ShowConnectors, Converter={x:Static s:BoolToVisibilityConverter.Instance}}" />
|
||||
<s:Connector DataContext="{Binding TopConnector}" Style="{StaticResource normalConnector}"
|
||||
Orientation="Top"
|
||||
VerticalAlignment="Top"
|
||||
HorizontalAlignment="Center"
|
||||
Visibility="{Binding Path=ShowConnectors, Converter={x:Static s:BoolToVisibilityConverter.Instance}}" />
|
||||
<s:Connector DataContext="{Binding RightConnector}" Style="{StaticResource normalConnector}"
|
||||
Orientation="Right"
|
||||
VerticalAlignment="Center"
|
||||
HorizontalAlignment="Right"
|
||||
Visibility="{Binding Path=ShowConnectors, Converter={x:Static s:BoolToVisibilityConverter.Instance}}" />
|
||||
<s:Connector DataContext="{Binding BottomConnector}" Style="{StaticResource normalConnector}"
|
||||
Orientation="Bottom"
|
||||
VerticalAlignment="Bottom"
|
||||
HorizontalAlignment="Center"
|
||||
Visibility="{Binding Path=ShowConnectors, Converter={x:Static s:BoolToVisibilityConverter.Instance}}" />
|
||||
</Grid>
|
||||
</ControlTemplate>
|
||||
|
||||
<ControlTemplate x:Key="RatioConnectorDecoratorTemplate"
|
||||
TargetType="{x:Type Control}">
|
||||
<s:ConnectorContainer x:Name="PART_ConnectorContainer" Style="{StaticResource logicConnectorContainer}" ItemsSource="{Binding Connectors}" Visibility="{Binding Path=ShowConnectors, Converter={x:Static s:BoolToVisibilityConverter.Instance}}">
|
||||
<s:ConnectorContainer.ItemTemplate>
|
||||
<DataTemplate>
|
||||
<Grid>
|
||||
<s:Connector Style="{StaticResource normalConnector}"/>
|
||||
</Grid>
|
||||
</DataTemplate>
|
||||
</s:ConnectorContainer.ItemTemplate>
|
||||
</s:ConnectorContainer>
|
||||
</ControlTemplate>
|
||||
|
||||
</ResourceDictionary>
|
||||
</UserControl.Resources>
|
||||
<UserControl.LayoutTransform>
|
||||
@@ -404,29 +443,7 @@
|
||||
</Control>
|
||||
|
||||
<!-- PART_ConnectorDecorator -->
|
||||
<Grid Margin="-5"
|
||||
x:Name="PART_ConnectorDecorator">
|
||||
<s:Connector DataContext="{Binding LeftConnector}" Style="{StaticResource normalConnector}"
|
||||
Orientation="Left"
|
||||
VerticalAlignment="Center"
|
||||
HorizontalAlignment="Left"
|
||||
Visibility="{Binding Path=ShowConnectors, Converter={x:Static s:BoolToVisibilityConverter.Instance}}" />
|
||||
<s:Connector DataContext="{Binding TopConnector}" Style="{StaticResource normalConnector}"
|
||||
Orientation="Top"
|
||||
VerticalAlignment="Top"
|
||||
HorizontalAlignment="Center"
|
||||
Visibility="{Binding Path=ShowConnectors, Converter={x:Static s:BoolToVisibilityConverter.Instance}}" />
|
||||
<s:Connector DataContext="{Binding RightConnector}" Style="{StaticResource normalConnector}"
|
||||
Orientation="Right"
|
||||
VerticalAlignment="Center"
|
||||
HorizontalAlignment="Right"
|
||||
Visibility="{Binding Path=ShowConnectors, Converter={x:Static s:BoolToVisibilityConverter.Instance}}" />
|
||||
<s:Connector DataContext="{Binding BottomConnector}" Style="{StaticResource normalConnector}"
|
||||
Orientation="Bottom"
|
||||
VerticalAlignment="Bottom"
|
||||
HorizontalAlignment="Center"
|
||||
Visibility="{Binding Path=ShowConnectors, Converter={x:Static s:BoolToVisibilityConverter.Instance}}" />
|
||||
</Grid>
|
||||
<Control x:Name="PART_ConnectorDecorator" Template="{StaticResource ConnectorDecoratorTemplate}"/>
|
||||
|
||||
<Grid.RenderTransform>
|
||||
<TransformGroup>
|
||||
@@ -456,6 +473,10 @@
|
||||
Binding="{Binding Connectors.Count}">
|
||||
<Setter TargetName="PART_ConnectorDecorator" Property="Visibility" Value="Collapsed" />
|
||||
</DataTrigger>
|
||||
<DataTrigger Value="True"
|
||||
Binding="{Binding IsRatioConnector}">
|
||||
<Setter TargetName="PART_ConnectorDecorator" Property="Template" Value="{StaticResource RatioConnectorDecoratorTemplate}" />
|
||||
</DataTrigger>
|
||||
</DataTemplate.Triggers>
|
||||
</DataTemplate>
|
||||
</Setter.Value>
|
||||
@@ -551,7 +572,7 @@
|
||||
Cursor="SizeAll" >
|
||||
<c:DragThumb.InputBindings>
|
||||
<MouseBinding MouseAction="LeftDoubleClick" Command="{Binding EditCommand}" CommandParameter="{Binding }" />
|
||||
</c:DragThumb.InputBindings>
|
||||
</c:DragThumb.InputBindings>
|
||||
</c:DragThumb>
|
||||
</Grid>
|
||||
<DataTemplate.Triggers>
|
||||
@@ -616,22 +637,8 @@
|
||||
<RotateTransform Angle="0" />
|
||||
</Setter.Value>
|
||||
</Setter>
|
||||
</DataTrigger>
|
||||
<MultiDataTrigger>
|
||||
<MultiDataTrigger.Conditions>
|
||||
<Condition Value="True" Binding="{Binding SinkConnectorInfo.IsInnerPoint}"/>
|
||||
<Condition Value="0" Binding="{Binding SinkConnectorInfo.XRatio}"/>
|
||||
</MultiDataTrigger.Conditions>
|
||||
<Setter TargetName="rightarrow" Property="Visibility" Value="Hidden"/>
|
||||
</MultiDataTrigger>
|
||||
<MultiDataTrigger>
|
||||
<MultiDataTrigger.Conditions>
|
||||
<Condition Value="True" Binding="{Binding SinkConnectorInfo.IsInnerPoint}"/>
|
||||
<Condition Value="1" Binding="{Binding SinkConnectorInfo.XRatio}"/>
|
||||
</MultiDataTrigger.Conditions>
|
||||
<Setter TargetName="rightarrow" Property="Visibility" Value="Hidden"/>
|
||||
</MultiDataTrigger>
|
||||
<DataTrigger Binding="{Binding Path=ColorViewModel.RightArrowStyle}" Value="None">
|
||||
</DataTrigger>
|
||||
<DataTrigger Binding="{Binding Path=ColorViewModel.RightArrowPathStyle}" Value="None">
|
||||
<Setter TargetName="rightarrow" Property="Visibility" Value="Hidden"/>
|
||||
</DataTrigger>
|
||||
|
||||
@@ -684,21 +691,7 @@
|
||||
</Setter.Value>
|
||||
</Setter>
|
||||
</DataTrigger>
|
||||
<MultiDataTrigger>
|
||||
<MultiDataTrigger.Conditions>
|
||||
<Condition Value="True" Binding="{Binding SourceConnectorInfo.IsInnerPoint}"/>
|
||||
<Condition Value="0" Binding="{Binding SourceConnectorInfo.XRatio}"/>
|
||||
</MultiDataTrigger.Conditions>
|
||||
<Setter TargetName="leftarrow" Property="Visibility" Value="Hidden"/>
|
||||
</MultiDataTrigger>
|
||||
<MultiDataTrigger>
|
||||
<MultiDataTrigger.Conditions>
|
||||
<Condition Value="True" Binding="{Binding SourceConnectorInfo.IsInnerPoint}"/>
|
||||
<Condition Value="1" Binding="{Binding SourceConnectorInfo.XRatio}"/>
|
||||
</MultiDataTrigger.Conditions>
|
||||
<Setter TargetName="leftarrow" Property="Visibility" Value="Hidden"/>
|
||||
</MultiDataTrigger>
|
||||
<DataTrigger Binding="{Binding Path=ColorViewModel.LeftArrowStyle}" Value="None">
|
||||
<DataTrigger Binding="{Binding Path=ColorViewModel.LeftArrowPathStyle}" Value="None">
|
||||
<Setter TargetName="leftarrow" Property="Visibility" Value="Hidden"/>
|
||||
</DataTrigger>
|
||||
</DataTemplate.Triggers>
|
||||
@@ -823,7 +816,7 @@
|
||||
</Grid.ContextMenu>
|
||||
|
||||
<!--PART_ConnectorDecorator-->
|
||||
<s:ConnectorContainer x:Name="PART_ConnectorContainer" Style="{StaticResource logicConnectorContainer}" ItemsSource="{Binding Connectors}" Margin="-4,0,0,0">
|
||||
<s:ConnectorContainer x:Name="PART_ConnectorContainer" Style="{StaticResource logicConnectorContainer}" ItemsSource="{Binding Connectors}" Margin="0,0,0,0">
|
||||
<s:ConnectorContainer.ItemTemplate>
|
||||
<DataTemplate>
|
||||
<Grid>
|
||||
|
||||
@@ -14,6 +14,8 @@ namespace Util.DiagramDesigner
|
||||
IQuickThemeViewModel QuickThemeViewModel { get; }
|
||||
ILockObjectViewModel LockObjectViewModel { get; }
|
||||
SelectableDesignerItemViewModelBase SelectedItem { get; set; }
|
||||
IColorViewModel CopyDefaultColorViewModel();
|
||||
IFontViewModel CopyDefaultFontViewModel();
|
||||
}
|
||||
|
||||
|
||||
@@ -43,6 +45,18 @@ namespace Util.DiagramDesigner
|
||||
RaisePropertyChanged(sender, e.PropertyName);
|
||||
}
|
||||
|
||||
public IColorViewModel CopyDefaultColorViewModel()
|
||||
{
|
||||
var viewModel = GetOldValue<ColorViewModel>(nameof(ColorViewModel));
|
||||
return CopyHelper.Mapper(viewModel);
|
||||
}
|
||||
|
||||
public IFontViewModel CopyDefaultFontViewModel()
|
||||
{
|
||||
var viewModel = GetOldValue<FontViewModel>(nameof(FontViewModel));
|
||||
return CopyHelper.Mapper<FontViewModel, IFontViewModel>(viewModel);
|
||||
}
|
||||
|
||||
private IColorViewModel _colorViewModel;
|
||||
public IColorViewModel ColorViewModel
|
||||
{
|
||||
|
||||
@@ -23,10 +23,7 @@ namespace Util.DiagramDesigner
|
||||
{
|
||||
base.Init();
|
||||
|
||||
connectors.Add(new FullyCreatedConnectorInfo(this, ConnectorOrientation.Top));
|
||||
connectors.Add(new FullyCreatedConnectorInfo(this, ConnectorOrientation.Bottom));
|
||||
connectors.Add(new FullyCreatedConnectorInfo(this, ConnectorOrientation.Left));
|
||||
connectors.Add(new FullyCreatedConnectorInfo(this, ConnectorOrientation.Right));
|
||||
InitConnector();
|
||||
}
|
||||
|
||||
protected override void LoadDesignerItemViewModel(IDiagramViewModel parent, SelectableDesignerItemBase designerbase)
|
||||
@@ -43,7 +40,14 @@ namespace Util.DiagramDesigner
|
||||
this.ItemWidth = designer.ItemWidth;
|
||||
this.ItemHeight = designer.ItemHeight;
|
||||
this.Icon = designer.Icon;
|
||||
}
|
||||
|
||||
protected virtual void InitConnector()
|
||||
{
|
||||
connectors.Add(new FullyCreatedConnectorInfo(this, ConnectorOrientation.Top));
|
||||
connectors.Add(new FullyCreatedConnectorInfo(this, ConnectorOrientation.Bottom));
|
||||
connectors.Add(new FullyCreatedConnectorInfo(this, ConnectorOrientation.Left));
|
||||
connectors.Add(new FullyCreatedConnectorInfo(this, ConnectorOrientation.Right));
|
||||
}
|
||||
|
||||
public FullyCreatedConnectorInfo TopConnector
|
||||
@@ -162,6 +166,7 @@ namespace Util.DiagramDesigner
|
||||
}
|
||||
|
||||
public bool ShowRotate { get; set; } = true;
|
||||
public bool ShowArrow { get; set; } = true;
|
||||
|
||||
private double _left;
|
||||
[Browsable(true)]
|
||||
@@ -263,6 +268,11 @@ namespace Util.DiagramDesigner
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 连接点是否可以按偏移自定义
|
||||
/// </summary>
|
||||
public bool IsRatioConnector { get; set; }
|
||||
|
||||
private ObservableCollection<FullyCreatedConnectorInfo> connectors = new ObservableCollection<FullyCreatedConnectorInfo>();
|
||||
public IEnumerable<FullyCreatedConnectorInfo> Connectors { get { return connectors; } }
|
||||
|
||||
@@ -321,28 +331,40 @@ namespace Util.DiagramDesigner
|
||||
{
|
||||
if (Parent.CellHorizontalAlignment == CellHorizontalAlignment.Center)
|
||||
{
|
||||
this.Left = (int)(this.Left / Parent.GridCellSize.Width) * Parent.GridCellSize.Width + Parent.GridMargin + (Parent.GridCellSize.Width > this.ItemWidth ? (Parent.GridCellSize.Width - this.ItemWidth) / 2 : 0);
|
||||
if (Parent.GridCellSize.Width > this.ItemWidth)
|
||||
{
|
||||
this.Left = (int)(this.Left / Parent.GridCellSize.Width) * Parent.GridCellSize.Width + Parent.GridMargin + (Parent.GridCellSize.Width - this.ItemWidth) / 2;
|
||||
}
|
||||
}
|
||||
else if(Parent.CellHorizontalAlignment == CellHorizontalAlignment.Left)
|
||||
else if (Parent.CellHorizontalAlignment == CellHorizontalAlignment.Left)
|
||||
{
|
||||
this.Left = (int)(this.Left / Parent.GridCellSize.Width) * Parent.GridCellSize.Width + Parent.GridMargin;
|
||||
}
|
||||
else if (Parent.CellHorizontalAlignment == CellHorizontalAlignment.Right)
|
||||
{
|
||||
this.Left = (int)(this.Left / Parent.GridCellSize.Width) * Parent.GridCellSize.Width + Parent.GridMargin + (Parent.GridCellSize.Width > this.ItemWidth ? (Parent.GridCellSize.Width - this.ItemWidth) : 0);
|
||||
if (Parent.GridCellSize.Width > this.ItemWidth)
|
||||
{
|
||||
this.Left = (int)(this.Left / Parent.GridCellSize.Width) * Parent.GridCellSize.Width + Parent.GridMargin + (Parent.GridCellSize.Width - this.ItemWidth);
|
||||
}
|
||||
}
|
||||
|
||||
if (Parent.CellVerticalAlignment == CellVerticalAlignment.Center)
|
||||
{
|
||||
this.Top = (int)(this.Top / Parent.GridCellSize.Height) * Parent.GridCellSize.Height + Parent.GridMargin + (Parent.GridCellSize.Height > this.ItemHeight ? (Parent.GridCellSize.Height - this.ItemHeight) / 2 : 0);
|
||||
{
|
||||
if (Parent.GridCellSize.Height > this.ItemHeight)
|
||||
{
|
||||
this.Top = (int)(this.Top / Parent.GridCellSize.Height) * Parent.GridCellSize.Height + Parent.GridMargin + (Parent.GridCellSize.Height - this.ItemHeight) / 2;
|
||||
}
|
||||
}
|
||||
else if (Parent.CellVerticalAlignment == CellVerticalAlignment.Top)
|
||||
{
|
||||
{
|
||||
this.Top = (int)(this.Top / Parent.GridCellSize.Height) * Parent.GridCellSize.Height + Parent.GridMargin;
|
||||
}
|
||||
else if (Parent.CellVerticalAlignment == CellVerticalAlignment.Bottom)
|
||||
{
|
||||
this.Top = (int)(this.Top / Parent.GridCellSize.Height) * Parent.GridCellSize.Height + Parent.GridMargin + (Parent.GridCellSize.Height > this.ItemHeight ? (Parent.GridCellSize.Height - this.ItemHeight) : 0);
|
||||
{
|
||||
if (Parent.GridCellSize.Height > this.ItemHeight)
|
||||
{
|
||||
this.Top = (int)(this.Top / Parent.GridCellSize.Height) * Parent.GridCellSize.Height + Parent.GridMargin + (Parent.GridCellSize.Height - this.ItemHeight);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -82,6 +82,7 @@ namespace Util.DiagramDesigner
|
||||
protected override void Init()
|
||||
{
|
||||
ShowRotate = false;
|
||||
ShowArrow = false;
|
||||
AddInputCommand = new SimpleCommand(para => ExecuteAddInput(para));
|
||||
AddOutputCommand = new SimpleCommand(para => ExecuteAddOutput(para));
|
||||
|
||||
@@ -217,7 +218,7 @@ namespace Util.DiagramDesigner
|
||||
Input.Add(Input.Count, connector);
|
||||
for (int i = 0; i < Input.Values.Count; i++)
|
||||
{
|
||||
Input[i].YRatio = (i + 1.0) / (Input.Values.Count + 1.0) - connector.ConnectorHeight / 2 / connector.DataItem.ItemHeight;
|
||||
Input[i].YRatio = (i + 1.0) / (Input.Values.Count + 1.0);
|
||||
}
|
||||
AddConnector(connector);
|
||||
}
|
||||
@@ -229,7 +230,7 @@ namespace Util.DiagramDesigner
|
||||
Output.Add(Output.Count, connector);
|
||||
for (int i = 0; i < Output.Values.Count; i++)
|
||||
{
|
||||
Output[i].YRatio = (i + 1.0) / (Output.Values.Count + 1.0) - connector.ConnectorHeight / 2 / connector.DataItem.ItemHeight;
|
||||
Output[i].YRatio = (i + 1.0) / (Output.Values.Count + 1.0);
|
||||
}
|
||||
AddConnector(connector);
|
||||
}
|
||||
|
||||
@@ -34,8 +34,8 @@ namespace Util.DiagramDesigner
|
||||
|
||||
protected virtual void Init()
|
||||
{
|
||||
ColorViewModel = CopyHelper.Mapper(_service.ColorViewModel);
|
||||
FontViewModel = CopyHelper.Mapper<FontViewModel, IFontViewModel>(_service.FontViewModel);
|
||||
ColorViewModel = _service.CopyDefaultColorViewModel();
|
||||
FontViewModel = _service.CopyDefaultFontViewModel();
|
||||
|
||||
LockObjectViewModel = new LockObjectViewModel();
|
||||
SelectItemCommand = new SimpleCommand(ExecuteSelectItemCommand);
|
||||
|
||||
@@ -184,7 +184,7 @@ namespace Util.DiagramDesigner
|
||||
UpdateConnectionPointsByLine();
|
||||
return;
|
||||
}
|
||||
if (Parent.DiagramType == DiagramType.FlowChart)
|
||||
if (Parent.DiagramType == DiagramType.FlowChart || Parent.DiagramType == DiagramType.SFC)
|
||||
{
|
||||
UpdateConnectionPointsByFlowChart();
|
||||
}
|
||||
@@ -379,6 +379,11 @@ namespace Util.DiagramDesigner
|
||||
this.SinkConnectorInfo = sinkConnectorInfo;
|
||||
PathFinder = new OrthogonalPathFinder();
|
||||
DeleteConnectionCommand = new SimpleCommand(DeleteConnection);
|
||||
|
||||
if (sinkConnectorInfo is FullyCreatedConnectorInfo sink && sink.DataItem.ShowArrow == false)
|
||||
{
|
||||
this.ColorViewModel.RightArrowPathStyle = ArrowPathStyle.None;
|
||||
}
|
||||
}
|
||||
|
||||
public SimpleCommand DeleteConnectionCommand { get; set; }
|
||||
|
||||
@@ -399,7 +399,7 @@ namespace Util.DiagramDesigner
|
||||
var attr = property.GetCustomAttributes(typeof(CanDoAttribute), true);
|
||||
if (attr != null && attr.Length != 0)
|
||||
{
|
||||
DoCommandManager.DoNewCommand(sender.ToString(), () => Do(sender, e.PropertyName, valuePropertyChangedEventArgs.NewValue), () => UnDo(sender, e.PropertyName, valuePropertyChangedEventArgs.OldValue), null, false);
|
||||
DoCommandManager.DoNewCommand(sender.ToString() + e.PropertyName, () => Do(sender, e.PropertyName, valuePropertyChangedEventArgs.NewValue), () => UnDo(sender, e.PropertyName, valuePropertyChangedEventArgs.OldValue), null, false);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -704,12 +704,12 @@ namespace Util.DiagramDesigner
|
||||
DoCommandManager.DoNewCommand(this.ToString(),
|
||||
() =>
|
||||
{
|
||||
double mid = selectedItems.Select(p => p.Top).Average();
|
||||
double mid = selectedItems.Select(p => p.Top + p.ItemHeight / 2).Average();
|
||||
|
||||
foreach (DesignerItemViewModelBase item in selectedItems)
|
||||
{
|
||||
item.SetOldValue(item.Top, nameof(item.Top), guid.ToString());
|
||||
item.Top = mid;
|
||||
item.Top = mid - item.ItemHeight / 2;
|
||||
}
|
||||
},
|
||||
() =>
|
||||
@@ -809,12 +809,12 @@ namespace Util.DiagramDesigner
|
||||
DoCommandManager.DoNewCommand(this.ToString(),
|
||||
() =>
|
||||
{
|
||||
double mid = selectedItems.Select(p => p.Left).Average();
|
||||
double mid = selectedItems.Select(p => p.Left + p.ItemWidth / 2).Average();
|
||||
|
||||
foreach (DesignerItemViewModelBase item in selectedItems)
|
||||
{
|
||||
item.SetOldValue(item.Left, nameof(item.Left), guid.ToString());
|
||||
item.Left = mid;
|
||||
item.Left = mid - item.ItemWidth / 2;
|
||||
}
|
||||
},
|
||||
() =>
|
||||
|
||||
@@ -45,6 +45,7 @@ namespace Util.DiagramDesigner
|
||||
Rect GetBoundingRectangle(IEnumerable<DesignerItemViewModelBase> items);
|
||||
void UpdateZIndex();
|
||||
Size PageSize { get;}
|
||||
PageSizeType PageSizeType { get; set; }
|
||||
bool ShowGrid { get; set; }
|
||||
Size GridCellSize { get; set; }
|
||||
PageSizeOrientation PageSizeOrientation { get; set; }
|
||||
|
||||
Reference in New Issue
Block a user