snappy 3.3__cp310-cp310-manylinux_2_24_aarch64.manylinux_2_28_aarch64.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.
Files changed (541) hide show
  1. snappy/CyOpenGL.cpython-310-aarch64-linux-gnu.so +0 -0
  2. snappy/SnapPy.cpython-310-aarch64-linux-gnu.so +0 -0
  3. snappy/SnapPy.ico +0 -0
  4. snappy/SnapPy.png +0 -0
  5. snappy/SnapPyHP.cpython-310-aarch64-linux-gnu.so +0 -0
  6. snappy/__init__.py +534 -0
  7. snappy/app.py +604 -0
  8. snappy/app_menus.py +372 -0
  9. snappy/browser.py +998 -0
  10. snappy/cache.py +25 -0
  11. snappy/canonical.py +249 -0
  12. snappy/cusps/__init__.py +280 -0
  13. snappy/cusps/cusp_area_matrix.py +98 -0
  14. snappy/cusps/cusp_areas_from_matrix.py +96 -0
  15. snappy/cusps/maximal_cusp_area_matrix.py +136 -0
  16. snappy/cusps/short_slopes_for_cusp.py +217 -0
  17. snappy/cusps/test.py +22 -0
  18. snappy/cusps/trig_cusp_area_matrix.py +63 -0
  19. snappy/database.py +454 -0
  20. snappy/db_utilities.py +79 -0
  21. snappy/decorated_isosig.py +717 -0
  22. snappy/dev/__init__.py +0 -0
  23. snappy/dev/extended_ptolemy/__init__.py +8 -0
  24. snappy/dev/extended_ptolemy/closed.py +106 -0
  25. snappy/dev/extended_ptolemy/complexVolumesClosed.py +149 -0
  26. snappy/dev/extended_ptolemy/direct.py +42 -0
  27. snappy/dev/extended_ptolemy/extended.py +406 -0
  28. snappy/dev/extended_ptolemy/giac_helper.py +43 -0
  29. snappy/dev/extended_ptolemy/giac_rur.py +129 -0
  30. snappy/dev/extended_ptolemy/gluing.py +46 -0
  31. snappy/dev/extended_ptolemy/phc_wrapper.py +220 -0
  32. snappy/dev/extended_ptolemy/printMatrices.py +70 -0
  33. snappy/dev/vericlosed/__init__.py +1 -0
  34. snappy/dev/vericlosed/computeApproxHyperbolicStructureNew.py +159 -0
  35. snappy/dev/vericlosed/computeApproxHyperbolicStructureOrb.py +90 -0
  36. snappy/dev/vericlosed/computeVerifiedHyperbolicStructure.py +111 -0
  37. snappy/dev/vericlosed/gimbalLoopFinder.py +130 -0
  38. snappy/dev/vericlosed/hyperbolicStructure.py +313 -0
  39. snappy/dev/vericlosed/krawczykCertifiedEdgeLengthsEngine.py +165 -0
  40. snappy/dev/vericlosed/oneVertexTruncatedComplex.py +122 -0
  41. snappy/dev/vericlosed/orb/__init__.py +1 -0
  42. snappy/dev/vericlosed/orb/orb_solution_for_snappea_finite_triangulation_mac +0 -0
  43. snappy/dev/vericlosed/parseVertexGramMatrixFile.py +47 -0
  44. snappy/dev/vericlosed/polishApproxHyperbolicStructure.py +61 -0
  45. snappy/dev/vericlosed/test.py +54 -0
  46. snappy/dev/vericlosed/truncatedComplex.py +176 -0
  47. snappy/dev/vericlosed/verificationError.py +58 -0
  48. snappy/dev/vericlosed/verifyHyperbolicStructureEngine.py +177 -0
  49. snappy/doc/_images/SnapPy-196.png +0 -0
  50. snappy/doc/_images/m004_paper_plane_on_systole.jpg +0 -0
  51. snappy/doc/_images/m125_paper_plane.jpg +0 -0
  52. snappy/doc/_images/mac.png +0 -0
  53. snappy/doc/_images/o9_00000_systole_paper_plane.jpg +0 -0
  54. snappy/doc/_images/o9_00000_systole_paper_plane_closer.jpg +0 -0
  55. snappy/doc/_images/plink-action.png +0 -0
  56. snappy/doc/_images/ubuntu.png +0 -0
  57. snappy/doc/_images/win7.png +0 -0
  58. snappy/doc/_sources/additional_classes.rst.txt +40 -0
  59. snappy/doc/_sources/bugs.rst.txt +14 -0
  60. snappy/doc/_sources/censuses.rst.txt +52 -0
  61. snappy/doc/_sources/credits.rst.txt +81 -0
  62. snappy/doc/_sources/development.rst.txt +261 -0
  63. snappy/doc/_sources/index.rst.txt +215 -0
  64. snappy/doc/_sources/installing.rst.txt +249 -0
  65. snappy/doc/_sources/manifold.rst.txt +6 -0
  66. snappy/doc/_sources/manifoldhp.rst.txt +46 -0
  67. snappy/doc/_sources/news.rst.txt +425 -0
  68. snappy/doc/_sources/other.rst.txt +25 -0
  69. snappy/doc/_sources/platonic_census.rst.txt +20 -0
  70. snappy/doc/_sources/plink.rst.txt +102 -0
  71. snappy/doc/_sources/ptolemy.rst.txt +66 -0
  72. snappy/doc/_sources/ptolemy_classes.rst.txt +42 -0
  73. snappy/doc/_sources/ptolemy_examples1.rst.txt +298 -0
  74. snappy/doc/_sources/ptolemy_examples2.rst.txt +363 -0
  75. snappy/doc/_sources/ptolemy_examples3.rst.txt +301 -0
  76. snappy/doc/_sources/ptolemy_examples4.rst.txt +61 -0
  77. snappy/doc/_sources/ptolemy_prelim.rst.txt +105 -0
  78. snappy/doc/_sources/screenshots.rst.txt +21 -0
  79. snappy/doc/_sources/snap.rst.txt +87 -0
  80. snappy/doc/_sources/snappy.rst.txt +28 -0
  81. snappy/doc/_sources/spherogram.rst.txt +103 -0
  82. snappy/doc/_sources/todo.rst.txt +47 -0
  83. snappy/doc/_sources/triangulation.rst.txt +11 -0
  84. snappy/doc/_sources/tutorial.rst.txt +49 -0
  85. snappy/doc/_sources/verify.rst.txt +210 -0
  86. snappy/doc/_sources/verify_internals.rst.txt +79 -0
  87. snappy/doc/_static/SnapPy-horizontal-128.png +0 -0
  88. snappy/doc/_static/SnapPy.ico +0 -0
  89. snappy/doc/_static/_sphinx_javascript_frameworks_compat.js +123 -0
  90. snappy/doc/_static/basic.css +906 -0
  91. snappy/doc/_static/css/badge_only.css +1 -0
  92. snappy/doc/_static/css/fonts/Roboto-Slab-Bold.woff +0 -0
  93. snappy/doc/_static/css/fonts/Roboto-Slab-Bold.woff2 +0 -0
  94. snappy/doc/_static/css/fonts/Roboto-Slab-Regular.woff +0 -0
  95. snappy/doc/_static/css/fonts/Roboto-Slab-Regular.woff2 +0 -0
  96. snappy/doc/_static/css/fonts/fontawesome-webfont.eot +0 -0
  97. snappy/doc/_static/css/fonts/fontawesome-webfont.svg +2671 -0
  98. snappy/doc/_static/css/fonts/fontawesome-webfont.ttf +0 -0
  99. snappy/doc/_static/css/fonts/fontawesome-webfont.woff +0 -0
  100. snappy/doc/_static/css/fonts/fontawesome-webfont.woff2 +0 -0
  101. snappy/doc/_static/css/fonts/lato-bold-italic.woff +0 -0
  102. snappy/doc/_static/css/fonts/lato-bold-italic.woff2 +0 -0
  103. snappy/doc/_static/css/fonts/lato-bold.woff +0 -0
  104. snappy/doc/_static/css/fonts/lato-bold.woff2 +0 -0
  105. snappy/doc/_static/css/fonts/lato-normal-italic.woff +0 -0
  106. snappy/doc/_static/css/fonts/lato-normal-italic.woff2 +0 -0
  107. snappy/doc/_static/css/fonts/lato-normal.woff +0 -0
  108. snappy/doc/_static/css/fonts/lato-normal.woff2 +0 -0
  109. snappy/doc/_static/css/theme.css +4 -0
  110. snappy/doc/_static/doctools.js +149 -0
  111. snappy/doc/_static/documentation_options.js +13 -0
  112. snappy/doc/_static/file.png +0 -0
  113. snappy/doc/_static/fonts/Lato/lato-bold.eot +0 -0
  114. snappy/doc/_static/fonts/Lato/lato-bold.ttf +0 -0
  115. snappy/doc/_static/fonts/Lato/lato-bold.woff +0 -0
  116. snappy/doc/_static/fonts/Lato/lato-bold.woff2 +0 -0
  117. snappy/doc/_static/fonts/Lato/lato-bolditalic.eot +0 -0
  118. snappy/doc/_static/fonts/Lato/lato-bolditalic.ttf +0 -0
  119. snappy/doc/_static/fonts/Lato/lato-bolditalic.woff +0 -0
  120. snappy/doc/_static/fonts/Lato/lato-bolditalic.woff2 +0 -0
  121. snappy/doc/_static/fonts/Lato/lato-italic.eot +0 -0
  122. snappy/doc/_static/fonts/Lato/lato-italic.ttf +0 -0
  123. snappy/doc/_static/fonts/Lato/lato-italic.woff +0 -0
  124. snappy/doc/_static/fonts/Lato/lato-italic.woff2 +0 -0
  125. snappy/doc/_static/fonts/Lato/lato-regular.eot +0 -0
  126. snappy/doc/_static/fonts/Lato/lato-regular.ttf +0 -0
  127. snappy/doc/_static/fonts/Lato/lato-regular.woff +0 -0
  128. snappy/doc/_static/fonts/Lato/lato-regular.woff2 +0 -0
  129. snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-bold.eot +0 -0
  130. snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-bold.ttf +0 -0
  131. snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-bold.woff +0 -0
  132. snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-bold.woff2 +0 -0
  133. snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-regular.eot +0 -0
  134. snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-regular.ttf +0 -0
  135. snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-regular.woff +0 -0
  136. snappy/doc/_static/fonts/RobotoSlab/roboto-slab-v7-regular.woff2 +0 -0
  137. snappy/doc/_static/jquery.js +2 -0
  138. snappy/doc/_static/js/badge_only.js +1 -0
  139. snappy/doc/_static/js/theme.js +1 -0
  140. snappy/doc/_static/js/versions.js +228 -0
  141. snappy/doc/_static/language_data.js +192 -0
  142. snappy/doc/_static/minus.png +0 -0
  143. snappy/doc/_static/plus.png +0 -0
  144. snappy/doc/_static/pygments.css +75 -0
  145. snappy/doc/_static/searchtools.js +635 -0
  146. snappy/doc/_static/snappy_furo.css +33 -0
  147. snappy/doc/_static/snappy_sphinx_rtd_theme.css +42 -0
  148. snappy/doc/_static/sphinx_highlight.js +154 -0
  149. snappy/doc/additional_classes.html +1500 -0
  150. snappy/doc/bugs.html +132 -0
  151. snappy/doc/censuses.html +453 -0
  152. snappy/doc/credits.html +184 -0
  153. snappy/doc/development.html +385 -0
  154. snappy/doc/doc-latest/additional_classes.html +1500 -0
  155. snappy/doc/doc-latest/bugs.html +132 -0
  156. snappy/doc/doc-latest/censuses.html +453 -0
  157. snappy/doc/doc-latest/credits.html +184 -0
  158. snappy/doc/doc-latest/development.html +385 -0
  159. snappy/doc/doc-latest/genindex.html +1349 -0
  160. snappy/doc/doc-latest/index.html +287 -0
  161. snappy/doc/doc-latest/installing.html +346 -0
  162. snappy/doc/doc-latest/manifold.html +3632 -0
  163. snappy/doc/doc-latest/manifoldhp.html +180 -0
  164. snappy/doc/doc-latest/news.html +438 -0
  165. snappy/doc/doc-latest/objects.inv +0 -0
  166. snappy/doc/doc-latest/other.html +160 -0
  167. snappy/doc/doc-latest/platonic_census.html +376 -0
  168. snappy/doc/doc-latest/plink.html +210 -0
  169. snappy/doc/doc-latest/ptolemy.html +253 -0
  170. snappy/doc/doc-latest/ptolemy_classes.html +1144 -0
  171. snappy/doc/doc-latest/ptolemy_examples1.html +409 -0
  172. snappy/doc/doc-latest/ptolemy_examples2.html +471 -0
  173. snappy/doc/doc-latest/ptolemy_examples3.html +414 -0
  174. snappy/doc/doc-latest/ptolemy_examples4.html +195 -0
  175. snappy/doc/doc-latest/ptolemy_prelim.html +248 -0
  176. snappy/doc/doc-latest/py-modindex.html +165 -0
  177. snappy/doc/doc-latest/screenshots.html +141 -0
  178. snappy/doc/doc-latest/search.html +135 -0
  179. snappy/doc/doc-latest/searchindex.js +1 -0
  180. snappy/doc/doc-latest/snap.html +202 -0
  181. snappy/doc/doc-latest/snappy.html +181 -0
  182. snappy/doc/doc-latest/spherogram.html +1346 -0
  183. snappy/doc/doc-latest/todo.html +166 -0
  184. snappy/doc/doc-latest/triangulation.html +1676 -0
  185. snappy/doc/doc-latest/tutorial.html +159 -0
  186. snappy/doc/doc-latest/verify.html +330 -0
  187. snappy/doc/doc-latest/verify_internals.html +1235 -0
  188. snappy/doc/genindex.html +1349 -0
  189. snappy/doc/index.html +287 -0
  190. snappy/doc/installing.html +346 -0
  191. snappy/doc/manifold.html +3632 -0
  192. snappy/doc/manifoldhp.html +180 -0
  193. snappy/doc/news.html +438 -0
  194. snappy/doc/objects.inv +0 -0
  195. snappy/doc/other.html +160 -0
  196. snappy/doc/platonic_census.html +376 -0
  197. snappy/doc/plink.html +210 -0
  198. snappy/doc/ptolemy.html +253 -0
  199. snappy/doc/ptolemy_classes.html +1144 -0
  200. snappy/doc/ptolemy_examples1.html +409 -0
  201. snappy/doc/ptolemy_examples2.html +471 -0
  202. snappy/doc/ptolemy_examples3.html +414 -0
  203. snappy/doc/ptolemy_examples4.html +195 -0
  204. snappy/doc/ptolemy_prelim.html +248 -0
  205. snappy/doc/py-modindex.html +165 -0
  206. snappy/doc/screenshots.html +141 -0
  207. snappy/doc/search.html +135 -0
  208. snappy/doc/searchindex.js +1 -0
  209. snappy/doc/snap.html +202 -0
  210. snappy/doc/snappy.html +181 -0
  211. snappy/doc/spherogram.html +1346 -0
  212. snappy/doc/todo.html +166 -0
  213. snappy/doc/triangulation.html +1676 -0
  214. snappy/doc/tutorial.html +159 -0
  215. snappy/doc/verify.html +330 -0
  216. snappy/doc/verify_internals.html +1235 -0
  217. snappy/drilling/__init__.py +456 -0
  218. snappy/drilling/barycentric.py +103 -0
  219. snappy/drilling/constants.py +5 -0
  220. snappy/drilling/crush.py +270 -0
  221. snappy/drilling/cusps.py +125 -0
  222. snappy/drilling/debug.py +242 -0
  223. snappy/drilling/epsilons.py +6 -0
  224. snappy/drilling/exceptions.py +55 -0
  225. snappy/drilling/moves.py +620 -0
  226. snappy/drilling/peripheral_curves.py +210 -0
  227. snappy/drilling/perturb.py +188 -0
  228. snappy/drilling/shorten.py +36 -0
  229. snappy/drilling/subdivide.py +274 -0
  230. snappy/drilling/test.py +23 -0
  231. snappy/drilling/test_cases.py +132 -0
  232. snappy/drilling/tracing.py +351 -0
  233. snappy/exceptions.py +26 -0
  234. snappy/export_stl.py +120 -0
  235. snappy/exterior_to_link/__init__.py +2 -0
  236. snappy/exterior_to_link/barycentric_geometry.py +463 -0
  237. snappy/exterior_to_link/exceptions.py +6 -0
  238. snappy/exterior_to_link/geodesic_map.json +14408 -0
  239. snappy/exterior_to_link/hyp_utils.py +112 -0
  240. snappy/exterior_to_link/link_projection.py +323 -0
  241. snappy/exterior_to_link/main.py +198 -0
  242. snappy/exterior_to_link/mcomplex_with_expansion.py +261 -0
  243. snappy/exterior_to_link/mcomplex_with_link.py +687 -0
  244. snappy/exterior_to_link/mcomplex_with_memory.py +162 -0
  245. snappy/exterior_to_link/pl_utils.py +491 -0
  246. snappy/exterior_to_link/put_in_S3.py +156 -0
  247. snappy/exterior_to_link/rational_linear_algebra.py +130 -0
  248. snappy/exterior_to_link/rational_linear_algebra_wrapped.py +135 -0
  249. snappy/exterior_to_link/simplify_to_base_tri.py +114 -0
  250. snappy/exterior_to_link/stored_moves.py +475 -0
  251. snappy/exterior_to_link/test.py +31 -0
  252. snappy/filedialog.py +28 -0
  253. snappy/geometric_structure/__init__.py +212 -0
  254. snappy/geometric_structure/cusp_neighborhood/__init__.py +3 -0
  255. snappy/geometric_structure/cusp_neighborhood/complex_cusp_cross_section.py +691 -0
  256. snappy/geometric_structure/cusp_neighborhood/cusp_cross_section_base.py +480 -0
  257. snappy/geometric_structure/cusp_neighborhood/exceptions.py +41 -0
  258. snappy/geometric_structure/cusp_neighborhood/real_cusp_cross_section.py +294 -0
  259. snappy/geometric_structure/cusp_neighborhood/tiles_for_cusp_neighborhood.py +156 -0
  260. snappy/geometric_structure/cusp_neighborhood/vertices.py +35 -0
  261. snappy/geometric_structure/geodesic/__init__.py +0 -0
  262. snappy/geometric_structure/geodesic/add_core_curves.py +152 -0
  263. snappy/geometric_structure/geodesic/avoid_core_curves.py +369 -0
  264. snappy/geometric_structure/geodesic/canonical_representatives.py +52 -0
  265. snappy/geometric_structure/geodesic/check_away_from_core_curve.py +60 -0
  266. snappy/geometric_structure/geodesic/constants.py +6 -0
  267. snappy/geometric_structure/geodesic/exceptions.py +22 -0
  268. snappy/geometric_structure/geodesic/fixed_points.py +106 -0
  269. snappy/geometric_structure/geodesic/geodesic_start_point_info.py +435 -0
  270. snappy/geometric_structure/geodesic/graph_trace_helper.py +67 -0
  271. snappy/geometric_structure/geodesic/line.py +30 -0
  272. snappy/geometric_structure/geodesic/multiplicity.py +127 -0
  273. snappy/geometric_structure/geodesic/tiles_for_geodesic.py +128 -0
  274. snappy/geometric_structure/test.py +22 -0
  275. snappy/gui.py +121 -0
  276. snappy/horoviewer.py +443 -0
  277. snappy/hyperboloid/__init__.py +212 -0
  278. snappy/hyperboloid/distances.py +259 -0
  279. snappy/hyperboloid/horoball.py +19 -0
  280. snappy/hyperboloid/line.py +35 -0
  281. snappy/hyperboloid/point.py +9 -0
  282. snappy/hyperboloid/triangle.py +29 -0
  283. snappy/info_icon.gif +0 -0
  284. snappy/infowindow.py +65 -0
  285. snappy/isometry_signature.py +389 -0
  286. snappy/len_spec/__init__.py +609 -0
  287. snappy/len_spec/geodesic_info.py +129 -0
  288. snappy/len_spec/geodesic_key_info_dict.py +116 -0
  289. snappy/len_spec/geodesic_piece.py +146 -0
  290. snappy/len_spec/geometric_structure.py +182 -0
  291. snappy/len_spec/geometry.py +136 -0
  292. snappy/len_spec/length_spectrum_geodesic_info.py +185 -0
  293. snappy/len_spec/spine.py +128 -0
  294. snappy/len_spec/test.py +24 -0
  295. snappy/len_spec/test_cases.py +69 -0
  296. snappy/len_spec/tile.py +276 -0
  297. snappy/len_spec/word.py +86 -0
  298. snappy/manifolds/HTWKnots/alternating.gz +0 -0
  299. snappy/manifolds/HTWKnots/nonalternating.gz +0 -0
  300. snappy/manifolds/__init__.py +3 -0
  301. snappy/margulis/__init__.py +332 -0
  302. snappy/margulis/cusp_neighborhood_neighborhood.py +66 -0
  303. snappy/margulis/geodesic_neighborhood.py +152 -0
  304. snappy/margulis/margulis_info.py +21 -0
  305. snappy/margulis/mu_from_neighborhood_pair.py +175 -0
  306. snappy/margulis/neighborhood.py +29 -0
  307. snappy/margulis/test.py +22 -0
  308. snappy/math_basics.py +187 -0
  309. snappy/matrix.py +525 -0
  310. snappy/number.py +657 -0
  311. snappy/numeric_output_checker.py +345 -0
  312. snappy/pari.py +41 -0
  313. snappy/phone_home.py +57 -0
  314. snappy/polyviewer.py +259 -0
  315. snappy/ptolemy/__init__.py +17 -0
  316. snappy/ptolemy/component.py +103 -0
  317. snappy/ptolemy/coordinates.py +2290 -0
  318. snappy/ptolemy/fieldExtensions.py +153 -0
  319. snappy/ptolemy/findLoops.py +473 -0
  320. snappy/ptolemy/geometricRep.py +59 -0
  321. snappy/ptolemy/homology.py +165 -0
  322. snappy/ptolemy/magma/default.magma_template +229 -0
  323. snappy/ptolemy/magma/radicalsOfPrimaryDecomposition.magma_template +79 -0
  324. snappy/ptolemy/manifoldMethods.py +395 -0
  325. snappy/ptolemy/matrix.py +350 -0
  326. snappy/ptolemy/numericalSolutionsToGroebnerBasis.py +113 -0
  327. snappy/ptolemy/polynomial.py +856 -0
  328. snappy/ptolemy/processComponents.py +173 -0
  329. snappy/ptolemy/processFileBase.py +247 -0
  330. snappy/ptolemy/processFileDispatch.py +46 -0
  331. snappy/ptolemy/processMagmaFile.py +392 -0
  332. snappy/ptolemy/processRurFile.py +150 -0
  333. snappy/ptolemy/ptolemyGeneralizedObstructionClass.py +102 -0
  334. snappy/ptolemy/ptolemyObstructionClass.py +64 -0
  335. snappy/ptolemy/ptolemyVariety.py +995 -0
  336. snappy/ptolemy/ptolemyVarietyPrimeIdealGroebnerBasis.py +140 -0
  337. snappy/ptolemy/reginaWrapper.py +698 -0
  338. snappy/ptolemy/regina_testing_files/DT_mcbbiceaibjklmdfgh__sl2_c0.magma_out.bz2 +0 -0
  339. snappy/ptolemy/regina_testing_files/DT_mcbbiceaibjklmdfgh__sl2_c1.magma_out.bz2 +0 -0
  340. snappy/ptolemy/regina_testing_files/DT_mcbbiceaibjklmdfgh__sl2_c2.magma_out.bz2 +0 -0
  341. snappy/ptolemy/regina_testing_files/DT_mcbbiceaibjklmdfgh__sl2_c3.magma_out.bz2 +0 -0
  342. snappy/ptolemy/regina_testing_files/DT_mcbbiceaibjklmdfgh__sl2_c4.magma_out.bz2 +0 -0
  343. snappy/ptolemy/regina_testing_files/DT_mcbbiceaibjklmdfgh__sl2_c5.magma_out.bz2 +0 -0
  344. snappy/ptolemy/regina_testing_files/DT_mcbbiceaibjklmdfgh__sl2_c6.magma_out.bz2 +0 -0
  345. snappy/ptolemy/regina_testing_files/DT_mcbbiceaibjklmdfgh__sl2_c7.magma_out.bz2 +0 -0
  346. snappy/ptolemy/regina_testing_files_generalized/m003__sl3_c0.magma_out.bz2 +0 -0
  347. snappy/ptolemy/regina_testing_files_generalized/m003__sl3_c1.magma_out.bz2 +0 -0
  348. snappy/ptolemy/regina_testing_files_generalized/m015__sl2_c0.magma_out.bz2 +0 -0
  349. snappy/ptolemy/regina_testing_files_generalized/m015__sl2_c1.magma_out.bz2 +0 -0
  350. snappy/ptolemy/regina_testing_files_generalized/m015__sl3_c0.magma_out.bz2 +0 -0
  351. snappy/ptolemy/regina_testing_files_generalized/m015__sl3_c1.magma_out.bz2 +0 -0
  352. snappy/ptolemy/rur.py +545 -0
  353. snappy/ptolemy/solutionsToPrimeIdealGroebnerBasis.py +277 -0
  354. snappy/ptolemy/test.py +1126 -0
  355. snappy/ptolemy/testing_files/3_1__sl2_c0.magma_out.bz2 +0 -0
  356. snappy/ptolemy/testing_files/3_1__sl2_c1.magma_out.bz2 +0 -0
  357. snappy/ptolemy/testing_files/4_1__sl2_c0.magma_out.bz2 +0 -0
  358. snappy/ptolemy/testing_files/4_1__sl2_c1.magma_out.bz2 +0 -0
  359. snappy/ptolemy/testing_files/4_1__sl3_c0.magma_out.bz2 +0 -0
  360. snappy/ptolemy/testing_files/4_1__sl4_c0.magma_out.bz2 +0 -0
  361. snappy/ptolemy/testing_files/4_1__sl4_c1.magma_out.bz2 +0 -0
  362. snappy/ptolemy/testing_files/5_2__sl2_c0.magma_out.bz2 +0 -0
  363. snappy/ptolemy/testing_files/5_2__sl2_c1.magma_out.bz2 +0 -0
  364. snappy/ptolemy/testing_files/DT_mcbbiceaibjklmdfgh__sl2_c0.magma_out.bz2 +0 -0
  365. snappy/ptolemy/testing_files/DT_mcbbiceaibjklmdfgh__sl2_c1.magma_out.bz2 +0 -0
  366. snappy/ptolemy/testing_files/DT_mcbbiceaibjklmdfgh__sl2_c2.magma_out.bz2 +0 -0
  367. snappy/ptolemy/testing_files/DT_mcbbiceaibjklmdfgh__sl2_c3.magma_out.bz2 +0 -0
  368. snappy/ptolemy/testing_files/DT_mcbbiceaibjklmdfgh__sl2_c4.magma_out.bz2 +0 -0
  369. snappy/ptolemy/testing_files/DT_mcbbiceaibjklmdfgh__sl2_c5.magma_out.bz2 +0 -0
  370. snappy/ptolemy/testing_files/DT_mcbbiceaibjklmdfgh__sl2_c6.magma_out.bz2 +0 -0
  371. snappy/ptolemy/testing_files/DT_mcbbiceaibjklmdfgh__sl2_c7.magma_out.bz2 +0 -0
  372. snappy/ptolemy/testing_files/data/pgl2/OrientableCuspedCensus/03_tetrahedra/m019__sl2_c0.magma_out +95 -0
  373. snappy/ptolemy/testing_files/data/pgl2/OrientableCuspedCensus/03_tetrahedra/m019__sl2_c1.magma_out +95 -0
  374. snappy/ptolemy/testing_files/m015__sl3_c0.magma_out.bz2 +0 -0
  375. snappy/ptolemy/testing_files/m135__sl2_c0.magma_out.bz2 +0 -0
  376. snappy/ptolemy/testing_files/m135__sl2_c1.magma_out.bz2 +0 -0
  377. snappy/ptolemy/testing_files/m135__sl2_c2.magma_out.bz2 +0 -0
  378. snappy/ptolemy/testing_files/m135__sl2_c3.magma_out.bz2 +0 -0
  379. snappy/ptolemy/testing_files/m135__sl2_c4.magma_out.bz2 +0 -0
  380. snappy/ptolemy/testing_files/m135__sl2_c5.magma_out.bz2 +0 -0
  381. snappy/ptolemy/testing_files/m135__sl2_c6.magma_out.bz2 +0 -0
  382. snappy/ptolemy/testing_files/m135__sl2_c7.magma_out.bz2 +0 -0
  383. snappy/ptolemy/testing_files/s000__sl2_c0.magma_out.bz2 +0 -0
  384. snappy/ptolemy/testing_files/s000__sl2_c1.magma_out.bz2 +0 -0
  385. snappy/ptolemy/testing_files/t00000__sl2_c0.magma_out.bz2 +0 -0
  386. snappy/ptolemy/testing_files/t00000__sl2_c1.magma_out.bz2 +0 -0
  387. snappy/ptolemy/testing_files/v0000__sl2_c0.magma_out.bz2 +0 -0
  388. snappy/ptolemy/testing_files/v0000__sl2_c1.magma_out.bz2 +0 -0
  389. snappy/ptolemy/testing_files/v0000__sl2_c2.magma_out.bz2 +0 -0
  390. snappy/ptolemy/testing_files/v0000__sl2_c3.magma_out.bz2 +0 -0
  391. snappy/ptolemy/testing_files_generalized/m003__sl2_c0.magma_out.bz2 +0 -0
  392. snappy/ptolemy/testing_files_generalized/m003__sl2_c1.magma_out.bz2 +0 -0
  393. snappy/ptolemy/testing_files_generalized/m003__sl3_c0.magma_out.bz2 +0 -0
  394. snappy/ptolemy/testing_files_generalized/m003__sl3_c1.magma_out.bz2 +0 -0
  395. snappy/ptolemy/testing_files_generalized/m004__sl2_c0.magma_out.bz2 +0 -0
  396. snappy/ptolemy/testing_files_generalized/m004__sl2_c1.magma_out.bz2 +0 -0
  397. snappy/ptolemy/testing_files_generalized/m015__sl2_c1.magma_out.bz2 +0 -0
  398. snappy/ptolemy/testing_files_generalized/m015__sl3_c0.magma_out.bz2 +0 -0
  399. snappy/ptolemy/testing_files_rur/m052__sl3_c0.rur.bz2 +0 -0
  400. snappy/ptolemy/utilities.py +236 -0
  401. snappy/raytracing/__init__.py +64 -0
  402. snappy/raytracing/additional_horospheres.py +64 -0
  403. snappy/raytracing/additional_len_spec_choices.py +63 -0
  404. snappy/raytracing/cohomology_fractal.py +197 -0
  405. snappy/raytracing/eyeball.py +124 -0
  406. snappy/raytracing/finite_raytracing_data.py +237 -0
  407. snappy/raytracing/finite_viewer.py +590 -0
  408. snappy/raytracing/geodesic_tube_info.py +174 -0
  409. snappy/raytracing/geodesics.py +246 -0
  410. snappy/raytracing/geodesics_window.py +258 -0
  411. snappy/raytracing/gui_utilities.py +293 -0
  412. snappy/raytracing/hyperboloid_navigation.py +556 -0
  413. snappy/raytracing/hyperboloid_utilities.py +234 -0
  414. snappy/raytracing/ideal_raytracing_data.py +592 -0
  415. snappy/raytracing/inside_viewer.py +974 -0
  416. snappy/raytracing/pack.py +22 -0
  417. snappy/raytracing/raytracing_data.py +126 -0
  418. snappy/raytracing/raytracing_view.py +454 -0
  419. snappy/raytracing/shaders/Eye.png +0 -0
  420. snappy/raytracing/shaders/NonGeometric.png +0 -0
  421. snappy/raytracing/shaders/__init__.py +101 -0
  422. snappy/raytracing/shaders/fragment.glsl +1744 -0
  423. snappy/raytracing/test.py +29 -0
  424. snappy/raytracing/tooltip.py +146 -0
  425. snappy/raytracing/upper_halfspace_utilities.py +98 -0
  426. snappy/raytracing/view_scale_controller.py +98 -0
  427. snappy/raytracing/zoom_slider/__init__.py +263 -0
  428. snappy/raytracing/zoom_slider/inward.png +0 -0
  429. snappy/raytracing/zoom_slider/inward18.png +0 -0
  430. snappy/raytracing/zoom_slider/outward.png +0 -0
  431. snappy/raytracing/zoom_slider/outward18.png +0 -0
  432. snappy/raytracing/zoom_slider/test.py +20 -0
  433. snappy/sage_helper.py +119 -0
  434. snappy/settings.py +407 -0
  435. snappy/shell.py +53 -0
  436. snappy/snap/__init__.py +117 -0
  437. snappy/snap/character_varieties.py +375 -0
  438. snappy/snap/find_field.py +372 -0
  439. snappy/snap/fox_milnor.py +271 -0
  440. snappy/snap/fundamental_polyhedron.py +569 -0
  441. snappy/snap/generators.py +39 -0
  442. snappy/snap/interval_reps.py +81 -0
  443. snappy/snap/kernel_structures.py +128 -0
  444. snappy/snap/mcomplex_base.py +18 -0
  445. snappy/snap/nsagetools.py +716 -0
  446. snappy/snap/peripheral/__init__.py +1 -0
  447. snappy/snap/peripheral/dual_cellulation.py +219 -0
  448. snappy/snap/peripheral/link.py +127 -0
  449. snappy/snap/peripheral/peripheral.py +159 -0
  450. snappy/snap/peripheral/surface.py +522 -0
  451. snappy/snap/peripheral/test.py +35 -0
  452. snappy/snap/polished_reps.py +335 -0
  453. snappy/snap/shapes.py +152 -0
  454. snappy/snap/slice_obs_HKL/__init__.py +194 -0
  455. snappy/snap/slice_obs_HKL/basics.py +236 -0
  456. snappy/snap/slice_obs_HKL/direct.py +217 -0
  457. snappy/snap/slice_obs_HKL/poly_norm.py +212 -0
  458. snappy/snap/slice_obs_HKL/rep_theory.py +424 -0
  459. snappy/snap/t3mlite/__init__.py +2 -0
  460. snappy/snap/t3mlite/arrow.py +243 -0
  461. snappy/snap/t3mlite/corner.py +22 -0
  462. snappy/snap/t3mlite/edge.py +172 -0
  463. snappy/snap/t3mlite/face.py +37 -0
  464. snappy/snap/t3mlite/files.py +211 -0
  465. snappy/snap/t3mlite/homology.py +53 -0
  466. snappy/snap/t3mlite/linalg.py +419 -0
  467. snappy/snap/t3mlite/mcomplex.py +1499 -0
  468. snappy/snap/t3mlite/perm4.py +320 -0
  469. snappy/snap/t3mlite/setup.py +12 -0
  470. snappy/snap/t3mlite/simplex.py +199 -0
  471. snappy/snap/t3mlite/spun.py +297 -0
  472. snappy/snap/t3mlite/surface.py +519 -0
  473. snappy/snap/t3mlite/test.py +20 -0
  474. snappy/snap/t3mlite/test_vs_regina.py +86 -0
  475. snappy/snap/t3mlite/tetrahedron.py +109 -0
  476. snappy/snap/t3mlite/vertex.py +42 -0
  477. snappy/snap/test.py +139 -0
  478. snappy/snap/utilities.py +288 -0
  479. snappy/test.py +213 -0
  480. snappy/test_cases.py +263 -0
  481. snappy/testing.py +131 -0
  482. snappy/tiling/__init__.py +2 -0
  483. snappy/tiling/dict_based_set.py +79 -0
  484. snappy/tiling/floor.py +49 -0
  485. snappy/tiling/hyperboloid_dict.py +54 -0
  486. snappy/tiling/iter_utils.py +78 -0
  487. snappy/tiling/lifted_tetrahedron.py +22 -0
  488. snappy/tiling/lifted_tetrahedron_set.py +54 -0
  489. snappy/tiling/quotient_dict.py +70 -0
  490. snappy/tiling/real_hash_dict.py +164 -0
  491. snappy/tiling/test.py +23 -0
  492. snappy/tiling/tile.py +224 -0
  493. snappy/tiling/triangle.py +33 -0
  494. snappy/tkterminal.py +920 -0
  495. snappy/twister/__init__.py +20 -0
  496. snappy/twister/main.py +646 -0
  497. snappy/twister/surfaces/S_0_1 +3 -0
  498. snappy/twister/surfaces/S_0_2 +3 -0
  499. snappy/twister/surfaces/S_0_4 +7 -0
  500. snappy/twister/surfaces/S_0_4_Lantern +8 -0
  501. snappy/twister/surfaces/S_1 +3 -0
  502. snappy/twister/surfaces/S_1_1 +4 -0
  503. snappy/twister/surfaces/S_1_2 +5 -0
  504. snappy/twister/surfaces/S_1_2_5 +6 -0
  505. snappy/twister/surfaces/S_2 +6 -0
  506. snappy/twister/surfaces/S_2_1 +8 -0
  507. snappy/twister/surfaces/S_2_heeg +10 -0
  508. snappy/twister/surfaces/S_3 +8 -0
  509. snappy/twister/surfaces/S_3_1 +10 -0
  510. snappy/twister/surfaces/S_4_1 +12 -0
  511. snappy/twister/surfaces/S_5_1 +14 -0
  512. snappy/twister/surfaces/heeg_fig8 +9 -0
  513. snappy/twister/twister_core.cpython-310-aarch64-linux-gnu.so +0 -0
  514. snappy/upper_halfspace/__init__.py +146 -0
  515. snappy/upper_halfspace/ideal_point.py +29 -0
  516. snappy/verify/__init__.py +13 -0
  517. snappy/verify/canonical.py +542 -0
  518. snappy/verify/complex_volume/__init__.py +18 -0
  519. snappy/verify/complex_volume/adjust_torsion.py +86 -0
  520. snappy/verify/complex_volume/closed.py +168 -0
  521. snappy/verify/complex_volume/compute_ptolemys.py +90 -0
  522. snappy/verify/complex_volume/cusped.py +56 -0
  523. snappy/verify/complex_volume/extended_bloch.py +201 -0
  524. snappy/verify/cusp_translations.py +85 -0
  525. snappy/verify/edge_equations.py +80 -0
  526. snappy/verify/exceptions.py +254 -0
  527. snappy/verify/hyperbolicity.py +224 -0
  528. snappy/verify/interval_newton_shapes_engine.py +523 -0
  529. snappy/verify/interval_tree.py +400 -0
  530. snappy/verify/krawczyk_shapes_engine.py +518 -0
  531. snappy/verify/real_algebra.py +286 -0
  532. snappy/verify/shapes.py +25 -0
  533. snappy/verify/square_extensions.py +1005 -0
  534. snappy/verify/test.py +72 -0
  535. snappy/verify/volume.py +128 -0
  536. snappy/version.py +2 -0
  537. snappy-3.3.dist-info/METADATA +58 -0
  538. snappy-3.3.dist-info/RECORD +541 -0
  539. snappy-3.3.dist-info/WHEEL +6 -0
  540. snappy-3.3.dist-info/entry_points.txt +2 -0
  541. snappy-3.3.dist-info/top_level.txt +28 -0
