Example #1
0
    def plot3d(self, ztail=0, zhead=0, **kwds):
        """
        Takes 2D plot and places it in 3D.  

        EXAMPLES::

            sage: A = arrow((0,0),(1,1))[0].plot3d()
            sage: A.jmol_repr(A.testing_render_params())[0]
            'draw line_1 diameter 2 arrow {0.0 0.0 0.0}  {1.0 1.0 0.0} '

        Note that we had to index the arrow to get the Arrow graphics
        primitive.  We can also change the height via the plot3d method
        of Graphics, but only as a whole::

            sage: A = arrow((0,0),(1,1)).plot3d(3)
            sage: A.jmol_repr(A.testing_render_params())[0][0]
            'draw line_1 diameter 2 arrow {0.0 0.0 3.0}  {1.0 1.0 3.0} '

        Optional arguments place both the head and tail outside the 
        `xy`-plane, but at different heights.  This must be done on 
        the graphics primitive obtained by indexing::

            sage: A=arrow((0,0),(1,1))[0].plot3d(3,4)
            sage: A.jmol_repr(A.testing_render_params())[0]
            'draw line_1 diameter 2 arrow {0.0 0.0 3.0}  {1.0 1.0 4.0} '
        """
        from sage.plot.plot3d.shapes2 import line3d
        options = self._plot3d_options()
        options.update(kwds)
        return line3d([(self.xtail, self.ytail, ztail), (self.xhead, self.yhead, zhead)], arrow_head=True, **options)
    def plot3d(self, z=0, **kwds):
        """
        Returns a 3D plot (Jmol) of the Bezier path.  Since a ``BezierPath``
        primitive contains only `x,y` coordinates, the path will be drawn in
        some plane (default is `z=0`).  To create a Bezier path with nonzero
        (and nonidentical) `z` coordinates in the path and control points, use
        the function :func:`~sage.plot.plot3d.shapes2.bezier3d` instead of
        :func:`bezier_path`.

        EXAMPLES::

            sage: b = bezier_path([[(0,0),(0,1),(1,0)]])
            sage: A = b.plot3d()
            sage: B = b.plot3d(z=2)
            sage: A+B

        ::

            sage: bezier3d([[(0,0,0),(1,0,0),(0,1,0),(0,1,1)]])
        """
        from sage.plot.plot3d.shapes2 import bezier3d
        options = self._plot3d_options()
        options.update(kwds)
        return bezier3d([[(x, y, 0) for x, y in self.path[i]]
                         for i in range(len(self.path))], **options)
Example #3
0
    def plot3d(self, ztail=0, zhead=0, **kwds):
        """
        Takes 2D plot and places it in 3D.

        EXAMPLES::

            sage: A = arrow((0,0),(1,1))[0].plot3d()
            sage: A.jmol_repr(A.testing_render_params())[0]
            'draw line_1 diameter 2 arrow {0.0 0.0 0.0}  {1.0 1.0 0.0} '

        Note that we had to index the arrow to get the Arrow graphics
        primitive.  We can also change the height via the :meth:`Graphics.plot3d`
        method, but only as a whole::

            sage: A = arrow((0,0),(1,1)).plot3d(3)
            sage: A.jmol_repr(A.testing_render_params())[0][0]
            'draw line_1 diameter 2 arrow {0.0 0.0 3.0}  {1.0 1.0 3.0} '

        Optional arguments place both the head and tail outside the
        `xy`-plane, but at different heights.  This must be done on
        the graphics primitive obtained by indexing::

            sage: A=arrow((0,0),(1,1))[0].plot3d(3,4)
            sage: A.jmol_repr(A.testing_render_params())[0]
            'draw line_1 diameter 2 arrow {0.0 0.0 3.0}  {1.0 1.0 4.0} '
        """
        from sage.plot.plot3d.shapes2 import line3d
        options = self._plot3d_options()
        options.update(kwds)
        return line3d([(self.xtail, self.ytail, ztail),
                       (self.xhead, self.yhead, zhead)],
                      arrow_head=True,
                      **options)
