def plot_fan_stereographically(rays, walls, northsign=1, north=vector((-1,-1,-1)), right=vector((1,0,0)), colors=None, thickness=None):
from sage.plot.graphics import Graphics
from sage.plot.point import point
from sage.misc.flatten import flatten
from sage.plot.line import line
from sage.misc.functional import norm
if colors == None:
colors = dict([('walls','black'),('rays','red')])
if thickness == None:
thickness = dict([('walls',0.5),('rays',20)])
G = Graphics()
for (u,v) in walls:
G += _stereo_arc(vector(u),vector(v),vector(u+v),north=northsign*north,right=right,color=colors['walls'],thickness=thickness['walls'],zorder=len(G))
for v in rays:
G += point(_stereo_coordinates(vector(v),north=northsign*north,right=right),color=colors['rays'],zorder=len(G),size=thickness['rays'])
G.set_aspect_ratio(1)
G._show_axes = False
return G
def legend_3d(hyperplane_arrangement, hyperplane_colors, length):
r"""
Create plot of a 3d legend for an arrangement of planes in 3-space. The
``length`` parameter determines whether short or long labels are used in
the legend.
INPUT:
- ``hyperplane_arrangement`` -- a hyperplane arrangement
- ``hyperplane_colors`` -- list of colors
- ``length`` -- either ``'short'`` or ``'long'``
OUTPUT:
- A graphics object.
EXAMPLES::
sage: a = hyperplane_arrangements.semiorder(3)
sage: from sage.geometry.hyperplane_arrangement.plot import legend_3d
sage: legend_3d(a, list(colors.values())[:6],length='long')
Graphics object consisting of 6 graphics primitives
sage: b = hyperplane_arrangements.semiorder(4)
sage: c = b.essentialization()
sage: legend_3d(c, list(colors.values())[:12], length='long')
Graphics object consisting of 12 graphics primitives
sage: legend_3d(c, list(colors.values())[:12], length='short')
Graphics object consisting of 12 graphics primitives
sage: p = legend_3d(c, list(colors.values())[:12], length='short')
sage: p.set_legend_options(ncol=4)
sage: type(p)
<class 'sage.plot.graphics.Graphics'>
"""
if hyperplane_arrangement.dimension() != 3:
raise ValueError('arrangements must be in 3-space')
hyps = hyperplane_arrangement.hyperplanes()
N = len(hyperplane_arrangement)
if length == 'short':
labels = [' ' + str(i) for i in range(N)]
else:
labels = [' ' + hyps[i]._repr_linear(include_zero=False) for i in
range(N)]
p = Graphics()
for i in range(N):
p += line([(0,0),(0,0)], color=hyperplane_colors[i], thickness=8,
legend_label=labels[i], axes=False)
p.set_legend_options(title='Hyperplanes', loc='center', labelspacing=0.4,
fancybox=True, font_size='x-large', ncol=2)
p.legend(True)
return p
def bezier_path(self):
"""
Return ``self`` as a Bezier path.
This is needed to concatenate arcs, in order to
create hyperbolic polygons.
EXAMPLES::
sage: from sage.plot.arc import Arc
sage: op = {'alpha':1,'thickness':1,'rgbcolor':'blue','zorder':0,
....: 'linestyle':'--'}
sage: Arc(2,3,2.2,2.2,0,2,3,op).bezier_path()
Graphics object consisting of 1 graphics primitive
sage: a = arc((0,0),2,1,0,(pi/5,pi/2+pi/12), linestyle="--", color="red")
sage: b = a[0].bezier_path()
sage: b[0]
Bezier path from (1.133..., 0.8237...) to (-0.2655..., 0.9911...)
"""
from sage.plot.bezier_path import BezierPath
from sage.plot.graphics import Graphics
from matplotlib.path import Path
import numpy as np
ma = self._matplotlib_arc()
def theta_stretch(theta, scale):
theta = np.deg2rad(theta)
x = np.cos(theta)
y = np.sin(theta)
return np.rad2deg(np.arctan2(scale * y, x))
theta1 = theta_stretch(ma.theta1, ma.width / ma.height)
theta2 = theta_stretch(ma.theta2, ma.width / ma.height)
pa = ma
pa._path = Path.arc(theta1, theta2)
transform = pa.get_transform().get_matrix()
cA, cC, cE = transform[0]
cB, cD, cF = transform[1]
points = []
for u in pa._path.vertices:
x, y = list(u)
points += [(cA * x + cC * y + cE, cB * x + cD * y + cF)]
cutlist = [points[0: 4]]
N = 4
while N < len(points):
cutlist += [points[N: N + 3]]
N += 3
g = Graphics()
opt = self.options()
opt['fill'] = False
g.add_primitive(BezierPath(cutlist, opt))
return g
def bar_chart(datalist, **options):
"""
A bar chart of (currently) one list of numerical data.
Support for more data lists in progress.
EXAMPLES:
A bar_chart with blue bars::
sage: bar_chart([1,2,3,4])
Graphics object consisting of 1 graphics primitive
A bar_chart with thinner bars::
sage: bar_chart([x^2 for x in range(1,20)], width=0.2)
Graphics object consisting of 1 graphics primitive
A bar_chart with negative values and red bars::
sage: bar_chart([-3,5,-6,11], rgbcolor=(1,0,0))
Graphics object consisting of 1 graphics primitive
A bar chart with a legend (it's possible, not necessarily useful)::
sage: bar_chart([-1,1,-1,1], legend_label='wave')
Graphics object consisting of 1 graphics primitive
Extra options will get passed on to show(), as long as they are valid::
sage: bar_chart([-2,8,-7,3], rgbcolor=(1,0,0), axes=False)
Graphics object consisting of 1 graphics primitive
sage: bar_chart([-2,8,-7,3], rgbcolor=(1,0,0)).show(axes=False) # These are equivalent
"""
dl = len(datalist)
#if dl > 1:
# print "WARNING, currently only 1 data set allowed"
# datalist = datalist[0]
if dl == 3:
datalist = datalist+[0]
#bardata = []
#cnt = 1
#for pnts in datalist:
#ind = [i+cnt/dl for i in range(len(pnts))]
#bardata.append([ind, pnts, xrange, yrange])
#cnt += 1
g = Graphics()
g._set_extra_kwds(Graphics._extract_kwds_for_show(options))
#TODO: improve below for multiple data sets!
#cnt = 1
#for ind, pnts, xrange, yrange in bardata:
#options={'rgbcolor':hue(cnt/dl),'width':0.5/dl}
# g._bar_chart(ind, pnts, xrange, yrange, options=options)
# cnt += 1
#else:
ind = list(range(len(datalist)))
g.add_primitive(BarChart(ind, datalist, options=options))
if options['legend_label']:
g.legend(True)
return g
def plot_n_matrices_eigenvectors(self, n, side='right', color_index=0, draw_line=False):
r"""
INPUT:
- ``n`` -- integer, length
- ``side`` -- ``'left'`` or ``'right'``, drawing left or right
eigenvectors
- ``color_index`` -- 0 for first letter, -1 for last letter
- ``draw_line`` -- boolean
EXAMPLES::
sage: from slabbe.matrix_cocycle import cocycles
sage: ARP = cocycles.ARP()
sage: G = ARP.plot_n_matrices_eigenvectors(2)
"""
from sage.plot.graphics import Graphics
from sage.plot.point import point
from sage.plot.line import line
from sage.plot.text import text
from sage.plot.colors import hue
from sage.modules.free_module_element import vector
from .matrices import M3to2
R = self.n_matrices_eigenvectors(n)
L = [(w, M3to2*(a/sum(a)), M3to2*(b/sum(b))) for (w,a,b) in R]
G = Graphics()
alphabet = self._language._alphabet
color_ = dict( (letter, hue(i/float(len(alphabet)))) for i,letter in
enumerate(alphabet))
for letter in alphabet:
L_filtered = [(w,p1,p2) for (w,p1,p2) in L if w[color_index] == letter]
words,rights,lefts = zip(*L_filtered)
if side == 'right':
G += point(rights, color=color_[letter], legend_label=letter)
elif side == 'left':
G += point(lefts, color=color_[letter], legend_label=letter)
else:
raise ValueError("side(=%s) should be left or right" % side)
if draw_line:
for (a,b) in L:
G += line([a,b], color='black', linestyle=":")
G += line([M3to2*vector(a) for a in [(1,0,0), (0,1,0), (0,0,1), (1,0,0)]])
title = "%s eigenvectors, colored by letter w[%s] of cylinder w" % (side, color_index)
G += text(title, (0.5, 1.05), axis_coords=True)
G.axes(False)
return G
def plot3d(self,depth=None):
# FIXME: refactor this before publishing
from sage.plot.graphics import Graphics
from sage.plot.point import point
from sage.misc.flatten import flatten
from sage.plot.plot3d.shapes2 import sphere
if self._n !=3:
raise ValueError("Can only 3d plot fans.")
if depth == None:
depth = self._depth
if not self.is_finite() and depth==infinity:
raise ValueError("For infinite algebras you must specify the depth.")
colors = dict([(0,'red'),(1,'green'),(2,'blue'),(3,'cyan')])
G = Graphics()
roots = self.d_vectors(depth=depth)
compatible = []
while roots:
x = roots.pop()
for y in roots:
if self.compatibility_degree(x,y) == 0:
compatible.append((x,y))
for (u,v) in compatible:
G += _arc3d((_normalize(vector(u)),_normalize(vector(v))),thickness=0.5,color='black')
for i in range(3):
orbit = self.ith_orbit(i,depth=depth)
for j in orbit:
G += point(_normalize(vector(orbit[j])),color=colors[i],size=10,zorder=len(G.all))
if self.is_affine():
tube_vectors=map(vector,flatten(self.affine_tubes()))
tube_vectors=map(_normalize,tube_vectors)
for v in tube_vectors:
G += point(v,color=colors[3],size=10,zorder=len(G.all))
G += _arc3d((tube_vectors[0],tube_vectors[1]),thickness=5,color='gray',zorder=0)
G += sphere((0,0,0),opacity=0.1,zorder=0)
G._extra_kwds['frame']=False
G._extra_kwds['aspect_ratio']=1
return G
def plot2d(self,depth=None):
# FIXME: refactor this before publishing
from sage.plot.line import line
from sage.plot.graphics import Graphics
if self._n !=2:
raise ValueError("Can only 2d plot fans.")
if depth == None:
depth = self._depth
if not self.is_finite() and depth==infinity:
raise ValueError("For infinite algebras you must specify the depth.")
colors = dict([(0,'red'),(1,'green')])
G = Graphics()
for i in range(2):
orbit = self.ith_orbit(i,depth=depth)
for j in orbit:
G += line([(0,0),vector(orbit[j])],color=colors[i],thickness=0.5, zorder=2*j+1)
G.set_aspect_ratio(1)
G._show_axes = False
return G
def bezier_path(self):
"""
Return ``self`` as a Bezier path.
This is needed to concatenate arcs, in order to
create hyperbolic polygons.
EXAMPLES::
sage: from sage.plot.arc import Arc
sage: op = {'alpha':1,'thickness':1,'rgbcolor':'blue','zorder':0,
....: 'linestyle':'--'}
sage: Arc(2,3,2.2,2.2,0,2,3,op).bezier_path()
Graphics object consisting of 1 graphics primitive
sage: a = arc((0,0),2,1,0,(pi/5,pi/2+pi/12), linestyle="--", color="red")
sage: b = a[0].bezier_path()
sage: b[0]
Bezier path from (1.618..., 0.5877...) to (-0.5176..., 0.9659...)
"""
from sage.plot.bezier_path import BezierPath
from sage.plot.graphics import Graphics
ma = self._matplotlib_arc()
transform = ma.get_transform().get_matrix()
cA, cC, cE = transform[0]
cB, cD, cF = transform[1]
points = []
for u in ma._path.vertices:
x, y = list(u)
points += [(cA * x + cC * y + cE, cB * x + cD * y + cF)]
cutlist = [points[0: 4]]
N = 4
while N < len(points):
cutlist += [points[N: N + 3]]
N += 3
g = Graphics()
opt = self.options()
opt['fill'] = False
g.add_primitive(BezierPath(cutlist, opt))
return g
开发者ID:ProgVal,项目名称:sage,代码行数:40,代码来源:arc.py
示例9: plot
def plot(self, m, pointsize=100, thickness=3, axes=False):
r"""
Return 2d graphics object contained in the primal box [-m,m]^d.
INPUT:
- ``pointsize``, integer (default:``100``),
- ``thickness``, integer (default:``3``),
- ``axes``, bool (default:``False``),
EXAMPLES::
sage: from slabbe import BondPercolationSample
sage: S = BondPercolationSample(0.5,2)
sage: S.plot(2) # optional long
It works in 3d!!::
sage: S = BondPercolationSample(0.5,3)
sage: S.plot(3, pointsize=10, thickness=1) # optional long
Graphics3d Object
"""
s = ""
s += "\\begin{tikzpicture}\n"
s += "[inner sep=0pt,thick,\n"
s += "reddot/.style={fill=red,draw=red,circle,minimum size=5pt}]\n"
s += "\\clip %s rectangle %s;\n" % ((-m-.4,-m-.4), (m+.4,m+.4))
G = Graphics()
for u in self.cluster_in_box(m+1):
G += point(u, color='blue', size=pointsize)
for (u,v) in self.edges_in_box(m+1):
G += line((u,v), thickness=thickness, alpha=0.8)
G += text("p=%.3f" % self._p, (0.5,1.03), axis_coords=True, color='black')
G += circle((0,0), 0.5, color='red', thickness=thickness)
if self._dimension == 2:
G.axes(axes)
return G
def plot_cluster_fan_stereographically(self, northsign=1, north=None, right=None, colors=None):
from sage.plot.graphics import Graphics
from sage.plot.point import point
from sage.misc.flatten import flatten
from sage.plot.line import line
from sage.misc.functional import norm
if self.rk !=3:
raise ValueError("Can only stereographically project fans in 3d.")
if not self.is_finite() and self._depth == infinity:
raise ValueError("For infinite algebras you must specify the depth.")
if north == None:
if self.is_affine():
north = vector(self.delta())
else:
north = vector( (-1,-1,-1) )
if right == None:
if self.is_affine():
right = vector(self.gamma())
else:
right = vector( (1,0,0) )
if colors == None:
colors = dict([(0,'red'),(1,'green'),(2,'blue'),(3,'cyan'),(4,'yellow')])
G = Graphics()
roots = list(self.g_vectors())
compatible = []
while roots:
x = roots.pop()
for y in roots:
if self.compatibility_degree(x,y) == 0:
compatible.append((x,y))
for (u,v) in compatible:
G += _stereo_arc(vector(u),vector(v),vector(u+v),north=northsign*north,right=right,thickness=0.5,color='black')
for i in range(3):
orbit = self.ith_orbit(i)
for j in orbit:
G += point(_stereo_coordinates(vector(orbit[j]),north=northsign*north,right=right),color=colors[i],zorder=len(G))
if self.is_affine():
tube_vectors = map(vector,flatten(self.affine_tubes()))
for v in tube_vectors:
G += point(_stereo_coordinates(v,north=northsign*north,right=right),color=colors[3],zorder=len(G))
if north != vector(self.delta()):
G += _stereo_arc(tube_vectors[0],tube_vectors[1],vector(self.delta()),north=northsign*north,right=right,thickness=2,color=colors[4],zorder=0)
else:
# FIXME: refactor this before publishing
tube_projections = [
_stereo_coordinates(v,north=northsign*north,right=right)
for v in tube_vectors ]
t=min((G.get_minmax_data()['xmax'],G.get_minmax_data()['ymax']))
G += line([tube_projections[0],tube_projections[0]+t*(_normalize(tube_projections[0]-tube_projections[1]))],thickness=2,color=colors[4],zorder=0)
G += line([tube_projections[1],tube_projections[1]+t*(_normalize(tube_projections[1]-tube_projections[0]))],thickness=2,color=colors[4],zorder=0)
G.set_aspect_ratio(1)
G._show_axes = False
return G
def finalize(self, G):
r"""
Finalize a root system plot.
INPUT:
- ``G`` -- a root system plot or ``0``
This sets the aspect ratio to 1 and remove the axes. This
should be called by all the user-level plotting methods of
root systems. This will become mostly obsolete when
customization options won't be lost anymore upon addition of
graphics objects and there will be a proper empty object for
2D and 3D plots.
EXAMPLES::
sage: L = RootSystem(["B",2,1]).ambient_space()
sage: options = L.plot_parse_options()
sage: p = L.plot_roots(plot_options=options)
sage: p += L.plot_coroots(plot_options=options)
sage: p.axes()
True
sage: p = options.finalize(p)
sage: p.axes()
False
sage: p.aspect_ratio()
1.0
sage: options = L.plot_parse_options(affine=False)
sage: p = L.plot_roots(plot_options=options)
sage: p += point([[1,1,0]])
sage: p = options.finalize(p)
sage: p.aspect_ratio()
[1.0, 1.0, 1.0]
If the input is ``0``, this returns an empty graphics object::
sage: type(options.finalize(0))
<class 'sage.plot.plot3d.base.Graphics3dGroup'>
sage: options = L.plot_parse_options()
sage: type(options.finalize(0))
<class 'sage.plot.graphics.Graphics'>
sage: list(options.finalize(0))
[]
"""
from sage.plot.graphics import Graphics
if self.dimension == 2:
if G == 0:
G = Graphics()
G.set_aspect_ratio(1)
# TODO: make this customizable
G.axes(False)
elif self.dimension == 3:
if G == 0:
from sage.plot.plot3d.base import Graphics3dGroup
G = Graphics3dGroup()
G.aspect_ratio(1)
# TODO: Configuration axes
return G
开发者ID:biasse,项目名称:sage,代码行数:61,代码来源:plot.py
示例12: plot
def plot(self, chart=None, ambient_coords=None, mapping=None,
chart_domain=None, fixed_coords=None, ranges=None, max_value=8,
nb_values=None, steps=None,scale=1, color='blue', parameters=None,
label_axes=True, **extra_options):
r"""
Plot the vector field in a Cartesian graph based on the coordinates
of some ambient chart.
The vector field is drawn in terms of two (2D graphics) or three
(3D graphics) coordinates of a given chart, called hereafter the
*ambient chart*.
The vector field's base points `p` (or their images `\Phi(p)` by some
differentiable mapping `\Phi`) must lie in the ambient chart's domain.
INPUT:
- ``chart`` -- (default: ``None``) the ambient chart (see above); if
``None``, the default chart of the vector field's domain is used
- ``ambient_coords`` -- (default: ``None``) tuple containing the 2 or 3
coordinates of the ambient chart in terms of which the plot is
performed; if ``None``, all the coordinates of the ambient chart are
considered
- ``mapping`` -- (default: ``None``) differentiable mapping `\Phi`
(instance of
:class:`~sage.geometry.manifolds.diffmapping.DiffMapping`)
providing the link between the vector field's domain and
the ambient chart ``chart``; if ``None``, the identity mapping is
assumed
- ``chart_domain`` -- (default: ``None``) chart on the vector
field's domain to define the points at which vector arrows are to be
plotted; if ``None``, the default chart of the vector field's domain
is used
- ``fixed_coords`` -- (default: ``None``) dictionary with keys the
coordinates of ``chart_domain`` that are kept fixed and with values
the value of these coordinates; if ``None``, all the coordinates of
``chart_domain`` are used
- ``ranges`` -- (default: ``None``) dictionary with keys the
coordinates of ``chart_domain`` to be used and values
tuples ``(x_min,x_max)`` specifying the
coordinate range for the plot; if ``None``, the entire coordinate
range declared during the construction of ``chart_domain`` is
considered (with ``-Infinity`` replaced by ``-max_value`` and
``+Infinity`` by ``max_value``)
- ``max_value`` -- (default: 8) numerical value substituted to
``+Infinity`` if the latter is the upper bound of the range of a
coordinate for which the plot is performed over the entire coordinate
range (i.e. for which no specific plot range has been set in
``ranges``); similarly ``-max_value`` is the numerical valued
substituted for ``-Infinity``
- ``nb_values`` -- (default: ``None``) either an integer or a dictionary
with keys the coordinates of ``chart_domain`` to be used and values
the number of values of the coordinate for sampling
the part of the vector field's domain involved in the plot ; if
``nb_values`` is a single integer, it represents the number of
values for all coordinates; if ``nb_values`` is ``None``, it is set
to 9 for a 2D plot and to 5 for a 3D plot
- ``steps`` -- (default: ``None``) dictionary with keys the coordinates
of ``chart_domain`` to be used and values the step between each
constant value of the coordinate; if ``None``, the step is computed
from the coordinate range (specified in ``ranges``) and ``nb_values``.
On the contrary, if the step is provided for some coordinate, the
corresponding number of values is deduced from it and the coordinate
range.
- ``scale`` -- (default: 1) value by which the lengths of the arrows
representing the vectors is multiplied
- ``color`` -- (default: 'blue') color of the arrows representing the
vectors
- ``parameters`` -- (default: ``None``) dictionary giving the numerical
values of the parameters that may appear in the coordinate expression
of the vector field (see example below)
- ``label_axes`` -- (default: ``True``) boolean determining whether the
labels of the coordinate axes of ``chart`` shall be added to the
graph; can be set to ``False`` if the graph is 3D and must be
superposed with another graph.
- ``**extra_options`` -- extra options for the arrow plot, like
``linestyle``, ``width`` or ``arrowsize`` (see
:func:`~sage.plot.arrow.arrow2d` and
:func:`~sage.plot.plot3d.shapes.arrow3d` for details)
OUTPUT:
- a graphic object, either an instance of
:class:`~sage.plot.graphics.Graphics` for a 2D plot (i.e. based on
2 coordinates of ``chart``) or an instance of
:class:`~sage.plot.plot3d.base.Graphics3d` for a 3D plot (i.e.
based on 3 coordinates of ``chart``)
EXAMPLES:
Plot of a vector field on a 2-dimensional manifold::
sage: Manifold._clear_cache_() # for doctests only
sage: M = Manifold(2, 'M')
sage: X.<x,y> = M.chart()
sage: v = M.vector_field(name='v')
sage: v[:] = -y, x ; v.display()
v = -y d/dx + x d/dy
sage: v.plot()
Graphics object consisting of 80 graphics primitives
#.........这里部分代码省略.........
def _graphics(self, plot_curve, ambient_coords, thickness=1,
aspect_ratio='automatic', color='red', style='-',
label_axes=True):
r"""
Plot a 2D or 3D curve in a Cartesian graph with axes labeled by
the ambient coordinates; it is invoked by the methods
:meth:`plot` of
:class:`~sage.manifolds.differentiable.curve.DifferentiableCurve`,
and its subclasses
(:class:`~sage.manifolds.differentiable.integrated_curve.IntegratedCurve`,
:class:`~sage.manifolds.differentiable.integrated_curve.IntegratedAutoparallelCurve`,
and
:class:`~sage.manifolds.differentiable.integrated_curve.IntegratedGeodesic`).
TESTS::
sage: M = Manifold(2, 'R^2')
sage: X.<x,y> = M.chart()
sage: R.<t> = RealLine()
sage: c = M.curve([cos(t), sin(t)], (t, 0, 2*pi), name='c')
sage: graph = c._graphics([[1,2], [3,4]], [x,y])
sage: graph._objects[0].xdata == [1,3]
True
sage: graph._objects[0].ydata == [2,4]
True
sage: graph._objects[0]._options['thickness'] == 1
True
sage: graph._extra_kwds['aspect_ratio'] == 'automatic'
True
sage: graph._objects[0]._options['rgbcolor'] == 'red'
True
sage: graph._objects[0]._options['linestyle'] == '-'
True
sage: l = [r'$'+latex(x)+r'$', r'$'+latex(y)+r'$']
sage: graph._extra_kwds['axes_labels'] == l
True
"""
from sage.plot.graphics import Graphics
from sage.plot.line import line
from sage.manifolds.utilities import set_axes_labels
#
# The plot
#
n_pc = len(ambient_coords)
resu = Graphics()
resu += line(plot_curve, color=color, linestyle=style,
thickness=thickness)
if n_pc == 2: # 2D graphic
resu.set_aspect_ratio(aspect_ratio)
if label_axes:
# We update the dictionary _extra_kwds (options to be passed
# to show()), instead of using the method
# Graphics.axes_labels() since the latter is not robust w.r.t.
# graph addition
resu._extra_kwds['axes_labels'] = [r'$'+latex(pc)+r'$'
for pc in ambient_coords]
else: # 3D graphic
if aspect_ratio == 'automatic':
aspect_ratio = 1
resu.aspect_ratio(aspect_ratio)
if label_axes:
labels = [str(pc) for pc in ambient_coords]
resu = set_axes_labels(resu, *labels)
return resu
def plot(hyperplane_arrangement, **kwds):
r"""
Return a plot of the hyperplane arrangement.
If the arrangement is in 4 dimensions but inessential, a plot of
the essentialization is returned.
.. NOTE::
This function is available as the
:meth:`~sage.geometry.hyperplane_arrangement.arrangement.HyperplaneArrangementElement.plot`
method of hyperplane arrangements. You should not call this
function directly, only through the method.
INPUT:
- ``hyperplane_arrangement`` -- the hyperplane arrangement to plot
- ``**kwds`` -- plot options: see
:mod:`sage.geometry.hyperplane_arrangement.plot`.
OUTPUT:
A graphics object of the plot.
EXAMPLES::
sage: B = hyperplane_arrangements.semiorder(4)
sage: B.plot()
Displaying the essentialization.
Graphics3d Object
"""
N = len(hyperplane_arrangement)
dim = hyperplane_arrangement.dimension()
if hyperplane_arrangement.base_ring().characteristic() != 0:
raise NotImplementedError('must be a field of characteristic 0')
elif dim == 4:
if not hyperplane_arrangement.is_essential():
print('Displaying the essentialization.')
hyperplane_arrangement = hyperplane_arrangement.essentialization()
elif dim not in [1,2,3]: # revise to handle 4d
return # silently
# handle extra keywords
if 'hyperplane_colors' in kwds:
hyp_colors = kwds.pop('hyperplane_colors')
if not isinstance(hyp_colors, list): # we assume its a single color then
hyp_colors = [hyp_colors] * N
else:
HSV_tuples = [(i*1.0/N, 0.8, 0.9) for i in range(N)]
hyp_colors = [hsv_to_rgb(*x) for x in HSV_tuples]
if 'hyperplane_labels' in kwds:
hyp_labels = kwds.pop('hyperplane_labels')
has_hyp_label = True
if not isinstance(hyp_labels, list): # we assume its a boolean then
hyp_labels = [hyp_labels] * N
relabeled = []
for i in range(N):
if hyp_labels[i] in [True,'long']:
relabeled.append(True)
else:
relabeled.append(str(i))
hyp_labels = relabeled
else:
has_hyp_label = False
if 'label_colors' in kwds:
label_colors = kwds.pop('label_colors')
has_label_color = True
if not isinstance(label_colors, list): # we assume its a single color then
label_colors = [label_colors] * N
else:
has_label_color = False
if 'label_fontsize' in kwds:
label_fontsize = kwds.pop('label_fontsize')
has_label_fontsize = True
if not isinstance(label_fontsize, list): # we assume its a single size then
label_fontsize = [label_fontsize] * N
else:
has_label_fontsize = False
if 'label_offsets' in kwds:
has_offsets = True
offsets = kwds.pop('label_offsets')
else:
has_offsets = False # give default values below
hyperplane_legend = kwds.pop('hyperplane_legend', 'long' if dim < 3 else False)
if 'hyperplane_opacities' in kwds:
hyperplane_opacities = kwds.pop('hyperplane_opacities')
has_opacity = True
if not isinstance(hyperplane_opacities, list): # we assume a single number then
hyperplane_opacities = [hyperplane_opacities] * N
else:
has_opacity = False
point_sizes = kwds.pop('point_sizes', 50)
if not isinstance(point_sizes, list):
point_sizes = [point_sizes] * N
if 'ranges' in kwds:
ranges_set = True
ranges = kwds.pop('ranges')
if not type(ranges) in [list,tuple]: # ranges is a single number
ranges = [ranges] * N
# So ranges is some type of list.
#.........这里部分代码省略.........
def plot(self, chart=None, ambient_coords=None, mapping=None,
chart_domain=None, fixed_coords=None, ranges=None,
number_values=None, steps=None,
parameters=None, label_axes=True, **extra_options):
r"""
Plot the vector field in a Cartesian graph based on the coordinates
of some ambient chart.
The vector field is drawn in terms of two (2D graphics) or three
(3D graphics) coordinates of a given chart, called hereafter the
*ambient chart*.
The vector field's base points `p` (or their images `\Phi(p)` by some
differentiable mapping `\Phi`) must lie in the ambient chart's domain.
INPUT:
- ``chart`` -- (default: ``None``) the ambient chart (see above); if
``None``, the default chart of the vector field's domain is used
- ``ambient_coords`` -- (default: ``None``) tuple containing the 2
or 3 coordinates of the ambient chart in terms of which the plot
is performed; if ``None``, all the coordinates of the ambient
chart are considered
- ``mapping`` -- :class:`~sage.manifolds.differentiable.diff_map.DiffMap`
(default: ``None``); differentiable map `\Phi` providing the link
between the vector field's domain and the ambient chart ``chart``;
if ``None``, the identity map is assumed
- ``chart_domain`` -- (default: ``None``) chart on the vector field's
domain to define the points at which vector arrows are to be plotted;
if ``None``, the default chart of the vector field's domain is used
- ``fixed_coords`` -- (default: ``None``) dictionary with keys the
coordinates of ``chart_domain`` that are kept fixed and with values
the value of these coordinates; if ``None``, all the coordinates of
``chart_domain`` are used
- ``ranges`` -- (default: ``None``) dictionary with keys the
coordinates of ``chart_domain`` to be used and values tuples
``(x_min, x_max)`` specifying the coordinate range for the plot;
if ``None``, the entire coordinate range declared during the
construction of ``chart_domain`` is considered (with ``-Infinity``
replaced by ``-max_range`` and ``+Infinity`` by ``max_range``)
- ``number_values`` -- (default: ``None``) either an integer or a
dictionary with keys the coordinates of ``chart_domain`` to be
used and values the number of values of the coordinate for sampling
the part of the vector field's domain involved in the plot ; if
``number_values`` is a single integer, it represents the number of
values for all coordinates; if ``number_values`` is ``None``, it is
set to 9 for a 2D plot and to 5 for a 3D plot
- ``steps`` -- (default: ``None``) dictionary with keys the
coordinates of ``chart_domain`` to be used and values the step
between each constant value of the coordinate; if ``None``, the
step is computed from the coordinate range (specified in ``ranges``)
and ``number_values``; on the contrary, if the step is provided
for some coordinate, the corresponding number of values is deduced
from it and the coordinate range
- ``parameters`` -- (default: ``None``) dictionary giving the numerical
values of the parameters that may appear in the coordinate expression
of the vector field (see example below)
- ``label_axes`` -- (default: ``True``) boolean determining whether
the labels of the coordinate axes of ``chart`` shall be added to
the graph; can be set to ``False`` if the graph is 3D and must be
superposed with another graph
- ``color`` -- (default: 'blue') color of the arrows representing
the vectors
- ``max_range`` -- (default: 8) numerical value substituted to
``+Infinity`` if the latter is the upper bound of the range of a
coordinate for which the plot is performed over the entire coordinate
range (i.e. for which no specific plot range has been set in
``ranges``); similarly ``-max_range`` is the numerical valued
substituted for ``-Infinity``
- ``scale`` -- (default: 1) value by which the lengths of the arrows
representing the vectors is multiplied
- ``**extra_options`` -- extra options for the arrow plot, like
``linestyle``, ``width`` or ``arrowsize`` (see
:func:`~sage.plot.arrow.arrow2d` and
:func:`~sage.plot.plot3d.shapes.arrow3d` for details)
OUTPUT:
- a graphic object, either an instance of
:class:`~sage.plot.graphics.Graphics` for a 2D plot (i.e. based on
2 coordinates of ``chart``) or an instance of
:class:`~sage.plot.plot3d.base.Graphics3d` for a 3D plot (i.e.
based on 3 coordinates of ``chart``)
EXAMPLES:
Plot of a vector field on a 2-dimensional manifold::
#.........这里部分代码省略.........
def plot(self,radius=1, orientation=1, cyclic_order_0=None, cyclic_order_1=None,verbose=False):
"""Plot the set of ideal curves on the surface S=S(g,1) of genus g with
one puncture.
The free group has rank N=2g, the trees T0 and T1 are roses
transverse to a maximal set of ideal curves on S. The convex
core is transverse to the two collections of curves: vertices
are connected components of the complement of the union of the
two sets of curves, edges are arcs separating two regions and
squares are around intersections points of curves.
For instance T0 can be set to be the rose with the trivial
marking, while T1 is obtained from T0 by applying a mapping
class (and not a general automorphism). The embedding of the
mapping class group is that generated by the
``surface_dehn_twist()`` method of the ``FreeGroup`` class.
The set of ideal curves of T0 is drawn as the boundary of a
regular 2N-gone, and the set of ideal curves of T1 is drawn
inside this 2N-gone.
INPUT:
- ``radius``: (default 1) the radius of the regular 2N-gone
which is the fondamental domain of the surface.
-``cyclic_order_0``: (default None) List of edges outgoing
from the sole vertex of T0 ordered according to the embedding
in the surface. A typical value in rank 4, compatible with
the definition of ``FreeGroup.surface_dehn_twist()`` is :
['A','B','a','C','D','c','d','b']
-``cyclic_order_1``: (default None) List of edges outgoing
from the sole vertex of T1 ordered according to the embedding
in the surface.
EXAMPLES::
sage: F=FreeGroup(4)
sage: phi=mul([F.surface_dehn_twist(i) for i in [2,1,1,4]])
sage: C=ConvexCore(phi)
sage: C.plot_ideal_curve_diagram(cyclic_order_0=['A','B','a','C','D','c','d','b'])
"""
from sage.plot.graphics import Graphics
from sage.plot.line import Line
from sage.plot.arrow import Arrow
T0=self.tree(0)
T1=self.tree(1)
A0=T0.alphabet()
N=len(A0)
A1=T1.alphabet()
# Let ``self`` be the convex core of trees T0 and T1. T0 and
# T1 need to be roses. The trees T0 and T1 may be given as
# embedded inside the surface. In this case the edges outgoing
# from the sole vertex are cyclically ordered.
if len(T0.vertices())!=1:
raise ValueError('The tree on side 0 must be a rose')
if len(T1.vertices())!=1:
raise ValueError('The tree on side 1 must be a rose')
if cyclic_order_0 is None:
cyclic_order_0=getattr(T0,'cyclic_order',None)
if cyclic_order_1 is None:
cyclic_order_1=getattr(T1,'cyclic_order',None)
if verbose:
if cyclic_order_0 is not None:
print "The tree on side 0 is embedded in the surface:",cyclic_order_0
else:
print "The tree on side 0 is not embedded in the surface, we will try to guess an embedding"
if cyclic_order_1 is not None:
print "The tree on side 1 is embedded in the surface:",cyclic_order_1
else:
print "The tree on side 1 is not embedded in the surface, we will try to guess an embedding"
squares=self.squares()
# Coherent orientation of the squares
orientation=self.squares_orientation(orientation=orientation,verbose=verbose and verbose>1 and verbose-1)
if verbose:
print "Orientation of the squares:"
if verbose>1:
for i,sq in enumerate(squares):
print i,":",sq,":",orientation[i]
boundary=self.surface_boundary(orientation=orientation,verbose=verbose and verbose>1 and verbose-1)
if verbose:
print "Edges of the boundary:"
#.........这里部分代码省略.........
请发表评论