Skip to content
This repository has been archived by the owner on Jan 30, 2023. It is now read-only.

Commit

Permalink
Reviewer changes simplifying plot implementation, more robust inputs,…
Browse files Browse the repository at this point in the history
… and misc doc changes.
  • Loading branch information
Travis Scrimshaw committed Feb 20, 2022
1 parent 767722e commit 900c36c
Show file tree
Hide file tree
Showing 4 changed files with 265 additions and 251 deletions.
46 changes: 33 additions & 13 deletions src/sage/geometry/hyperbolic_space/hyperbolic_geodesic.py
Original file line number Diff line number Diff line change
Expand Up @@ -696,15 +696,27 @@ def complete(self):
::
sage: KM = H.KM()
sage: KM.get_geodesic(-I, 1).complete()
sage: KM.get_geodesic((0,0), (0,1/2)).complete()
Geodesic in KM from (0, -1) to (0, 1)
.. PLOT::
g = HyperbolicPlane().KM().get_geodesic(CC(0,-1), CC(0, 1))
g = HyperbolicPlane().KM().get_geodesic(CC(0,0), CC(0, 0.5))
h = g.complete()
sphinx_plot(g.plot()+h.plot(linestyle='dashed'))
::
sage: KM.get_geodesic(-I, 1).complete()
Geodesic in KM from -I to 1
.. PLOT::
g = HyperbolicPlane().KM().get_geodesic(CC(0,-1), CC(1, 0))
h = g.complete()
sphinx_plot(g.plot()+h.plot(linestyle='dashed'))
::
sage: HM = H.HM()
Expand Down Expand Up @@ -2177,11 +2189,9 @@ class HyperbolicGeodesicPD(HyperbolicGeodesic):
g = PD.get_geodesic(I,-I/2)
h = PD.get_geodesic(-0.5+I*0.5,0.5+I*0.5)
sphinx_plot(g.plot()+h.plot(color='green'))
"""

def plot(self, boundary=True, **options):

r"""
Plot ``self``.
Expand Down Expand Up @@ -2279,13 +2289,11 @@ class HyperbolicGeodesicKM(HyperbolicGeodesic):
EXAMPLES::
sage: KM = HyperbolicPlane().KM()
sage: g = KM.get_geodesic(KM.get_point((0.1,0.9)), KM.get_point((-0.1,-0.9)))
sage: g = KM.get_geodesic((0.1,0.9),(-0.1,-0.9))
sage: h = KM.get_geodesic((-0.707106781,-0.707106781),(0.707106781,-0.707106781))
sage: P = g.plot(color='orange')+h.plot(); P # optional - sage.plot
Graphics object consisting of 4 graphics primitives
.. PLOT::
KM = HyperbolicPlane().KM()
Expand Down Expand Up @@ -2315,7 +2323,11 @@ def plot(self, boundary=True, **options):
opts = {'axes': False, 'aspect_ratio': 1}
opts.update(self.graphics_options())
opts.update(options)
end_1, end_2 = [CC(k.coordinates()) for k in self.endpoints()]
def map_pt(pt):
if pt in CC:
return CC(pt)
return CC(*pt)
end_1, end_2 = [map_pt(k.coordinates()) for k in self.endpoints()]
pic = bezier_path([[(real(end_1), imag(end_1)), (real(end_2), imag(end_2))]], **opts)
if boundary:
pic += self._model.get_background_graphic()
Expand All @@ -2338,7 +2350,6 @@ class HyperbolicGeodesicHM(HyperbolicGeodesic):
EXAMPLES::
sage: from sage.geometry.hyperbolic_space.hyperbolic_geodesic import *
sage: HM = HyperbolicPlane().HM()
sage: p1 = HM.get_point((4, -4, sqrt(33)))
sage: p2 = HM.get_point((-3,-3,sqrt(19)))
Expand All @@ -2356,12 +2367,23 @@ class HyperbolicGeodesicHM(HyperbolicGeodesic):
"""
def _plot_vertices(self, points=75):
r"""
Return ``self`` plotting vertices in R^3.
Return ``self`` plotting vertices in `\RR^3`.
Auxiliary function needed to plot polygons.
"""
EXAMPLES::
sage: HM = HyperbolicPlane().HM()
sage: p1 = HM.get_point((4, -4, sqrt(33)))
sage: p2 = HM.get_point((-3,-3,sqrt(19)))
sage: g = HM.get_geodesic(p1, p2)
sage: g._plot_vertices(5)
[(4.0, -4.0, 5.744562646538029),
(1.3632131724692114, -1.6370738298435326, 2.353372235315133),
(0.13856858387448234, -0.9699800871213693, 1.4000223647674197),
(-0.9425338542843988, -1.3076813974501533, 1.8969450977056184),
(-3.0, -3.0, 4.358898943540652)]
"""
from sage.plot.misc import setup_for_eval_on_grid
from sage.arith.srange import xsrange

