Exact Symbolic Demonstrations (demos/)

All executable Python constructions for Albrecht Dürer’s Underweysung der Messung live cleanly outside the historical codex in demos/ and src/geometor/durer/. Every Model instance runs with auto_intersect=False and 100% exact SymPy coordinates over $\mathbb{Q}$, $\mathbb{Q}(\sqrt{2})$, $\mathbb{Q}(\sqrt{3})$, $\mathbb{Q}(\phi)$, and $\mathbb{Q}(\sqrt{5}, \sin 36^\circ)$.

1. Book I — Spirals & Two-View Conic Sections

Constructs Dürer’s 12-sector Archimedean spiral (Schneckenlini) over $\mathbb{Q}(\sqrt{3})$ and verifies his 12-station descriptive-geometry transfer law $w_k = \frac{\sqrt{2k(12 - k)}}{3}$ for the right circular cone, proving exact bilateral symmetry $w_{12-k} = w_k$ (Elipsis vs. Eierlini).

 1"""Runnable demonstration of Book I Archimedean spirals & two-view orthographic conic sections."""
         2
         3from __future__ import annotations
         4
         5import sys
         6from pathlib import Path
         7
         8ROOT = Path(__file__).resolve().parents[1]
         9for p in (ROOT / "src", ROOT.parent / "model" / "src"):
        10    if str(p) not in sys.path:
        11        sys.path.insert(0, str(p))
        12
        13from rich.console import Console
        14from rich.table import Table
        15
        16from geometor.durer import construct_durer_conic_sections, construct_durer_spiral_volute
        17
        18
        19def main() -> None:
        20    console = Console()
        21    spiral = construct_durer_spiral_volute(turns=2)
        22    conics = construct_durer_conic_sections()
        23
        24    console.print("[bold cyan]Book I — 12-Sector Archimedean Spiral & Two-View Conic Projection[/bold cyan]")
        25    console.print(
        26        f"Spiral sectors: {spiral.sector_count}, outer radius: {spiral.outer_radius}, "
        27        f"constructed exact points in Q(sqrt(3)): {len(spiral.spiral_points)}"
        28    )
        29
        30    tbl = Table(title="Book I, Fig. 34 — Orthographic Cone-Section Stations (Elipsis / Eierlini)")
        31    tbl.add_column("Station k", justify="right")
        32    tbl.add_column("Elevation x_k")
        33    tbl.add_column("Height z_k")
        34    tbl.add_column("Plan Radius r_k")
        35    tbl.add_column("Exact Half-Width w_k", style="green")
        36
        37    for k, xk, zk, rk, wk in conics.ellipse_stations:
        38        tbl.add_row(str(k), str(xk), str(zk), str(rk), str(wk))
        39
        40    console.print(tbl)
        41    console.print(
        42        f"Bilateral symmetry w_k == w_{{12-k}} verified: [bold green]{conics.ellipse_bilateral_symmetry_verified}[/bold green]  |  "
        43        f"a = {conics.ellipse_semi_major}, b = {conics.ellipse_semi_minor}, "
        44        f"c = {conics.ellipse_focal_distance}, e = {conics.ellipse_eccentricity}"
        45    )
        46    console.print(
        47        f"Parabola focal length f = {conics.parabola_focal_length}  |  "
        48        f"Hyperbola (a_h, b_h) = ({conics.hyperbola_semi_transverse}, {conics.hyperbola_semi_conjugate})"
        49    )
        50
        51
        52if __name__ == "__main__":
        53    main()
        

2. Book II — Pentagon, Heptagon & Quadrature Audit

