static void node_induce(graph_t * par, graph_t * g) { node_t *n, *nn; edge_t *e; int i; /* enforce that a node is in at most one cluster at this level */ for (n = agfstnode(g); n; n = nn) { nn = agnxtnode(g, n); if (ND_ranktype(n)) { agdelete(g, n); continue; } for (i = 1; i < GD_n_cluster(par); i++) if (agcontains(GD_clust(par)[i], n)) break; if (i < GD_n_cluster(par)) agdelete(g, n); ND_clust(n) = NULL; } for (n = agfstnode(g); n; n = agnxtnode(g, n)) { for (e = agfstout(dot_root(g), n); e; e = agnxtout(dot_root(g), e)) { if (agcontains(g, aghead(e))) agsubedge(g,e,1); } } }
/* deleteObj: * Remove obj from g. * obj may belong to a subgraph of g, so we first must map * obj to its version in g. * If g is null, remove object from root graph. * If obj is a (sub)graph, close it. The g parameter is unused. * Return 0 on success, non-zero on failure. */ int deleteObj(Agraph_t * g, Agobj_t * obj) { gdata *data; if (AGTYPE(obj) == AGRAPH) { g = (Agraph_t *) obj; if (g != agroot(g)) return agclose(g); data = gData(g); if (data->lock & 1) { error(ERROR_WARNING, "Cannot delete locked graph %s", agnameof(g)); data->lock |= 2; return -1; } else return agclose(g); } /* node or edge */ if (!g) g = agroot(agraphof(obj)); if (obj) return agdelete(g, obj); else return -1; }
/* dfs: * Return the number of reversed edges for this component. */ static int dfs(Agraph_t * g, Agnode_t * t, int hasCycle) { Agedge_t *e; Agedge_t *f; Agnode_t *h; ND_mark(t) = 1; ND_onstack(t) = 1; for (e = agfstout(g, t); e; e = f) { f = agnxtout(g, e); if (agtail(e) == aghead(e)) continue; h = aghead(e); if (ND_onstack(h)) { if (agisstrict(g)) { if (agedge(g, h, t, 0, 0) == 0) addRevEdge(g, e); } else { char* key = agnameof (e); if (!key || (agedge(g, h, t, key, 0) == 0)) addRevEdge(g, e); } agdelete(g, e); hasCycle = 1; } else if (ND_mark(h) == 0) hasCycle |= dfs(g, h, hasCycle); } ND_onstack(t) = 0; return hasCycle; }
void GVSkeletonGraph::removeNode(const QString& name){ setlocale(LC_NUMERIC,"en_US.UTF-8"); // Débug séparateur de décimales en version française if(_nodes.contains(name)){ agdelete(_graph, _nodes[name]); _nodes.remove(name); } }
void GVSkeletonGraph::removeEdge(const QPair<QString, QString>& key) { setlocale(LC_NUMERIC,"en_US.UTF-8"); // Débug séparateur de décimales en version française if(_edges.contains(key)) { agdelete(_graph, _edges[key]); _edges.remove(key); } }
static int dfs(Agraph_t * g, Agnode_t * t, int hasCycle) { Agedge_t *e; Agedge_t *f; Agnode_t *h; ND_mark(t) = 1; ND_onstack(t) = 1; for (e = agfstout(g, t); e; e = f) { f = agnxtout(g, e); if (e->tail == e->head) continue; h = e->head; if (ND_onstack(h)) { if (AG_IS_STRICT(g)) { if (agfindedge(g, h, t) == 0) addRevEdge(g, e); } else addRevEdge(g, e); agdelete(g, e); hasCycle = 1; } else if (ND_mark(h) == 0) hasCycle = dfs(g, h, hasCycle); } ND_onstack(t) = 0; return hasCycle; }
void rm(Agnode_t *n) { // removal of the protonode is not permitted if (n->name[0] == '\001' && strcmp (n->name, "\001proto") ==0) return; agdelete(n->graph, n); }
/* processClusterEdges: * Look for cluster edges. Replace cluster edge endpoints * corresponding to a cluster with special cluster nodes. * Delete original nodes. * Return 0 if no cluster edges; 1 otherwise. */ int processClusterEdges(graph_t * g) { int rv; node_t *n; node_t *nxt; edge_t *e; graph_t *clg; agxbuf xb; Dt_t *map; Dt_t *cmap = mkClustMap (g); unsigned char buf[SMALLBUF]; map = dtopen(&mapDisc, Dtoset); clg = agsubg(g, "__clusternodes",1); agbindrec(clg, "Agraphinfo_t", sizeof(Agraphinfo_t), TRUE); agxbinit(&xb, SMALLBUF, buf); for (n = agfstnode(g); n; n = agnxtnode(g, n)) { if (IS_CLUST_NODE(n)) continue; for (e = agfstout(g, n); e; e = agnxtout(g, e)) { checkCompound(e, clg, &xb, map, cmap); } } agxbfree(&xb); dtclose(map); rv = agnnodes(clg); for (n = agfstnode(clg); n; n = nxt) { nxt = agnxtnode(clg, n); agdelete(g, n); } agclose(clg); if (rv) SET_CLUST_EDGE(g); dtclose(cmap); return rv; }
/* processClusterEdges: * Look for cluster edges. Replace cluster edge endpoints * corresponding to a cluster with special cluster nodes. * Delete original nodes. * Return 0 if no cluster edges; 1 otherwise. */ int processClusterEdges(graph_t * g) { int rv; node_t *n; edge_t *e; graph_t *clg; agxbuf xb; Dt_t *map; unsigned char buf[SMALLBUF]; map = dtopen(&mapDisc, Dtoset); clg = agsubg(g, "__clusternodes"); agxbinit(&xb, SMALLBUF, buf); for (n = agfstnode(g); n; n = agnxtnode(g, n)) { for (e = agfstout(g, n); e; e = agnxtout(g, e)) { checkCompound(e, clg, &xb, map); } } agxbfree(&xb); dtclose(map); rv = agnnodes(clg); for (n = agfstnode(clg); n; n = agnxtnode(clg, n)) { agdelete(g, n); } agclose(clg); if (rv) SET_CLUST_EDGE(g); return rv; }
static int dfs(Agnode_t * n, Agedge_t * link, int warn) { Agedge_t *e; Agedge_t *f; Agraph_t *g = agrootof(n); MARK(n) = 1; for (e = agfstin(g, n); e; e = f) { f = agnxtin(g, e); if (e == link) continue; if (MARK(agtail(e))) agdelete(g, e); } for (e = agfstout(g, n); e; e = agnxtout(g, e)) { if (MARK(aghead(e))) { if (!warn) { warn++; fprintf(stderr, "warning: %s has cycle(s), transitive reduction not unique\n", agnameof(g)); fprintf(stderr, "cycle involves edge %s -> %s\n", agnameof(agtail(e)), agnameof(aghead(e))); } } else warn = dfs(aghead(e), AGOUT2IN(e), warn); } MARK(n) = 0; return warn; }
void deleteEdge(gctx_t *gctx, Agraph_t * g, Agedge_t *e) { char *hndl; hndl = obj2cmd(e); agdelete(gctx->g, e); /* delete edge from root graph */ Tcl_DeleteCommand(gctx->ictx->interp, hndl); }
void rm(Agedge_t *e) { // removal of the protoedge is not permitted if ((e->head->name[0] == '\001' && strcmp (e->head->name, "\001proto") == 0) || (e->tail->name[0] == '\001' && strcmp (e->tail->name, "\001proto") == 0)) return; agdelete(e->head->graph->root, e); }
void GVSkeletonGraph::removeNode(const QString& name){ setlocale(LC_NUMERIC,"en_US.UTF-8"); if(_nodes.contains(name)){ agdelete(_graph, _nodes[name]); _nodes.remove(name); } }
void GVSkeletonGraph::removeEdge(const QPair<QString, QString>& key) { setlocale(LC_NUMERIC,"en_US.UTF-8"); if(_edges.contains(key)) { agdelete(_graph, _edges[key]); _edges.remove(key); } }
static void cls_node_edge_free (ClsNodeEdge *cls_edge) { /* Delete agedeges here? */ gtk_object_destroy (GTK_OBJECT (cls_edge->canvas_line)); agdelete (cls_edge->cls_node_from->graph, cls_edge->agedge); g_free (cls_edge); }
static void reverse_edge(graph_t *g, edge_t *e) { edge_t *rev; rev = agfindedge(g,e->head,e->tail); if (!rev) rev = agedge(g,e->head,e->tail); merge(rev,ED_minlen(e),ED_weight(e)); agdelete(g,e); }
/* doDot: * Assume g has nodes. */ static void doDot (Agraph_t* g) { Agraph_t **ccs; Agraph_t *sg; int ncc; int i; pack_info pinfo; int Pack = getPack(g, -1, CL_OFFSET); pack_mode mode = getPackModeInfo (g, l_undef, &pinfo); getPackInfo(g, l_node, CL_OFFSET, &pinfo); if ((mode == l_undef) && (Pack < 0)) { /* No pack information; use old dot with components * handled during layout */ dotLayout(g); } else { /* fill in default values */ if (mode == l_undef) pinfo.mode = l_node; else if (Pack < 0) Pack = CL_OFFSET; pinfo.margin = Pack; pinfo.fixed = 0; /* components using clusters */ ccs = cccomps(g, &ncc, 0); if (ncc == 1) { dotLayout(g); } else if (GD_drawing(g)->ratio_kind == R_NONE) { pinfo.doSplines = 1; for (i = 0; i < ncc; i++) { sg = ccs[i]; initSubg (sg, g); dotLayout (sg); } attachPos (g); packSubgraphs(ncc, ccs, g, &pinfo); resetCoord (g); } else { /* Not sure what semantics should be for non-trivial ratio * attribute with multiple components. * One possibility is to layout nodes, pack, then apply the ratio * adjustment. We would then have to re-adjust all positions. */ dotLayout(g); } for (i = 0; i < ncc; i++) { free (GD_drawing(ccs[i])); agdelete(g, ccs[i]); } free(ccs); } }
/* scan_graph_mode: * Prepare the graph and data structures depending on the layout mode. * If Reduce is true, eliminate singletons and trees. Since G may be a * subgraph, we remove the nodes from the root graph. * Return the number of nodes in the reduced graph. */ int scan_graph_mode(graph_t * G, int mode) { int i, lenx, nV, nE, deg; char *str; node_t *np, *xp, *other; double total_len = 0.0; if (Verbose) fprintf(stderr, "Scanning graph %s, %d nodes\n", G->name, agnnodes(G)); /* Eliminate singletons and trees */ if (Reduce) { for (np = agfstnode(G); np; np = xp) { xp = agnxtnode(G, np); deg = degreeKind(G, np, &other); if (deg == 0) { /* singleton node */ agdelete(G->root, np); } else if (deg == 1) { agdelete(G->root, np); xp = prune(G, other, xp); } } } nV = agnnodes(G); nE = agnedges(G); lenx = agindex(G->root->proto->e, "len"); if (mode == MODE_KK) { Epsilon = .0001 * nV; getdouble(G, "epsilon", &Epsilon); if ((str = agget(G->root, "Damping"))) Damping = atof(str); else Damping = .99; GD_neato_nlist(G) = N_NEW(nV + 1, node_t *); for (i = 0, np = agfstnode(G); np; np = agnxtnode(G, np)) { GD_neato_nlist(G)[i] = np; ND_id(np) = i++; ND_heapindex(np) = -1; total_len += setEdgeLen(G, np, lenx); } } else {
bool rm(Agnode_t *n) { if (!n) return false; // removal of the protonode is not permitted if (agnameof(n)[0] == '\001' && strcmp (agnameof(n), "\001proto") ==0) return false; agdelete(agraphof(n), n); return true; }
void deleteNode(gctx_t * gctx, Agraph_t *g, Agnode_t *n) { char *hndl; deleteNodeEdges(gctx, gctx->g, n); /* delete all edges to/from node in root graph */ hndl = obj2cmd(n); agdelete(gctx->g, n); /* delete node from root graph */ Tcl_DeleteCommand(gctx->ictx->interp, hndl); }
void GVSubGraph::removeNode(const QString& name) { if(_nodes.contains(name)) { agdelete(_graph, _nodes[name]); _nodes.remove(name); QList<QPair<QString, QString> >keys=_edges.keys(); for(int i=0; i<keys.size(); ++i) if(keys.at(i).first==name || keys.at(i).second==name) removeEdge(keys.at(i)); } }
/* twopi_layout: */ void twopi_layout(Agraph_t * g) { Agnode_t *ctr = 0; char *s; twopi_init_graph(g); s = agget(g, "root"); if (s && (*s != '\0')) { ctr = agfindnode(g, s); if (!ctr) { agerr(AGWARN, "specified root node \"%s\" was not found.", s); agerr(AGPREV, "Using default calculation for root node\n"); } } if (agnnodes(g)) { Agraph_t **ccs; Agraph_t *sg; Agnode_t *c = NULL; int ncc; int i; ccs = ccomps(g, &ncc, 0); if (ncc == 1) { circleLayout(g, ctr); adjustNodes(g); spline_edges(g); } else { pack_info pinfo; pack_mode pmode = getPackMode(g, l_node); for (i = 0; i < ncc; i++) { sg = ccs[i]; if (ctr && agcontains(sg, ctr)) c = ctr; else c = 0; nodeInduce(sg); circleLayout(sg, c); adjustNodes(sg); } spline_edges(g); pinfo.margin = getPack(g, CL_OFFSET, CL_OFFSET); pinfo.doSplines = 1; pinfo.mode = pmode; pinfo.fixed = 0; packSubgraphs(ncc, ccs, g, &pinfo); } for (i = 0; i < ncc; i++) { agdelete(g, ccs[i]); } free(ccs); } dotneato_postprocess(g); }
bool rm(Agedge_t *e) { if (!e) return false; // removal of the protoedge is not permitted if ((agnameof(aghead(e))[0] == '\001' && strcmp (agnameof(aghead(e)), "\001proto") == 0) || (agnameof(agtail(e))[0] == '\001' && strcmp (agnameof(agtail(e)), "\001proto") == 0)) return false; agdelete(agroot(agraphof(aghead(e))), e); return true; }
static void cls_node_free (ClsNode *cls_node) { g_free (cls_node->sym_name); g_hash_table_destroy (cls_node->edges_to); g_hash_table_destroy (cls_node->edges_from); g_hash_table_destroy (cls_node->members); if (cls_node->canvas_group) gtk_object_destroy (GTK_OBJECT (cls_node->canvas_group)); agdelete (cls_node->graph, cls_node->agnode); g_free (cls_node); }
/* prune: * np is at end of a chain. If its degree is 0, remove it. * If its degree is 1, remove it and recurse. * If its degree > 1, stop. * The node next is the next node to be visited during iteration. * If it is equal to a node being deleted, set it to next one. * Delete from root graph, since G may be a connected component subgraph. * Return next. */ static node_t *prune(graph_t * G, node_t * np, node_t * next) { node_t *other; int deg; while (np) { deg = degreeKind(G, np, &other); if (deg == 0) { if (next == np) next = agnxtnode(G, np); agdelete(G->root, np); np = 0; } else if (deg == 1) { if (next == np) next = agnxtnode(G, np); agdelete(G->root, np); np = other; } else np = 0; } return next; }
bool rm(Agraph_t *g) { Agedge_t *e; if (!g) return false; Agraph_t* sg; for (sg = agfstsubg (g); sg; sg = agnxtsubg (sg)) rm(sg); if (g == agroot(g)) agclose(g); else agdelete(agroot(g), g); return true; }
/* undoClusterEdges: * Replace cluster nodes with originals. Make sure original has * no attributes. Replace original edges. Delete cluster nodes, * which will also delete cluster edges. */ void undoClusterEdges(graph_t * g) { node_t *n; edge_t *e; graph_t *clg; clg = agsubg(g, "__clusternodes"); for (n = agfstnode(g); n; n = agnxtnode(g, n)) { for (e = agfstout(g, n); e; e = agnxtout(g, e)) { undoCompound(e, clg); } } for (n = agfstnode(clg); n; n = agnxtnode(clg, n)) { agdelete(g, n); } agclose(clg); }
/* remove_pair_edges: * Create layout skeleton of ing. * Why is returned graph connected? */ static Agraph_t *remove_pair_edges(Agraph_t * ing) { int counter = 0; int nodeCount; Agraph_t *outg; Agraph_t *g; deglist_t *dl; Agnode_t *currnode, *adjNode; Agedge_t *e; outg = clone_graph(ing, &g); nodeCount = agnnodes(g); dl = getList(g); while (counter < (nodeCount - 3)) { currnode = firstDeglist(dl); /* Remove all adjacent nodes since they have to be reinserted */ for (e = agfstedge(g, currnode); e; e = agnxtedge(g, e, currnode)) { adjNode = e->head; if (currnode == adjNode) adjNode = e->tail; removeDeglist(dl, adjNode); } find_pair_edges(g, currnode, outg); for (e = agfstedge(g, currnode); e; e = agnxtedge(g, e, currnode)) { adjNode = e->head; if (currnode == adjNode) adjNode = e->tail; DEGREE(adjNode)--; insertDeglist(dl, adjNode); } agdelete(g, currnode); counter++; } agclose(g); freeDeglist(dl); return outg; }
/* undoClusterEdges: * Replace cluster nodes with originals. Make sure original has * no attributes. Replace original edges. Delete cluster nodes, * which will also delete cluster edges. */ void undoClusterEdges(graph_t * g) { node_t *n; edge_t *e; graph_t *clg; clg = agsubg(g, "__clusternodes",1); agbindrec(clg, "Agraphinfo_t", sizeof(Agraphinfo_t), TRUE); for (n = agfstnode(g); n; n = agnxtnode(g, n)) { for (e = agfstout(g, n); e; e = agnxtout(g, e)) { undoCompound(e, clg); } } for (n = agfstnode(clg); n; n = agnxtnode(clg, n)) { agdelete(g, n); } agclose(clg); }
void rm(Agraph_t *g) { Agedge_t *e; if (g->meta_node) { for (e = agfstout(g->meta_node->graph, g->meta_node); e; e = agnxtout(g->meta_node->graph, e)) { rm(agusergraph(e->head)); } if (g == g->root) { agclose(g); } else { agdelete(g->meta_node->graph, g->meta_node); } } else { fprintf(stderr, "subgraph has no meta_node\n"); } }