Expand All @@ -2380,15 +2402,13 @@ def _plot_vertices(self, points=75):
# Now v1 and v2 are Lorentz orthogonal, and |v1| = -1, |v2|=1
# That is, v1 is unit timelike and v2 is unit spacelike.
# This means that cosh(x)*v1 + sinh(x)*v2 is unit timelike.
hyperbola = cosh(x)*v1 + sinh(x)*v2
hyperbola = tuple(cosh(x)*v1 + sinh(x)*v2)
endtime = arcsinh(v2_ldot_u2)
# mimic the function _parametric_plot3d_curve using a bezier3d instead of a line3d
# this is required in order to be able to plot hyperbolic polygons whithin the plot library
g, ranges = setup_for_eval_on_grid(hyperbola, [(x, 0, endtime)], points)
f_x, f_y, f_z = g
points = [(f_x(u), f_y(u), f_z(u)) for u in xsrange(*ranges[0], include_endpoint=True)]
# convert points to a path3d
points = list(points)
return points

def plot(self, show_hyperboloid=True, **graphics_options):
Expand Down
50 changes: 37 additions & 13 deletions src/sage/geometry/hyperbolic_space/hyperbolic_model.py
Original file line number Diff line number Diff line change
Expand Up @@ -109,8 +109,8 @@

lazy_import('sage.modules.free_module_element', 'vector')

# ####################################################################
# Abstract model
#####################################################################
## Abstract model


class HyperbolicModel(Parent, UniqueRepresentation, BindableClass):
Expand Down Expand Up @@ -776,7 +776,7 @@ def isometry_from_fixed_points(self, repel, attract):


#####################################################################
# Upper half plane model
## Upper half plane model

class HyperbolicModelUHP(HyperbolicModel):
r"""
Expand Down Expand Up @@ -854,7 +854,11 @@ def point_in_model(self, p):
"""
if isinstance(p, HyperbolicPoint):
return p.is_boundary()
return bool(imag(CC(p)) > 0)
if p in CC:
p = CC(p)
else:
p = CC(*p)
return bool(imag(p) > 0)

def boundary_point_in_model(self, p):
r"""
Expand Down Expand Up @@ -888,7 +892,11 @@ def boundary_point_in_model(self, p):
"""
if isinstance(p, HyperbolicPoint):
return p.is_boundary()
im = abs(imag(CC(p)).n())
if p in CC:
p = CC(p)
else:
p = CC(*p)
im = abs(imag(p).n())
return (im < EPSILON) or bool(p == infinity)

def isometry_in_model(self, A):
Expand Down Expand Up @@ -1142,8 +1150,8 @@ def _moebius_sending(z, w): # UHP
B = HyperbolicGeodesicUHP._crossratio_matrix(w[0], w[1], w[2])
return B.inverse() * A

# ####################################################################
# Poincaré disk model
#####################################################################
## Poincaré disk model


class HyperbolicModelPD(HyperbolicModel):
Expand Down Expand Up @@ -1210,7 +1218,11 @@ def point_in_model(self, p):
"""
if isinstance(p, HyperbolicPoint):
return p.is_boundary()
return bool(abs(CC(p)) < 1)
if p in CC:
p = CC(p)
else:
p = CC(*p)
return bool(abs(p) < 1)

def boundary_point_in_model(self, p):
r"""
Expand All @@ -1228,7 +1240,11 @@ def boundary_point_in_model(self, p):
"""
if isinstance(p, HyperbolicPoint):
return p.is_boundary()
return bool(abs(abs(CC(p)) - 1) < EPSILON)
if p in CC:
p = CC(p)
else:
p = CC(*p)
return bool(abs(abs(p) - 1) < EPSILON)

def isometry_in_model(self, A):
r"""
Expand Down Expand Up @@ -1264,7 +1280,7 @@ def get_background_graphic(self, **bdry_options):


#####################################################################
# Klein disk model
## Klein disk model

class HyperbolicModelKM(HyperbolicModel):
r"""
Expand Down Expand Up @@ -1327,8 +1343,12 @@ def point_in_model(self, p):
"""
if isinstance(p, HyperbolicPoint):
return p.is_boundary()
if p in CC:
p = CC(p)
else:
p = CC(*p)
# return len(p) == 2 and bool(p[0]**2 + p[1]**2 < 1)
return bool(abs(CC(p)) < 1)
return bool(abs(p) < 1)

def boundary_point_in_model(self, p):
r"""
Expand All @@ -1347,8 +1367,12 @@ def boundary_point_in_model(self, p):
"""
if isinstance(p, HyperbolicPoint):
return p.is_boundary()
if p in CC:
p = CC(p)
else:
p = CC(*p)
# return len(p) == 2 and bool(abs(p[0]**2 + p[1]**2 - 1) < EPSILON)
return bool(abs(abs(CC(p)) - 1) < EPSILON)
return bool(abs(abs(p) - 1) < EPSILON)

def isometry_in_model(self, A):
r"""
Expand Down Expand Up @@ -1379,7 +1403,7 @@ def get_background_graphic(self, **bdry_options):
return circle((0, 0), 1, axes=False, color='black')

#####################################################################
# Hyperboloid model
## Hyperboloid model


class HyperbolicModelHM(HyperbolicModel):
Expand Down
Loading

0 comments on commit 900c36c

Please sign in to comment.