Example #4
0
    def plot3d(self, z=0, **kwds):
        """
        Plots a 2D polygon in 3D, with default height zero.

        INPUT:


        -  ``z`` - optional 3D height above `xy`-plane, or a list of
           heights corresponding to the list of 2D polygon points.

        EXAMPLES:

        A pentagon::

            sage: polygon([(cos(t), sin(t)) for t in srange(0, 2*pi, 2*pi/5)]).plot3d()
            Graphics3d Object

        Showing behavior of the optional parameter z::

            sage: P = polygon([(0,0), (1,2), (0,1), (-1,2)])
            sage: p = P[0]; p
            Polygon defined by 4 points
            sage: q = p.plot3d()
            sage: q.obj_repr(q.testing_render_params())[2]
            ['v 0 0 0', 'v 1 2 0', 'v 0 1 0', 'v -1 2 0']
            sage: r = p.plot3d(z=3)
            sage: r.obj_repr(r.testing_render_params())[2]
            ['v 0 0 3', 'v 1 2 3', 'v 0 1 3', 'v -1 2 3']
            sage: s = p.plot3d(z=[0,1,2,3])
            sage: s.obj_repr(s.testing_render_params())[2]
            ['v 0 0 0', 'v 1 2 1', 'v 0 1 2', 'v -1 2 3']

        TESTS:

        Heights passed as a list should have same length as
        number of points::

            sage: P = polygon([(0,0), (1,2), (0,1), (-1,2)])
            sage: p = P[0]
            sage: q = p.plot3d(z=[2,-2])
            Traceback (most recent call last):
            ...
            ValueError: Incorrect number of heights given
        """
        from sage.plot.plot3d.index_face_set import IndexFaceSet
        options = self._plot3d_options()
        options.update(kwds)
        zdata = []
        if isinstance(z, list):
            zdata = z
        else:
            zdata = [z] * len(self.xdata)
        if len(zdata) == len(self.xdata):
            return IndexFaceSet(
                [[(x, y, z)
                  for x, y, z in zip(self.xdata, self.ydata, zdata)]],
                **options)
        else:
            raise ValueError('Incorrect number of heights given')
Example #5
0
    def plot3d(self, z=0, **kwds):
        """
        Plots a 2D polygon in 3D, with default height zero.

        INPUT:


        -  ``z`` - optional 3D height above `xy`-plane, or a list of
           heights corresponding to the list of 2D polygon points.

        EXAMPLES:

        A pentagon::

            sage: polygon([(cos(t), sin(t)) for t in srange(0, 2*pi, 2*pi/5)]).plot3d()
            Graphics3d Object

        Showing behavior of the optional parameter z::

            sage: P = polygon([(0,0), (1,2), (0,1), (-1,2)])
            sage: p = P[0]; p
            Polygon defined by 4 points
            sage: q = p.plot3d()
            sage: q.obj_repr(q.testing_render_params())[2]
            ['v 0 0 0', 'v 1 2 0', 'v 0 1 0', 'v -1 2 0']
            sage: r = p.plot3d(z=3)
            sage: r.obj_repr(r.testing_render_params())[2]
            ['v 0 0 3', 'v 1 2 3', 'v 0 1 3', 'v -1 2 3']
            sage: s = p.plot3d(z=[0,1,2,3])
            sage: s.obj_repr(s.testing_render_params())[2]
            ['v 0 0 0', 'v 1 2 1', 'v 0 1 2', 'v -1 2 3']

        TESTS:

        Heights passed as a list should have same length as
        number of points::

            sage: P = polygon([(0,0), (1,2), (0,1), (-1,2)])
            sage: p = P[0]
            sage: q = p.plot3d(z=[2,-2])
            Traceback (most recent call last):
            ...
            ValueError: Incorrect number of heights given
        """
        from sage.plot.plot3d.index_face_set import IndexFaceSet
        options = self._plot3d_options()
        options.update(kwds)
        zdata=[]
        if isinstance(z, list):
            zdata=z
        else:
            zdata=[z]*len(self.xdata)
        if len(zdata)==len(self.xdata):
            return IndexFaceSet([[(x, y, z) for x, y, z in zip(self.xdata, self.ydata, zdata)]], **options)
        else:
            raise ValueError('Incorrect number of heights given')
Example #6
0
File: line.py Project: Etn40ff/sage
    def plot3d(self, z=0, **kwds):
        """
        Plots a 2D line in 3D, with default height zero.

        EXAMPLES::

            sage: E = EllipticCurve('37a').plot(thickness=5).plot3d()
            sage: F = EllipticCurve('37a').plot(thickness=5).plot3d(z=2)
            sage: E + F  # long time (5s on sage.math, 2012)
        """
        from sage.plot.plot3d.shapes2 import line3d
        options = self._plot3d_options()
        options.update(kwds)
        return line3d([(x, y, z) for x, y in zip(self.xdata, self.ydata)], **options)
