From: Mark Hansen Date: Fri, 16 Sep 2022 11:01:32 +0000 (+1000) Subject: Remove addingLayout.txt, it's moved to docs repo X-Git-Tag: 6.0.2~36^2 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=32566043b41998b9c51b3275db940bb00c111617;p=graphviz Remove addingLayout.txt, it's moved to docs repo Converted to markdown for the website at https://gitlab.com/graphviz/graphviz.gitlab.io/-/merge_requests/543 No need to maintain two versions of this doc. --- diff --git a/doc/Makefile.am b/doc/Makefile.am index e159087db..7130292b3 100644 --- a/doc/Makefile.am +++ b/doc/Makefile.am @@ -9,6 +9,6 @@ dist_pdf_DATA += smyrna/smyrna.pdf endif dist_html_DATA = build.html FAQ.html index.html winbuild.html pspdf.png char.html gdtclft.entities.example.png todo.html internal_todo.html -dist_doc_DATA = Dot.ref latex_suggestions.txt addingLayout.txt +dist_doc_DATA = Dot.ref latex_suggestions.txt EXTRA_DIST = schema/*.xml schema/*.xslt infosrc/* diff --git a/doc/addingLayout.txt b/doc/addingLayout.txt deleted file mode 100644 index 5e147f00d..000000000 --- a/doc/addingLayout.txt +++ /dev/null @@ -1,297 +0,0 @@ -To create a new layout plugin called xxx, you first need -to provide two functions: xxx_layout and xxx_cleanup. The -semantics of these are described below. - -======================== - - void xxx_layout(Agraph_t * g) - - Initialize the graph. - - If the algorithm will use the common edge routing code, it should - call setEdgeType (g, ...); - - - For each node, call common_init_node and gv_nodesize. - - If the algorithm will use spline_edges() to route the edges, the - node coordinates need to be stored in ND_pos, so this should be - allocated here. This, and the two calls mentioned above, are all - handled by a call to neato_init_node(). - - - For each edge, call common_init_edge - - - The algorithm should allocate whatever other data structures it - needs. This can involve fields in the A*info_t fields. In addition, - each of these fields contains a void* alg; subfield that the algorithm - can use the store additional data. - Once we move to cgraph, this will all be replace with - algorithm specific records. - - Layout the graph. When finished, each node should have its coordinates - stored in points in ND_coord_i(n), each edge should have its layout - described in ED_spl(e). - (N.B. As of version 2.21, ND_coord_i has been replaced by ND_coord, - which are now floating point coordinates.) - - To add edges, there are 3 functions available: - - - spline_edges1 (Agraph_t*, int edgeType) - Assumes the node coordinates are stored in ND_coord_i, and that - GD_bb is set. For each edge, this function constructs the appropriate - data and stores it in ED_spl. - - spline_edges0 (Agraph_t*) - Assumes the node coordinates are stored in ND_pos, and that - GD_bb is set. This function uses the ratio attribute if set, - copies the values in ND_pos to ND_coord_i (converting from - inches to points); and calls spline_edges1 using the edge type - specified by setEdgeType(). - - spline_edges (Agraph_t*) - Assumes the node coordinates are stored in ND_pos. This - function calculates the bounding box of g and stores it in GD_bb, - then calls spline_edges0(). - - If the algorithm only works with connected components, the code can - use the pack library to get components, lay them out individually, and - pack them together based on user specifications. A typical schema is - given below. One can look at the code for twopi, circo, neato or fdp - for more detailed examples. - - Agraph_t **ccs; - Agraph_t *sg; - Agnode_t *c = NULL; - int ncc; - int i; - - ccs = ccomps(g, &ncc, 0); - if (ncc == 1) { - /* layout nodes of g */ - adjustNodes(g); /* if you need to remove overlaps */ - spline_edges(g); /* generic edge routing code */ - - } else { - pack_info pinfo; - pack_mode pmode = getPackMode(g, l_node); - - for (i = 0; i < ncc; i++) { - sg = ccs[i]; - /* layout sg */ - adjustNodes(sg); /* if you need to remove overlaps */ - } - spline_edges(g); /* generic edge routing */ - - /* initialize packing info, e.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); - - Be careful in laying of subgraphs if you rely on attributes that have - only been set in the root graph. With connected components, edges can - be added with each component, before packing (as above) or after the - components have been packed (see circo). - - It good to check for trivial cases where the graph has 0 or 1 nodes, - or no edges. - - At the end of xxx_layout, call - - dotneato_postprocess(g); - - The following template will work in most cases, ignoring the problems of - handling disconnected graphs and removing node overlaps: - - static void - xxx_init_node(node_t * n) - { - neato_init_node(n); - /* add algorithm-specific data, if desired */ - } - - static void - xxx_init_edge(edge_t * e) - { - common_init_edge(e); - /* add algorithm-specific data, if desired */ - } - - static void - xxx_init_node_edge(graph_t * g) - { - node_t *n; - edge_t *e; - - for (n = agfstnode(g); n; n = agnxtnode(g, n)) { - xxx_init_node(n); - } - for (n = agfstnode(g); n; n = agnxtnode(g, n)) { - for (e = agfstout(g, n); e; e = agnxtout(g, e)){ - xxx_init_edge(e); - } - } - } - - void - xxx_layout (Agraph_t* g) - { - xxx_init_node_edge(g); - /* Set ND_pos(n) for each node n */ - spline_edges(g); - dotneato_postprocess(g); - } - -====================== - - void xxx_cleanup(Agraph_t * g) - - Free up any resources allocated in the layout. - - Finish with calls to gv_cleanup_node and gv_cleanup_edge for - each node and edge. This cleans up splines labels, ND_pos, shapes - and 0's out the A*info_t, so these have to occur last, but could be - part of explicit xxx_cleanup_node and xxx_cleanup_edge, if desired. - At the end, you should do - - if (g != g->root) memset(&(g->u), 0, sizeof(Agraphinfo_t)); - - This is necessary for the graph to be laid out again, as the layout - code assumes this structure is clean. - - libgvc does a final cleanup to the root graph, freeing any drawing, - freeing its label, and zeroing out Agraphinfo_t of the root graph. - - The following template will work in most cases: - - static void xxx_cleanup_graph(Agraph_t * g) - { - /* Free any algorithm-specific data attached to the graph */ - if (g != g->root) memset(&(g->u), 0, sizeof(Agraphinfo_t)); - } - - static void xxx_cleanup_edge (Agedge_t* e) - { - /* Free any algorithm-specific data attached to the edge */ - gv_cleanup_edge(e); - } - - static void xxx_cleanup_node (Agnode_t* n) - { - /* Free any algorithm-specific data attached to the node */ - gv_cleanup_node(e); - } - - void xxx_cleanup(Agraph_t * g) - { - Agnode_t *n; - Agedge_t *e; - - for (n = agfstnode(g); n; n = agnxtnode(g, n)) { - for (e = agfstout(g, n); e; e = agnxtout(g, e)) { - xxx_cleanup_edge(e); - } - xxx_cleanup_node(n); - } - xxx_cleanup_graph(g); - } - -================== - -Most layouts use auxiliary routines similar to neato, so -the entry points can be added in plugin/neato_layout - -Add to gvlayout_neato_layout.c: - -gvlayout_engine_t xxxgen_engine = { - xxx_layout, - xxx_cleanup, -}; - -and the line - - {LAYOUT_XXX, "xxx", 0, &xxxgen_engine, &neatogen_features}, - -to gvlayout_neato_types and a new emum - - LAYOUT_XXX - -to layout_type in that file. - -The above allows the new layout to piggyback on top of the neato -plugin, but requires rebuilding the plugin. In general, a user -can (and probably should) build a layout plugin totally separately. - -To do this, after writing xxx_layout and xxx_cleanup, it is necessary to: - - - add the types and data structures - -typedef enum { LAYOUT_XXX } layout_type; - -static gvlayout_features_t xxxgen_features = { - 0 -}; -gvlayout_engine_t xxxgen_engine = { - xxx_layout, - xxx_cleanup, -}; -static gvplugin_installed_t gvlayout_xxx_types[] = { - {LAYOUT_XXX, "xxx", 0, &xxxgen_engine, &xxxgen_features}, - {0, NULL, 0, NULL, NULL} -}; -static gvplugin_api_t apis[] = { - {API_layout, &gvlayout_xxx_types}, - {(api_t)0, 0}, -}; -gvplugin_library_t gvplugin_xxx_layout_LTX_library = { "xxx_layout", apis }; - - - combine all of this into a dynamic library whose name contains the - string "gvplugin_" and install the library in the same directory as the - other Graphviz plugins. For example, on Linux systems, the dot layout - plugin is in the library libgvplugin_dot_layout.so. - - - run - dot -c - to regenerate the config file. - -NOTES: - - Additional layouts can be added as extra lines in gvlayout_xxx_types. - - Obviously, most of the names and strings can be arbitrary. One - constraint is that external identifier for the gvplugin_library_t - type must end in "_LTX_library". In addition, the string "xxx" in - each entry of gvlayout_xxx_types is the name used to identify the - layout algorithm, so needs to be distinct from any other layout name. - - The features of a layout algorithm are currently limited to a - flag of bits, and the only flag supported is LAYOUT_USES_RANKDIR, - which enables the layout to the rankdir attribute. - -Changes need to be made to any applications that -statically know about layout algorithms. - -================== - -Software configuration - automake - -If you want to integrate your code into the Graphviz software -and use its build system, follow the instructions below. -You can certainly build and install your plugin using your own -build software. - -0. Put your software in lib/xxxgen, and added the hooks describe above -into gvlayout_neato_layout.c -1. In lib/xxxgen, provide a Makefile.am (based on a simple example -like lib/fdpgen/Makefile.am) -3. In lib/Makefile.am, add xxxgen to SUBDIRS -2. In configure.ac, add lib/xxxgen/Makefile to AC_CONFIG_FILES. -4. In lib/plugin/neato_layout/Makefile.am, insert - $(top_builddir)/lib/xxxgen/libxxxgen_C.la - in libgvplugin_neato_layout_C_la_LIBADD -5. Remember to run autogen.sh because on its own configure can guess wrong. - -This also assumes you have a good version of the various automake tools -on your system. - - diff --git a/windows/graphviz-msi/setup/setup.vdproj b/windows/graphviz-msi/setup/setup.vdproj index aaf955fc3..d5b944a4e 100644 --- a/windows/graphviz-msi/setup/setup.vdproj +++ b/windows/graphviz-msi/setup/setup.vdproj @@ -9452,26 +9452,6 @@ "IsDependency" = "11:FALSE" "IsolateTo" = "8:" } - "{1FB2D0AE-D3B9-43D4-B9DD-F88EC61E35DE}:_64B73DB0B6B84BDCA4A3233B8EB2441D" - { - "SourcePath" = "8:..\\..\\release\\share\\graphviz\\doc\\addingLayout.txt" - "TargetName" = "8:addingLayout.txt" - "Tag" = "8:" - "Folder" = "8:_EA2EA6B45DEE4C35ACA33AA91E799532" - "Condition" = "8:" - "Transitive" = "11:FALSE" - "Vital" = "11:TRUE" - "ReadOnly" = "11:FALSE" - "Hidden" = "11:FALSE" - "System" = "11:FALSE" - "Permanent" = "11:FALSE" - "SharedLegacy" = "11:FALSE" - "PackageAs" = "3:1" - "Register" = "3:1" - "Exclude" = "11:FALSE" - "IsDependency" = "11:FALSE" - "IsolateTo" = "8:" - } "{1FB2D0AE-D3B9-43D4-B9DD-F88EC61E35DE}:_64D68BB5756241F3BFCC5C3D404F3D31" { "SourcePath" = "8:..\\..\\release\\share\\graphviz\\doc\\html\\info\\a_normal.gif" diff --git a/windows/graphviz-msi/setup/setup_stable.vdproj b/windows/graphviz-msi/setup/setup_stable.vdproj index 46c2ceb86..831f6629c 100755 --- a/windows/graphviz-msi/setup/setup_stable.vdproj +++ b/windows/graphviz-msi/setup/setup_stable.vdproj @@ -9342,26 +9342,6 @@ "IsDependency" = "11:FALSE" "IsolateTo" = "8:" } - "{1FB2D0AE-D3B9-43D4-B9DD-F88EC61E35DE}:_64B73DB0B6B84BDCA4A3233B8EB2441D" - { - "SourcePath" = "8:..\\..\\release\\share\\graphviz\\doc\\addingLayout.txt" - "TargetName" = "8:addingLayout.txt" - "Tag" = "8:" - "Folder" = "8:_EA2EA6B45DEE4C35ACA33AA91E799532" - "Condition" = "8:" - "Transitive" = "11:FALSE" - "Vital" = "11:TRUE" - "ReadOnly" = "11:FALSE" - "Hidden" = "11:FALSE" - "System" = "11:FALSE" - "Permanent" = "11:FALSE" - "SharedLegacy" = "11:FALSE" - "PackageAs" = "3:1" - "Register" = "3:1" - "Exclude" = "11:FALSE" - "IsDependency" = "11:FALSE" - "IsolateTo" = "8:" - } "{1FB2D0AE-D3B9-43D4-B9DD-F88EC61E35DE}:_64D68BB5756241F3BFCC5C3D404F3D31" { "SourcePath" = "8:..\\..\\release\\share\\graphviz\\doc\\html\\info\\a_normal.gif"