snappy 3.1.1__cp38-cp38-win_amd64.whl → 3.2__cp38-cp38-win_amd64.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.
- snappy/CyOpenGL.cp38-win_amd64.pyd +0 -0
- snappy/SnapPy.cp38-win_amd64.pyd +0 -0
- snappy/SnapPyHP.cp38-win_amd64.pyd +0 -0
- snappy/__init__.py +299 -402
- snappy/app.py +70 -20
- snappy/browser.py +18 -17
- snappy/canonical.py +249 -0
- snappy/{verify/cusp_shapes.py → cusps/__init__.py} +8 -18
- snappy/cusps/cusp_area_matrix.py +101 -0
- snappy/{verify/cusp_areas.py → cusps/cusp_areas_from_matrix.py} +23 -39
- snappy/cusps/maximal_cusp_area_matrix.py +136 -0
- snappy/cusps/test.py +21 -0
- snappy/cusps/trig_cusp_area_matrix.py +63 -0
- snappy/database.py +10 -9
- snappy/decorated_isosig.py +337 -114
- snappy/dev/extended_ptolemy/complexVolumesClosed.py +40 -7
- snappy/dev/extended_ptolemy/extended.py +3 -3
- snappy/dev/extended_ptolemy/phc_wrapper.py +10 -10
- snappy/dev/vericlosed/oneVertexTruncatedComplex.py +1 -1
- snappy/doc/_images/m004_paper_plane_on_systole.jpg +0 -0
- snappy/doc/_images/m125_paper_plane.jpg +0 -0
- snappy/doc/_images/o9_00000_systole_paper_plane.jpg +0 -0
- snappy/doc/_images/o9_00000_systole_paper_plane_closer.jpg +0 -0
- snappy/doc/_sources/additional_classes.rst.txt +40 -40
- snappy/doc/_sources/bugs.rst.txt +14 -14
- snappy/doc/_sources/censuses.rst.txt +51 -51
- snappy/doc/_sources/credits.rst.txt +75 -75
- snappy/doc/_sources/development.rst.txt +259 -239
- snappy/doc/_sources/index.rst.txt +182 -115
- snappy/doc/_sources/installing.rst.txt +247 -264
- snappy/doc/_sources/manifold.rst.txt +6 -6
- snappy/doc/_sources/manifoldhp.rst.txt +46 -46
- snappy/doc/_sources/news.rst.txt +355 -283
- snappy/doc/_sources/other.rst.txt +25 -25
- snappy/doc/_sources/platonic_census.rst.txt +20 -20
- snappy/doc/_sources/plink.rst.txt +102 -102
- snappy/doc/_sources/ptolemy.rst.txt +66 -66
- snappy/doc/_sources/ptolemy_classes.rst.txt +42 -42
- snappy/doc/_sources/ptolemy_examples1.rst.txt +298 -297
- snappy/doc/_sources/ptolemy_examples2.rst.txt +363 -363
- snappy/doc/_sources/ptolemy_examples3.rst.txt +301 -301
- snappy/doc/_sources/ptolemy_examples4.rst.txt +61 -61
- snappy/doc/_sources/ptolemy_prelim.rst.txt +105 -105
- snappy/doc/_sources/screenshots.rst.txt +21 -21
- snappy/doc/_sources/snap.rst.txt +87 -87
- snappy/doc/_sources/snappy.rst.txt +28 -28
- snappy/doc/_sources/spherogram.rst.txt +103 -103
- snappy/doc/_sources/todo.rst.txt +47 -47
- snappy/doc/_sources/triangulation.rst.txt +11 -11
- snappy/doc/_sources/tutorial.rst.txt +49 -49
- snappy/doc/_sources/verify.rst.txt +210 -150
- snappy/doc/_sources/verify_internals.rst.txt +79 -90
- snappy/doc/_static/basic.css +924 -902
- snappy/doc/_static/css/badge_only.css +1 -1
- snappy/doc/_static/css/theme.css +1 -1
- snappy/doc/_static/doctools.js +1 -1
- snappy/doc/_static/documentation_options.js +12 -13
- snappy/doc/_static/fonts/Lato/lato-bold.eot +0 -0
- snappy/doc/_static/fonts/Lato/lato-bold.ttf +0 -0
- snappy/doc/_static/fonts/Lato/lato-bold.woff +0 -0
- snappy/doc/_static/fonts/Lato/lato-bold.woff2 +0 -0
- snappy/doc/_static/fonts/Lato/lato-bolditalic.eot +0 -0
- snappy/doc/_static/fonts/Lato/lato-bolditalic.ttf +0 -0
- snappy/doc/_static/fonts/Lato/lato-bolditalic.woff +0 -0
- snappy/doc/_static/fonts/Lato/lato-bolditalic.woff2 +0 -0
- snappy/doc/_static/fonts/Lato/lato-italic.eot +0 -0
- snappy/doc/_static/fonts/Lato/lato-italic.ttf +0 -0
- snappy/doc/_static/fonts/Lato/lato-italic.woff +0 -0
- snappy/doc/_static/fonts/Lato/lato-italic.woff2 +0 -0
- snappy/doc/_static/fonts/Lato/lato-regular.eot +0 -0
- snappy/doc/_static/fonts/Lato/lato-regular.ttf +0 -0
- snappy/doc/_static/fonts/Lato/lato-regular.woff +0 -0
- snappy/doc/_static/fonts/Lato/lato-regular.woff2 +0 -0
- snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-bold.eot +0 -0
- snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-bold.ttf +0 -0
- snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-bold.woff +0 -0
- snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-bold.woff2 +0 -0
- snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-regular.eot +0 -0
- snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-regular.ttf +0 -0
- snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-regular.woff +0 -0
- snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-regular.woff2 +0 -0
- snappy/doc/_static/js/versions.js +228 -0
- snappy/doc/_static/language_data.js +199 -199
- snappy/doc/_static/pygments.css +74 -73
- snappy/doc/_static/searchtools.js +125 -71
- snappy/doc/_static/snappy_furo.css +33 -33
- snappy/doc/_static/snappy_sphinx_rtd_theme.css +42 -42
- snappy/doc/_static/sphinx_highlight.js +13 -3
- snappy/doc/additional_classes.html +1499 -1330
- snappy/doc/bugs.html +131 -134
- snappy/doc/censuses.html +426 -445
- snappy/doc/credits.html +180 -183
- snappy/doc/development.html +383 -363
- snappy/doc/genindex.html +1330 -1409
- snappy/doc/index.html +261 -206
- snappy/doc/installing.html +345 -363
- snappy/doc/manifold.html +3451 -2839
- snappy/doc/manifoldhp.html +179 -182
- snappy/doc/news.html +387 -329
- snappy/doc/objects.inv +0 -0
- snappy/doc/other.html +160 -162
- snappy/doc/platonic_census.html +374 -377
- snappy/doc/plink.html +209 -212
- snappy/doc/ptolemy.html +253 -255
- snappy/doc/ptolemy_classes.html +1143 -1146
- snappy/doc/ptolemy_examples1.html +408 -410
- snappy/doc/ptolemy_examples2.html +470 -473
- snappy/doc/ptolemy_examples3.html +413 -416
- snappy/doc/ptolemy_examples4.html +194 -197
- snappy/doc/ptolemy_prelim.html +247 -250
- snappy/doc/py-modindex.html +164 -167
- snappy/doc/screenshots.html +140 -142
- snappy/doc/search.html +134 -137
- snappy/doc/searchindex.js +1 -1
- snappy/doc/snap.html +201 -204
- snappy/doc/snappy.html +180 -182
- snappy/doc/spherogram.html +1210 -1213
- snappy/doc/todo.html +165 -168
- snappy/doc/triangulation.html +1583 -1474
- snappy/doc/tutorial.html +158 -161
- snappy/doc/verify.html +329 -275
- snappy/doc/verify_internals.html +1234 -1691
- snappy/drilling/__init__.py +153 -235
- snappy/drilling/barycentric.py +103 -0
- snappy/drilling/constants.py +0 -2
- snappy/drilling/crush.py +56 -130
- snappy/drilling/cusps.py +12 -6
- snappy/drilling/debug.py +2 -1
- snappy/drilling/exceptions.py +7 -40
- snappy/drilling/moves.py +302 -243
- snappy/drilling/perturb.py +63 -37
- snappy/drilling/shorten.py +36 -0
- snappy/drilling/subdivide.py +0 -5
- snappy/drilling/test.py +23 -0
- snappy/drilling/test_cases.py +126 -0
- snappy/drilling/tracing.py +9 -37
- snappy/exceptions.py +18 -5
- snappy/exterior_to_link/barycentric_geometry.py +2 -4
- snappy/exterior_to_link/main.py +8 -7
- snappy/exterior_to_link/mcomplex_with_link.py +2 -2
- snappy/exterior_to_link/rational_linear_algebra.py +1 -1
- snappy/exterior_to_link/rational_linear_algebra_wrapped.py +1 -1
- snappy/exterior_to_link/test.py +21 -33
- snappy/geometric_structure/__init__.py +212 -0
- snappy/geometric_structure/cusp_neighborhood/__init__.py +3 -0
- snappy/geometric_structure/cusp_neighborhood/complex_cusp_cross_section.py +697 -0
- snappy/geometric_structure/cusp_neighborhood/cusp_cross_section_base.py +484 -0
- snappy/geometric_structure/cusp_neighborhood/exceptions.py +42 -0
- snappy/geometric_structure/cusp_neighborhood/real_cusp_cross_section.py +298 -0
- snappy/geometric_structure/cusp_neighborhood/tiles_for_cusp_neighborhood.py +159 -0
- snappy/geometric_structure/cusp_neighborhood/vertices.py +32 -0
- snappy/geometric_structure/geodesic/__init__.py +0 -0
- snappy/geometric_structure/geodesic/add_core_curves.py +152 -0
- snappy/geometric_structure/geodesic/avoid_core_curves.py +369 -0
- snappy/geometric_structure/geodesic/canonical_keys.py +52 -0
- snappy/geometric_structure/geodesic/check_away_from_core_curve.py +60 -0
- snappy/geometric_structure/geodesic/constants.py +6 -0
- snappy/geometric_structure/geodesic/exceptions.py +22 -0
- snappy/{drilling → geometric_structure/geodesic}/fixed_points.py +34 -9
- snappy/{drilling/geodesic_info.py → geometric_structure/geodesic/geodesic_start_point_info.py} +139 -180
- snappy/geometric_structure/geodesic/graph_trace_helper.py +67 -0
- snappy/geometric_structure/geodesic/line.py +30 -0
- snappy/geometric_structure/geodesic/multiplicity.py +127 -0
- snappy/geometric_structure/geodesic/tiles_for_geodesic.py +101 -0
- snappy/geometric_structure/test.py +22 -0
- snappy/gui.py +23 -13
- snappy/horoviewer.py +7 -7
- snappy/hyperboloid/__init__.py +96 -31
- snappy/hyperboloid/distances.py +245 -0
- snappy/hyperboloid/horoball.py +19 -0
- snappy/hyperboloid/line.py +35 -0
- snappy/hyperboloid/point.py +9 -0
- snappy/hyperboloid/triangle.py +29 -0
- snappy/isometry_signature.py +382 -0
- snappy/len_spec/__init__.py +596 -0
- snappy/len_spec/geodesic_info.py +110 -0
- snappy/len_spec/geodesic_key_info_dict.py +117 -0
- snappy/len_spec/geodesic_piece.py +143 -0
- snappy/len_spec/geometric_structure.py +182 -0
- snappy/len_spec/geometry.py +80 -0
- snappy/len_spec/length_spectrum_geodesic_info.py +170 -0
- snappy/len_spec/spine.py +206 -0
- snappy/len_spec/test.py +24 -0
- snappy/len_spec/test_cases.py +69 -0
- snappy/len_spec/tile.py +275 -0
- snappy/len_spec/word.py +86 -0
- snappy/math_basics.py +39 -13
- snappy/matrix.py +52 -9
- snappy/number.py +12 -6
- snappy/numeric_output_checker.py +2 -3
- snappy/pari.py +8 -4
- snappy/phone_home.py +2 -1
- snappy/polyviewer.py +8 -8
- snappy/ptolemy/__init__.py +1 -1
- snappy/ptolemy/component.py +2 -2
- snappy/ptolemy/coordinates.py +25 -25
- snappy/ptolemy/findLoops.py +9 -9
- snappy/ptolemy/manifoldMethods.py +27 -29
- snappy/ptolemy/polynomial.py +50 -57
- snappy/ptolemy/processFileBase.py +60 -0
- snappy/ptolemy/ptolemyVariety.py +109 -41
- snappy/ptolemy/reginaWrapper.py +4 -4
- snappy/ptolemy/rur.py +1 -1
- snappy/ptolemy/solutionsToPrimeIdealGroebnerBasis.py +9 -9
- snappy/ptolemy/test.py +99 -54
- snappy/ptolemy/utilities.py +1 -1
- snappy/raytracing/__init__.py +64 -0
- snappy/raytracing/additional_horospheres.py +64 -0
- snappy/raytracing/additional_len_spec_choices.py +63 -0
- snappy/raytracing/cohomology_fractal.py +0 -3
- snappy/raytracing/eyeball.py +123 -0
- snappy/raytracing/finite_raytracing_data.py +17 -17
- snappy/raytracing/finite_viewer.py +15 -15
- snappy/raytracing/geodesic_tube_info.py +93 -63
- snappy/raytracing/geodesics.py +94 -64
- snappy/raytracing/geodesics_window.py +56 -34
- snappy/raytracing/gui_utilities.py +21 -6
- snappy/raytracing/hyperboloid_navigation.py +29 -4
- snappy/raytracing/hyperboloid_utilities.py +73 -73
- snappy/raytracing/ideal_raytracing_data.py +121 -91
- snappy/raytracing/inside_viewer.py +199 -66
- snappy/raytracing/pack.py +22 -0
- snappy/raytracing/raytracing_data.py +37 -25
- snappy/raytracing/raytracing_view.py +70 -65
- snappy/raytracing/shaders/Eye.png +0 -0
- snappy/raytracing/shaders/NonGeometric.png +0 -0
- snappy/raytracing/shaders/__init__.py +39 -3
- snappy/raytracing/shaders/fragment.glsl +451 -133
- snappy/raytracing/test.py +29 -0
- snappy/raytracing/tooltip.py +146 -0
- snappy/raytracing/upper_halfspace_utilities.py +42 -9
- snappy/sage_helper.py +67 -134
- snappy/settings.py +90 -77
- snappy/shell.py +2 -0
- snappy/snap/character_varieties.py +2 -2
- snappy/snap/find_field.py +4 -3
- snappy/snap/fundamental_polyhedron.py +2 -2
- snappy/snap/kernel_structures.py +5 -1
- snappy/snap/nsagetools.py +9 -8
- snappy/snap/peripheral/dual_cellulation.py +4 -3
- snappy/snap/peripheral/peripheral.py +2 -2
- snappy/snap/peripheral/surface.py +5 -5
- snappy/snap/peripheral/test.py +1 -1
- snappy/snap/polished_reps.py +8 -8
- snappy/snap/slice_obs_HKL.py +16 -14
- snappy/snap/t3mlite/arrow.py +3 -3
- snappy/snap/t3mlite/edge.py +3 -3
- snappy/snap/t3mlite/homology.py +2 -2
- snappy/snap/t3mlite/mcomplex.py +3 -3
- snappy/snap/t3mlite/simplex.py +12 -0
- snappy/snap/t3mlite/spun.py +18 -17
- snappy/snap/t3mlite/test_vs_regina.py +4 -4
- snappy/snap/test.py +37 -53
- snappy/snap/utilities.py +4 -5
- snappy/test.py +121 -138
- snappy/test_cases.py +263 -0
- snappy/testing.py +131 -0
- snappy/tiling/__init__.py +2 -0
- snappy/tiling/canonical_key_dict.py +59 -0
- snappy/tiling/dict_based_set.py +79 -0
- snappy/tiling/floor.py +49 -0
- snappy/tiling/hyperboloid_dict.py +54 -0
- snappy/tiling/iter_utils.py +78 -0
- snappy/tiling/lifted_tetrahedron.py +22 -0
- snappy/tiling/lifted_tetrahedron_set.py +54 -0
- snappy/tiling/real_hash_dict.py +164 -0
- snappy/tiling/test.py +23 -0
- snappy/tiling/tile.py +215 -0
- snappy/tiling/triangle.py +33 -0
- snappy/tkterminal.py +113 -84
- snappy/twister/main.py +1 -7
- snappy/twister/twister_core.cp38-win_amd64.pyd +0 -0
- snappy/upper_halfspace/__init__.py +78 -17
- snappy/verify/__init__.py +3 -7
- snappy/verify/{verifyCanonical.py → canonical.py} +78 -70
- snappy/verify/complex_volume/adjust_torsion.py +1 -2
- snappy/verify/complex_volume/closed.py +13 -13
- snappy/verify/complex_volume/cusped.py +6 -6
- snappy/verify/complex_volume/extended_bloch.py +5 -8
- snappy/verify/{cuspTranslations.py → cusp_translations.py} +1 -1
- snappy/verify/edge_equations.py +80 -0
- snappy/verify/exceptions.py +0 -55
- snappy/verify/{verifyHyperbolicity.py → hyperbolicity.py} +3 -3
- snappy/verify/interval_newton_shapes_engine.py +7 -5
- snappy/verify/interval_tree.py +5 -5
- snappy/verify/krawczyk_shapes_engine.py +17 -18
- snappy/verify/maximal_cusp_area_matrix/__init__.py +7 -74
- snappy/verify/maximal_cusp_area_matrix/cusp_tiling_engine.py +3 -4
- snappy/verify/maximal_cusp_area_matrix/cusp_translate_engine.py +1 -1
- snappy/verify/{realAlgebra.py → real_algebra.py} +1 -1
- snappy/verify/shapes.py +5 -3
- snappy/verify/short_slopes.py +39 -41
- snappy/verify/{squareExtensions.py → square_extensions.py} +14 -11
- snappy/verify/test.py +57 -60
- snappy/verify/upper_halfspace/extended_matrix.py +1 -1
- snappy/verify/upper_halfspace/finite_point.py +3 -4
- snappy/verify/upper_halfspace/ideal_point.py +9 -9
- snappy/verify/volume.py +2 -2
- snappy/version.py +2 -2
- {snappy-3.1.1.dist-info → snappy-3.2.dist-info}/METADATA +14 -10
- snappy-3.2.dist-info/RECORD +503 -0
- {snappy-3.1.1.dist-info → snappy-3.2.dist-info}/WHEEL +1 -1
- {snappy-3.1.1.dist-info → snappy-3.2.dist-info}/top_level.txt +6 -1
- snappy/__pycache__/__init__.cpython-38.pyc +0 -0
- snappy/__pycache__/browser.cpython-38.pyc +0 -0
- snappy/__pycache__/cache.cpython-38.pyc +0 -0
- snappy/__pycache__/database.cpython-38.pyc +0 -0
- snappy/__pycache__/db_utilities.cpython-38.pyc +0 -0
- snappy/__pycache__/decorated_isosig.cpython-38.pyc +0 -0
- snappy/__pycache__/exceptions.cpython-38.pyc +0 -0
- snappy/__pycache__/export_stl.cpython-38.pyc +0 -0
- snappy/__pycache__/filedialog.cpython-38.pyc +0 -0
- snappy/__pycache__/gui.cpython-38.pyc +0 -0
- snappy/__pycache__/horoviewer.cpython-38.pyc +0 -0
- snappy/__pycache__/math_basics.cpython-38.pyc +0 -0
- snappy/__pycache__/matrix.cpython-38.pyc +0 -0
- snappy/__pycache__/number.cpython-38.pyc +0 -0
- snappy/__pycache__/numeric_output_checker.cpython-38.pyc +0 -0
- snappy/__pycache__/pari.cpython-38.pyc +0 -0
- snappy/__pycache__/polyviewer.cpython-38.pyc +0 -0
- snappy/__pycache__/sage_helper.cpython-38.pyc +0 -0
- snappy/__pycache__/version.cpython-38.pyc +0 -0
- snappy/doc/_sources/verify_canon.rst.txt +0 -90
- snappy/doc/_static/jquery-3.6.0.js +0 -10881
- snappy/doc/_static/js/html5shiv-printshiv.min.js +0 -4
- snappy/doc/_static/js/html5shiv.min.js +0 -4
- snappy/doc/_static/underscore-1.13.1.js +0 -2042
- snappy/doc/_static/underscore.js +0 -6
- snappy/doc/verify_canon.html +0 -304
- snappy/drilling/__pycache__/__init__.cpython-38.pyc +0 -0
- snappy/drilling/__pycache__/constants.cpython-38.pyc +0 -0
- snappy/drilling/__pycache__/crush.cpython-38.pyc +0 -0
- snappy/drilling/__pycache__/cusps.cpython-38.pyc +0 -0
- snappy/drilling/__pycache__/debug.cpython-38.pyc +0 -0
- snappy/drilling/__pycache__/epsilons.cpython-38.pyc +0 -0
- snappy/drilling/__pycache__/exceptions.cpython-38.pyc +0 -0
- snappy/drilling/__pycache__/fixed_points.cpython-38.pyc +0 -0
- snappy/drilling/__pycache__/geodesic_info.cpython-38.pyc +0 -0
- snappy/drilling/__pycache__/geodesic_tube.cpython-38.pyc +0 -0
- snappy/drilling/__pycache__/geometric_structure.cpython-38.pyc +0 -0
- snappy/drilling/__pycache__/line.cpython-38.pyc +0 -0
- snappy/drilling/__pycache__/moves.cpython-38.pyc +0 -0
- snappy/drilling/__pycache__/peripheral_curves.cpython-38.pyc +0 -0
- snappy/drilling/__pycache__/perturb.cpython-38.pyc +0 -0
- snappy/drilling/__pycache__/quotient_space.cpython-38.pyc +0 -0
- snappy/drilling/__pycache__/spatial_dict.cpython-38.pyc +0 -0
- snappy/drilling/__pycache__/subdivide.cpython-38.pyc +0 -0
- snappy/drilling/__pycache__/tracing.cpython-38.pyc +0 -0
- snappy/drilling/geodesic_tube.py +0 -441
- snappy/drilling/geometric_structure.py +0 -366
- snappy/drilling/line.py +0 -122
- snappy/drilling/quotient_space.py +0 -94
- snappy/drilling/spatial_dict.py +0 -128
- snappy/exterior_to_link/__pycache__/__init__.cpython-38.pyc +0 -0
- snappy/exterior_to_link/__pycache__/barycentric_geometry.cpython-38.pyc +0 -0
- snappy/exterior_to_link/__pycache__/exceptions.cpython-38.pyc +0 -0
- snappy/exterior_to_link/__pycache__/hyp_utils.cpython-38.pyc +0 -0
- snappy/exterior_to_link/__pycache__/link_projection.cpython-38.pyc +0 -0
- snappy/exterior_to_link/__pycache__/main.cpython-38.pyc +0 -0
- snappy/exterior_to_link/__pycache__/mcomplex_with_expansion.cpython-38.pyc +0 -0
- snappy/exterior_to_link/__pycache__/mcomplex_with_link.cpython-38.pyc +0 -0
- snappy/exterior_to_link/__pycache__/mcomplex_with_memory.cpython-38.pyc +0 -0
- snappy/exterior_to_link/__pycache__/pl_utils.cpython-38.pyc +0 -0
- snappy/exterior_to_link/__pycache__/put_in_S3.cpython-38.pyc +0 -0
- snappy/exterior_to_link/__pycache__/rational_linear_algebra.cpython-38.pyc +0 -0
- snappy/exterior_to_link/__pycache__/simplify_to_base_tri.cpython-38.pyc +0 -0
- snappy/exterior_to_link/__pycache__/stored_moves.cpython-38.pyc +0 -0
- snappy/hyperboloid/__pycache__/__init__.cpython-38.pyc +0 -0
- snappy/manifolds/__pycache__/__init__.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/__init__.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/component.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/coordinates.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/fieldExtensions.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/findLoops.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/homology.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/manifoldMethods.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/matrix.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/numericalSolutionsToGroebnerBasis.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/polynomial.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/processComponents.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/processFileBase.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/processFileDispatch.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/processMagmaFile.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/processRurFile.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/ptolemyGeneralizedObstructionClass.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/ptolemyObstructionClass.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/ptolemyVariety.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/ptolemyVarietyPrimeIdealGroebnerBasis.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/rur.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/solutionsToPrimeIdealGroebnerBasis.cpython-38.pyc +0 -0
- snappy/ptolemy/__pycache__/utilities.cpython-38.pyc +0 -0
- snappy/snap/__pycache__/__init__.cpython-38.pyc +0 -0
- snappy/snap/__pycache__/character_varieties.cpython-38.pyc +0 -0
- snappy/snap/__pycache__/fundamental_polyhedron.cpython-38.pyc +0 -0
- snappy/snap/__pycache__/interval_reps.cpython-38.pyc +0 -0
- snappy/snap/__pycache__/kernel_structures.cpython-38.pyc +0 -0
- snappy/snap/__pycache__/mcomplex_base.cpython-38.pyc +0 -0
- snappy/snap/__pycache__/nsagetools.cpython-38.pyc +0 -0
- snappy/snap/__pycache__/polished_reps.cpython-38.pyc +0 -0
- snappy/snap/__pycache__/shapes.cpython-38.pyc +0 -0
- snappy/snap/__pycache__/slice_obs_HKL.cpython-38.pyc +0 -0
- snappy/snap/__pycache__/utilities.cpython-38.pyc +0 -0
- snappy/snap/peripheral/__pycache__/__init__.cpython-38.pyc +0 -0
- snappy/snap/peripheral/__pycache__/dual_cellulation.cpython-38.pyc +0 -0
- snappy/snap/peripheral/__pycache__/link.cpython-38.pyc +0 -0
- snappy/snap/peripheral/__pycache__/peripheral.cpython-38.pyc +0 -0
- snappy/snap/peripheral/__pycache__/surface.cpython-38.pyc +0 -0
- snappy/snap/t3mlite/__pycache__/__init__.cpython-38.pyc +0 -0
- snappy/snap/t3mlite/__pycache__/arrow.cpython-38.pyc +0 -0
- snappy/snap/t3mlite/__pycache__/corner.cpython-38.pyc +0 -0
- snappy/snap/t3mlite/__pycache__/edge.cpython-38.pyc +0 -0
- snappy/snap/t3mlite/__pycache__/face.cpython-38.pyc +0 -0
- snappy/snap/t3mlite/__pycache__/files.cpython-38.pyc +0 -0
- snappy/snap/t3mlite/__pycache__/homology.cpython-38.pyc +0 -0
- snappy/snap/t3mlite/__pycache__/linalg.cpython-38.pyc +0 -0
- snappy/snap/t3mlite/__pycache__/mcomplex.cpython-38.pyc +0 -0
- snappy/snap/t3mlite/__pycache__/perm4.cpython-38.pyc +0 -0
- snappy/snap/t3mlite/__pycache__/simplex.cpython-38.pyc +0 -0
- snappy/snap/t3mlite/__pycache__/spun.cpython-38.pyc +0 -0
- snappy/snap/t3mlite/__pycache__/surface.cpython-38.pyc +0 -0
- snappy/snap/t3mlite/__pycache__/tetrahedron.cpython-38.pyc +0 -0
- snappy/snap/t3mlite/__pycache__/vertex.cpython-38.pyc +0 -0
- snappy/togl/__init__.py +0 -3
- snappy/togl/darwin-tk8.6/Togl2.1/LICENSE +0 -28
- snappy/togl/darwin-tk8.6/Togl2.1/libTogl2.1.dylib +0 -0
- snappy/togl/darwin-tk8.6/Togl2.1/pkgIndex.tcl +0 -5
- snappy/togl/darwin-tk8.7/Togl2.1/LICENSE +0 -28
- snappy/togl/darwin-tk8.7/Togl2.1/libTogl2.1.dylib +0 -0
- snappy/togl/darwin-tk8.7/Togl2.1/pkgIndex.tcl +0 -5
- snappy/togl/linux2-x86_64-tk8.6/Togl2.1/LICENSE +0 -28
- snappy/togl/linux2-x86_64-tk8.6/Togl2.1/libTogl2.1.so +0 -0
- snappy/togl/linux2-x86_64-tk8.6/Togl2.1/pkgIndex.tcl +0 -5
- snappy/togl/win32VC-tk8.6/Togl2.1/LICENSE +0 -28
- snappy/togl/win32VC-tk8.6/Togl2.1/Togl21.dll +0 -0
- snappy/togl/win32VC-tk8.6/Togl2.1/Togl21.lib +0 -0
- snappy/togl/win32VC-tk8.6/Togl2.1/pkgIndex.tcl +0 -6
- snappy/togl/win32VC-x86_64-tk8.6/Togl2.1/LICENSE +0 -28
- snappy/togl/win32VC-x86_64-tk8.6/Togl2.1/Togl21.dll +0 -0
- snappy/togl/win32VC-x86_64-tk8.6/Togl2.1/Togl21.lib +0 -0
- snappy/togl/win32VC-x86_64-tk8.6/Togl2.1/pkgIndex.tcl +0 -6
- snappy/twister/__pycache__/__init__.cpython-38.pyc +0 -0
- snappy/twister/__pycache__/main.cpython-38.pyc +0 -0
- snappy/upper_halfspace/__pycache__/__init__.cpython-38.pyc +0 -0
- snappy/upper_halfspace/__pycache__/ideal_point.cpython-38.pyc +0 -0
- snappy/verify/__pycache__/__init__.cpython-38.pyc +0 -0
- snappy/verify/__pycache__/cuspCrossSection.cpython-38.pyc +0 -0
- snappy/verify/__pycache__/cuspTranslations.cpython-38.pyc +0 -0
- snappy/verify/__pycache__/cusp_areas.cpython-38.pyc +0 -0
- snappy/verify/__pycache__/cusp_shapes.cpython-38.pyc +0 -0
- snappy/verify/__pycache__/exceptions.cpython-38.pyc +0 -0
- snappy/verify/__pycache__/interval_newton_shapes_engine.cpython-38.pyc +0 -0
- snappy/verify/__pycache__/interval_tree.cpython-38.pyc +0 -0
- snappy/verify/__pycache__/krawczyk_shapes_engine.cpython-38.pyc +0 -0
- snappy/verify/__pycache__/realAlgebra.cpython-38.pyc +0 -0
- snappy/verify/__pycache__/shapes.cpython-38.pyc +0 -0
- snappy/verify/__pycache__/short_slopes.cpython-38.pyc +0 -0
- snappy/verify/__pycache__/squareExtensions.cpython-38.pyc +0 -0
- snappy/verify/__pycache__/verifyCanonical.cpython-38.pyc +0 -0
- snappy/verify/__pycache__/verifyHyperbolicity.cpython-38.pyc +0 -0
- snappy/verify/__pycache__/volume.cpython-38.pyc +0 -0
- snappy/verify/complex_volume/__pycache__/__init__.cpython-38.pyc +0 -0
- snappy/verify/complex_volume/__pycache__/adjust_torsion.cpython-38.pyc +0 -0
- snappy/verify/complex_volume/__pycache__/closed.cpython-38.pyc +0 -0
- snappy/verify/complex_volume/__pycache__/compute_ptolemys.cpython-38.pyc +0 -0
- snappy/verify/complex_volume/__pycache__/cusped.cpython-38.pyc +0 -0
- snappy/verify/complex_volume/__pycache__/extended_bloch.cpython-38.pyc +0 -0
- snappy/verify/cuspCrossSection.py +0 -1422
- snappy/verify/maximal_cusp_area_matrix/__pycache__/__init__.cpython-38.pyc +0 -0
- snappy/verify/maximal_cusp_area_matrix/__pycache__/cusp_tiling_engine.cpython-38.pyc +0 -0
- snappy/verify/maximal_cusp_area_matrix/__pycache__/cusp_translate_engine.cpython-38.pyc +0 -0
- snappy/verify/upper_halfspace/__pycache__/__init__.cpython-38.pyc +0 -0
- snappy/verify/upper_halfspace/__pycache__/extended_matrix.cpython-38.pyc +0 -0
- snappy/verify/upper_halfspace/__pycache__/finite_point.cpython-38.pyc +0 -0
- snappy/verify/upper_halfspace/__pycache__/ideal_point.cpython-38.pyc +0 -0
- snappy-3.1.1.dist-info/RECORD +0 -575
- {snappy-3.1.1.dist-info → snappy-3.2.dist-info}/entry_points.txt +0 -0
@@ -0,0 +1,369 @@
|
|
1
|
+
from ...tiling.lifted_tetrahedron import LiftedTetrahedron
|
2
|
+
from ...hyperboloid.line import R13Line
|
3
|
+
from ...hyperboloid.distances import distance_r13_lines, distance_r13_point_line
|
4
|
+
from ...hyperboloid import r13_dot, time_r13_normalise, space_r13_normalise
|
5
|
+
from ...snap.t3mlite import Tetrahedron, simplex
|
6
|
+
from ...math_basics import correct_min, correct_max
|
7
|
+
from ...exceptions import InsufficientPrecisionError
|
8
|
+
from ...matrix import make_identity_matrix
|
9
|
+
|
10
|
+
from .graph_trace_helper import find_lifted_tetrahedra_containing_point
|
11
|
+
from . import constants
|
12
|
+
from . import exceptions
|
13
|
+
|
14
|
+
from typing import Optional, Tuple, Any, Sequence
|
15
|
+
|
16
|
+
"""
|
17
|
+
A geodesic intersecting one core curve:
|
18
|
+
gLLPQcdefeffpvauppb_acbBbBaaBbacbBa(0,0)(0,0)(1,0)
|
19
|
+
|
20
|
+
A geodesic intersecting two core curves:
|
21
|
+
mvLAPvMQQcedggikjlklkloboppbaapuaob_acbdBbBaBaaBCBbacbbb(0,0)(0,0)(1,0)(1,0)
|
22
|
+
"""
|
23
|
+
|
24
|
+
def replace_piece_in_core_curve_tube(
|
25
|
+
lifted_tetrahedron : LiftedTetrahedron,
|
26
|
+
geodesic : R13Line,
|
27
|
+
inverse_lifted_geodesic : R13Line,
|
28
|
+
verified : bool) -> Optional[Sequence[LiftedTetrahedron]]:
|
29
|
+
"""
|
30
|
+
Computes the intersection of the given geodesic with the lifted_tetrahedron.
|
31
|
+
|
32
|
+
If the intersection can be verified to lie entirely in an embedded tube
|
33
|
+
about a (lifted) core curve, then it computes the intersection points of
|
34
|
+
the geodesic with the boundary of the tube and returns lifted tetrahedra
|
35
|
+
guaranteed to contain those intersection points. Otherwise, returns None.
|
36
|
+
|
37
|
+
Note that the function also requires the inverse_lifted_geodesic, that is
|
38
|
+
the geodesic transformed by o13_inverse(lifted_tetrahedron.o13_matrix).
|
39
|
+
This input is redundant but used to speed up the computation.
|
40
|
+
|
41
|
+
There are two applications two this function:
|
42
|
+
|
43
|
+
1. Draw a geodesic intersecting several core curves in the inside view.
|
44
|
+
We cannot draw the infinitely many pieces required to draw the entire
|
45
|
+
geodesic. Thus, we use this function when tiling about the geodesic.
|
46
|
+
The tiling with the one lifted tetrahedron or two lifted tetrahedra
|
47
|
+
containing some point on the geodesic. Once we have a piece of the
|
48
|
+
geodesic completely inside the tube about the core curve, we do not
|
49
|
+
continue with the neighboring tetrahedra. Instead, we graph trace here
|
50
|
+
our way out of the tube and continue tiling on the other side of the
|
51
|
+
tube.
|
52
|
+
|
53
|
+
Technically speaking, this function returns lifted tetrahedra
|
54
|
+
to continue to either side of the intersection of the tube with the
|
55
|
+
geodesic. But the side from which we came will already be marked as
|
56
|
+
visited and quickly be discarded.
|
57
|
+
|
58
|
+
Also note that if the geodesic intersects only one core curve, this
|
59
|
+
function could just drop the piece instead of continuing on the other
|
60
|
+
side of the intersection of the geodesic with the core curve. That is
|
61
|
+
because we are approaching this intersection from both sides already.
|
62
|
+
|
63
|
+
Thus, to really test this function in the inside view, one has two
|
64
|
+
have an example of a geodesic intersecting at least two distinct
|
65
|
+
core curves.
|
66
|
+
|
67
|
+
2. Arguably, the more important application is for de-duplicating geodesics
|
68
|
+
during the length spectrum computation.
|
69
|
+
|
70
|
+
This de-duplication works by computing the intersection of the geodesic
|
71
|
+
with the tetrahedra in the fundamental domain. That is, we consider all
|
72
|
+
lifts of the geodesic in H^3 and see how they intersect the fundamental
|
73
|
+
domain.
|
74
|
+
|
75
|
+
We do this again by tiling about the geodesic in H^3.
|
76
|
+
|
77
|
+
We do not need all the intersections of the geodesic with the tetrahedra
|
78
|
+
in the fundamental domain. In particular, we can drop all the pieces of
|
79
|
+
geodesic completely contained in a tube about a core curve. Provided that
|
80
|
+
the system of tubes we pick is embedded. This is because a geodesic
|
81
|
+
entirely contained in an embedded tube would be homotopic to the core
|
82
|
+
curve. And we enumerate core curves during the length spectrum
|
83
|
+
computation separately already.
|
84
|
+
"""
|
85
|
+
|
86
|
+
tet = lifted_tetrahedron.tet
|
87
|
+
m = lifted_tetrahedron.o13_matrix
|
88
|
+
|
89
|
+
v : Optional[int] = _vertex_of_core_curve_tube_containing_geodesic_piece(
|
90
|
+
tet, inverse_lifted_geodesic, verified)
|
91
|
+
if v is None:
|
92
|
+
return None
|
93
|
+
|
94
|
+
core_curve : R13Line = tet.core_curves[v].r13_line
|
95
|
+
lifted_core_curve : R13Line = core_curve.transformed(m)
|
96
|
+
r = tet.Class[v].core_curve_tube_radius
|
97
|
+
|
98
|
+
# The intersection points of the geodesic with the boundary
|
99
|
+
# of the tube about the core curve.
|
100
|
+
#
|
101
|
+
# Note that _vertex_of_core_curve_tube_containing_geodesic_piece already
|
102
|
+
# checked that the geodesic intersects the tube.
|
103
|
+
#
|
104
|
+
points = _compute_intersection_points_geodesic_and_tube(
|
105
|
+
geodesic,
|
106
|
+
lifted_core_curve, r)
|
107
|
+
|
108
|
+
# Find lifted tetrahedra containing those intersection points.
|
109
|
+
return [
|
110
|
+
new_lifted_tetrahedron
|
111
|
+
for point in points
|
112
|
+
for new_lifted_tetrahedron in _graph_trace(
|
113
|
+
tet, point, verified) ]
|
114
|
+
|
115
|
+
def _vertex_of_core_curve_tube_containing_geodesic_piece(
|
116
|
+
tet : Tetrahedron,
|
117
|
+
geodesic : R13Line,
|
118
|
+
verified : bool) -> Optional[int]:
|
119
|
+
"""
|
120
|
+
Can the intersection of the geodesic with the given tetrahedron be
|
121
|
+
verified to be entirely contained in a core curve associated with one of
|
122
|
+
the vertices of the tetrahedron?
|
123
|
+
|
124
|
+
Is yes, return that vertex (as element in simplex.ZeroSubsimplices).
|
125
|
+
Otherwise, return None.
|
126
|
+
"""
|
127
|
+
|
128
|
+
# Before doing the expensive computation of the intersection of the
|
129
|
+
# geodesic with the tetrahedron, check whether the geodesic as a whole
|
130
|
+
# is intersecting the tube.
|
131
|
+
#
|
132
|
+
# Note that when in doubt (intervals too big), it is better to
|
133
|
+
# fail claiming this piece is not contained in the core curve
|
134
|
+
# tube.
|
135
|
+
#
|
136
|
+
# Elements of simplex.ZeroSubsimplices corresponding to candidate core
|
137
|
+
# curve tubes.
|
138
|
+
#
|
139
|
+
candidate_vertices : Sequence[int] = [
|
140
|
+
v
|
141
|
+
for v, core_curve in tet.core_curves.items()
|
142
|
+
if distance_r13_lines(geodesic, core_curve.r13_line) < (
|
143
|
+
tet.Class[v].core_curve_tube_radius) ]
|
144
|
+
|
145
|
+
if len(candidate_vertices) == 0:
|
146
|
+
return None
|
147
|
+
|
148
|
+
# Compute intersection points of geodesic with tetrahedron.
|
149
|
+
points : Optional[Sequence[Any]] = (
|
150
|
+
_compute_intersection_points_geodesic_and_tet(
|
151
|
+
geodesic, tet, verified))
|
152
|
+
if points is None:
|
153
|
+
# Geodesic not intersecting tetrahedron.
|
154
|
+
# Or we could not verify the intersection points.
|
155
|
+
return None
|
156
|
+
|
157
|
+
for v in candidate_vertices:
|
158
|
+
# Both points must be inside the core curve tube.
|
159
|
+
core_curve = tet.core_curves[v]
|
160
|
+
r = tet.Class[v].core_curve_tube_radius
|
161
|
+
if all(distance_r13_point_line(point, core_curve.r13_line) < r
|
162
|
+
for point in points):
|
163
|
+
return v
|
164
|
+
|
165
|
+
return None
|
166
|
+
|
167
|
+
def _compute_intersection_points_geodesic_and_tet(
|
168
|
+
geodesic : R13Line,
|
169
|
+
tet : Tetrahedron,
|
170
|
+
verified : bool) -> Optional[Sequence[Any]]:
|
171
|
+
"""
|
172
|
+
Intersection points of geodesic with the tetrahedron.
|
173
|
+
Returns either two points or nothing if the geodesic does not
|
174
|
+
intersect the tetrahedron or could not be verified to intersect the
|
175
|
+
tetrahedron.
|
176
|
+
"""
|
177
|
+
|
178
|
+
if verified:
|
179
|
+
epsilon = 0
|
180
|
+
else:
|
181
|
+
epsilon = 1e-5
|
182
|
+
|
183
|
+
# We parametrize the geodesic as point0 + p * direction.
|
184
|
+
# Note that to determine whether a point is in a plane, we do
|
185
|
+
# not need to normalize the vector associated with the point.
|
186
|
+
point0 = geodesic.points[0]
|
187
|
+
point1 = geodesic.points[1]
|
188
|
+
direction = point1 - point0
|
189
|
+
|
190
|
+
# For each half-space defined by a tetrahedron plane, we say that
|
191
|
+
# the geodesic is entering if it starts outside of the half-space
|
192
|
+
# and ends in the half-space. Exit in the opposite case. Record the
|
193
|
+
# parameter at which time the geodesic crosses the plane in each case.
|
194
|
+
#
|
195
|
+
enter_params = []
|
196
|
+
exit_params = []
|
197
|
+
|
198
|
+
for plane in tet.R13_unnormalised_planes.values():
|
199
|
+
# Sign tells us whether start/end point of geodesic is in that
|
200
|
+
# half-space.
|
201
|
+
d0 = r13_dot(point0, plane)
|
202
|
+
d1 = r13_dot(point1, plane)
|
203
|
+
|
204
|
+
d0_out = d0 > epsilon
|
205
|
+
d1_out = d1 > epsilon
|
206
|
+
|
207
|
+
if d0_out and d1_out:
|
208
|
+
# Geodesic entirely outside of tetrahedron. Bail.
|
209
|
+
return None
|
210
|
+
|
211
|
+
d0_in = d0 < -epsilon
|
212
|
+
d1_in = d1 < -epsilon
|
213
|
+
|
214
|
+
if d0_in and d1_out:
|
215
|
+
exit_params .append(-d0 / r13_dot(plane, direction))
|
216
|
+
|
217
|
+
if d1_in and d0_out:
|
218
|
+
enter_params.append(-d0 / r13_dot(plane, direction))
|
219
|
+
|
220
|
+
# If ambiguous, do not enter to either exit or enter parameters.
|
221
|
+
# Note that this can happen if the geodesic is inside one of the
|
222
|
+
# planes supporting the faces of the tetrahedron.
|
223
|
+
#
|
224
|
+
# In that case, we ignore that plane when computing the intersection.
|
225
|
+
#
|
226
|
+
# It is ok to compute a larger intersection: that will just mean that
|
227
|
+
# we might not be able to verify a piece to be entirely contained in
|
228
|
+
# the core curve tube.
|
229
|
+
|
230
|
+
if len(exit_params) == 0:
|
231
|
+
raise InsufficientPrecisionError(
|
232
|
+
"When computing intersection of geodesic with tetrahedron, could "
|
233
|
+
"not determine how geodesic exited tetrahedron. Increasing "
|
234
|
+
"precision should fix this.")
|
235
|
+
if len(enter_params) == 0:
|
236
|
+
raise InsufficientPrecisionError(
|
237
|
+
"When computing intersection of geodesic with tetrahedron, could "
|
238
|
+
"not determine how geodesic exited tetrahedron. Increasing "
|
239
|
+
"precision should fix this.")
|
240
|
+
|
241
|
+
enter_param = correct_max(enter_params)
|
242
|
+
exit_param = correct_min(exit_params)
|
243
|
+
|
244
|
+
if not enter_param < exit_param:
|
245
|
+
# We cannot compute the intersection. Bail.
|
246
|
+
return None
|
247
|
+
|
248
|
+
return [
|
249
|
+
time_r13_normalise(point0 + param * direction)
|
250
|
+
for param in [ enter_param, exit_param ]]
|
251
|
+
|
252
|
+
def _compute_intersection_points_geodesic_and_tube(
|
253
|
+
geodesic : R13Line,
|
254
|
+
|
255
|
+
core_geodesic : R13Line,
|
256
|
+
tube_radius) -> Sequence[Any]:
|
257
|
+
"""
|
258
|
+
Compute intersection points of geodesic with boundary of tube above
|
259
|
+
core_geodesic with radius tube_radius.
|
260
|
+
|
261
|
+
Assumes that the geodesic actually intersects the tube.
|
262
|
+
"""
|
263
|
+
|
264
|
+
# We parametrize the geodesic by
|
265
|
+
# r(t) = ((1 - t) * geodesic.points[0] + (1 + t) * geodesic.points[1]) / 2
|
266
|
+
#
|
267
|
+
# Note that
|
268
|
+
# r(t) * r(t) = geodesic.points[0] * geodesic.points[1] * (1 - t^2) / -2
|
269
|
+
#
|
270
|
+
# We need to solve for t in
|
271
|
+
# d(time_r13_normalise(r(t)), core_geodesic) = tube_radius
|
272
|
+
# which gives a quadratic equation.
|
273
|
+
|
274
|
+
start0_dot = r13_dot(geodesic.points[0], core_geodesic.points[0])
|
275
|
+
start1_dot = r13_dot(geodesic.points[0], core_geodesic.points[1])
|
276
|
+
end0_dot = r13_dot(geodesic.points[1], core_geodesic.points[0])
|
277
|
+
end1_dot = r13_dot(geodesic.points[1], core_geodesic.points[1])
|
278
|
+
|
279
|
+
p = (tube_radius.cosh() ** 2 *
|
280
|
+
geodesic.inner_product * core_geodesic.inner_product)
|
281
|
+
s = start0_dot * start1_dot
|
282
|
+
e = end0_dot * end1_dot
|
283
|
+
m = (start0_dot * end1_dot +
|
284
|
+
start1_dot * end0_dot)
|
285
|
+
|
286
|
+
se = s + e
|
287
|
+
m_minus_p = m - p
|
288
|
+
|
289
|
+
return [
|
290
|
+
time_r13_normalise((1 - t) * geodesic.points[0] +
|
291
|
+
(1 + t) * geodesic.points[1])
|
292
|
+
for t in _solve_quadratic( m_minus_p - se,
|
293
|
+
2 * (s - e),
|
294
|
+
-m_minus_p - se) ]
|
295
|
+
|
296
|
+
def _solve_quadratic(a, b, c):
|
297
|
+
"""
|
298
|
+
Returns the two real solutions to a * t^2 + b * t + c = 0.
|
299
|
+
"""
|
300
|
+
|
301
|
+
d = b * b - 4 * a * c
|
302
|
+
|
303
|
+
if not d > 0:
|
304
|
+
raise InsufficientPrecisionError(
|
305
|
+
"Discriminant of quadratic equation to solve intersection with "
|
306
|
+
"core curve tube could not be verified to be positive. "
|
307
|
+
"Increasing precision should fix this.")
|
308
|
+
|
309
|
+
sqrt_d = d.sqrt()
|
310
|
+
|
311
|
+
return [ (-b + s * sqrt_d) / ( 2 * a)
|
312
|
+
for s in [ +1, -1 ] ]
|
313
|
+
|
314
|
+
def _graph_trace(tet : Tetrahedron,
|
315
|
+
lifted_pt,
|
316
|
+
verified : bool) -> Sequence[LiftedTetrahedron]:
|
317
|
+
"""
|
318
|
+
Given some tetrahedron, find one tetrahedron or two lifted tetrahedra
|
319
|
+
containing the given lifted_pt.
|
320
|
+
"""
|
321
|
+
|
322
|
+
# Similar to GeodesicStartPointInfo._graph_trace
|
323
|
+
|
324
|
+
RF = lifted_pt[0].parent()
|
325
|
+
if verified:
|
326
|
+
epsilon = 0
|
327
|
+
def key(face_and_signed_distance):
|
328
|
+
return face_and_signed_distance[1].center()
|
329
|
+
else:
|
330
|
+
epsilon = _compute_epsilon(RF)
|
331
|
+
def key(face_and_signed_distance):
|
332
|
+
return face_and_signed_distance[1]
|
333
|
+
|
334
|
+
m = make_identity_matrix(ring=RF, n=4)
|
335
|
+
|
336
|
+
entry_cell = simplex.T
|
337
|
+
for i in range(constants.graph_trace_max_steps):
|
338
|
+
faces_and_signed_distances = [
|
339
|
+
(face, r13_dot(lifted_pt, tet.R13_planes[face]))
|
340
|
+
for face in simplex.TwoSubsimplices ]
|
341
|
+
|
342
|
+
if not any( signed_distance > epsilon
|
343
|
+
for face, signed_distance
|
344
|
+
in faces_and_signed_distances ):
|
345
|
+
return find_lifted_tetrahedra_containing_point(
|
346
|
+
LiftedTetrahedron(tet, m),
|
347
|
+
faces_and_signed_distances,
|
348
|
+
lifted_pt,
|
349
|
+
epsilon)
|
350
|
+
|
351
|
+
face, worst_distance = max(
|
352
|
+
[ face_and_signed_distance
|
353
|
+
for face_and_signed_distance in faces_and_signed_distances
|
354
|
+
if face_and_signed_distance[0] != entry_cell ],
|
355
|
+
key=key)
|
356
|
+
|
357
|
+
lifted_pt = tet.O13_matrices[face] * lifted_pt
|
358
|
+
entry_cell = tet.Gluing[face].image(face)
|
359
|
+
tet = tet.Neighbor[face]
|
360
|
+
m = m * tet.O13_matrices[entry_cell]
|
361
|
+
|
362
|
+
raise exceptions.UnfinishedGraphTraceGeodesicError(
|
363
|
+
constants.graph_trace_max_steps)
|
364
|
+
|
365
|
+
def _compute_epsilon(RF):
|
366
|
+
return RF(0.5) ** (RF.prec() // 2)
|
367
|
+
|
368
|
+
def _make_unit_tangent_vector(point, direction):
|
369
|
+
return space_r13_normalise(direction + r13_dot(direction, point) * point)
|
@@ -0,0 +1,52 @@
|
|
1
|
+
from .line import R13LineWithMatrix
|
2
|
+
from ...tiling.floor import floor_as_integers
|
3
|
+
|
4
|
+
from ...matrix import make_identity_matrix # type: ignore
|
5
|
+
from ...hyperboloid import r13_dot, o13_inverse # type: ignore
|
6
|
+
from ...hyperboloid.line import R13Line
|
7
|
+
|
8
|
+
def canonical_keys_function_for_line(line_with_matrix : R13LineWithMatrix):
|
9
|
+
|
10
|
+
line : R13Line = line_with_matrix.r13_line
|
11
|
+
m = line_with_matrix.o13_matrix
|
12
|
+
|
13
|
+
pt = line.points[0]
|
14
|
+
a = pt[0]
|
15
|
+
b = (m * pt)[0]
|
16
|
+
log_scale_factor = 2 * (b / a).log()
|
17
|
+
|
18
|
+
power_cache = _O13MatrixPowerCache(m)
|
19
|
+
|
20
|
+
def result(point):
|
21
|
+
a = r13_dot(point, line.points[0])
|
22
|
+
b = r13_dot(point, line.points[1])
|
23
|
+
|
24
|
+
r = (a / b).log() / log_scale_factor
|
25
|
+
|
26
|
+
return [ power_cache.power(i) * point
|
27
|
+
for i in floor_as_integers(r) ]
|
28
|
+
|
29
|
+
return result
|
30
|
+
|
31
|
+
class _O13MatrixPowerCache:
|
32
|
+
def __init__(self, m):
|
33
|
+
self._positive_cache = _MatrixNonNegativePowerCache(m)
|
34
|
+
self._negative_cache = _MatrixNonNegativePowerCache(o13_inverse(m))
|
35
|
+
|
36
|
+
def power(self, i):
|
37
|
+
if i >= 0:
|
38
|
+
return self._positive_cache.power( i)
|
39
|
+
else:
|
40
|
+
return self._negative_cache.power(-i)
|
41
|
+
|
42
|
+
|
43
|
+
class _MatrixNonNegativePowerCache:
|
44
|
+
def __init__(self, m):
|
45
|
+
self._m = m
|
46
|
+
self._powers = [ make_identity_matrix(ring=m.base_ring(),
|
47
|
+
n=m.dimensions()[0]) ]
|
48
|
+
|
49
|
+
def power(self, i):
|
50
|
+
while not i < len(self._powers):
|
51
|
+
self._powers.append(self._m * self._powers[-1])
|
52
|
+
return self._powers[i]
|
@@ -0,0 +1,60 @@
|
|
1
|
+
from .line import R13LineWithMatrix
|
2
|
+
|
3
|
+
from ...snap.t3mlite import simplex, Tetrahedron
|
4
|
+
from ...hyperboloid.distances import distance_r13_lines
|
5
|
+
from ...hyperboloid.line import R13Line
|
6
|
+
|
7
|
+
from typing import Optional
|
8
|
+
|
9
|
+
class ObjectCloseToCoreCurve(RuntimeError):
|
10
|
+
def __init__(self, obj_name, cusp_index, distance):
|
11
|
+
self.obj_name = obj_name
|
12
|
+
self.cusp_index = cusp_index
|
13
|
+
self.distance = distance
|
14
|
+
s = self.obj_name if self.obj_name else "Given geometric object"
|
15
|
+
super().__init__(
|
16
|
+
"%s is very close to the core curve "
|
17
|
+
"of cusp %d and might intersect it. Distance: %r." % (
|
18
|
+
s, cusp_index, distance))
|
19
|
+
|
20
|
+
def check_away_from_core_curve_iter(iterator, epsilon, obj_name = None):
|
21
|
+
for tile in iterator:
|
22
|
+
check_away_from_core_curve(
|
23
|
+
tile.inverse_lifted_geometric_object,
|
24
|
+
tile.lifted_tetrahedron.tet,
|
25
|
+
simplex.T,
|
26
|
+
epsilon,
|
27
|
+
obj_name)
|
28
|
+
|
29
|
+
yield tile
|
30
|
+
|
31
|
+
def check_away_from_core_curve(line : R13Line,
|
32
|
+
tet : Tetrahedron,
|
33
|
+
subsimplex : int,
|
34
|
+
epsilon,
|
35
|
+
obj_name = None):
|
36
|
+
"""
|
37
|
+
If the geodesic is intersecting a core curve, the tracing would
|
38
|
+
fail in that it would never reach the intersection point and thus
|
39
|
+
either hit the iteration limit or breaking down because of
|
40
|
+
rounding-errors.
|
41
|
+
|
42
|
+
This function is catching this case to give a meaningful exception
|
43
|
+
faster. It does so by computing the distance between the lift of
|
44
|
+
the geodesic we are tracing and the lifts of the core curve
|
45
|
+
corresponding to the vertices of the tetrahedra adjacent to the
|
46
|
+
given face.
|
47
|
+
"""
|
48
|
+
|
49
|
+
for v in simplex.ZeroSubsimplices:
|
50
|
+
if not simplex.is_subset(v, subsimplex):
|
51
|
+
continue
|
52
|
+
core_curve : Optional[R13LineWithMatrix] = tet.core_curves.get(v, None)
|
53
|
+
if core_curve is None:
|
54
|
+
continue
|
55
|
+
d = distance_r13_lines(
|
56
|
+
core_curve.r13_line,
|
57
|
+
line)
|
58
|
+
if not d > epsilon:
|
59
|
+
raise ObjectCloseToCoreCurve(
|
60
|
+
obj_name, tet.Class[v].Index, d)
|
@@ -0,0 +1,22 @@
|
|
1
|
+
class WordAppearsToBeParabolic(RuntimeError):
|
2
|
+
def __init__(self, word, trace):
|
3
|
+
self.word = word
|
4
|
+
self.trace = trace
|
5
|
+
super().__init__(
|
6
|
+
"Attempting to drill a geodesic corresponding to a matrix "
|
7
|
+
"that could be parabolic. "
|
8
|
+
"Word: %s, trace: %r." % (word, trace))
|
9
|
+
|
10
|
+
class UnfinishedGraphTraceGeodesicError(RuntimeError):
|
11
|
+
def __init__(self, steps):
|
12
|
+
self.steps = steps
|
13
|
+
super().__init__(
|
14
|
+
"The line fixed by the given word could not be moved (by "
|
15
|
+
"Decktransformations) to intersect the fundamental domain after "
|
16
|
+
"%d steps.\n"
|
17
|
+
"This is probably due to a pathology, e.g., a bad conjugate "
|
18
|
+
"was picked and the line is very far away from the fundamental "
|
19
|
+
"domain or the given geodesic is very close to a core curve of "
|
20
|
+
"a filled cusp.\n"
|
21
|
+
"If not a verified computation, it might be due to insufficient "
|
22
|
+
"pecision." % steps)
|
@@ -1,10 +1,13 @@
|
|
1
|
-
from
|
2
|
-
from
|
3
|
-
from
|
4
|
-
from
|
5
|
-
|
6
|
-
|
1
|
+
from .line import R13LineWithMatrix
|
2
|
+
from ...hyperboloid.line import R13Line
|
3
|
+
from ...upper_halfspace import psl2c_to_o13, complex_length_of_psl2c_matrix # type: ignore
|
4
|
+
from ...upper_halfspace.ideal_point import ideal_point_to_r13 # type: ignore
|
5
|
+
from ...matrix import make_matrix # type: ignore
|
6
|
+
from ...math_basics import (is_RealIntervalFieldElement,
|
7
|
+
is_ComplexIntervalFieldElement) # type: ignore
|
7
8
|
|
9
|
+
__all__ = ['r13_fixed_points_of_psl2c_matrix',
|
10
|
+
'r13_fixed_line_of_psl2c_matrix']
|
8
11
|
|
9
12
|
def r13_fixed_points_of_psl2c_matrix(m):
|
10
13
|
"""
|
@@ -31,14 +34,27 @@ def r13_fixed_points_of_psl2c_matrix(m):
|
|
31
34
|
if e0 > e1:
|
32
35
|
return _r13_fixed_points_of_psl2c_matrix(m)
|
33
36
|
|
34
|
-
t =
|
35
|
-
tinv =
|
37
|
+
t = make_matrix([[ 1, 0],[ 1, 1]], ring=m.base_ring())
|
38
|
+
tinv = make_matrix([[ 1, 0],[-1, 1]], ring=m.base_ring())
|
36
39
|
|
37
40
|
pts = _r13_fixed_points_of_psl2c_matrix(tinv * m * t)
|
38
41
|
o13_t = psl2c_to_o13(t)
|
39
42
|
|
40
43
|
return [ o13_t * pt for pt in pts ]
|
41
44
|
|
45
|
+
|
46
|
+
def r13_fixed_line_of_psl2c_matrix(m) -> R13LineWithMatrix:
|
47
|
+
"""
|
48
|
+
Given a loxodromic PSL(2,C)-matrix m, returns the line (together
|
49
|
+
with the O(1,3)-matrix corresponding to m) fixed by m in
|
50
|
+
the hyperboloid model.
|
51
|
+
"""
|
52
|
+
|
53
|
+
return R13LineWithMatrix(
|
54
|
+
R13Line(r13_fixed_points_of_psl2c_matrix(m)),
|
55
|
+
psl2c_to_o13(m),
|
56
|
+
complex_length_of_psl2c_matrix(m))
|
57
|
+
|
42
58
|
###############################################################################
|
43
59
|
# Helpers
|
44
60
|
|
@@ -64,5 +80,14 @@ def _complex_fixed_points_of_psl2c_matrix(m):
|
|
64
80
|
c = -m[0, 1]
|
65
81
|
|
66
82
|
# Use usual formula z = (-b +/- sqrt(b^2 - 4 * a * c)) / (2 * a)
|
67
|
-
d = (b * b - 4 * a * c)
|
83
|
+
d = _safe_complex_sqrt(b * b - 4 * a * c)
|
68
84
|
return [ (-b + s * d) / (2 * a) for s in [+1, -1] ]
|
85
|
+
|
86
|
+
def _safe_complex_sqrt(z):
|
87
|
+
if is_ComplexIntervalFieldElement(z):
|
88
|
+
if z.contains_zero():
|
89
|
+
CIF = z.parent()
|
90
|
+
m = z.abs().sqrt().upper()
|
91
|
+
return CIF((-m, m), (-m, m))
|
92
|
+
|
93
|
+
return z.sqrt()
|