Constructs both Dürer’s single-aperture (“rusty compass”) pentagon and Euclid’s $\mathbb{Q}(\phi)$ regular pentagon on shared base $AB$, proving exact unit side quadrances $Q = 1$ and quantifying the $+21.97'$ base-angle discrepancy, alongside the Eisenstein cubic residual $P_7\left(\frac{3}{4}\right) = -\frac{1}{64}$ for the workshop heptagon and $\pi_{\text{Dürer}} = \frac{25}{8}$.

 1"""Runnable demonstration auditing Book II regular polygons (Dürer vs. Euclid) & circle quadrature."""
         2
         3from __future__ import annotations
         4
         5import sys
         6from pathlib import Path
         7
         8ROOT = Path(__file__).resolve().parents[1]
         9for p in (ROOT / "src", ROOT.parent / "model" / "src"):
        10    if str(p) not in sys.path:
        11        sys.path.insert(0, str(p))
        12
        13from rich.console import Console
        14from rich.table import Table
        15
        16from geometor.durer import (
        17    construct_durer_heptagon_workshop,
        18    construct_durer_vs_euclid_pentagon,
        19)
        20
        21
        22def main() -> None:
        23    console = Console()
        24    pent = construct_durer_vs_euclid_pentagon()
        25    hep = construct_durer_heptagon_workshop()
        26
        27    console.print("[bold cyan]Book II — Demonstrative vs. Mechanice Regular Polygons[/bold cyan]")
        28    console.print(f"Euclid regular pentagon over Q(phi) verified: [green]{pent.euclid_regular}[/green]")
        29    console.print(
        30        f"Dürer single-aperture pentagon: equilateral=[green]{pent.durer_equilateral}[/green], "
        31        f"equiangular=[yellow]{pent.durer_equiangular}[/yellow]"
        32    )
        33    console.print(
        34        f"Dürer base interior angle = {pent.durer_base_interior_deg:.5f}° vs. 108.00000° "
        35        f"(error = {pent.base_angle_error_deg:+.5f}° = {pent.base_angle_error_arcmin:+.2f}')"
        36    )
        37    console.print(
        38        f"Heptagon minimal polynomial P_7(q) = {hep.minimal_polynomial_expr}; "
        39        f"P_7(3/4) = [bold yellow]{hep.minimal_polynomial_at_durer}[/bold yellow] (Eisenstein p={hep.eisenstein_prime})"
        40    )
        41
        42    tbl = Table(title="Book II Polygon & Quadrature Accuracy Audit")
        43    tbl.add_column("n", justify="right")
        44    tbl.add_column("Construction")
        45    tbl.add_column("Type", style="magenta")
        46    tbl.add_column("Exact s/R")
        47    tbl.add_column("Rel. Chord Error", justify="right")
        48    tbl.add_column("Step Angle", justify="right")
        49
        50    for row in hep.workshop_catalog:
        51        tbl.add_row(
        52            str(row.n_sides),
        53            row.durer_label,
        54            row.classification,
        55            str(row.exact_chord_over_r),
        56            f"{row.relative_chord_error * 100:+.4f}%",
        57            f"{row.central_angle_durer_deg:.4f}° (true {row.central_angle_true_deg:.4f}°)",
        58        )
        59    console.print(tbl)
        60    console.print(
        61        f"Circle Quadrature (Fig. 34): d/a = {hep.quadrature_circle_diameter_over_side} "
        62        f"=> pi_Durer = {hep.quadrature_implied_pi} = {float(hep.quadrature_implied_pi):.4f}"
        63    )
        64
        65
        66if __name__ == "__main__":
        67    main()
        

3. Book III — Roman Antiqua Capitals & Modular Textura

Constructs Roman capitals A, O, and Q inside the $10 \times 10$ square (rechte Fierung) with $1 : \frac{1}{3}$ stroke contrast, circular serif fillets ($r = \frac{10}{7}, \frac{1}{2}$), and shifted-diagonal bowls ($r = 5 - \frac{\sqrt{2}}{4}$), paired with modular Gothic Textura minuscules i, n, m.

 1"""Runnable demonstration of Book III Roman Antiqua capitals (A, O, Q) & Gothic Textura minuscules."""
         2
         3from __future__ import annotations
         4
         5import sys
         6from pathlib import Path
         7
         8ROOT = Path(__file__).resolve().parents[1]
         9for p in (ROOT / "src", ROOT.parent / "model" / "src"):
        10    if str(p) not in sys.path:
        11        sys.path.insert(0, str(p))
        12
        13from rich.console import Console
        14from rich.table import Table
        15
        16from geometor.durer import (
        17    construct_durer_roman_letter_A,
        18    construct_durer_roman_letter_O,
        19    construct_durer_roman_letter_Q,
        20    construct_durer_textura_minuscules,
        21)
        22
        23
        24def main() -> None:
        25    console = Console()
        26    let_a = construct_durer_roman_letter_A()
        27    let_o = construct_durer_roman_letter_O()
        28    let_q = construct_durer_roman_letter_Q()
        29    tex = construct_durer_textura_minuscules()
        30
        31    tbl = Table(title="Book III — Geometric Typography (Antiqua & Textura)")
        32    tbl.add_column("Glyph", style="cyan")
        33    tbl.add_column("Framing Grid")
        34    tbl.add_column("Exact Algebraic Parameters", style="green")
        35
        36    tbl.add_row(
        37        "Roman A",
        38        "10 x 10 Square",
        39        f"thick={let_a.thick_stroke}, thin={let_a.thin_stroke}, "
        40        f"outer serif r={let_a.outer_serif_radius}, inner serif r={let_a.inner_serif_radius}, "
        41        f"counter apex=({let_a.counter_triangle[2].x}, {let_a.counter_triangle[2].y})",
        42    )
        43    tbl.add_row(
        44        "Roman O",
        45        "10 x 10 Square (cb diagonal)",
        46        f"centers f=({let_o.shifted_center_f.x}, {let_o.shifted_center_f.y}), "
        47        f"g=({let_o.shifted_center_g.x}, {let_o.shifted_center_g.y}), r={let_o.bowl_radius}",
        48    )
        49    tbl.add_row(
        50        "Roman Q",
        51        "10 x 10 Square + ad tail",
        52        f"bowl r={let_q.bowl_radius}, tail tip=({let_q.tail_points[-1].x}, {let_q.tail_points[-1].y})",
        53    )
        54    tbl.add_row(
        55        "Textura i, n, m",
        56        "3 Unit Squares + 45° Diamonds",
        57        f"stem width={tex.stem_width}, modules: i={len(tex.glyph_polygons['i'])}, "
        58        f"n={len(tex.glyph_polygons['n'])}, m={len(tex.glyph_polygons['m'])}",
        59    )
        60    console.print(tbl)
        61
        62
        63if __name__ == "__main__":
        64    main()
        

