This commit is contained in:
2021-10-26 17:28:29 +02:00
parent f0c9ed5e51
commit 28576035eb
6 changed files with 94 additions and 75 deletions

View File

@@ -64,12 +64,12 @@ name = "move_forward"
controller_axis = "LeftStickY" controller_axis = "LeftStickY"
[[axis]] [[axis]]
name = "move_sideways" name = "move_right"
positive_button = "button_right" positive_button = "button_right"
negative_button = "button_left" negative_button = "button_left"
[[axis]] [[axis]]
name = "move_sideways" name = "move_right"
controller_axis = "LeftStickX" controller_axis = "LeftStickX"
[[axis]] [[axis]]

View File

@@ -50,15 +50,15 @@
"player": { "player": {
"mesh_index": null, "mesh_index": null,
"position": [ "position": [
2.5716693, 0.0,
1.304583, 0.0,
-8.255934 10.0
], ],
"rotation": [ "rotation": [
-0.23996419, 1.0,
-0.011724341, 0.0,
0.9695545, 0.0,
0.047371186 0.0
], ],
"scale": [ "scale": [
1.0, 1.0,

View File

@@ -21,14 +21,6 @@ out gl_PerVertex {
}; };
void main() { void main() {
float scale = 0.01;
mat4 invert = mat4(
scale, 0., 0., 0.,
0., scale, 0., 0.,
0., 0., scale, 0.,
0., 0., 0., 1.
);
// Vertex position in camera // Vertex position in camera
gl_Position = ubo.ortho_projection * vec4(position, 1.0); gl_Position = ubo.ortho_projection * vec4(position, 1.0);

View File

@@ -1,10 +1,9 @@
use cgmath::{Deg, InnerSpace, Matrix4, One, Quaternion, Rad, Rotation, Rotation3, SquareMatrix, Vector2, Vector3, Vector4, vec3, vec4}; use cgmath::{Deg, InnerSpace, Matrix4, One, Quaternion, Rad, Rotation, Rotation3, SquareMatrix, Vector2, Vector3, vec3, vec4};
use vulkano::buffer::TypedBufferAccess;
use crate::game::player::PlayerMovementMode::{FirstPerson, Flying}; use crate::game::player::PlayerMovementMode::{FirstPerson, Flying};
use crate::input::InputState; use crate::input::InputState;
use crate::vulkan::Mesh; use crate::util::{intersection_distance, print_matrix};
use crate::vulkan::gameobject::GameObject; use crate::vulkan::gameobject::GameObject;
use crate::vulkan::{ use crate::vulkan::{
gameobject::Updatable, gameobject::Updatable,
@@ -51,7 +50,6 @@ impl Camera {
0.1, 0.1,
100.0 100.0
); );
// Why?
self.proj.y.y *= -1.0; self.proj.y.y *= -1.0;
self.ortho_proj = cgmath::ortho(0., width, 0., height, -1., 1.); self.ortho_proj = cgmath::ortho(0., width, 0., height, -1., 1.);
@@ -123,58 +121,6 @@ impl Player {
} }
} }
pub fn vec4_from_pos(pos: [f32; 3]) -> Vector4<f32> {
vec4(pos[0], pos[1], pos[2], 1.0)
}
pub fn intersection_distance(ray_origin: Vector3<f32>, ray_direction: Vector3<f32>, mesh: &Mesh<crate::vulkan::Vertex>, game_object: &GameObject) -> Option<f32> {
let index_lock = mesh.index_buffer.read().unwrap();
let vertex_lock = mesh.vertex_buffer.read().unwrap();
(0..mesh.index_buffer.len() / 3).map(|tri_idx| {
let vtx_a = game_object.get_model_matrix() * vec4_from_pos(vertex_lock[index_lock[tri_idx as usize * 3 ] as usize].position);
let vtx_b = game_object.get_model_matrix() * vec4_from_pos(vertex_lock[index_lock[tri_idx as usize * 3 + 1] as usize].position);
let vtx_c = game_object.get_model_matrix() * vec4_from_pos(vertex_lock[index_lock[tri_idx as usize * 3 + 2] as usize].position);
intersect_triangle(ray_origin, ray_direction, vtx_a.truncate().into(), vtx_b.truncate().into(), vtx_c.truncate().into())
}).fold(None, |acc, x| {
if let Some(smallest) = acc {
if let Some(new) = x {
if new < smallest {
Some(new)
} else {
Some(smallest)
}
} else {
acc
}
} else {
x
}
})
}
// https://en.wikipedia.org/wiki/M%C3%B6ller%E2%80%93Trumbore_intersection_algorithm
pub fn intersect_triangle(ray_origin: Vector3<f32>, ray_direction: Vector3<f32>, vtx_a: [f32; 3], vtx_b: [f32; 3], vtx_c: [f32; 3]) -> Option<f32> {
let edge_1 = vec3(vtx_b[0] - vtx_a[0], vtx_b[1] - vtx_a[1], vtx_b[2] - vtx_a[2]);
let edge_2 = vec3(vtx_c[0] - vtx_a[0], vtx_c[1] - vtx_a[1], vtx_c[2] - vtx_a[2]);
let h = ray_direction.cross(edge_2);
let a = edge_1.dot(h);
if a > -f32::EPSILON && a < f32::EPSILON { return None; }
let f = 1. / a;
let s: Vector3<f32> = ray_origin - Vector3::from(vtx_a);
let u = f * s.dot(h);
if u < 0. || u > 1. { return None; }
let q = s.cross(edge_1);
let v = f * ray_direction.dot(q);
if v < 0. || u + v > 1. { return None; }
let t = f * edge_2.dot(q);
if t > f32::EPSILON { return Some(t); }
None
}
impl Updatable for Player { impl Updatable for Player {
fn update(&mut self, delta_time: f32, input: &InputState, _game_state: &mut GameState, game_objects: &mut Vec<GameObject>, renderer: &mut VulkanRenderer) { fn update(&mut self, delta_time: f32, input: &InputState, _game_state: &mut GameState, game_objects: &mut Vec<GameObject>, renderer: &mut VulkanRenderer) {
// Edit mode // Edit mode
@@ -204,7 +150,7 @@ impl Updatable for Player {
self.camera.rotation = x_rot * y_rot; self.camera.rotation = x_rot * y_rot;
// Movement // Movement
let local_input = vec3(input.get_axis("move_sideways"), 0.0, -input.get_axis("move_forward")) * self.movement_speed * delta_time; let local_input = vec3(input.get_axis("move_right"), 0.0, -input.get_axis("move_forward")) * self.movement_speed * delta_time;
if self.movement_mode == FirstPerson { if self.movement_mode == FirstPerson {
let mut world_input = self.camera.local_to_world(local_input); let mut world_input = self.camera.local_to_world(local_input);
@@ -217,4 +163,4 @@ impl Updatable for Player {
// Update // Update
self.camera.update(renderer); self.camera.update(renderer);
} }
} }

View File

@@ -12,6 +12,7 @@ mod config;
mod game; mod game;
mod tests; mod tests;
mod text; mod text;
mod util;
fn main() { fn main() {
let log_config = LogConfig::from_file("config/log.toml"); let log_config = LogConfig::from_file("config/log.toml");

80
src/util.rs Normal file
View File

@@ -0,0 +1,80 @@
use cgmath::{InnerSpace, Matrix4, SquareMatrix, Vector3, Vector4, vec3, vec4};
use vulkano::buffer::TypedBufferAccess;
use crate::vulkan::{Mesh, gameobject::GameObject};
pub fn print_matrix(mat: Matrix4<f32>) {
let cols = [
[mat.x.x, mat.x.y, mat.x.z, mat.x.w],
[mat.y.x, mat.y.y, mat.y.z, mat.y.w],
[mat.z.x, mat.z.y, mat.z.z, mat.z.w],
[mat.w.x, mat.w.y, mat.w.z, mat.w.w],
].map(|v| v.map(|e| format!("{:.2}", e)));
let col_sizes: Vec<usize> = cols.iter().map(|col| col.iter().map(|s| s.len()).max().unwrap()).collect();
println!("Mat4: {}", mat.determinant());
for row_index in 0..4 {
for col_index in 0..4 {
let mut str = format!("{}", cols[col_index][row_index]);
while str.len() < col_sizes[col_index] {
str.insert(0, ' ');
}
print!("{}", str);
if col_index < 3 { print!(", "); }
}
println!();
}
}
pub fn intersection_distance(ray_origin: Vector3<f32>, ray_direction: Vector3<f32>, mesh: &Mesh<crate::vulkan::Vertex>, game_object: &GameObject) -> Option<f32> {
let index_lock = mesh.index_buffer.read().unwrap();
let vertex_lock = mesh.vertex_buffer.read().unwrap();
(0..mesh.index_buffer.len() / 3).map(|tri_idx| {
let vtx_a = game_object.get_model_matrix() * vec4_from_pos(vertex_lock[index_lock[tri_idx as usize * 3 ] as usize].position);
let vtx_b = game_object.get_model_matrix() * vec4_from_pos(vertex_lock[index_lock[tri_idx as usize * 3 + 1] as usize].position);
let vtx_c = game_object.get_model_matrix() * vec4_from_pos(vertex_lock[index_lock[tri_idx as usize * 3 + 2] as usize].position);
intersect_triangle(ray_origin, ray_direction, vtx_a.truncate().into(), vtx_b.truncate().into(), vtx_c.truncate().into())
}).fold(None, |acc, x| {
if let Some(smallest) = acc {
if let Some(new) = x {
if new < smallest {
Some(new)
} else {
Some(smallest)
}
} else {
acc
}
} else {
x
}
})
}
// https://en.wikipedia.org/wiki/M%C3%B6ller%E2%80%93Trumbore_intersection_algorithm
pub fn intersect_triangle(ray_origin: Vector3<f32>, ray_direction: Vector3<f32>, vtx_a: [f32; 3], vtx_b: [f32; 3], vtx_c: [f32; 3]) -> Option<f32> {
let edge_1 = vec3(vtx_b[0] - vtx_a[0], vtx_b[1] - vtx_a[1], vtx_b[2] - vtx_a[2]);
let edge_2 = vec3(vtx_c[0] - vtx_a[0], vtx_c[1] - vtx_a[1], vtx_c[2] - vtx_a[2]);
let h = ray_direction.cross(edge_2);
let a = edge_1.dot(h);
if a > -f32::EPSILON && a < f32::EPSILON { return None; }
let f = 1. / a;
let s: Vector3<f32> = ray_origin - Vector3::from(vtx_a);
let u = f * s.dot(h);
if u < 0. || u > 1. { return None; }
let q = s.cross(edge_1);
let v = f * ray_direction.dot(q);
if v < 0. || u + v > 1. { return None; }
let t = f * edge_2.dot(q);
if t > f32::EPSILON { return Some(t); }
None
}
pub fn vec4_from_pos(pos: [f32; 3]) -> Vector4<f32> {
vec4(pos[0], pos[1], pos[2], 1.0)
}