Skip to content

Commit

Permalink
Migrate to using points as vertex coordinates
Browse files Browse the repository at this point in the history
* Store points in Mesh
* Use points in solids
* Parse points in obj loader
* Change projection matrix apply to take Point
  • Loading branch information
jdahlstrom committed Dec 8, 2024
1 parent 855688a commit 7e581e7
Show file tree
Hide file tree
Showing 11 changed files with 119 additions and 100 deletions.
11 changes: 7 additions & 4 deletions core/src/geom.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,10 @@
//! Basic geometric primitives.
use crate::math::vec::{Vec2, Vec3};
use crate::render::Model;
use crate::{
math::point::{Point2, Point3},
math::vec::{Vec2, Vec3},
render::Model,
};

pub use mesh::Mesh;

Expand All @@ -15,10 +18,10 @@ pub struct Vertex<P, A> {
}

/// Two-dimensional vertex type.
pub type Vertex2<A, B = Model> = Vertex<Vec2<B>, A>;
pub type Vertex2<A, B = Model> = Vertex<Point2<B>, A>;

/// Three-dimensional vertex type.
pub type Vertex3<A, B = Model> = Vertex<Vec3<B>, A>;
pub type Vertex3<A, B = Model> = Vertex<Point3<B>, A>;

/// Triangle, defined by three vertices.
#[derive(Copy, Clone, Debug, Eq, PartialEq)]
Expand Down
42 changes: 22 additions & 20 deletions core/src/geom/mesh.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,8 @@ use alloc::{vec, vec::Vec};

use crate::math::{
mat::{Mat4x4, RealToReal},
point::Point3,
space::Linear,
vec::Vec3,
};
use crate::render::Model;

