Skip to main content

base_2/
lib.rs

1#![warn(missing_docs)]
2//! # `base_2`
3//!
4//! Exact fixed-point geometry. Float in, float out, zero drift inside.
5//!
6//! ## The problem
7//!
8//! Floating point geometry drifts. Every transform, every frame, every
9//! physics tick adds a tiny error. Over time vertices shift, collision
10//! checks disagree, and multiplayer clients desync. The root cause is always
11//! the same: floating point math is approximate by design.
12//!
13//! ## The fix
14//!
15//! `base_2` intercepts your geometry once, freezes it to exact 64-bit integers,
16//! and gives you back two representations:
17//!
18//! - **Exact `i64`** — for logic, physics, collision. Deterministic on a given platform.
19//! - **Clean `f32`** — freshly derived from the exact source every frame, for your GPU.
20//!
21//! Error is introduced exactly once, at freeze time, bounded at ≤ 2^-33 of your input unit.
22//! It does not grow with subsequent operations.
23//!
24//! ## Coordinate system
25//!
26//! Internally, 1 unit = 2^-32 of your input unit.
27//! This gives:
28//! - **Resolution**: 2^-32 per input unit
29//! - **Range**: ±2^31 input units with `i64`, ±2^95 input units with `i128`
30//! - **Overflow**: predictable — `i64` always uses all 64 bits, so worst-case
31//!   arithmetic behavior is known upfront, not discovered at runtime
32//!
33//! Units in your API are user-defined. Pass millimeters, game units, or
34//! anything else — as long as you are consistent.
35//!
36//! ## Quick start
37//!
38//! ```rust
39//! use base_2::api::Mesh;
40//!
41//! // load from any float source — STL, OBJ, GLTF, engine mesh, etc.
42//! let mesh = Mesh::from_floats(&float_verts)
43//!     .translate(10.0, 0.0, 0.0)
44//!     .rotate_quat(0.0, 0.0, 0.707, 0.707);
45//!
46//! // compute once per frame
47//! let pts = mesh.compute();
48//!
49//! let gpu   = pts.to_f32();  // clean floats for renderer — derived fresh each frame
50//! let logic = pts.to_i64();  // exact integers for physics and collision
51//! ```
52//!
53//! ## Why `base_2`?
54//!
55//! The 2^-32 scaling is not arbitrary. It means every coordinate uses all 64 bits,
56//! giving uniform precision across the entire range. There is no false headroom,
57//! no "works on small inputs but breaks on large ones." Overflow behavior is
58//! always worst-case, always documented, always the same.
59//!
60//! It is the fixed-point equivalent of Rust's ownership model:
61//! honest about what it costs, in exchange for guarantees you can rely on.
62
63mod coord;
64mod point;
65mod transforms;
66
67pub mod api;
68
69pub use api::{Mesh, Points, Transform, RotationMatrix};
70pub use coord::{Coord64, Coord128};
71pub use point::{Point3, Point2};