mirror of
https://github.com/Mercantec-GHC/h5-projekt-mst.git
synced 2026-08-26 21:27:38 +02:00
fix phweedee wendewing
This commit is contained in:
parent
e831c07ac1
commit
f9af4ffe28
@ -11,11 +11,13 @@ impl V3 {
|
||||
Self(v, v, v)
|
||||
}
|
||||
|
||||
/// See https://en.wikipedia.org/wiki/3D_projection#Mathematical_formula
|
||||
/// for details on the implementation.
|
||||
pub fn project_2d(&self, camera_pos: V3) -> V2 {
|
||||
// V2(self.0 / self.2, self.1 / self.2)
|
||||
let a = *self;
|
||||
let c = camera_pos;
|
||||
let d = *self - c;
|
||||
let e = V3(0.0, 0.0, 0.0) - c;
|
||||
let d = a - c;
|
||||
let e = (camera_pos + V3(0.0, 0.0, 1.0)) - c;
|
||||
V2(e.2 / d.2 * d.0 + e.0, e.2 / d.2 * d.1 + e.1)
|
||||
}
|
||||
|
||||
@ -32,7 +34,7 @@ impl V3 {
|
||||
}
|
||||
|
||||
pub fn len(&self) -> f64 {
|
||||
f64::sqrt(self.0.powi(2) + self.1.powi(2) + self.2.powi(2))
|
||||
(self.0.powi(2) + self.1.powi(2) + self.2.powi(2)).sqrt()
|
||||
}
|
||||
|
||||
pub fn unit(&self) -> Self {
|
||||
@ -51,6 +53,10 @@ impl V3 {
|
||||
pub fn distance(&self, rhs: Self) -> f64 {
|
||||
(*self - rhs).len()
|
||||
}
|
||||
|
||||
pub fn angle(&self, rhs: Self) -> f64 {
|
||||
(self.dot(rhs) / (self.len() * rhs.len())).acos()
|
||||
}
|
||||
}
|
||||
|
||||
impl Add for V3 {
|
||||
|
||||
@ -3,7 +3,6 @@
|
||||
mod error;
|
||||
mod game;
|
||||
mod math;
|
||||
mod r3d;
|
||||
mod scene;
|
||||
mod sdl_io;
|
||||
mod shapes;
|
||||
@ -11,7 +10,6 @@ mod shapes;
|
||||
pub use error::*;
|
||||
pub use game::*;
|
||||
pub use math::*;
|
||||
pub use r3d::*;
|
||||
pub use scene::*;
|
||||
pub use sdl_io::*;
|
||||
pub use shapes::*;
|
||||
|
||||
@ -1,81 +0,0 @@
|
||||
use crate::engine::{game::Renderer, Color, Shape, Triangle2, Triangle3, V2, V3};
|
||||
|
||||
pub struct R3d<'r, R: Renderer> {
|
||||
r: &'r mut R,
|
||||
triangle_buffer: Vec<Triangle2>,
|
||||
camera_pos: V3,
|
||||
}
|
||||
|
||||
impl<'r, R: Renderer> R3d<'r, R> {
|
||||
pub fn new(r: &'r mut R, camera_pos: V3) -> Self {
|
||||
Self {
|
||||
r,
|
||||
triangle_buffer: Vec::new(),
|
||||
camera_pos,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn draw_line(&mut self, from: V3, to: V3, color: Color) {
|
||||
self.r.draw_line(
|
||||
from.project_2d(self.camera_pos),
|
||||
to.project_2d(self.camera_pos),
|
||||
color,
|
||||
);
|
||||
}
|
||||
|
||||
pub fn draw_triangle(&mut self, triangle: Triangle3, color: Color) {
|
||||
let triangle = triangle
|
||||
.translate(self.camera_pos)
|
||||
.project_2d(self.camera_pos);
|
||||
|
||||
self.r.draw_line(triangle.0, triangle.1, color);
|
||||
self.r.draw_line(triangle.1, triangle.2, color);
|
||||
self.r.draw_line(triangle.2, triangle.0, color);
|
||||
}
|
||||
|
||||
pub fn draw_shape(&mut self, pos: V3, shape: &Shape, outline_color: Color, fill_color: Color) {
|
||||
self.triangle_buffer.clear();
|
||||
self.triangle_buffer.extend(
|
||||
shape
|
||||
.faces()
|
||||
.map(|tri| tri.translate(pos).project_2d(self.camera_pos)),
|
||||
);
|
||||
|
||||
self.r.draw_triangles(&self.triangle_buffer, fill_color);
|
||||
|
||||
for face in shape.faces() {
|
||||
if face.normal().dot(face.0 - self.camera_pos + pos) >= 0.0 {
|
||||
continue;
|
||||
}
|
||||
// let pxyz = face.middle() + face.normal();
|
||||
// self.draw_line(
|
||||
// face.middle() + pos,
|
||||
// face.middle() + (face.1 - face.0).unit() * 0.02 + pos,
|
||||
// Color::HEX(0xffaa00),
|
||||
// );
|
||||
// self.draw_line(
|
||||
// face.middle() + pos,
|
||||
// face.middle() + (face.2 - face.1).unit() * 0.02 + pos,
|
||||
// Color::HEX(0x00ffaa),
|
||||
// );
|
||||
// self.draw_line(
|
||||
// face.middle() + pos,
|
||||
// face.middle() + (face.0 - face.2).unit() * 0.02 + pos,
|
||||
// Color::HEX(0xaa00ff),
|
||||
// );
|
||||
// self.draw_line(face.middle() + pos, pxyz + pos, Color::HEX(0xffffff));
|
||||
|
||||
// self.draw_triangle(face.translate(pos - CAMERA_POS), outline_color);
|
||||
self.r.draw_line(
|
||||
(face.0 + pos).project_2d(self.camera_pos),
|
||||
(face.1 + pos).project_2d(self.camera_pos),
|
||||
outline_color,
|
||||
);
|
||||
self.r.draw_line(
|
||||
(face.2 + pos).project_2d(self.camera_pos),
|
||||
(face.0 + pos).project_2d(self.camera_pos),
|
||||
outline_color,
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -1,72 +1,60 @@
|
||||
use std::f64::consts::PI;
|
||||
|
||||
use crate::engine::{Color, Renderer, Shape, Triangle3, V3};
|
||||
|
||||
pub struct DrawnTriangle {
|
||||
triangle: Triangle3,
|
||||
outline_color: Color,
|
||||
fill_color: Color,
|
||||
}
|
||||
|
||||
pub struct Scene {
|
||||
objects: Vec<DrawnTriangle>,
|
||||
tris: Vec<(Triangle3, V3, Color, Color)>,
|
||||
}
|
||||
|
||||
impl Scene {
|
||||
pub fn new() -> Self {
|
||||
Self {
|
||||
objects: Vec::new(),
|
||||
}
|
||||
Self { tris: Vec::new() }
|
||||
}
|
||||
|
||||
pub fn render<R: Renderer>(&mut self, r: &mut R, camera_pos: V3, camera_rot: V3) {
|
||||
pub fn render<R: Renderer>(&mut self, r: &mut R, camera_pos: V3) {
|
||||
let mut indices_with_scores = self
|
||||
.objects
|
||||
.tris
|
||||
.iter()
|
||||
.enumerate()
|
||||
.map(|(i, object)| {
|
||||
let mut point_scores = object.triangle.points().map(|p| p.distance(camera_pos));
|
||||
point_scores.sort_by(|a, b| a.total_cmp(b));
|
||||
.map(|(i, (tri, ..))| {
|
||||
let mut p_scores = [tri.0, tri.1, tri.2].map(|p| (camera_pos - p).len());
|
||||
|
||||
(i, point_scores[0])
|
||||
p_scores.sort_by(|a, b| a.total_cmp(b));
|
||||
|
||||
let score = p_scores[0] * p_scores[1];
|
||||
(i, score)
|
||||
})
|
||||
.rev()
|
||||
.collect::<Vec<_>>();
|
||||
|
||||
indices_with_scores.sort_by(|a, b| b.1.total_cmp(&a.1));
|
||||
|
||||
for (i, _) in indices_with_scores {
|
||||
let object = &self.objects[i];
|
||||
let tri3 = object
|
||||
.triangle
|
||||
.translate(camera_pos * -1.0)
|
||||
.rotate(camera_rot);
|
||||
'render_tri_loop: for (i, _) in indices_with_scores {
|
||||
let (tri3, normal, outline_color, fill_color) = &self.tris[i];
|
||||
|
||||
// check if behind camera
|
||||
// TODO: doesn't take camera_pos or camera_rot into accout
|
||||
if !(tri3.0 .2 >= 0.0 && tri3.1 .2 >= 0.0 && tri3.2 .2 >= 0.0) {
|
||||
for v in [tri3.0, tri3.1, tri3.2] {
|
||||
if v.2 < camera_pos.2 {
|
||||
continue 'render_tri_loop;
|
||||
}
|
||||
}
|
||||
|
||||
if normal.dot(camera_pos - tri3.0) < 0.0 {
|
||||
continue;
|
||||
}
|
||||
|
||||
if tri3.normal().dot(tri3.0 - camera_pos) >= 0.0 {
|
||||
continue;
|
||||
}
|
||||
let tri2 = tri3.project_2d(camera_pos);
|
||||
|
||||
let tri2 = tri3
|
||||
.translate(V3(0.0, 0.0, -1.0))
|
||||
.project_2d(V3(0.0, 0.0, -1.0));
|
||||
|
||||
r.draw_triangle(tri2.clone(), object.fill_color);
|
||||
r.draw_line(tri2.0, tri2.1, object.outline_color);
|
||||
r.draw_line(tri2.0, tri2.2, object.outline_color);
|
||||
r.draw_triangle(tri2.clone(), *fill_color);
|
||||
r.draw_line(tri2.0, tri2.1, *outline_color);
|
||||
r.draw_line(tri2.0, tri2.2, *outline_color);
|
||||
}
|
||||
}
|
||||
|
||||
pub fn draw_shape(&mut self, pos: V3, shape: &Shape, outline_color: Color, fill_color: Color) {
|
||||
for triangle in shape.faces() {
|
||||
self.objects.push(DrawnTriangle {
|
||||
triangle: triangle.translate(pos),
|
||||
outline_color,
|
||||
fill_color,
|
||||
})
|
||||
let tri = triangle.translate(pos);
|
||||
let normal = tri.normal();
|
||||
self.tris.push((tri, normal, outline_color, fill_color))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -231,7 +231,7 @@ impl<R: Renderer> engine::Game<R> for Game {
|
||||
for object in &self.objects {
|
||||
object.render(&mut scene);
|
||||
}
|
||||
scene.render(r, self.camera_pos, V3(0.0, 0.0, 0.0));
|
||||
scene.render(r, self.camera_pos);
|
||||
}
|
||||
|
||||
fn event(&mut self, event: engine::Event) {
|
||||
|
||||
@ -220,7 +220,7 @@ impl MotionDevice {
|
||||
}
|
||||
|
||||
fn main() {
|
||||
let mut reader = csv::Reader::from_path("assets/inputs_moving.csv").unwrap();
|
||||
let mut reader = csv::Reader::from_path("assets/inputs_still.csv").unwrap();
|
||||
let mut measurements = Vec::<Measurement>::new();
|
||||
for entry in reader.deserialize::<Measurement>() {
|
||||
let entry: Measurement = entry.unwrap();
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user