Example #7
0
    def plot3d(self, z=0, **kwds):
        """
        Plots a 2D line in 3D, with default height zero.

        EXAMPLES::

            sage: E = EllipticCurve('37a').plot(thickness=5).plot3d()
            sage: F = EllipticCurve('37a').plot(thickness=5).plot3d(z=2)
            sage: E + F  # long time (5s on sage.math, 2012)
        """
        from sage.plot.plot3d.shapes2 import line3d
        options = self._plot3d_options()
        options.update(kwds)
        return line3d([(x, y, z) for x, y in zip(self.xdata, self.ydata)], **options)
Example #8
0
    def plot3d(self, **kwds):
        """
        Plots 2D text in 3D.

        EXAMPLES::

            sage: T = text("ABC",(1,1))
            sage: t = T[0]
            sage: s=t.plot3d()
            sage: s.jmol_repr(s.testing_render_params())[0][2]
            'label "ABC"'
            sage: s._trans
            (1.0, 1.0, 0)
        """
        from sage.plot.plot3d.shapes2 import text3d
        options = self._plot3d_options()
        options.update(kwds)
        return text3d(self.string, (self.x, self.y, 0), **options)
Example #9
0
    def plot3d(self, **kwds):
        """
        Plots 2D text in 3D.

        EXAMPLES::

            sage: T = text("ABC",(1,1))
            sage: t = T[0]
            sage: s=t.plot3d()
            sage: s.jmol_repr(s.testing_render_params())[0][2]
            'label "ABC"'
            sage: s._trans
            (1.0, 1.0, 0)
        """
        from sage.plot.plot3d.shapes2 import text3d
        options = self._plot3d_options()
        options.update(kwds)
        return text3d(self.string, (self.x, self.y, 0), **options)
Example #10
0
    def plot3d(self, z=0, **kwds):
        """
        Returns a 3D plot (Jmol) of the Bezier path.  Since a ``BezierPath``
        primitive contains only `x,y` coordinates, the path will be drawn in
        some plane (default is `z=0`).  To create a Bezier path with nonzero
        (and nonidentical) `z` coordinates in the path and control points, use
        the function :func:`~sage.plot.plot3d.shapes2.bezier3d` instead of
        :func:`bezier_path`.

        EXAMPLES::

            sage: b = bezier_path([[(0,0),(0,1),(1,0)]])
            sage: A = b.plot3d()
            sage: B = b.plot3d(z=2)
            sage: A + B
            Graphics3d Object

        .. PLOT::

            b = bezier_path([[(0,0),(0,1),(1,0)]])
            A = b.plot3d()
            B = b.plot3d(z=2)
            sphinx_plot(A + B)

        ::

            sage: bezier3d([[(0,0,0),(1,0,0),(0,1,0),(0,1,1)]])
            Graphics3d Object

        .. PLOT::

            sphinx_plot(bezier3d([[(0,0,0),(1,0,0),(0,1,0),(0,1,1)]]))

        """
        from sage.plot.plot3d.shapes2 import bezier3d
        options = self._plot3d_options()
        options.update(kwds)
        return bezier3d([[(x,y,0) for x,y in self.path[i]] for i in range(len(self.path))], **options)
Example #11
0
    def plot3d(self, z=0, **kwds):
        """
        Plots a two-dimensional point in 3-D, with default height zero.

        INPUT:


        -  ``z`` - optional 3D height above `xy`-plane.  May be a list
           if self is a list of points.

        EXAMPLES:

        One point::

            sage: A=point((1,1))
            sage: a=A[0];a
            Point set defined by 1 point(s)
            sage: b=a.plot3d()

        One point with a height::

            sage: A=point((1,1))
            sage: a=A[0];a
            Point set defined by 1 point(s)
            sage: b=a.plot3d(z=3)
            sage: b.loc[2]
            3.0

        Multiple points::

            sage: P=point([(0,0), (1,1)])
            sage: p=P[0]; p
            Point set defined by 2 point(s)
            sage: q=p.plot3d(size=22)

        Multiple points with different heights::

            sage: P=point([(0,0), (1,1)])
            sage: p=P[0]
            sage: q=p.plot3d(z=[2,3])
            sage: q.all[0].loc[2]
            2.0
            sage: q.all[1].loc[2]
            3.0

        Note that keywords passed must be valid point3d options::

            sage: A=point((1,1),size=22)
            sage: a=A[0];a
            Point set defined by 1 point(s)
            sage: b=a.plot3d()
            sage: b.size
            22
            sage: b=a.plot3d(pointsize=23) # only 2D valid option
            sage: b.size
            22
            sage: b=a.plot3d(size=23) # correct keyword
            sage: b.size
            23

        TESTS:

        Heights passed as a list should have same length as
        number of points::

            sage: P=point([(0,0), (1,1), (2,3)])
            sage: p=P[0]
            sage: q=p.plot3d(z=2)
            sage: q.all[1].loc[2]
            2.0
            sage: q=p.plot3d(z=[2,-2])
            Traceback (most recent call last):
            ...
            ValueError: Incorrect number of heights given
        """
        from sage.plot.plot3d.base import Graphics3dGroup
        from sage.plot.plot3d.shapes2 import point3d
        options = self._plot3d_options()
        options.update(kwds)
        zdata = []
        if isinstance(z, list):
            zdata = z
        else:
            zdata = [z] * len(self.xdata)
        if len(zdata) == len(self.xdata):
            all = [
                point3d(list(zip(self.xdata, self.ydata, zdata)), **options)
            ]
            if len(all) == 1:
                return all[0]
            else:
                return Graphics3dGroup(all)
        else:
            raise ValueError('Incorrect number of heights given')