Expand Down Expand Up @@ -51,16 +51,17 @@ impl<A, B> Mesh<A, B> {
/// # Examples
/// ```
/// # use retrofire_core::geom::{Tri, Mesh, vertex};
/// # use retrofire_core::math::vec3;
/// # use retrofire_core::math::point::pt3;
/// let verts = [
/// vec3(0.0, 0.0, 0.0),
/// vec3(1.0, 0.0, 0.0),
/// vec3(0.0, 1.0, 0.0),
/// vec3(0.0, 0.0, 1.0)
/// pt3(0.0, 0.0, 0.0),
/// pt3(1.0, 0.0, 0.0),
/// pt3(0.0, 1.0, 0.0),
/// pt3(0.0, 0.0, 1.0)
/// ]
/// .map(|v| vertex(v, ()));
///
/// let faces = [
/// // Indices point to the verts array
/// Tri([0, 1, 2]),
/// Tri([0, 1, 3]),
/// Tri([0, 2, 3]),
Expand Down Expand Up @@ -126,16 +127,16 @@ impl<A> Builder<A> {
}

/// Appends a vertex with the given position and attribute.
pub fn push_vert(&mut self, pos: Vec3, attrib: A) {
pub fn push_vert(&mut self, pos: Point3, attrib: A) {
self.mesh.verts.push(vertex(pos.to(), attrib));
}

/// Appends all the vertices yielded by the given iterator.
pub fn push_verts<Vs>(&mut self, verts: Vs)
where
Vs: IntoIterator<Item = (Vec3, A)>,
Vs: IntoIterator<Item = (Point3, A)>,
{
let vs = verts.into_iter().map(|(v, a)| vertex(v.to(), a));
let vs = verts.into_iter().map(|(p, a)| vertex(p.to(), a));
self.mesh.verts.extend(vs);
}

Expand Down Expand Up @@ -164,7 +165,7 @@ impl Builder<()> {
.mesh
.verts
.into_iter()
.map(|v| vertex(tf.apply(&v.pos), v.attrib))
.map(|v| vertex(tf.apply_pt(&v.pos), v.attrib))
.collect(),
};
mesh.into_builder()
Expand Down Expand Up @@ -254,6 +255,7 @@ mod tests {
use core::f32::consts::FRAC_1_SQRT_2;

use crate::geom::vertex;
use crate::math::point::pt3;
use crate::math::vec3;
use crate::prelude::splat;

Expand All @@ -265,9 +267,9 @@ mod tests {
let _: Mesh<()> = Mesh::new(
[Tri([0, 1, 2]), Tri([1, 2, 3])],
[
vertex(vec3(0.0, 0.0, 0.0), ()),
vertex(vec3(1.0, 1.0, 1.0), ()),
vertex(vec3(2.0, 2.0, 2.0), ()),
vertex(pt3(0.0, 0.0, 0.0), ()),
vertex(pt3(1.0, 1.0, 1.0), ()),
vertex(pt3(2.0, 2.0, 2.0), ()),
],
);
}
Expand All @@ -278,9 +280,9 @@ mod tests {
let mut b = Mesh::builder();
b.push_faces([[0, 1, 2], [1, 2, 3]]);
b.push_verts([
(vec3(0.0, 0.0, 0.0), ()),
(vec3(1.0, 1.0, 1.0), ()),
(vec3(2.0, 2.0, 2.0), ()),
(pt3(0.0, 0.0, 0.0), ()),
(pt3(1.0, 1.0, 1.0), ()),
(pt3(2.0, 2.0, 2.0), ()),
]);
_ = b.build();
}
Expand All @@ -292,10 +294,10 @@ mod tests {
let mut b = Mesh::builder();
b.push_faces([[0, 2, 1], [0, 1, 3], [0, 3, 2]]);
b.push_verts([
(vec3(0.0, 0.0, 0.0), ()),
(vec3(1.0, 0.0, 0.0), ()),
(vec3(0.0, 1.0, 0.0), ()),
(vec3(0.0, 0.0, 1.0), ()),
(pt3(0.0, 0.0, 0.0), ()),
(pt3(1.0, 0.0, 0.0), ()),
(pt3(0.0, 1.0, 0.0), ()),
(pt3(0.0, 0.0, 1.0), ()),
]);
let b = b.with_vertex_normals();

Expand Down
18 changes: 10 additions & 8 deletions core/src/math/mat.rs
Original file line number Diff line number Diff line change
Expand Up @@ -386,7 +386,7 @@ impl<Src> Mat4x4<RealToProj<Src>> {
/// \ · · M33 / \ 1 /
/// ```
#[must_use]
pub fn apply(&self, v: &Vec3<Src>) -> ProjVec4 {
pub fn apply(&self, v: &Point3<Src>) -> ProjVec4 {
let v = Vector::from([v.x(), v.y(), v.z(), 1.0]);
[
self.row_vec(0).dot(&v),
Expand Down Expand Up @@ -623,6 +623,7 @@ pub fn perspective(
/// # Parameters
/// * `lbn`: The left-bottom-near corner of the projection box.
/// * `rtf`: The right-bottom-far corner of the projection box.
// TODO Change to take points
pub fn orthographic(lbn: Vec3, rtf: Vec3) -> Mat4x4<ViewToProj> {
let [dx, dy, dz] = (rtf - lbn).0;
let [sx, sy, sz] = (rtf + lbn).0;
Expand Down Expand Up @@ -660,6 +661,7 @@ mod tests {

#[cfg(feature = "fp")]
use crate::math::angle::degs;
use crate::math::point::pt3;

use super::*;

Expand Down Expand Up @@ -929,26 +931,26 @@ mod tests {

#[test]
fn orthographic_box_maps_to_unit_cube() {
let lbn = vec3(-20.0, 0.0, 0.01);
let rtf = vec3(100.0, 50.0, 100.0);
let lbn = pt3(-20.0, 0.0, 0.01);
let rtf = pt3(100.0, 50.0, 100.0);

let m = orthographic(lbn, rtf);
let m = orthographic(lbn.to_vec(), rtf.to_vec());

assert_approx_eq!(m.apply(&lbn.to()), [-1.0, -1.0, -1.0, 1.0].into());
assert_approx_eq!(m.apply(&rtf.to()), splat(1.0));
assert_approx_eq!(m.apply(&rtf.to()), [1.0, 1.0, 1.0, 1.0].into());
}

#[test]
fn perspective_frustum_maps_to_unit_cube() {
let left_bot_near = vec3(-0.125, -0.0625, 0.1);
let right_top_far = vec3(125.0, 62.5, 100.0);
let left_bot_near = pt3(-0.125, -0.0625, 0.1);
let right_top_far = pt3(125.0, 62.5, 100.0);

let m = perspective(0.8, 2.0, 0.1..100.0);

let lbn = m.apply(&left_bot_near);
assert_approx_eq!(lbn / lbn.w(), [-1.0, -1.0, -1.0, 1.0].into());

let rtf = m.apply(&right_top_far);
assert_approx_eq!(rtf / rtf.w(), splat(1.0));
assert_approx_eq!(rtf / rtf.w(), [1.0, 1.0, 1.0, 1.0].into());
}
}
3 changes: 1 addition & 2 deletions core/src/render.rs
Original file line number Diff line number Diff line change
Expand Up @@ -16,10 +16,9 @@ use crate::math::{
Lerp,
};

use crate::render::raster::ScreenVec;
use clip::{view_frustum, Clip, ClipVert};
use ctx::{Context, DepthSort, FaceCull};
use raster::tri_fill;
use raster::{tri_fill, ScreenVec};
use shader::{FragmentShader, VertexShader};
use stats::Stats;
use target::Target;
Expand Down
4 changes: 2 additions & 2 deletions demos/src/bin/crates.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ use core::ops::ControlFlow::*;
use re::prelude::*;

use re::geom::Vertex3;
use re::math::color::gray;
use re::math::{color::gray, point::pt3};
use re::render::{
batch::Batch,
cam::{Camera, FirstPerson},
Expand Down Expand Up @@ -121,7 +121,7 @@ fn floor() -> Mesh<Color3f> {
for i in -size..=size {
let even_odd = ((i & 1) ^ (j & 1)) == 1;

let pos = vec3(i as f32, -1.0, j as f32);
let pos = pt3(i as f32, -1.0, j as f32);
let col = if even_odd { gray(0.2) } else { gray(0.9) };
bld.push_vert(pos, col);

Expand Down
13 changes: 7 additions & 6 deletions demos/src/bin/solids.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,8 @@ use re::prelude::*;

use re::geom::Vertex3;
use re::math::{
color::gray, mat::RealToReal, spline::smootherstep, vec::ProjVec4,
color::gray, mat::RealToReal, point::pt2, spline::smootherstep,
vec::ProjVec4,
};
use re::render::{batch::Batch, cam::Camera, ModelToProj, ModelToWorld};

Expand Down Expand Up @@ -157,11 +158,11 @@ fn objects(res: u32) -> [Mesh<Normal3>; 13] {
fn lathe(secs: u32) -> Mesh<Normal3> {
Lathe::new(
vec![
vertex(vec2(0.75, -0.5), vec2(1.0, 1.0)),
vertex(vec2(0.55, -0.25), vec2(1.0, 0.5)),
vertex(vec2(0.5, 0.0), vec2(1.0, 0.0)),
vertex(vec2(0.55, 0.25), vec2(1.0, -0.5)),
vertex(vec2(0.75, 0.5), vec2(1.0, 1.0)),
vertex(pt2(0.75, -0.5), vec2(1.0, 1.0)),
vertex(pt2(0.55, -0.25), vec2(1.0, 0.5)),
vertex(pt2(0.5, 0.0), vec2(1.0, 0.0)),
vertex(pt2(0.55, 0.25), vec2(1.0, -0.5)),
vertex(pt2(0.75, 0.5), vec2(1.0, 1.0)),
],
secs,
)
Expand Down
5 changes: 3 additions & 2 deletions demos/src/bin/sprites.rs
Original file line number Diff line number Diff line change
Expand Up @@ -20,10 +20,11 @@ fn main() {
];
let count = 10000;
let rng = Xorshift64::default();
// TODO Points in unit ball and other distribs
let verts: Vec<Vertex3<Vec2<_>>> = UnitBall
.samples(rng)
.take(count)
.flat_map(|pos| verts.map(|v| vertex(pos.to(), v)))
.flat_map(|pos| verts.map(|v| vertex(pos.to().to_pt(), v)))
.collect();

let tris: Vec<_> = (0..count)
Expand All @@ -40,7 +41,7 @@ fn main() {
|v: Vertex3<Vec2<_>>,
(mv, proj): (&Mat4x4<ModelToView>, &Mat4x4<ViewToProj>)| {
let vertex_pos = 0.008 * vec3(v.attrib.x(), v.attrib.y(), 0.0);
let view_pos = mv.apply(&v.pos) + vertex_pos;
let view_pos = mv.apply_pt(&v.pos) + vertex_pos;
vertex(proj.apply(&view_pos), v.attrib)
},
|frag: Frag<Vec2<_>>| {
Expand Down
16 changes: 10 additions & 6 deletions demos/src/bin/square.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,16 +2,20 @@ use std::ops::ControlFlow::*;

use re::prelude::*;

use re::geom::Vertex3;
use re::render::{ctx::Context, render, tex::SamplerClamp, ModelToProj};
use re::{
geom::Vertex3,
math::point::pt3,
render::{ctx::Context, render, tex::SamplerClamp, ModelToProj},
};

use re_front::minifb::Window;

fn main() {
let verts: [Vertex3<TexCoord>; 4] = [
vertex(vec3(-1.0, -1.0, 0.0), uv(0.0, 0.0)),
vertex(vec3(-1.0, 1.0, 0.0), uv(0.0, 1.0)),
vertex(vec3(1.0, -1.0, 0.0), uv(1.0, 0.0)),
vertex(vec3(1.0, 1.0, 0.0), uv(1.0, 1.0)),
vertex(pt3(-1.0, -1.0, 0.0), uv(0.0, 0.0)),
vertex(pt3(-1.0, 1.0, 0.0), uv(0.0, 1.0)),
vertex(pt3(1.0, -1.0, 0.0), uv(1.0, 0.0)),
vertex(pt3(1.0, 1.0, 0.0), uv(1.0, 1.0)),
];

let mut win = Window::builder()
Expand Down
10 changes: 5 additions & 5 deletions demos/wasm/src/triangle.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,13 +6,13 @@ use re::geom::{vertex, Tri, Vertex3};
use re::math::{
color::{rgba, Color4f},
mat::{perspective, rotate_z, translate, viewport},
point::pt3,
rads, vec2, vec3,
};
use re::render::{raster::Frag, render, shader::Shader, ModelToView};
use re::util::Dims;

use re_front::dims::SVGA_800_600;
use re_front::wasm::Window;
use re_front::{dims::SVGA_800_600, wasm::Window};

// Entry point from JS
#[wasm_bindgen(start)]
Expand All @@ -25,9 +25,9 @@ pub fn start() {
win.ctx.color_clear = Some(rgba(0, 0, 0, 0x80));

let vs = [
vertex(vec3(-2.0, 1.0, 0.0), rgba(1.0, 0.2, 0.1, 0.9)),
vertex(vec3(2.0, 2.0, 0.0), rgba(0.2, 0.9, 0.1, 0.8)),
vertex(vec3(0.0, -2.0, 0.0), rgba(0.3, 0.4, 1.0, 1.0)),
vertex(pt3(-2.0, 1.0, 0.0), rgba(1.0, 0.2, 0.1, 0.9)),
vertex(pt3(2.0, 2.0, 0.0), rgba(0.2, 0.9, 0.1, 0.8)),
vertex(pt3(0.0, -2.0, 0.0), rgba(0.3, 0.4, 1.0, 1.0)),
];

let proj = perspective(1.0, 4.0 / 3.0, 0.1..1000.0);
Expand Down
Loading

0 comments on commit 7e581e7

Please sign in to comment.