4. Book IV — Planar Polyhedral Nets & Perspective Apparatus

Unfolds exact non-overlapping planar nets for the Tetrahedron, Cube, Octahedron, Dodecahedron (double 6-pentagon rosette), Icosahedron, and Archimedean Cuboctahedron, projects a 3D cube in $\mathbb{Q}^3$ onto Dürer’s glass picture plane verifying harmonic cross-ratio invariance $\operatorname{CR}(A', E'; M', V_x) = -1$, and generates all 11 .euclid-graphic SVG plates.

 1"""Runnable demonstration of Book IV planar polyhedral nets, perspective glass frame & cube doubling."""
         2
         3from __future__ import annotations
         4
         5import sys
         6from pathlib import Path
         7
         8ROOT = Path(__file__).resolve().parents[1]
         9for p in (ROOT / "src", ROOT.parent / "model" / "src"):
        10    if str(p) not in sys.path:
        11        sys.path.insert(0, str(p))
        12
        13from rich.console import Console
        14from rich.table import Table
        15
        16from geometor.durer import (
        17    construct_durer_perspective_apparatus,
        18    construct_durer_polyhedral_nets,
        19    generate_all_codex_figures,
        20)
        21
        22
        23def main() -> None:
        24    console = Console()
        25    nets = construct_durer_polyhedral_nets()
        26    persp = construct_durer_perspective_apparatus()
        27
        28    tbl = Table(title="Book IV — Exact Planar Polyhedral Fold-Out Nets")
        29    tbl.add_column("Net", style="cyan")
        30    tbl.add_column("Field", style="magenta")
        31    tbl.add_column("V, E, F (chi)")
        32    tbl.add_column("Folds / Cuts")
        33    tbl.add_column("Unit Q=1", style="green")
        34    tbl.add_column("Disjoint", style="green")
        35
        36    for net in nets.values():
        37        tbl.add_row(
        38            net.title,
        39            net.algebraic_field,
        40            f"({net.vertices_3d}, {net.edges_3d}, {net.faces_3d}) -> {net.euler_characteristic}",
        41            f"{len(net.fold_edges)} / {len(net.cut_edges)}",
        42            str(net.unit_edge_verified),
        43            str(net.non_overlapping_verified),
        44        )
        45    console.print(tbl)
        46
        47    console.print(
        48        f"Perspective Apparatus: Eye={persp.eye_3d} -> Vanishing Point V_x="
        49        f"({persp.vanishing_point.x}, {persp.vanishing_point.y}), "
        50        f"Harmonic Cross-Ratio CR={persp.harmonic_cross_ratio_2d} "
        51        f"(verified={persp.cross_ratio_invariant_verified})"
        52    )
        53    console.print(
        54        f"Delian Doubling of the Cube (Fig. 50): g={persp.delian_cube.given_g}, "
        55        f"c={persp.delian_cube.first_mean_c}, d={persp.delian_cube.second_mean_d}, "
        56        f"e={persp.delian_cube.given_e} => c^3/g^3 = {persp.delian_cube.volume_ratio}"
        57    )
        58
        59    figs_dir = ROOT / "docsrc" / "_static" / "figures"
        60    paths = generate_all_codex_figures(figs_dir)
        61    console.print(f"[bold green]Generated {len(paths)} .euclid-graphic SVG figures in {figs_dir}[/bold green]")
        62
        63
        64if __name__ == "__main__":
        65    main()