Example #12
0
    def plot(self, **kwds):
        """
        Returns a graphics object representing the (di)graph.

        INPUT:

        The options accepted by this method are to be found in the documentation
        of the :mod:`sage.graphs.graph_plot` module, and the
        :meth:`~sage.plot.graphics.Graphics.show` method.

        .. NOTE::

            See :mod:`the module's documentation <sage.graphs.graph_plot>` for
            information on default values of this method.

        We can specify some pretty precise plotting of familiar graphs::

            sage: from math import sin, cos, pi
            sage: P = graphs.PetersenGraph()
            sage: d = {'#FF0000':[0,5], '#FF9900':[1,6], '#FFFF00':[2,7], '#00FF00':[3,8], '#0000FF':[4,9]}
            sage: pos_dict = {}
            sage: for i in range(5):
            ...    x = float(cos(pi/2 + ((2*pi)/5)*i))
            ...    y = float(sin(pi/2 + ((2*pi)/5)*i))
            ...    pos_dict[i] = [x,y]
            ...
            sage: for i in range(10)[5:]:
            ...    x = float(0.5*cos(pi/2 + ((2*pi)/5)*i))
            ...    y = float(0.5*sin(pi/2 + ((2*pi)/5)*i))
            ...    pos_dict[i] = [x,y]
            ...
            sage: pl = P.graphplot(pos=pos_dict, vertex_colors=d)
            sage: pl.show()

        Here are some more common graphs with typical options::

            sage: C = graphs.CubeGraph(8)
            sage: P = C.graphplot(vertex_labels=False, vertex_size=0, graph_border=True)
            sage: P.show()

            sage: G = graphs.HeawoodGraph().copy(sparse=True)
            sage: for u,v,l in G.edges():
            ...    G.set_edge_label(u,v,'(' + str(u) + ',' + str(v) + ')')
            sage: G.graphplot(edge_labels=True).show()

        The options for plotting also work with directed graphs::

            sage: D = DiGraph( { 0: [1, 10, 19], 1: [8, 2], 2: [3, 6], 3: [19, 4], 4: [17, 5], 5: [6, 15], 6: [7], 7: [8, 14], 8: [9], 9: [10, 13], 10: [11], 11: [12, 18], 12: [16, 13], 13: [14], 14: [15], 15: [16], 16: [17], 17: [18], 18: [19], 19: []})
            sage: for u,v,l in D.edges():
            ...    D.set_edge_label(u,v,'(' + str(u) + ',' + str(v) + ')')
            sage: D.graphplot(edge_labels=True, layout='circular').show()

        This example shows off the coloring of edges::

            sage: from sage.plot.colors import rainbow
            sage: C = graphs.CubeGraph(5)
            sage: R = rainbow(5)
            sage: edge_colors = {}
            sage: for i in range(5):
            ...    edge_colors[R[i]] = []
            sage: for u,v,l in C.edges():
            ...    for i in range(5):
            ...        if u[i] != v[i]:
            ...            edge_colors[R[i]].append((u,v,l))
            sage: C.graphplot(vertex_labels=False, vertex_size=0, edge_colors=edge_colors).show()


        With the ``partition`` option, we can separate out same-color groups
        of vertices::

            sage: D = graphs.DodecahedralGraph()
            sage: Pi = [[6,5,15,14,7],[16,13,8,2,4],[12,17,9,3,1],[0,19,18,10,11]]
            sage: D.show(partition=Pi)

        Loops are also plotted correctly::

            sage: G = graphs.PetersenGraph()
            sage: G.allow_loops(True)
            sage: G.add_edge(0,0)
            sage: G.show()

        ::

            sage: D = DiGraph({0:[0,1], 1:[2], 2:[3]}, loops=True)
            sage: D.show()
            sage: D.show(edge_colors={(0,1,0):[(0,1,None),(1,2,None)],(0,0,0):[(2,3,None)]})

        More options::

            sage: pos = {0:[0.0, 1.5], 1:[-0.8, 0.3], 2:[-0.6, -0.8], 3:[0.6, -0.8], 4:[0.8, 0.3]}
            sage: g = Graph({0:[1], 1:[2], 2:[3], 3:[4], 4:[0]})
            sage: g.graphplot(pos=pos, layout='spring', iterations=0).plot()
            Graphics object consisting of 11 graphics primitives

            sage: G = Graph()
            sage: P = G.graphplot().plot()
            sage: P.axes()
            False
            sage: G = DiGraph()
            sage: P = G.graphplot().plot()
            sage: P.axes()
            False

        We can plot multiple graphs::

            sage: T = list(graphs.trees(7))
            sage: t = T[3]
            sage: t.graphplot(heights={0:[0], 1:[4,5,1], 2:[2], 3:[3,6]}).plot()
            Graphics object consisting of 14 graphics primitives

        ::

            sage: T = list(graphs.trees(7))
            sage: t = T[3]
            sage: t.graphplot(heights={0:[0], 1:[4,5,1], 2:[2], 3:[3,6]}).plot()
            Graphics object consisting of 14 graphics primitives
            sage: t.set_edge_label(0,1,-7)
            sage: t.set_edge_label(0,5,3)
            sage: t.set_edge_label(0,5,99)
            sage: t.set_edge_label(1,2,1000)
            sage: t.set_edge_label(3,2,'spam')
            sage: t.set_edge_label(2,6,3/2)
            sage: t.set_edge_label(0,4,66)
            sage: t.graphplot(heights={0:[0], 1:[4,5,1], 2:[2], 3:[3,6]}, edge_labels=True).plot()
            Graphics object consisting of 20 graphics primitives

        ::

            sage: T = list(graphs.trees(7))
            sage: t = T[3]
            sage: t.graphplot(layout='tree').show()

        The tree layout is also useful::

            sage: t = DiGraph('JCC???@A??GO??CO??GO??')
            sage: t.graphplot(layout='tree', tree_root=0, tree_orientation="up").show()

        More examples::

            sage: D = DiGraph({0:[1,2,3], 2:[1,4], 3:[0]})
            sage: D.graphplot().show()

            sage: D = DiGraph(multiedges=True, sparse=True)
            sage: for i in range(5):
            ...     D.add_edge((i,i+1,'a'))
            ...     D.add_edge((i,i-1,'b'))
            sage: D.graphplot(edge_labels=True,edge_colors=D._color_by_label()).plot()
            Graphics object consisting of 34 graphics primitives

            sage: g = Graph({}, loops=True, multiedges=True, sparse=True)
            sage: g.add_edges([(0,0,'a'),(0,0,'b'),(0,1,'c'),(0,1,'d'),
            ...     (0,1,'e'),(0,1,'f'),(0,1,'f'),(2,1,'g'),(2,2,'h')])
            sage: g.graphplot(edge_labels=True, color_by_label=True, edge_style='dashed').plot()
            Graphics object consisting of 22 graphics primitives

        The ``edge_style`` option may be provided in the short format too::

            sage: g.graphplot(edge_labels=True, color_by_label=True, edge_style='--').plot()
            Graphics object consisting of 22 graphics primitives

        TESTS:

        Make sure that show options work with plot also::

            sage: g = Graph({})
            sage: g.plot(title='empty graph', axes=True)
            Graphics object consisting of 0 graphics primitives

        Check for invalid inputs::

            sage: p = graphs.PetersenGraph().plot(egabrag='garbage')
            Traceback (most recent call last):
            ...
            ValueError: Invalid input 'egabrag=garbage'

        Make sure that no graphics primitive is clipped::

            sage: tadpole = Graph({0:[0,1]}).plot()
            sage: bbox = tadpole.get_minmax_data()
            sage: for part in tadpole:
            ....:      part_bbox = part.get_minmax_data()
            ....:      assert bbox['xmin'] <= part_bbox['xmin'] <= part_bbox['xmax'] <= bbox['xmax']
            ....:      assert bbox['ymin'] <= part_bbox['ymin'] <= part_bbox['ymax'] <= bbox['ymax']
        """
        G = Graphics()
        options = self._options.copy()
        options.update(kwds)
        G._set_extra_kwds(Graphics._extract_kwds_for_show(options))

        # Check the arguments
        for o in options:
            if o not in graphplot_options and o not in G._extra_kwds:
                raise ValueError("Invalid input '{}={}'".format(o, options[o]))

        for comp in self._plot_components.values():
            if not isinstance(comp, list):
                G += comp
            else:
                for item in comp:
                    G += item

        if self._options['graph_border']:
            xmin = G.xmin()
            xmax = G.xmax()
            ymin = G.ymin()
            ymax = G.ymax()
            dx = (xmax - xmin) / 10.0
            dy = (ymax - ymin) / 10.0
            border = (line([(xmin - dx, ymin - dy), (xmin - dx, ymax + dy),
                            (xmax + dx, ymax + dy), (xmax + dx, ymin - dy),
                            (xmin - dx, ymin - dy)],
                           thickness=1.3))
            border.axes_range(xmin=(xmin - dx),
                              xmax=(xmax + dx),
                              ymin=(ymin - dy),
                              ymax=(ymax + dy))
            G += border
        G.set_aspect_ratio(1)
        G.axes(False)
        return G