@@ -0,0 +1,480 @@
1
+ from .exceptions import CuspDevelopmentExactVerifyError
2
+
3
+ from ...math_basics import correct_min, correct_max, lower
4
+
5
+ from ...snap import t3mlite as t3m
6
+ from ...snap.t3mlite import simplex
7
+ from ...snap.mcomplex_base import *
8
+
9
+ from typing import Any, List, Optional
10
+
11
+ class HoroTriangleBase:
12
+ @staticmethod
13
+ def _make_second(sides, x):
14
+ """
15
+ Cyclically rotate sides = (a,b,c) so that x is the second entry"
16
+ """
17
+ i = (sides.index(x) + 2) % len(sides)
18
+ return sides[i:]+sides[:i]
19
+
20
+ @staticmethod
21
+ def _sides_and_cross_ratios(tet, vertex, side):
22
+ sides = simplex.FacesAroundVertexCounterclockwise[vertex]
23
+ left_side, center_side, right_side = (
24
+ HoroTriangleBase._make_second(sides, side))
25
+ z_left = tet.ShapeParameters[left_side & center_side ]
26
+ z_right = tet.ShapeParameters[center_side & right_side ]
27
+ return left_side, center_side, right_side, z_left, z_right
28
+
29
+ class CuspCrossSectionBase(McomplexEngine):
30
+ """
31
+ Base class for RealCuspCrossSection and ComplexCuspCrossSection.
32
+ """
33
+
34
+ def add_structures(self, one_cocycle=None):
35
+ self._add_edge_dict()
36
+ self._add_cusp_cross_sections(one_cocycle)
37
+
38
+ def _add_edge_dict(self):
39
+ """
40
+ Adds a dictionary that maps a pair of vertices to all edges
41
+ of the triangulation connecting these vertices.
42
+ The key is a pair (v0, v1) of integers with v0 < v1 that are the
43
+ indices of the two vertices.
44
+ """
45
+
46
+ self._edge_dict = {}
47
+ for edge in self.mcomplex.Edges:
48
+ vert0, vert1 = edge.Vertices
49
+ key = tuple(sorted([vert0.Index, vert1.Index]))
50
+ self._edge_dict.setdefault(key, []).append(edge)
51
+
52
+ def _add_cusp_cross_sections(self, one_cocycle):
53
+ for T in self.mcomplex.Tetrahedra:
54
+ T.horotriangles = {}
55
+ for cusp in self.mcomplex.Vertices:
56
+ if cusp.is_complete or one_cocycle:
57
+ self._add_one_cusp_cross_section(cusp, one_cocycle)
58
+
59
+ def _add_one_cusp_cross_section(self, cusp, one_cocycle):
60
+ """
61
+ Build a cusp cross section as described in Section 3.6 of the paper
62
+
63
+ Asymmetric hyperbolic L-spaces, Heegaard genus, and Dehn filling
64
+ Nathan M. Dunfield, Neil R. Hoffman, Joan E. Licata
65
+ http://arxiv.org/abs/1407.7827
66
+ """
67
+ corner0 = cusp.Corners[0]
68
+ tet0, vert0 = corner0.Tetrahedron, corner0.Subsimplex
69
+ face0 = simplex.FacesAroundVertexCounterclockwise[vert0][0]
70
+ tet0.horotriangles[vert0] = self.HoroTriangle(tet0, vert0, face0)
71
+ active = [(tet0, vert0)]
72
+ while active:
73
+ tet0, vert0 = active.pop()
74
+ for face0 in simplex.FacesAroundVertexCounterclockwise[vert0]:
75
+ tet1, face1, vert1 = CuspCrossSectionBase._glued_to(
76
+ tet0, face0, vert0)
77
+ if not vert1 in tet1.horotriangles:
78
+ known_side = (self.HoroTriangle.direction_sign() *
79
+ tet0.horotriangles[vert0].lengths[face0])
80
+ if one_cocycle and not one_cocycle == 'develop':
81
+ known_side *= one_cocycle[tet0.Index, face0, vert0]
82
+
83
+ tet1.horotriangles[vert1] = self.HoroTriangle(
84
+ tet1, vert1, face1, known_side)
85
+ active.append((tet1, vert1))
86
+
87
+ @staticmethod
88
+ def _glued_to(tetrahedron, face, vertex):
89
+ """
90
+ Returns (other tet, other face, other vertex).
91
+ """
92
+ gluing = tetrahedron.Gluing[face]
93
+ return tetrahedron.Neighbor[face], gluing.image(face), gluing.image(vertex)
94
+
95
+ @staticmethod
96
+ def cusp_area(cusp):
97
+ area = 0
98
+ for corner in cusp.Corners:
99
+ subsimplex = corner.Subsimplex
100
+ area += corner.Tetrahedron.horotriangles[subsimplex].area
101
+ return area
102
+
103
+ def cusp_areas(self):
104
+ """
105
+ List of all cusp areas.
106
+ """
107
+ return [ CuspCrossSectionBase.cusp_area(cusp) for cusp in self.mcomplex.Vertices ]
108
+
109
+ @staticmethod
110
+ def _scale_cusp(cusp, scale):
111
+ for corner in cusp.Corners:
112
+ subsimplex = corner.Subsimplex
113
+ corner.Tetrahedron.horotriangles[subsimplex].rescale(scale)
114
+
115
+ def scale_cusps(self, scales):
116
+ """
117
+ Scale each cusp by Euclidean dilation by values in given array.
118
+ """
119
+ for cusp, scale in zip(self.mcomplex.Vertices, scales):
120
+ CuspCrossSectionBase._scale_cusp(cusp, scale)
121
+
122
+ def normalize_cusps(self, areas=None):
123
+ """
124
+ Scale cusp so that they have the given target area.
125
+ Without argument, each cusp is scaled to have area 1.
126
+ If the argument is a number, scale each cusp to have that area.
127
+ If the argument is an array, scale each cusp by the respective
128
+ entry in the array.
129
+ """
130
+ current_areas = self.cusp_areas()
131
+ if not areas:
132
+ areas = [ 1 for area in current_areas ]
133
+ elif not isinstance(areas, list):
134
+ areas = [ areas for area in current_areas ]
135
+ scales = [ (area / current_area).sqrt()
136
+ for area, current_area in zip(areas, current_areas) ]
137
+ self.scale_cusps(scales)
138
+
139
+ def check_cusp_development_exactly(self):
140
+ """
141
+ Check that all side lengths of horo triangles are consistent.
142
+ If the logarithmic edge equations are fulfilled, this implices
143
+ that the all cusps are complete and thus the manifold is complete.
144
+ """
145
+
146
+ for tet0 in self.mcomplex.Tetrahedra:
147
+ for vert0 in simplex.ZeroSubsimplices:
148
+ for face0 in simplex.FacesAroundVertexCounterclockwise[vert0]:
149
+ tet1, face1, vert1 = CuspCrossSectionBase._glued_to(
150
+ tet0, face0, vert0)
151
+ side0 = tet0.horotriangles[vert0].lengths[face0]
152
+ side1 = tet1.horotriangles[vert1].lengths[face1]
153
+ if not side0 == side1 * self.HoroTriangle.direction_sign():
154
+ raise CuspDevelopmentExactVerifyError(side0, side1)
155
+
156
+ def _testing_check_against_snappea(self, epsilon):
157
+ # Short-hand
158
+ ZeroSubs = simplex.ZeroSubsimplices
159
+
160
+ # SnapPea kernel results
161
+ snappea_tilts, snappea_edges = self.manifold._cusp_cross_section_info()
162
+
163
+ # Check edge lengths
164
+ # Iterate through tet
165
+ for tet, snappea_tet_edges in zip(self.mcomplex.Tetrahedra, snappea_edges):
166
+ # Iterate through vertices of tet
167
+ for v, snappea_triangle_edges in zip(ZeroSubs, snappea_tet_edges):
168
+ # Iterate through faces touching that vertex
169
+ for f, snappea_triangle_edge in zip(ZeroSubs,
170
+ snappea_triangle_edges):
171
+ if v != f:
172
+ F = simplex.comp(f)
173
+ length = abs(tet.horotriangles[v].lengths[F])
174
+ if not abs(length - snappea_triangle_edge) < epsilon:
175
+ raise ConsistencyWithSnapPeaNumericalVerifyError(
176
+ snappea_triangle_edge, length)
177
+
178
+ @staticmethod
179
+ def _lower_bound_max_area_triangle_for_std_form(z):
180
+ """
181
+ Imagine an ideal tetrahedron in the upper half space model with
182
+ vertices at 0, 1, z, and infinity. Pick the lowest (horizontal)
183
+ horosphere about infinity that intersects the tetrahedron in a
184
+ triangle, i.e, just touches the face opposite to infinity.
185
+ This method will return the hyperbolic area of that triangle.
186
+
187
+ The result is the same for z, 1/(1-z), and 1 - 1/z.
188
+ """
189
+
190
+ # First, we check whether the center of the circumcenter of the
191
+ # triangle containing 0, 1, and z is contained within the triangle.
192
+
193
+ # If the center is outside of the triangle, the Euclidean height of the
194
+ # horosphere is that of the highest point of the three arcs between
195
+ # 0, 1, and z.
196
+ # The height is half of the length e of the longest edge of the
197
+ # triangle.
198
+ # Given that the Euclidean area of the triangle is given by
199
+ # A = Im(z) / 2, its hyperbolic area is
200
+ # A / (e/2)^2 = Im(z) / 2 / (e^2/4) = 2 * Im(z) / e^2
201
+ #
202
+ # This is similar to fef_gen.py except that it had a bug in version 1.3
203
+ # and implemented the last inequality the other way around!
204
+ #
205
+ # The center is outside if one of the angles is > pi/2, cover each case
206
+ #
207
+
208
+ # Angle at 0 is > pi/2
209
+ if z.real() < 0:
210
+ # So longest edge of the triangle must be opposite of 0
211
+ return 2 * z.imag() / (abs(z - 1) ** 2)
212
+ # Angle at 1 is > pi/2
213
+ if z.real() > 1:
214
+ # So longest edge of the triangle must be opposite of 1
215
+ return 2 * z.imag() / (abs(z) ** 2)
216
+ # Angle at z is > pi/2
217
+ if abs(2 * z - 1) < 1:
218
+ # So longest edge of the triangle must be opposite of z
219
+ return 2 * z.imag()
220
+
221
+ # An interval note: the circumcenter might still be in the triangle,
222
+ # we just were not able to prove it. The area we compute is a lower
223
+ # bound in any case. Thus, the function is not guaranteed to compute
224
+ # the maximal area, just a lower bound for it.
225
+
226
+ # Now cover the case that the center of the triangle is within the
227
+ # triangle.
228
+
229
+ # The Euclidean area of the above triangle is given by
230
+ # A = Im(z) / 2
231
+ # and its Euclidean side lengths are given by
232
+ # a = 1, b = abs(z), and c = abs(z - 1).
233
+ #
234
+ # The Euclidean circumradius r of the triangle is given by the usual
235
+ # formula
236
+ # r = a * b * c / (4 * A)
237
+ #
238
+ # This is also the Euclidean radius of the circle containing 0, 1, and
239
+ # z and of the halfsphere above that circle that contains the face
240
+ # opposite to infinity.
241
+ # Therefore, r is also the Euclidean height of the above horosphere and
242
+ # hence, the hyperbolic metric at that height is 1/r.
243
+ # So the hyperbolic area of the triangle becomes
244
+ #
245
+ # A / r^2 = A / (a * b * c / (4 * A))^2 = 16 * A^3 / (a * b * c)^2
246
+ # = 2 * Im(z)^3 / (abs(z) * abs(z-1)) ^ 2
247
+
248
+ return 2 * z.imag() ** 3 / (abs(z) * abs(z - 1)) ** 2
249
+
250
+ @staticmethod
251
+ def _max_area_triangle_to_avoid_incenter(z):
252
+ abs_z = abs(z)
253
+ abs_z_minus_one = abs(z - 1)
254
+ return z.imag() * (1 + abs_z + abs_z_minus_one) / (4 * abs_z * abs_z_minus_one)
255
+
256
+ @staticmethod
257
+ def _compute_area_scale(corner : t3m.Corner, area_function):
258
+ """
259
+ For a tetrahedron and vertex of the tetrahedron, compute how much
260
+ the cusp neighborhood about the vertex can be scaled so that the cusp
261
+ triangle is given the by area_function.
262
+ """
263
+
264
+ tet = corner.Tetrahedron
265
+ z = tet.ShapeParameters[simplex.E01]
266
+ return area_function(z) / tet.horotriangles[corner.Subsimplex].area
267
+
268
+ @staticmethod
269
+ def _compute_max_scale(v : t3m.Vertex, max_area_function):
270
+ area_scales = [
271
+ CuspCrossSectionBase._compute_area_scale(corner, max_area_function)
272
+ for corner in v.Corners ]
273
+
274
+ return correct_min(area_scales).sqrt()
275
+
276
+ def compute_scale_for_std_form(self, v : t3m.Vertex):
277
+ """
278
+ Computes scale for cusp neighborhood about given vertex to ensure
279
+ that each tetrahedron adjacent to the vertex intersects the the
280
+ cusp neighborhood in standard form.
281
+ """
282
+ return CuspCrossSectionBase._compute_max_scale(
283
+ v, CuspCrossSectionBase._lower_bound_max_area_triangle_for_std_form)
284
+
285
+ def compute_scale_to_avoid_incenter(self, v : t3m.Vertex):
286
+ """
287
+ Computes scale for cusp neighborhood about given vertex to ensure
288
+ that the cusp neighborhood avoid the incenter of each tetrahedron.
289
+ """
290
+ return CuspCrossSectionBase._compute_max_scale(
291
+ v, CuspCrossSectionBase._max_area_triangle_to_avoid_incenter)
292
+
293
+ def ensure_std_form(self, allow_scaling_up=False):
294
+ """
295
+ Makes sure that the cusp neighborhoods intersect each tetrahedron
296
+ in standard form by scaling the cusp neighborhoods down if necessary.
297
+ """
298
+
299
+ z = self.mcomplex.Tetrahedra[0].ShapeParameters[simplex.E01]
300
+ RF = z.real().parent()
301
+ one = RF(1)
302
+
303
+ for v in self.mcomplex.Vertices:
304
+ scale = self.compute_scale_for_std_form(v)
305
+ if not allow_scaling_up:
306
+ scale = correct_min([one, scale])
307
+ CuspCrossSectionBase._scale_cusp(v, scale)
308
+
309
+ @staticmethod
310
+ def _exp_distance_edge_embedding(tet, perm):
311
+ # Get a face of the tetrahedron adjacent to that edge
312
+ face3 = simplex.TwoSubsimplices[perm[3]]
313
+ # At each end of the edge, this tetrahedron gives us one
314
+ # triangle of a cusp cross-section and the intersection of the
315
+ # face with the cusp cross-section gives us one edge of the
316
+ # triangle.
317
+ # Multiply the two edge lengths. If these are complex edge
318
+ # lengths, the result is actually the square of a Ptolemy
319
+ # coordinate (see C. Zickert, The volume and Chern-Simons
320
+ # invariant of a representation).
321
+ v0 = simplex.ZeroSubsimplices[perm[0]]
322
+ length0 = tet.horotriangles[v0].get_real_lengths()[face3]
323
+
324
+ v1 = simplex.ZeroSubsimplices[perm[1]]
325
+ length1 = tet.horotriangles[v1].get_real_lengths()[face3]
326
+
327
+ return 1 / (length0 * length1)
328
+
329
+ @staticmethod
330
+ def _exp_distance_edge(edge : t3m.Edge):
331
+ """
332
+ Given an edge, returns the maximal scaling factor of the two cusp
333
+ neighborhoods at the end of the edges so that the neighborhoods do
334
+ not intersect in the given edge.
335
+ """
336
+
337
+ distances = []
338
+ # Walk around the edge.
339
+ for i, (tet, perm) in enumerate(edge.embeddings()):
340
+ d = CuspCrossSectionBase._exp_distance_edge_embedding(tet, perm)
341
+
342
+ if i == 0:
343
+ v0 = simplex.ZeroSubsimplices[perm[0]]
344
+ v1 = simplex.ZeroSubsimplices[perm[1]]
345
+ if tet.Class[v0].is_complete and tet.Class[v1].is_complete:
346
+ # If both cusps are complete, then the horotriangles
347
+ # of one of the cusp neighborhoods all intersect the edge
348
+ # in the manifold in the same point. Thus, the distance
349
+ # we compute is the same, no matter from what tetrahedron
350
+ # we measure it.
351
+ return d
352
+
353
+ distances.append(d)
354
+
355
+ return correct_min(distances)
356
+
357
+ @staticmethod
358
+ def _exp_distance_of_edges(edges: List[t3m.Edge]):
359
+ """
360
+ Implements exp_distance_neighborhoods_measured_along_edges given
361
+ all edges connecting two cusps in question.
362
+ """
363
+ return correct_min(
364
+ [ CuspCrossSectionBase._exp_distance_edge(edge)
365
+ for edge in edges])
366
+
367
+ def exp_distance_neighborhoods_measured_along_edges(
368
+ self, i : int, j : int) -> Optional[Any]:
369
+ """
370
+ Computes the maximal scaling factor of the cusp neighborhoods
371
+ about cusp i and j such that the two neighborhoods stay disjoint
372
+ along the edges.
373
+
374
+ That is if we scale both cusp i and j, then they are disjoint along
375
+ edges if the product of the scale factor is less than the maximal
376
+ scaling factor.
377
+
378
+ Note that if i and j are the same, because the scaling factor applies
379
+ to the same cusp twice, we only can scale the one cusp by a factor
380
+ sqrt(maximal scaling factor) to stay disjoint along edges.
381
+
382
+ This function can return None if no edge between the two given
383
+ cusps exists.
384
+
385
+ Assume two cusp neighborhoods are disjoing along edges. They could
386
+ still intersect if they are not in standard form.
387
+
388
+ Note that this method also works for filled cusps. In this case,
389
+ the neighborhood is about a core curve in the manifold and consists
390
+ of the intersections with a tetrahedra by horoballs about its vertices.
391
+ o
392
+ When using filled cusps, it is advisable to call
393
+ scale_triangles_to_avoid_standard_tube first.
394
+ """
395
+ if i > j:
396
+ i, j = j, i
397
+ if not (i, j) in self._edge_dict:
398
+ return None
399
+ return CuspCrossSectionBase._exp_distance_of_edges(
400
+ self._edge_dict[(i,j)])
401
+
402
+ def ensure_disjoint_on_edges(self):
403
+ """
404
+ Scales the cusp neighborhoods down until they are disjoint when
405
+ intersected with the edges of the triangulations.
406
+
407
+ Given an edge of a triangulation, we can easily compute the signed
408
+ distance between the two cusp neighborhoods at the ends of the edge
409
+ measured along that edge. Thus, we can easily check that all the
410
+ distances measured along all the edges are positive and scale the
411
+ cusps down if necessary.
412
+
413
+ Unfortunately, this is not sufficient to ensure that two cusp
414
+ neighborhoods are disjoint since there might be a geodesic between
415
+ the two cusps such that the distance between the two cusps measured
416
+ along the geodesic is shorter than measured along any edge of the
417
+ triangulation.
418
+
419
+ Thus, it is necessary to call ensure_std_form as well:
420
+ it will make sure that the cusp neighborhoods are small enough so
421
+ that they intersect the tetrahedra in "standard" form.
422
+ Here, "standard" form means that the corresponding horoball about a
423
+ vertex of a tetrahedron intersects the three faces of the tetrahedron
424
+ adjacent to the vertex but not the one opposite to the vertex.
425
+
426
+ For any geometric triangulation, standard form and positive distance
427
+ measured along all edges of the triangulation is sufficient for
428
+ disjoint neighborhoods.
429
+
430
+ The SnapPea kernel uses the proto-canonical triangulation associated
431
+ to the cusp neighborhood to get around this when computing the
432
+ "reach" and the "stoppers" for the cusps.
433
+
434
+ **Remark:** This means that the cusp neighborhoods might be scaled down
435
+ more than necessary. Related open questions are: given maximal disjoint
436
+ cusp neighborhoods (maximal in the sense that no neighborhood can be
437
+ expanded without bumping into another or itself), is there always a
438
+ geometric triangulation intersecting the cusp neighborhoods in standard
439
+ form? Is there an easy algorithm to find this triangulation, e.g., by
440
+ applying a 2-3 move whenever we see a non-standard intersection?
441
+ """
442
+
443
+ num_cusps = len(self.mcomplex.Vertices)
444
+
445
+ # First check for every cusp that its cusp neighborhood does not bump
446
+ # into itself - at least when measured along the edges of the
447
+ # triangulation
448
+ for i in range(num_cusps):
449
+ # Get all edges
450
+ if (i,i) in self._edge_dict:
451
+ dist = CuspCrossSectionBase._exp_distance_of_edges(
452
+ self._edge_dict[(i,i)])
453
+ # For verified computations, do not use the seemingly
454
+ # equivalent dist <= 1. We want to scale down every time
455
+ # we cannot ensure they are disjoint.
456
+ if not (dist > 1):
457
+ scale = dist.sqrt()
458
+ # Scale the one cusp
459
+ CuspCrossSectionBase._scale_cusp(self.mcomplex.Vertices[i],
460
+ scale)
461
+
462
+ # Now check for the pairs of two distinct cusps that the corresponding
463
+ # neighborhoods do not bump into each other - at least when measured
464
+ # along the edges of the triangulation
465
+ for i in range(num_cusps):
466
+ for j in range(i):
467
+ dist = self.exp_distance_neighborhoods_measured_along_edges(i, j)
468
+ # Above comment applies
469
+ if dist is not None:
470
+ if not (dist > 1):
471
+ # Scale the two cusps by the same amount
472
+ # We have choices here, for example, we could only
473
+ # scale one cusp by dist.
474
+ scale = dist.sqrt()
475
+ CuspCrossSectionBase._scale_cusp(self.mcomplex.Vertices[i],
476
+ scale)
477
+ CuspCrossSectionBase._scale_cusp(self.mcomplex.Vertices[j],
478
+ scale)
479
+
480
+
@@ -0,0 +1,41 @@
1
+ class IncompleteCuspError(ValueError):
2
+ """
3
+ Exception raised when trying to use a method requiring a complete
4
+ geometric structure.
5
+ """
6
+ def __init__(self, manifold):
7
+ self.manifold = manifold
8
+
9
+ def __str__(self):
10
+ return (('Method only supports complete geometric structure but '
11
+ 'is given a manifold with Dehn-fillings: %s') % self.manifold)
12
+
13
+ class ConsistencyWithSnapPeaNumericalVerifyError(RuntimeError):
14
+ """
15
+ Exception raised when there is a significant numerical difference
16
+ between the values computed by the SnapPea kernel and by this module
17
+ for a given quantity.
18
+ """
19
+ def __init__(self, value, snappea_value):
20
+ self.value = value
21
+ self.snappea_value = snappea_value
22
+
23
+ def __str__(self):
24
+ return ('Inconsistency between SnapPea kernel and verify: '
25
+ '%r == %r' % (self.snappea_value, self.value))
26
+
27
+ class CuspDevelopmentExactVerifyError(RuntimeError):
28
+ """
29
+ Raised when finding a consistent assignment of side lengths to the
30
+ Euclidean Horotriangles to form a Euclidean Horotorus for a cusp failed
31
+ using exact arithmetic.
32
+ """
33
+
34
+ def __init__(self, value1, value2):
35
+ self.value1 = value1
36
+ self.value2 = value2
37
+
38
+ def __str__(self):
39
+ return ('Inconsistency in the side lengths of the Euclidean '
40
+ 'Horotriangles for a cusp: '
41
+ '%r = %r' % (self.value1, self.value2))