using System; using System.Collections.Generic; using System.Text; using AIStudio.Wpf.DiagramDesigner; using Newtonsoft.Json; using System.Linq; using System.Windows.Media; using AIStudio.Wpf.Flowchart.ViewModels; namespace AIStudio.Wpf.Flowchart.Models { public static class DiagramDataExtention { #region ToJson public static string ToJson(this IDiagramViewModel diagram) { var json = JsonConvert.SerializeObject(new { Nodes = diagram.Items.OfType().Select(p => p.ToDiagramNode()).Where(p => p != null), Links = diagram.Items.OfType().Select(p => p.ToDiagramLink()).Where(p => p != null) }, new JsonSerializerSettings { ReferenceLoopHandling = ReferenceLoopHandling.Ignore }); return json; } public static DiagramNode ToDiagramNode(this DesignerItemViewModelBase nodeModel) { DiagramNode diagramNode; if (nodeModel is FlowNode flowNode) { var flowchartNode = new FlowchartNode(); diagramNode = flowchartNode; diagramNode.Name = flowNode.Name; flowchartNode.Color = flowNode.Color; flowchartNode.Kind = flowNode.Kind; if (nodeModel is MiddleFlowNode middleflowNode) { flowchartNode.UserIds = middleflowNode.UserIds; flowchartNode.RoleIds = middleflowNode.RoleIds; flowchartNode.ActType = middleflowNode.ActType; } } else { return null; } diagramNode.Id = nodeModel.Id.ToString(); if (nodeModel.ParentId != Guid.Empty) { diagramNode.ParentId = nodeModel.ParentId.ToString(); } diagramNode.Label = nodeModel.Text; diagramNode.Width = nodeModel.ItemWidth * nodeModel.Parent.ScreenScale; diagramNode.Height = nodeModel.ItemHeight * nodeModel.Parent.ScreenScale; diagramNode.X = nodeModel.Left * nodeModel.Parent.ScreenScale; diagramNode.Y = nodeModel.Top * nodeModel.Parent.ScreenScale; diagramNode.ZIndex = nodeModel.ZIndex; diagramNode.Type = diagramNode.GetType().Name; diagramNode.PortAlignmentList = nodeModel.Connectors.Select(p => p.Orientation.ToString()).ToList(); return diagramNode; } public static DiagramLink ToDiagramLink(this ConnectorViewModel linkModel) { DiagramLink diagramLink = new DiagramLink(); diagramLink.Id = linkModel.Id.ToString(); diagramLink.Color = SerializeHelper.SerializeColor(linkModel.ColorViewModel.LineColor.Color); diagramLink.SelectedColor = SerializeHelper.SerializeColor(Colors.Black); diagramLink.Width = linkModel.ColorViewModel.LineWidth; diagramLink.Label = linkModel.Text; if (linkModel.IsFullConnection) { diagramLink.SourceId = linkModel.SourceConnectorInfo.DataItem.Id.ToString(); diagramLink.TargetId = linkModel.SinkConnectorInfoFully.DataItem.Id.ToString(); //线条形状与箭头待处理 //diagramLink.Router = baseLinkModel.Router?.Method.Name; //diagramLink.PathGenerator = baseLinkModel.PathGenerator?.Method.Name; //diagramLink.SourceMarkerPath = baseLinkModel.SourceMarker?.Path; //diagramLink.SourceMarkerWidth = baseLinkModel.SourceMarker?.Width; //diagramLink.TargetMarkerPath = baseLinkModel.TargetMarker?.Path; //diagramLink.TargetMarkerWidth = baseLinkModel.TargetMarker?.Width; diagramLink.Type = diagramLink.GetType().Name; diagramLink.SourcePortAlignment = linkModel.SourceConnectorInfo.Orientation.ToString(); diagramLink.TargetPortAlignment = linkModel.SinkConnectorInfoFully.Orientation.ToString(); } else { return null; } return diagramLink; } #endregion #region ToObject public static void ToObject(this IDiagramViewModel diagram, string json) { var data = JsonConvert.DeserializeObject(json, new JsonConverter[] { new DiagramNodeConverter(), new DiagramLinkConverter() }); if (data != null) { ToObject(diagram, data); } } public static void ToObject(this IDiagramViewModel diagram, DiagramData data) { diagram.Items.Clear(); List nodes = new List(); if (data.Nodes != null) { foreach (var node in data.Nodes) { var nodemodel = node.ToNodelModel(diagram); nodes.Add(nodemodel); diagram.Items.Add(nodemodel); } } if (data.Links != null) { foreach (var link in data.Links) { var source = nodes.FirstOrDefault(p => p.Id == new Guid(link.SourceId)); var target = nodes.FirstOrDefault(p => p.Id == new Guid(link.TargetId)); var linkmodel = link.ToLinkModel(diagram, source, target); diagram.Items.Add(linkmodel); } } } private static DesignerItemViewModelBase ToNodelModel(this DiagramNode diagramNode, IDiagramViewModel diagram) { DesignerItemViewModelBase nodeModel; if (diagramNode is FlowchartNode flowchartNode) { FlowNode flowNode = null; switch (flowchartNode.Kind) { case NodeKinds.Start: { var flowchartNodelModel = new StartFlowNode(); flowNode = flowchartNodelModel; break; } case NodeKinds.End: { var flowchartNodelModel = new EndFlowNode(); flowNode = flowchartNodelModel; break; } case NodeKinds.Decide: { var flowchartNodelModel = new DecideFlowNode(); flowNode = flowchartNodelModel; break; } case NodeKinds.COBegin: { var flowchartNodelModel = new COBeginFlowNode(); flowNode = flowchartNodelModel; break; } case NodeKinds.COEnd: { var flowchartNodelModel = new COEndFlowNode(); flowNode = flowchartNodelModel; break; } case NodeKinds.Middle: { var flowchartNodelModel = new MiddleFlowNode(); flowNode = flowchartNodelModel; flowchartNodelModel.UserIds = flowchartNode.UserIds?.ToList(); flowchartNodelModel.RoleIds = flowchartNode.RoleIds?.ToList(); flowchartNodelModel.ActType = flowchartNode.ActType; break; } default: { var flowNodelModel = new FlowNode(NodeKinds.Normal); flowNode = flowNodelModel; break; } } nodeModel = flowNode; flowNode.Name = flowchartNode.Name; flowNode.Color = flowchartNode.Color; flowNode.Kind = flowchartNode.Kind; } else { nodeModel = new TextDesignerItemViewModel(); } nodeModel.Id = new Guid(diagramNode.Id); if (!string.IsNullOrEmpty(diagramNode.ParentId)) { nodeModel.ParentId = new Guid(diagramNode.ParentId); } nodeModel.Parent = diagram; nodeModel.Text = diagramNode.Label; nodeModel.ItemWidth = diagramNode.Width / diagram.ScreenScale; nodeModel.ItemHeight = diagramNode.Height / diagram.ScreenScale; nodeModel.Left = diagramNode.X / diagram.ScreenScale; nodeModel.Top = diagramNode.Y / diagram.ScreenScale; nodeModel.ZIndex = diagramNode.ZIndex; diagramNode.PortAlignmentList?.ForEach(p => nodeModel.AddConnector(new FullyCreatedConnectorInfo(nodeModel, p.ToEnum()))); return nodeModel; } public static ConnectorViewModel ToLinkModel(this DiagramLink diagramLink, IDiagramViewModel diagram, DesignerItemViewModelBase sourceNode, DesignerItemViewModelBase targetNode) { FullyCreatedConnectorInfo sourceConnectorInfo = sourceNode.Connectors.FirstOrDefault(p => p.Orientation.ToString() == diagramLink.SourcePortAlignment); FullyCreatedConnectorInfo sinkConnectorInfo = targetNode.Connectors.FirstOrDefault(p => p.Orientation.ToString() == diagramLink.TargetPortAlignment); ConnectorViewModel linkModel = new ConnectorViewModel(diagram, sourceConnectorInfo, sinkConnectorInfo, diagram.DrawModeViewModel?.VectorLineDrawMode ?? DrawMode.BoundaryConnectingLine); linkModel.Id = new Guid(diagramLink.Id); linkModel.ColorViewModel.LineColor.Color = SerializeHelper.DeserializeColor(diagramLink.Color); linkModel.ColorViewModel.LineWidth = diagramLink.Width; if (!string.IsNullOrEmpty(diagramLink.Label)) { linkModel.AddText(diagramLink.Label); } //线条形状与箭头待处理 //switch (diagramLink.Router) //{ // case "Normal": linkModel.Router = Routers.Normal; break; // case "Orthogonal": linkModel.Router = Routers.Orthogonal; break; //} //switch (diagramLink.PathGenerator) //{ // case "Smooth": linkModel.PathGenerator = PathGenerators.Smooth; break; // case "Straight": linkModel.PathGenerator = PathGenerators.Straight; break; //} //if (!string.IsNullOrEmpty(diagramLink.SourceMarkerPath)) //{ // linkModel.SourceMarker = new LinkMarker(diagramLink.SourceMarkerPath, diagramLink.SourceMarkerWidth ?? 10.0); //} //if (!string.IsNullOrEmpty(diagramLink.TargetMarkerPath)) //{ // linkModel.TargetMarker = new LinkMarker(diagramLink.TargetMarkerPath, diagramLink.TargetMarkerWidth ?? 10.0); //} return linkModel; } #endregion } }