Example #13
0
File: point.py Project: bukzor/sage
    def plot3d(self, z=0, **kwds):
        """
        Plots a two-dimensional point in 3-D, with default height zero.

        INPUT:


        -  ``z`` - optional 3D height above `xy`-plane.  May be a list
           if self is a list of points.

        EXAMPLES:

        One point::

            sage: A=point((1,1))
            sage: a=A[0];a
            Point set defined by 1 point(s)
            sage: b=a.plot3d()

        One point with a height::

            sage: A=point((1,1))
            sage: a=A[0];a
            Point set defined by 1 point(s)
            sage: b=a.plot3d(z=3)
            sage: b.loc[2]
            3.0

        Multiple points::

            sage: P=point([(0,0), (1,1)])
            sage: p=P[0]; p
            Point set defined by 2 point(s)
            sage: q=p.plot3d(size=22)

        Multiple points with different heights::

            sage: P=point([(0,0), (1,1)])
            sage: p=P[0]
            sage: q=p.plot3d(z=[2,3])
            sage: q.all[0].loc[2]
            2.0
            sage: q.all[1].loc[2]
            3.0

        Note that keywords passed must be valid point3d options::

            sage: A=point((1,1),size=22)
            sage: a=A[0];a
            Point set defined by 1 point(s)
            sage: b=a.plot3d()
            sage: b.size
            22
            sage: b=a.plot3d(pointsize=23) # only 2D valid option
            sage: b.size
            22
            sage: b=a.plot3d(size=23) # correct keyword
            sage: b.size
            23

        TESTS:

        Heights passed as a list should have same length as
        number of points::

            sage: P=point([(0,0), (1,1), (2,3)])
            sage: p=P[0]
            sage: q=p.plot3d(z=2)
            sage: q.all[1].loc[2]
            2.0
            sage: q=p.plot3d(z=[2,-2])
            Traceback (most recent call last):
            ...
            ValueError: Incorrect number of heights given
        """
        from sage.plot.plot3d.base import Graphics3dGroup
        from sage.plot.plot3d.shapes2 import point3d
        options = self._plot3d_options()
        options.update(kwds)
        zdata=[]
        if isinstance(z, list):
            zdata=z
        else:
            zdata=[z]*len(self.xdata)
        if len(zdata)==len(self.xdata):
            all = [point3d([(x, y, z) for x, y, z in zip(self.xdata, self.ydata, zdata)], **options)]
            if len(all) == 1:
                return all[0]
            else:
                return Graphics3dGroup(all)
        else:
            raise ValueError('Incorrect number of heights given')
