passagemath-graphs 10.6.1rc1__cp310-cp310-musllinux_1_2_aarch64.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- passagemath_graphs-10.6.1rc1.dist-info/METADATA +292 -0
- passagemath_graphs-10.6.1rc1.dist-info/RECORD +260 -0
- passagemath_graphs-10.6.1rc1.dist-info/WHEEL +5 -0
- passagemath_graphs-10.6.1rc1.dist-info/top_level.txt +2 -0
- passagemath_graphs.libs/libgcc_s-69c45f16.so.1 +0 -0
- passagemath_graphs.libs/libgmp-8e78bd9b.so.10.5.0 +0 -0
- passagemath_graphs.libs/libstdc++-1f1a71be.so.6.0.33 +0 -0
- sage/all__sagemath_graphs.py +39 -0
- sage/combinat/abstract_tree.py +2723 -0
- sage/combinat/all__sagemath_graphs.py +34 -0
- sage/combinat/binary_tree.py +5306 -0
- sage/combinat/cluster_algebra_quiver/all.py +22 -0
- sage/combinat/cluster_algebra_quiver/cluster_seed.py +5208 -0
- sage/combinat/cluster_algebra_quiver/interact.py +124 -0
- sage/combinat/cluster_algebra_quiver/mutation_class.py +625 -0
- sage/combinat/cluster_algebra_quiver/mutation_type.py +1555 -0
- sage/combinat/cluster_algebra_quiver/quiver.py +2290 -0
- sage/combinat/cluster_algebra_quiver/quiver_mutation_type.py +2468 -0
- sage/combinat/designs/MOLS_handbook_data.py +570 -0
- sage/combinat/designs/all.py +58 -0
- sage/combinat/designs/bibd.py +1655 -0
- sage/combinat/designs/block_design.py +1071 -0
- sage/combinat/designs/covering_array.py +269 -0
- sage/combinat/designs/covering_design.py +530 -0
- sage/combinat/designs/database.py +5615 -0
- sage/combinat/designs/design_catalog.py +122 -0
- sage/combinat/designs/designs_pyx.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/combinat/designs/designs_pyx.pxd +21 -0
- sage/combinat/designs/designs_pyx.pyx +993 -0
- sage/combinat/designs/difference_family.py +3951 -0
- sage/combinat/designs/difference_matrices.py +279 -0
- sage/combinat/designs/evenly_distributed_sets.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/combinat/designs/evenly_distributed_sets.pyx +661 -0
- sage/combinat/designs/ext_rep.py +1064 -0
- sage/combinat/designs/gen_quadrangles_with_spread.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/combinat/designs/gen_quadrangles_with_spread.pyx +339 -0
- sage/combinat/designs/group_divisible_designs.py +361 -0
- sage/combinat/designs/incidence_structures.py +2357 -0
- sage/combinat/designs/latin_squares.py +581 -0
- sage/combinat/designs/orthogonal_arrays.py +2244 -0
- sage/combinat/designs/orthogonal_arrays_build_recursive.py +1780 -0
- sage/combinat/designs/orthogonal_arrays_find_recursive.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/combinat/designs/orthogonal_arrays_find_recursive.pyx +967 -0
- sage/combinat/designs/resolvable_bibd.py +815 -0
- sage/combinat/designs/steiner_quadruple_systems.py +1306 -0
- sage/combinat/designs/subhypergraph_search.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/combinat/designs/subhypergraph_search.pyx +530 -0
- sage/combinat/designs/twographs.py +306 -0
- sage/combinat/finite_state_machine.py +14874 -0
- sage/combinat/finite_state_machine_generators.py +2006 -0
- sage/combinat/graph_path.py +448 -0
- sage/combinat/interval_posets.py +3908 -0
- sage/combinat/nu_tamari_lattice.py +269 -0
- sage/combinat/ordered_tree.py +1446 -0
- sage/combinat/posets/all.py +46 -0
- sage/combinat/posets/bubble_shuffle.py +247 -0
- sage/combinat/posets/cartesian_product.py +493 -0
- sage/combinat/posets/d_complete.py +182 -0
- sage/combinat/posets/elements.py +273 -0
- sage/combinat/posets/forest.py +30 -0
- sage/combinat/posets/hasse_cython.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/combinat/posets/hasse_cython.pyx +174 -0
- sage/combinat/posets/hasse_diagram.py +3672 -0
- sage/combinat/posets/hochschild_lattice.py +158 -0
- sage/combinat/posets/incidence_algebras.py +794 -0
- sage/combinat/posets/lattices.py +5117 -0
- sage/combinat/posets/linear_extension_iterator.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/combinat/posets/linear_extension_iterator.pyx +292 -0
- sage/combinat/posets/linear_extensions.py +1037 -0
- sage/combinat/posets/mobile.py +275 -0
- sage/combinat/posets/moebius_algebra.py +776 -0
- sage/combinat/posets/poset_examples.py +2178 -0
- sage/combinat/posets/posets.py +9360 -0
- sage/combinat/rooted_tree.py +1070 -0
- sage/combinat/shard_order.py +239 -0
- sage/combinat/tamari_lattices.py +384 -0
- sage/combinat/yang_baxter_graph.py +923 -0
- sage/databases/all__sagemath_graphs.py +1 -0
- sage/databases/knotinfo_db.py +1231 -0
- sage/ext_data/all__sagemath_graphs.py +1 -0
- sage/ext_data/graphs/graph_plot_js.html +330 -0
- sage/ext_data/kenzo/CP2.txt +45 -0
- sage/ext_data/kenzo/CP3.txt +349 -0
- sage/ext_data/kenzo/CP4.txt +4774 -0
- sage/ext_data/kenzo/README.txt +49 -0
- sage/ext_data/kenzo/S4.txt +20 -0
- sage/graphs/all.py +42 -0
- sage/graphs/asteroidal_triples.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/asteroidal_triples.pyx +320 -0
- sage/graphs/base/all.py +1 -0
- sage/graphs/base/boost_graph.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/base/boost_graph.pxd +106 -0
- sage/graphs/base/boost_graph.pyx +3045 -0
- sage/graphs/base/c_graph.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/base/c_graph.pxd +106 -0
- sage/graphs/base/c_graph.pyx +5096 -0
- sage/graphs/base/dense_graph.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/base/dense_graph.pxd +28 -0
- sage/graphs/base/dense_graph.pyx +801 -0
- sage/graphs/base/graph_backends.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/base/graph_backends.pxd +5 -0
- sage/graphs/base/graph_backends.pyx +797 -0
- sage/graphs/base/overview.py +85 -0
- sage/graphs/base/sparse_graph.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/base/sparse_graph.pxd +90 -0
- sage/graphs/base/sparse_graph.pyx +1653 -0
- sage/graphs/base/static_dense_graph.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/base/static_dense_graph.pxd +5 -0
- sage/graphs/base/static_dense_graph.pyx +1032 -0
- sage/graphs/base/static_sparse_backend.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/base/static_sparse_backend.pxd +27 -0
- sage/graphs/base/static_sparse_backend.pyx +1583 -0
- sage/graphs/base/static_sparse_graph.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/base/static_sparse_graph.pxd +37 -0
- sage/graphs/base/static_sparse_graph.pyx +1375 -0
- sage/graphs/bipartite_graph.py +2732 -0
- sage/graphs/centrality.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/centrality.pyx +1038 -0
- sage/graphs/cographs.py +519 -0
- sage/graphs/comparability.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/comparability.pyx +851 -0
- sage/graphs/connectivity.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/connectivity.pxd +157 -0
- sage/graphs/connectivity.pyx +4813 -0
- sage/graphs/convexity_properties.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/convexity_properties.pxd +16 -0
- sage/graphs/convexity_properties.pyx +870 -0
- sage/graphs/digraph.py +4754 -0
- sage/graphs/digraph_generators.py +1993 -0
- sage/graphs/distances_all_pairs.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/distances_all_pairs.pxd +12 -0
- sage/graphs/distances_all_pairs.pyx +2938 -0
- sage/graphs/domination.py +1363 -0
- sage/graphs/dot2tex_utils.py +100 -0
- sage/graphs/edge_connectivity.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/edge_connectivity.pyx +1215 -0
- sage/graphs/generators/all.py +1 -0
- sage/graphs/generators/basic.py +1769 -0
- sage/graphs/generators/chessboard.py +538 -0
- sage/graphs/generators/classical_geometries.py +1611 -0
- sage/graphs/generators/degree_sequence.py +235 -0
- sage/graphs/generators/distance_regular.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/generators/distance_regular.pyx +2846 -0
- sage/graphs/generators/families.py +4759 -0
- sage/graphs/generators/intersection.py +565 -0
- sage/graphs/generators/platonic_solids.py +262 -0
- sage/graphs/generators/random.py +2623 -0
- sage/graphs/generators/smallgraphs.py +5741 -0
- sage/graphs/generators/world_map.py +724 -0
- sage/graphs/generic_graph.py +26867 -0
- sage/graphs/generic_graph_pyx.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/generic_graph_pyx.pxd +34 -0
- sage/graphs/generic_graph_pyx.pyx +1673 -0
- sage/graphs/genus.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/genus.pyx +622 -0
- sage/graphs/graph.py +9645 -0
- sage/graphs/graph_coloring.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/graph_coloring.pyx +2284 -0
- sage/graphs/graph_database.py +1177 -0
- sage/graphs/graph_decompositions/all.py +1 -0
- sage/graphs/graph_decompositions/bandwidth.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/graph_decompositions/bandwidth.pyx +428 -0
- sage/graphs/graph_decompositions/clique_separators.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/graph_decompositions/clique_separators.pyx +616 -0
- sage/graphs/graph_decompositions/cutwidth.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/graph_decompositions/cutwidth.pyx +753 -0
- sage/graphs/graph_decompositions/fast_digraph.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/graph_decompositions/fast_digraph.pxd +13 -0
- sage/graphs/graph_decompositions/fast_digraph.pyx +212 -0
- sage/graphs/graph_decompositions/graph_products.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/graph_decompositions/graph_products.pyx +508 -0
- sage/graphs/graph_decompositions/modular_decomposition.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/graph_decompositions/modular_decomposition.pxd +27 -0
- sage/graphs/graph_decompositions/modular_decomposition.pyx +1536 -0
- sage/graphs/graph_decompositions/slice_decomposition.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/graph_decompositions/slice_decomposition.pxd +18 -0
- sage/graphs/graph_decompositions/slice_decomposition.pyx +1106 -0
- sage/graphs/graph_decompositions/tree_decomposition.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/graph_decompositions/tree_decomposition.pxd +17 -0
- sage/graphs/graph_decompositions/tree_decomposition.pyx +1996 -0
- sage/graphs/graph_decompositions/vertex_separation.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/graph_decompositions/vertex_separation.pxd +5 -0
- sage/graphs/graph_decompositions/vertex_separation.pyx +1963 -0
- sage/graphs/graph_editor.py +82 -0
- sage/graphs/graph_generators.py +3314 -0
- sage/graphs/graph_generators_pyx.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/graph_generators_pyx.pyx +95 -0
- sage/graphs/graph_input.py +812 -0
- sage/graphs/graph_latex.py +2064 -0
- sage/graphs/graph_list.py +410 -0
- sage/graphs/graph_plot.py +1756 -0
- sage/graphs/graph_plot_js.py +338 -0
- sage/graphs/hyperbolicity.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/hyperbolicity.pyx +1704 -0
- sage/graphs/hypergraph_generators.py +364 -0
- sage/graphs/independent_sets.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/independent_sets.pxd +13 -0
- sage/graphs/independent_sets.pyx +402 -0
- sage/graphs/isgci.py +1033 -0
- sage/graphs/isoperimetric_inequalities.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/isoperimetric_inequalities.pyx +489 -0
- sage/graphs/line_graph.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/line_graph.pyx +743 -0
- sage/graphs/lovasz_theta.py +77 -0
- sage/graphs/matching.py +1633 -0
- sage/graphs/matching_covered_graph.py +3590 -0
- sage/graphs/orientations.py +1489 -0
- sage/graphs/partial_cube.py +459 -0
- sage/graphs/path_enumeration.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/path_enumeration.pyx +2040 -0
- sage/graphs/pq_trees.py +1129 -0
- sage/graphs/print_graphs.py +201 -0
- sage/graphs/schnyder.py +865 -0
- sage/graphs/spanning_tree.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/spanning_tree.pyx +1457 -0
- sage/graphs/strongly_regular_db.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/strongly_regular_db.pyx +3340 -0
- sage/graphs/traversals.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/traversals.pxd +9 -0
- sage/graphs/traversals.pyx +1872 -0
- sage/graphs/trees.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/trees.pxd +15 -0
- sage/graphs/trees.pyx +310 -0
- sage/graphs/tutte_polynomial.py +713 -0
- sage/graphs/views.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/views.pyx +794 -0
- sage/graphs/weakly_chordal.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/graphs/weakly_chordal.pyx +604 -0
- sage/groups/all__sagemath_graphs.py +1 -0
- sage/groups/perm_gps/all__sagemath_graphs.py +1 -0
- sage/groups/perm_gps/partn_ref/all__sagemath_graphs.py +1 -0
- sage/groups/perm_gps/partn_ref/refinement_graphs.cpython-310-aarch64-linux-gnu.so +0 -0
- sage/groups/perm_gps/partn_ref/refinement_graphs.pxd +38 -0
- sage/groups/perm_gps/partn_ref/refinement_graphs.pyx +1666 -0
- sage/knots/all.py +6 -0
- sage/knots/free_knotinfo_monoid.py +507 -0
- sage/knots/gauss_code.py +291 -0
- sage/knots/knot.py +682 -0
- sage/knots/knot_table.py +284 -0
- sage/knots/knotinfo.py +2900 -0
- sage/knots/link.py +4715 -0
- sage/sandpiles/all.py +13 -0
- sage/sandpiles/examples.py +225 -0
- sage/sandpiles/sandpile.py +6365 -0
- sage/topology/all.py +22 -0
- sage/topology/cell_complex.py +1214 -0
- sage/topology/cubical_complex.py +1976 -0
- sage/topology/delta_complex.py +1806 -0
- sage/topology/filtered_simplicial_complex.py +744 -0
- sage/topology/moment_angle_complex.py +823 -0
- sage/topology/simplicial_complex.py +5160 -0
- sage/topology/simplicial_complex_catalog.py +92 -0
- sage/topology/simplicial_complex_examples.py +1680 -0
- sage/topology/simplicial_complex_homset.py +205 -0
- sage/topology/simplicial_complex_morphism.py +836 -0
- sage/topology/simplicial_set.py +4102 -0
- sage/topology/simplicial_set_catalog.py +55 -0
- sage/topology/simplicial_set_constructions.py +2954 -0
- sage/topology/simplicial_set_examples.py +865 -0
- sage/topology/simplicial_set_morphism.py +1464 -0
@@ -0,0 +1,338 @@
|
|
1
|
+
# sage_setup: distribution = sagemath-graphs
|
2
|
+
# sage.doctest: needs sage.plot
|
3
|
+
r"""
|
4
|
+
Graph plotting in Javascript with d3.js
|
5
|
+
|
6
|
+
This module implements everything that can be used to draw graphs with `d3.js
|
7
|
+
<https://d3js.org/>`_ in Sage.
|
8
|
+
|
9
|
+
On Python's side, this is mainly done by wrapping a graph's edges and vertices
|
10
|
+
in a structure that can then be used in the javascript code. This javascript
|
11
|
+
code is then inserted into a .html file to be opened by a browser.
|
12
|
+
|
13
|
+
In the browser, the displayed page contains at the bottom right a menu
|
14
|
+
that allows to save the picture under the svg file format.
|
15
|
+
|
16
|
+
What Sage feeds javascript with is a "graph" object with the following content:
|
17
|
+
|
18
|
+
- ``vertices`` -- each vertex is a dictionary defining :
|
19
|
+
|
20
|
+
- ``name`` -- the vertex's label
|
21
|
+
|
22
|
+
- ``group`` -- the vertex' color (integer)
|
23
|
+
|
24
|
+
The ID of a vertex is its index in the vertex list.
|
25
|
+
|
26
|
+
- ``edges`` -- each edge is a dictionary defining :
|
27
|
+
|
28
|
+
- ``source`` -- the ID (int) of the edge's source
|
29
|
+
|
30
|
+
- ``target`` -- the ID (int) of the edge's destination
|
31
|
+
|
32
|
+
- ``color`` -- the edge's color (integer)
|
33
|
+
|
34
|
+
- ``value`` -- thickness of the edge
|
35
|
+
|
36
|
+
- ``strength`` -- the edge's strength in the automatic layout
|
37
|
+
|
38
|
+
- ``color`` -- color (hexadecimal code)
|
39
|
+
|
40
|
+
- ``curve`` -- distance from the barycenter of the two endpoints and the
|
41
|
+
center of the edge. It defines the curve of the edge, which can be useful
|
42
|
+
for multigraphs.
|
43
|
+
|
44
|
+
- ``pos`` -- list whose `i` th element is a dictionary defining the position
|
45
|
+
of the `i` th vertex
|
46
|
+
|
47
|
+
It also contains the definition of some numerical/boolean variables whose
|
48
|
+
definition can be found in the documentation of
|
49
|
+
:meth:`~sage.graphs.generic_graph.GenericGraph.show` : ``directed``, ``charge``,
|
50
|
+
``link_distance``, ``link_strength``, ``gravity``, ``vertex_size``,
|
51
|
+
``edge_thickness``.
|
52
|
+
|
53
|
+
.. WARNING::
|
54
|
+
|
55
|
+
Since the d3js package is not standard yet, the javascript is fetched from
|
56
|
+
d3js.org website by the browser. If you want to avoid that (e.g. to protect
|
57
|
+
your privacy or by lack of internet connection), you can install the d3js
|
58
|
+
package for offline use by running ``sage -i d3js`` from the command line.
|
59
|
+
|
60
|
+
.. TODO::
|
61
|
+
|
62
|
+
- Add tooltip like in `<http://bl.ocks.org/bentwonk/2514276>`_.
|
63
|
+
|
64
|
+
- Add a zoom through scrolling (`<http://bl.ocks.org/mbostock/3681006>`_).
|
65
|
+
|
66
|
+
Authors:
|
67
|
+
|
68
|
+
- Nathann Cohen, Brice Onfroy -- July 2013 --
|
69
|
+
Initial version of the Sage code,
|
70
|
+
Javascript code, using examples from `d3.js <https://d3js.org/>`_.
|
71
|
+
|
72
|
+
- Thierry Monteil (June 2014): allow offline use of d3.js provided by d3js spkg.
|
73
|
+
|
74
|
+
Functions
|
75
|
+
---------
|
76
|
+
"""
|
77
|
+
from pathlib import Path
|
78
|
+
from sage.misc.temporary_file import tmp_filename
|
79
|
+
from sage.misc.lazy_import import lazy_import
|
80
|
+
lazy_import("sage.plot.colors", "rainbow")
|
81
|
+
|
82
|
+
# ****************************************************************************
|
83
|
+
# Copyright (C) 2013 Nathann Cohen <nathann.cohen@gmail.com>
|
84
|
+
# Brice Onfroy <onfroy.brice@gmail.com>
|
85
|
+
#
|
86
|
+
# Distributed under the terms of the GNU General Public License (GPL)
|
87
|
+
# as published by the Free Software Foundation; either version 2 of
|
88
|
+
# the License, or (at your option) any later version.
|
89
|
+
# https://www.gnu.org/licenses/
|
90
|
+
# ****************************************************************************
|
91
|
+
|
92
|
+
|
93
|
+
def gen_html_code(G,
|
94
|
+
vertex_labels=True,
|
95
|
+
edge_labels=False,
|
96
|
+
vertex_partition=[],
|
97
|
+
vertex_colors=None,
|
98
|
+
edge_partition=[],
|
99
|
+
force_spring_layout=False,
|
100
|
+
charge=-120,
|
101
|
+
link_distance=30,
|
102
|
+
link_strength=2,
|
103
|
+
gravity=.04,
|
104
|
+
vertex_size=7,
|
105
|
+
edge_thickness=4):
|
106
|
+
r"""
|
107
|
+
Create a .html file showing the graph using `d3.js <https://d3js.org/>`_.
|
108
|
+
|
109
|
+
This function returns the name of the .html file. If you want to visualize
|
110
|
+
the actual graph use :meth:`~sage.graphs.generic_graph.GenericGraph.show`.
|
111
|
+
|
112
|
+
INPUT:
|
113
|
+
|
114
|
+
- ``G`` -- the graph
|
115
|
+
|
116
|
+
- ``vertex_labels`` -- boolean (default: ``False``); whether to display
|
117
|
+
vertex labels
|
118
|
+
|
119
|
+
- ``edge_labels`` -- boolean (default: ``False``); whether to display edge
|
120
|
+
labels
|
121
|
+
|
122
|
+
- ``vertex_partition`` -- list (default: ``[]``); a list of lists
|
123
|
+
representing a partition of the vertex set. Vertices are then colored in
|
124
|
+
the graph according to the partition.
|
125
|
+
|
126
|
+
- ``vertex_colors`` -- dictionary (default: ``None``); a dictionary
|
127
|
+
representing a partition of the vertex set. Keys are colors (ignored) and
|
128
|
+
values are lists of vertices. Vertices are then colored in the graph
|
129
|
+
according to the partition.
|
130
|
+
|
131
|
+
- ``edge_partition`` -- list (default: ``[]``); same as
|
132
|
+
``vertex_partition``, with edges instead
|
133
|
+
|
134
|
+
- ``force_spring_layout`` -- boolean (default: ``False``); whether to take
|
135
|
+
previously computed position of nodes into account if there is one, or to
|
136
|
+
compute a spring layout
|
137
|
+
|
138
|
+
- ``vertex_size`` -- integer (default: 7); the size of a vertex' circle
|
139
|
+
|
140
|
+
- ``edge_thickness`` -- integer (default: 4); thickness of an edge
|
141
|
+
|
142
|
+
- ``charge`` -- integer (default: -120); the vertices' charge. Defines
|
143
|
+
how they repulse each other. See
|
144
|
+
`<https://github.com/mbostock/d3/wiki/Force-Layout>`_ for more
|
145
|
+
information
|
146
|
+
|
147
|
+
- ``link_distance`` -- integer (default: 30); see
|
148
|
+
`<https://github.com/mbostock/d3/wiki/Force-Layout>`_ for more
|
149
|
+
information
|
150
|
+
|
151
|
+
- ``link_strength`` -- integer (default: 2); see
|
152
|
+
`<https://github.com/mbostock/d3/wiki/Force-Layout>`_ for more
|
153
|
+
information
|
154
|
+
|
155
|
+
- ``gravity`` -- float (default: 0.04); see
|
156
|
+
`<https://github.com/mbostock/d3/wiki/Force-Layout>`_ for more
|
157
|
+
information
|
158
|
+
|
159
|
+
.. WARNING::
|
160
|
+
|
161
|
+
Since the d3js package is not standard yet, the javascript is fetched
|
162
|
+
from d3js.org website by the browser. If you want to avoid that (e.g.
|
163
|
+
to protect your privacy or by lack of internet connection), you can
|
164
|
+
install the d3js package for offline use by running ``sage -i d3js``
|
165
|
+
from the command line.
|
166
|
+
|
167
|
+
EXAMPLES::
|
168
|
+
|
169
|
+
sage: graphs.RandomTree(50).show(method='js') # optional - internet
|
170
|
+
|
171
|
+
sage: g = graphs.PetersenGraph()
|
172
|
+
sage: g.show(method='js', vertex_partition=g.coloring()) # optional - internet
|
173
|
+
|
174
|
+
sage: graphs.DodecahedralGraph().show(method='js', # optional - internet
|
175
|
+
....: force_spring_layout=True)
|
176
|
+
|
177
|
+
sage: graphs.DodecahedralGraph().show(method='js') # optional - internet
|
178
|
+
|
179
|
+
sage: # needs sage.combinat
|
180
|
+
sage: g = digraphs.DeBruijn(2, 2)
|
181
|
+
sage: g.allow_multiple_edges(True)
|
182
|
+
sage: g.add_edge("10", "10", "a")
|
183
|
+
sage: g.add_edge("10", "10", "b")
|
184
|
+
sage: g.add_edge("10", "10", "c")
|
185
|
+
sage: g.add_edge("10", "10", "d")
|
186
|
+
sage: g.add_edge("01", "11", "1")
|
187
|
+
sage: g.show(method='js', vertex_labels=True, edge_labels=True, # optional - internet
|
188
|
+
....: link_distance=200, gravity=.05, charge=-500,
|
189
|
+
....: edge_partition=[[("11", "12", "2"), ("21", "21", "a")]],
|
190
|
+
....: edge_thickness=4)
|
191
|
+
|
192
|
+
TESTS::
|
193
|
+
|
194
|
+
sage: from sage.graphs.graph_plot_js import gen_html_code
|
195
|
+
sage: filename = gen_html_code(graphs.PetersenGraph())
|
196
|
+
|
197
|
+
:issue:`17370`::
|
198
|
+
|
199
|
+
sage: filename = gen_html_code(graphs.CompleteBipartiteGraph(4, 5))
|
200
|
+
|
201
|
+
In the generated html code, the source (resp. target) of a link is the index
|
202
|
+
of the node in the list defining the names of the nodes. We check that the
|
203
|
+
order is correct (:issue:`27460`)::
|
204
|
+
|
205
|
+
sage: filename = gen_html_code(DiGraph({1: [10]}))
|
206
|
+
sage: with open(filename, 'r') as f:
|
207
|
+
....: data = f.read()
|
208
|
+
sage: nodes = data.partition('"nodes":')[2]; nodes
|
209
|
+
...[{..."name": "10"...}, {..."name": "1"...}]...
|
210
|
+
sage: links = data.partition('"links":')[2]
|
211
|
+
sage: '"source": 1' in links and '"target": 0' in links
|
212
|
+
True
|
213
|
+
"""
|
214
|
+
directed = G.is_directed()
|
215
|
+
multiple_edges = G.has_multiple_edges()
|
216
|
+
|
217
|
+
# Associated an integer to each vertex
|
218
|
+
v_to_id = {v: i for i, v in enumerate(G)}
|
219
|
+
|
220
|
+
# Vertex colors
|
221
|
+
if vertex_colors is not None:
|
222
|
+
vertex_partition = list(vertex_colors.values())
|
223
|
+
len_vertex_partition = len(vertex_partition)
|
224
|
+
color = {i: len_vertex_partition for i in range(G.order())}
|
225
|
+
for i, l in enumerate(vertex_partition):
|
226
|
+
for v in l:
|
227
|
+
color[v_to_id[v]] = i
|
228
|
+
|
229
|
+
# Vertex list
|
230
|
+
# Data for vertex v must be at position v_to_id[v] in list nodes
|
231
|
+
nodes = [{"name": str(v), "group": str(color[v_to_id[v]])} for v in G]
|
232
|
+
|
233
|
+
# Edge colors.
|
234
|
+
edge_color_default = "#aaa"
|
235
|
+
color_list = rainbow(len(edge_partition))
|
236
|
+
edge_color = {}
|
237
|
+
for i, l in enumerate(edge_partition):
|
238
|
+
for e in l:
|
239
|
+
u, v, label = e if len(e) == 3 else e+(None,)
|
240
|
+
edge_color[u, v, label] = color_list[i]
|
241
|
+
if not directed:
|
242
|
+
edge_color[v, u, label] = color_list[i]
|
243
|
+
|
244
|
+
# Edge list
|
245
|
+
edges = []
|
246
|
+
seen = {} # How many times has this edge been seen ?
|
247
|
+
|
248
|
+
for u, v, l in G.edge_iterator():
|
249
|
+
|
250
|
+
# Edge color
|
251
|
+
color = edge_color.get((u, v, l), edge_color_default)
|
252
|
+
|
253
|
+
# Computes the curve of the edge
|
254
|
+
curve = 0
|
255
|
+
|
256
|
+
# Loop ?
|
257
|
+
if u == v:
|
258
|
+
seen[u, v] = seen.get((u, v), 0) + 1
|
259
|
+
curve = seen[u, v] * 10 + 10
|
260
|
+
|
261
|
+
# For directed graphs, one also has to take into accounts
|
262
|
+
# edges in the opposite direction
|
263
|
+
elif directed:
|
264
|
+
if G.has_edge(v, u):
|
265
|
+
seen[u, v] = seen.get((u, v), 0) + 1
|
266
|
+
curve = seen[u, v] * 15
|
267
|
+
else:
|
268
|
+
if multiple_edges and len(G.edge_label(u, v)) != 1:
|
269
|
+
# Multiple edges. The first one has curve 15, then
|
270
|
+
# -15, then 30, then -30, ...
|
271
|
+
seen[u, v] = seen.get((u, v), 0) + 1
|
272
|
+
curve = (1 if seen[u, v] % 2 else -1) * (seen[u, v] // 2) * 15
|
273
|
+
|
274
|
+
elif not directed and multiple_edges:
|
275
|
+
# Same formula as above for multiple edges
|
276
|
+
if len(G.edge_label(u, v)) != 1:
|
277
|
+
seen[u, v] = seen.get((u, v), 0) + 1
|
278
|
+
curve = (1 if seen[u, v] % 2 else -1) * (seen[u, v] // 2) * 15
|
279
|
+
|
280
|
+
# Adding the edge to the list
|
281
|
+
# The source (resp. target) is the index of u (resp. v) in list nodes
|
282
|
+
edges.append({"source": v_to_id[u],
|
283
|
+
"target": v_to_id[v],
|
284
|
+
"strength": 0,
|
285
|
+
"color": color,
|
286
|
+
"curve": curve,
|
287
|
+
"name": str(l) if edge_labels else ""})
|
288
|
+
|
289
|
+
loops = [e for e in edges if e["source"] == e["target"]]
|
290
|
+
edges = [e for e in edges if e["source"] != e["target"]]
|
291
|
+
|
292
|
+
# Defines the vertices' layout if possible
|
293
|
+
Gpos = G.get_pos()
|
294
|
+
pos = []
|
295
|
+
if Gpos is not None and force_spring_layout is False:
|
296
|
+
charge = 0
|
297
|
+
link_strength = 0
|
298
|
+
gravity = 0
|
299
|
+
|
300
|
+
for v in G:
|
301
|
+
x, y = Gpos[v]
|
302
|
+
pos.append([float(x), float(-y)])
|
303
|
+
|
304
|
+
# Encodes the data as a JSON string
|
305
|
+
from json import JSONEncoder
|
306
|
+
string = JSONEncoder().encode({"nodes": nodes,
|
307
|
+
"links": edges,
|
308
|
+
"loops": loops,
|
309
|
+
"pos": pos,
|
310
|
+
"directed": G.is_directed(),
|
311
|
+
"charge": int(charge),
|
312
|
+
"link_distance": int(link_distance),
|
313
|
+
"link_strength": int(link_strength),
|
314
|
+
"gravity": float(gravity),
|
315
|
+
"vertex_labels": bool(vertex_labels),
|
316
|
+
"edge_labels": bool(edge_labels),
|
317
|
+
"vertex_size": int(vertex_size),
|
318
|
+
"edge_thickness": int(edge_thickness)})
|
319
|
+
|
320
|
+
from sage.env import SAGE_EXTCODE, SAGE_SHARE
|
321
|
+
with open(Path(SAGE_EXTCODE) / "graphs" / "graph_plot_js.html") as f:
|
322
|
+
js_code = f.read().replace("// GRAPH_DATA_HEREEEEEEEEEEE", string)
|
323
|
+
|
324
|
+
# Add d3.js script depending on whether d3js package is installed.
|
325
|
+
d3js_filepath = Path(SAGE_SHARE) / 'd3js' / 'd3.min.js'
|
326
|
+
if d3js_filepath.exists():
|
327
|
+
with open(d3js_filepath) as d3js_code_file:
|
328
|
+
d3js_script = '<script>' + d3js_code_file.read() + '</script>'
|
329
|
+
else:
|
330
|
+
d3js_script = '<script src="http://d3js.org/d3.v3.min.js"></script>'
|
331
|
+
js_code = js_code.replace('// D3JS_SCRIPT_HEREEEEEEEEEEE', d3js_script)
|
332
|
+
|
333
|
+
# Writes the temporary .html file
|
334
|
+
filename = tmp_filename(ext='.html')
|
335
|
+
with open(filename, 'w') as f:
|
336
|
+
f.write(js_code)
|
337
|
+
|
338
|
+
return filename
|
Binary file
|