Define the base field.
{{{id=3| K.Note that sqrt2 now stores the actual square root of 2.
{{{id=8| RR(sqrt2) /// 1.41421356237309 }}}The following is the parent for polygons with coordinates in the field K.
Remarks:
To construct a polygon, use the parent to build the parent. Passing a list of edge vectors will produce the polygon. The edge vectors must sum to zero.
{{{id=5| p = Polygons(K)([(1,0), (sqrt2/2, sqrt2/2), (0, 1), (-sqrt2/2, sqrt2/2), (-1,0), (-sqrt2/2, -sqrt2/2), (0, -1), (sqrt2/2, -sqrt2/2) ]) print(p) /// Polygon: (0, 0), (1, 0), (1/2*sqrt2 + 1, 1/2*sqrt2), (1/2*sqrt2 + 1, 1/2*sqrt2 + 1), (1, sqrt2 + 1), (0, sqrt2 + 1), (-1/2*sqrt2, 1/2*sqrt2 + 1), (-1/2*sqrt2, 1/2*sqrt2) }}} {{{id=10| p.plot() /// }}}A translation surface is a gluing of one or more polygons with edge identifications glued by translation.
We will construct the octagon with opposite edges identified. Edges of our polygons are indexed by $[0, 1, 2, ..., n-1]$ where n is the number of sides of the polygon. An edge of a polygon is indexed by a pair $(p,e)$ where $p$ is a polygon index and $e$ is an edge index.
The gluings are specified as a list of pairs of edges of polygons. For example we want to the bottom edge $(0,0)$ to the top edge $(0,4)$.
Define a surface built from polygons with vertices in K^2.
{{{id=23| surface = Surface_list(K) /// }}}We add the polygon p to the surface. It gets a label, in this case 0.
{{{id=60| surface.add_polygon(p) /// 0 }}}We now glue the edges together. The line below says "glue edge e of polygon 0 to edge e+4 of polygon 0."
{{{id=64| for e in range(4): surface.change_edge_gluing(0,e,0,e+4) /// }}}We want to view the surface we built as a translation surface.
{{{id=24| s=TranslationSurface(surface) /// }}}Run some tests to make sure the surface is okay.
{{{id=65| TestSuite(s).run(verbose=True) /// running ._test_base_label() . . . pass running ._test_base_ring() . . . pass running ._test_category() . . . pass running ._test_edge_matrix() . . . pass running ._test_gluings() . . . pass running ._test_not_implemented_methods() . . . pass running ._test_override() . . . pass running ._test_pickling() . . . pass running ._test_polygons() . . . pass }}}A graphical surface is a version of a surface which stores some extra data that can be used to draw the surface.
{{{id=28| gs=s.graphical_surface() /// }}} {{{id=29| gs.plot() /// }}}Construct the tangent vector in polygon 0 based at (0,0) pointed pointed in direction (1,2).
{{{id=54| v=s.tangent_vector(0,(0,0),(1,2)) print(v) /// SimilaritySurfaceTangentVector in polygon 0 based at (0, 0) with vector (1, 2) }}}You can convert the tangent vector to a StraightLineTrajectory, which is a finite list of intersections of the straight-line trajectory with the polygons defining the surface.
{{{id=35| traj=v.straight_line_trajectory() /// }}} {{{id=58| print traj /// Straight line trajectory made of 1 segments from (0, 0) in polygon 0 to (1/3*sqrt2 + 2/3, 2/3*sqrt2 + 4/3) in polygon 0 }}} {{{id=57| gs.plot()+traj.graphical_trajectory(gs).plot() /// }}}The flow(n) method constructs the next n segments obtained by straight-line flowing forward and intersecting with the provided polygons. It will just stop if a singularity is hit.
{{{id=39| traj.flow(100) print(traj) print("It has length: "+str(traj.combinatorial_length())) /// Straight line trajectory made of 17 segments from (0, 0) in polygon 0 to (0, sqrt2 + 1) in polygon 0 It has length: 17 }}} {{{id=43| traj.is_saddle_connection() /// True }}}We can draw a picture of this saddle connection by converting it to a GraphicalStraightLineTrajectory.
{{{id=44| gtraj = traj.graphical_trajectory(gs) /// }}} {{{id=53| gs.plot()+gtraj.plot() /// }}}