Example #14
0
    def plot(self, **kwds):
        """
        Returns a graphics object representing the (di)graph.

        INPUT:

        The options accepted by this method are to be found in the documentation
        of the :mod:`sage.graphs.graph_plot` module, and the
        :meth:`~sage.plot.graphics.Graphics.show` method.

        .. NOTE::

            See :mod:`the module's documentation <sage.graphs.graph_plot>` for
            information on default values of this method.

        We can specify some pretty precise plotting of familiar graphs::

            sage: from math import sin, cos, pi
            sage: P = graphs.PetersenGraph()
            sage: d = {'#FF0000':[0,5], '#FF9900':[1,6], '#FFFF00':[2,7], '#00FF00':[3,8], '#0000FF':[4,9]}
            sage: pos_dict = {}
            sage: for i in range(5):
            ...    x = float(cos(pi/2 + ((2*pi)/5)*i))
            ...    y = float(sin(pi/2 + ((2*pi)/5)*i))
            ...    pos_dict[i] = [x,y]
            ...
            sage: for i in range(10)[5:]:
            ...    x = float(0.5*cos(pi/2 + ((2*pi)/5)*i))
            ...    y = float(0.5*sin(pi/2 + ((2*pi)/5)*i))
            ...    pos_dict[i] = [x,y]
            ...
            sage: pl = P.graphplot(pos=pos_dict, vertex_colors=d)
            sage: pl.show()

        Here are some more common graphs with typical options::

            sage: C = graphs.CubeGraph(8)
            sage: P = C.graphplot(vertex_labels=False, vertex_size=0, graph_border=True)
            sage: P.show()

            sage: G = graphs.HeawoodGraph().copy(sparse=True)
            sage: for u,v,l in G.edges():
            ...    G.set_edge_label(u,v,'(' + str(u) + ',' + str(v) + ')')
            sage: G.graphplot(edge_labels=True).show()

        The options for plotting also work with directed graphs::

            sage: D = DiGraph( { 0: [1, 10, 19], 1: [8, 2], 2: [3, 6], 3: [19, 4], 4: [17, 5], 5: [6, 15], 6: [7], 7: [8, 14], 8: [9], 9: [10, 13], 10: [11], 11: [12, 18], 12: [16, 13], 13: [14], 14: [15], 15: [16], 16: [17], 17: [18], 18: [19], 19: []})
            sage: for u,v,l in D.edges():
            ...    D.set_edge_label(u,v,'(' + str(u) + ',' + str(v) + ')')
            sage: D.graphplot(edge_labels=True, layout='circular').show()

        This example shows off the coloring of edges::

            sage: from sage.plot.colors import rainbow
            sage: C = graphs.CubeGraph(5)
            sage: R = rainbow(5)
            sage: edge_colors = {}
            sage: for i in range(5):
            ...    edge_colors[R[i]] = []
            sage: for u,v,l in C.edges():
            ...    for i in range(5):
            ...        if u[i] != v[i]:
            ...            edge_colors[R[i]].append((u,v,l))
            sage: C.graphplot(vertex_labels=False, vertex_size=0, edge_colors=edge_colors).show()


        With the ``partition`` option, we can separate out same-color groups
        of vertices::

            sage: D = graphs.DodecahedralGraph()
            sage: Pi = [[6,5,15,14,7],[16,13,8,2,4],[12,17,9,3,1],[0,19,18,10,11]]
            sage: D.show(partition=Pi)

        Loops are also plotted correctly::

            sage: G = graphs.PetersenGraph()
            sage: G.allow_loops(True)
            sage: G.add_edge(0,0)
            sage: G.show()

        ::

            sage: D = DiGraph({0:[0,1], 1:[2], 2:[3]}, loops=True)
            sage: D.show()
            sage: D.show(edge_colors={(0,1,0):[(0,1,None),(1,2,None)],(0,0,0):[(2,3,None)]})

        More options::

            sage: pos = {0:[0.0, 1.5], 1:[-0.8, 0.3], 2:[-0.6, -0.8], 3:[0.6, -0.8], 4:[0.8, 0.3]}
            sage: g = Graph({0:[1], 1:[2], 2:[3], 3:[4], 4:[0]})
            sage: g.graphplot(pos=pos, layout='spring', iterations=0).plot()
            Graphics object consisting of 11 graphics primitives

            sage: G = Graph()
            sage: P = G.graphplot().plot()
            sage: P.axes()
            False
            sage: G = DiGraph()
            sage: P = G.graphplot().plot()
            sage: P.axes()
            False

        We can plot multiple graphs::

            sage: T = list(graphs.trees(7))
            sage: t = T[3]
            sage: t.graphplot(heights={0:[0], 1:[4,5,1], 2:[2], 3:[3,6]}).plot()
            Graphics object consisting of 14 graphics primitives

        ::

            sage: T = list(graphs.trees(7))
            sage: t = T[3]
            sage: t.graphplot(heights={0:[0], 1:[4,5,1], 2:[2], 3:[3,6]}).plot()
            Graphics object consisting of 14 graphics primitives
            sage: t.set_edge_label(0,1,-7)
            sage: t.set_edge_label(0,5,3)
            sage: t.set_edge_label(0,5,99)
            sage: t.set_edge_label(1,2,1000)
            sage: t.set_edge_label(3,2,'spam')
            sage: t.set_edge_label(2,6,3/2)
            sage: t.set_edge_label(0,4,66)
            sage: t.graphplot(heights={0:[0], 1:[4,5,1], 2:[2], 3:[3,6]}, edge_labels=True).plot()
            Graphics object consisting of 20 graphics primitives

        ::

            sage: T = list(graphs.trees(7))
            sage: t = T[3]
            sage: t.graphplot(layout='tree').show()

        The tree layout is also useful::

            sage: t = DiGraph('JCC???@A??GO??CO??GO??')
            sage: t.graphplot(layout='tree', tree_root=0, tree_orientation="up").show()

        More examples::

            sage: D = DiGraph({0:[1,2,3], 2:[1,4], 3:[0]})
            sage: D.graphplot().show()

            sage: D = DiGraph(multiedges=True, sparse=True)
            sage: for i in range(5):
            ...     D.add_edge((i,i+1,'a'))
            ...     D.add_edge((i,i-1,'b'))
            sage: D.graphplot(edge_labels=True,edge_colors=D._color_by_label()).plot()
            Graphics object consisting of 34 graphics primitives

            sage: g = Graph({}, loops=True, multiedges=True, sparse=True)
            sage: g.add_edges([(0,0,'a'),(0,0,'b'),(0,1,'c'),(0,1,'d'),
            ...     (0,1,'e'),(0,1,'f'),(0,1,'f'),(2,1,'g'),(2,2,'h')])
            sage: g.graphplot(edge_labels=True, color_by_label=True, edge_style='dashed').plot()
            Graphics object consisting of 22 graphics primitives

        The ``edge_style`` option may be provided in the short format too::

            sage: g.graphplot(edge_labels=True, color_by_label=True, edge_style='--').plot()
            Graphics object consisting of 22 graphics primitives

        TESTS:

        Make sure that show options work with plot also::

            sage: g = Graph({})
            sage: g.plot(title='empty graph', axes=True)
            Graphics object consisting of 0 graphics primitives

        Check for invalid inputs::

            sage: p = graphs.PetersenGraph().plot(egabrag='garbage')
            Traceback (most recent call last):
            ...
            ValueError: Invalid input 'egabrag=garbage'

        Make sure that no graphics primitive is clipped::

            sage: tadpole = Graph({0:[0,1]}).plot()
            sage: bbox = tadpole.get_minmax_data()
            sage: for part in tadpole:
            ....:      part_bbox = part.get_minmax_data()
            ....:      assert bbox['xmin'] <= part_bbox['xmin'] <= part_bbox['xmax'] <= bbox['xmax']
            ....:      assert bbox['ymin'] <= part_bbox['ymin'] <= part_bbox['ymax'] <= bbox['ymax']
        """
        G = Graphics()
        options = self._options.copy()
        options.update(kwds)
        G._set_extra_kwds(Graphics._extract_kwds_for_show(options))

        # Check the arguments
        for o in options:
            if o not in graphplot_options and o not in G._extra_kwds:
                raise ValueError("Invalid input '{}={}'".format(o, options[o]))

        for comp in self._plot_components.values():
            if not isinstance(comp, list):
                G += comp
            else:
                for item in comp:
                    G += item

        if self._options['graph_border']:
            xmin = G.xmin()
            xmax = G.xmax()
            ymin = G.ymin()
            ymax = G.ymax()
            dx = (xmax-xmin)/10.0
            dy = (ymax-ymin)/10.0
            border = (line([( xmin - dx, ymin - dy), ( xmin - dx, ymax + dy ), ( xmax + dx, ymax + dy ), ( xmax + dx, ymin - dy ), ( xmin - dx, ymin - dy )], thickness=1.3))
            border.axes_range(xmin = (xmin - dx), xmax = (xmax + dx), ymin = (ymin - dy), ymax = (ymax + dy))
            G += border
        G.set_aspect_ratio(1)
        G.axes(False)
        return G