/// <summary> /// Returns all the directed,connected pairs of shapes in the page /// </summary> /// <param name="page"></param> /// <param name="flag"></param> /// <returns></returns> public static IList <ConnectorEdge> GetDirectedEdges( IVisio.Page page, ConnectorEdgeHandling flag) { if (page == null) { throw new System.ArgumentNullException(nameof(page)); } var edges = PathAnalysis.GetDirectedEdgesRaw(page); if (flag == ConnectorEdgeHandling.Raw) { return(edges); } // At this point we know we need to analyze the connetor arrows to produce the correct results var connnector_ids = edges.Select(e => e.Connector.ID).ToList(); // Get the arrows for each connector var src_beginarrow = ShapeSheet.SRCConstants.BeginArrow; var src_endarrow = ShapeSheet.SRCConstants.EndArrow; var query = new ShapeSheet.Query.CellQuery(); var col_beginarrow = query.AddCell(src_beginarrow, "BeginArrow"); var col_endarrow = query.AddCell(src_endarrow, "EndArrow"); var arrow_table = query.GetResults <int>(page, connnector_ids); IList <ConnectorEdge> directed_edges = new List <ConnectorEdge>(); int connector_index = 0; foreach (var e in edges) { int beginarrow = arrow_table[connector_index][col_beginarrow]; int endarrow = arrow_table[connector_index][col_endarrow]; if ((beginarrow < 1) && (endarrow < 1)) { // the line has no arrows if (flag == ConnectorEdgeHandling.Arrow_TreatConnectorsWithoutArrowsAsBidirectional) { // in this case treat the connector as pointing in both directions var de1 = new ConnectorEdge(e.Connector, e.To, e.From); var de2 = new ConnectorEdge(e.Connector, e.From, e.To); directed_edges.Add(de1); directed_edges.Add(de2); } else if (flag == ConnectorEdgeHandling.Arrow_ExcludeConnectorsWithoutArrows) { // in this case ignore the connector completely } else { throw new AutomationException("Internal error"); } } else { // The connector has either a from-arrow, a to-arrow, or both // handle if it has a from arrow if (beginarrow > 0) { var de = new ConnectorEdge(e.Connector, e.To, e.From); directed_edges.Add(de); } // handle if it has a to arrow if (endarrow > 0) { var de = new ConnectorEdge(e.Connector, e.From, e.To); directed_edges.Add(de); } } connector_index++; } return(directed_edges); }
internal static IEnumerable <DirectedEdge <A, object> > GetClosureFromEdges <A, B>( IEnumerable <DirectedEdge <A, B> > edges) { if (edges == null) { throw new System.ArgumentNullException(nameof(edges)); } var object_to_id = new Dictionary <A, int>(); var id_to_object = new Dictionary <int, A>(); foreach (var edge in edges) { if (!object_to_id.ContainsKey(edge.From)) { object_to_id[edge.From] = object_to_id.Count; } if (!object_to_id.ContainsKey(edge.To)) { object_to_id[edge.To] = object_to_id.Count; } } foreach (var i in object_to_id) { id_to_object[i.Value] = i.Key; } var internal_edges = new List <DirectedEdge <int, object> >(); foreach (var edge in edges) { int fromid = object_to_id[edge.From]; int toid = object_to_id[edge.To]; var directed_edge = new DirectedEdge <int, object>(fromid, toid, null); internal_edges.Add(directed_edge); } if (internal_edges.Count == 0) { yield break; } int num_vertices = object_to_id.Count; var adj_matrix = new VisioAutomation.Shapes.Connections.BitArray2D(num_vertices, num_vertices); foreach (var iedge in internal_edges) { adj_matrix[iedge.From, iedge.To] = true; } var warshall_result = adj_matrix.Clone(); PathAnalysis.PerformWarshall(warshall_result); for (int row = 0; row < adj_matrix.Width; row++) { for (int col = 0; col < adj_matrix.Height; col++) { if (warshall_result.Get(row, col) && (row != col)) { var de = new DirectedEdge <A, object>(id_to_object[row], id_to_object[col], null); yield return(de); } } } }