diff --git a/Cargo.toml b/Cargo.toml index 801589f..d50f172 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -9,4 +9,5 @@ edition = "2018" [dependencies] mat4 = "0.2.1" vec3 = "0.2.1" +vec4 = "0.2.1" sdl2 = "0.34.3" \ No newline at end of file diff --git a/src/main.rs b/src/main.rs index e20a28c..1141c87 100644 --- a/src/main.rs +++ b/src/main.rs @@ -16,13 +16,13 @@ fn main() { let video_subsystem = sdl_context.video().unwrap(); let window = video_subsystem - .window("rust-sdl2 demo", 800, 600) + .window("rust-sdl2 demo", 800, 800) .position_centered() .opengl() .build() .unwrap(); // let surface = Surface::new(512, 512, PixelFormatEnum::RGB24).unwrap(); - let mut data = Box::new([255u8; 1_440_000]); + let mut data = Box::new([255u8; 1_920_000]); // println!("{:?}", data); let mut canvas = window.into_canvas().build().unwrap(); // let mut canvas = surface.into_canvas().unwrap(); @@ -49,7 +49,7 @@ fn main() { // } // canvas.set_draw_color(Color::RGB(i, 64, 255 - i)); let surface = - Surface::from_data(&mut *data, 800, 600, 2400, PixelFormatEnum::RGB24).unwrap(); + Surface::from_data(&mut *data, 800, 800, 2400, PixelFormatEnum::RGB24).unwrap(); let texture = texture_creator .create_texture_from_surface(surface) .unwrap(); diff --git a/src/ray.rs b/src/ray.rs index 7432011..7459bb1 100644 --- a/src/ray.rs +++ b/src/ray.rs @@ -1,4 +1,4 @@ -#[derive(Clone, Copy)] +#[derive(Clone, Copy, Debug)] pub struct Ray { pub origin: [f64; 3], pub direction: [f64; 3], diff --git a/src/render.rs b/src/render.rs index 40f2f41..7827ec8 100644 --- a/src/render.rs +++ b/src/render.rs @@ -1,5 +1,6 @@ extern crate mat4; extern crate vec3; +extern crate vec4; use crate::object::Object; use crate::ray::Ray; @@ -17,40 +18,163 @@ pub fn render(data: &mut [u8]) { let projection_matrix: [f64; 16] = *mat4::perspective( &mut mat4::new_zero(), &(45. * 3.141592 / 180.), - &(800. / 600.), + &(800. / 800.), &(0.1), &(1000.), ); - let view_matrix: [f64; 16] = *mat4::translate( + // let view_matrix: [f64; 16] = *mat4::translate( + // &mut mat4::new_identity(), + // &mat4::new_identity(), + // &vec3::new(0., 0., -10.), + // ); + let mut view_matrix = mat4::new_zero(); + // view_matrix[0] = 1.; + // view_matrix[4] = 0.; + // view_matrix[8] = 0.; + // view_matrix[12] = 0.; + // view_matrix[1] = 0.; + // view_matrix[5] = 1.; + // view_matrix[9] = 0.; + // view_matrix[13] = 0.; + // view_matrix[2] = 0.; + // view_matrix[6] = 0.; + // view_matrix[10] = 1.; + // view_matrix[14] = 0.; + // view_matrix[3] = 0.; + // view_matrix[7] = 0.; + // view_matrix[11] = -10.; + // view_matrix[15] = 1.; + view_matrix[0] = 1.; + view_matrix[1] = 0.; + view_matrix[2] = 0.; + view_matrix[3] = 0.; + view_matrix[4] = 0.; + view_matrix[5] = 1.; + view_matrix[6] = 0.; + view_matrix[7] = 0.; + view_matrix[8] = 0.; + view_matrix[9] = 0.; + view_matrix[10] = 1.; + view_matrix[11] = 0.; + view_matrix[12] = 0.; + view_matrix[13] = 0.; + view_matrix[14] = 10.; + view_matrix[15] = 1.; + let _model_matrix: [f64; 16] = *mat4::rotate_y( + &mut mat4::new_identity(), + mat4::translate( + &mut mat4::new_identity(), + &mat4::new_identity(), + &vec3::new(0.5, 0.5, 0.), + ), + &(3.141592 / 4.), + ); + let _model_matrix: [f64; 16] = *mat4::translate( + &mut mat4::new_identity(), + mat4::rotate_y( + &mut mat4::new_identity(), + &mat4::new_identity(), + &(3.141592 / 4.), + ), + &vec3::new(0.5, 0.5, 0.), + ); + let _model_matrix: [f64; 16] = *mat4::translate( &mut mat4::new_identity(), &mat4::new_identity(), - &vec3::new(0., 0., -10.), + &vec3::new(0.5, 0.5, 0.), ); - let model_matrix: [f64; 16] = *mat4::translate( + let _model_matrix: [f64; 16] = *mat4::rotate_y( &mut mat4::new_identity(), &mat4::new_identity(), - &vec3::new(1., 1., 0.), + &(3.141592 / 40.), ); + let _model_matrix: [f64; 16] = + *mat4::rotate_y(&mut mat4::new_identity(), &mat4::new_identity(), &0.03); + let model_matrix: [f64; 16] = *mat4::scale( + &mut mat4::new_zero(), + mat4::rotate_y( + &mut mat4::new_zero(), + mat4::translate( + &mut mat4::new_zero(), + &mat4::new_identity(), + &vec3::new(0., 0., 0.), + ), + &(3.141592 / 4.), + ), + &vec3::new(1., 1., 1.), + ); + // let model_matrix: [f64; 16] = *mat4::scale( + // &mut mat4::new_zero(), + // mat4::translate( + // &mut mat4::new_zero(), + // &mat4::new_identity(), + // &vec3::new(0.5, 0.5, 0.), + // ), + // &vec3::new(1., 2., 1.), + // ); + // let model_matrix = mat4::new_identity(); for x in 0..800 { - for y in 0..600 { + for y in 0..800 { + let mut view_projection_matrix = mat4::new_zero(); + mat4::mul(&mut view_projection_matrix, &model_matrix, &view_matrix); + let mut model_view_projection_matrix = mat4::new_zero(); + mat4::mul( + &mut model_view_projection_matrix, + &view_projection_matrix, + &projection_matrix, + ); + let mut inverse_view_projection_matrix = mat4::new_zero(); + mat4::inv( + &mut inverse_view_projection_matrix, + &model_view_projection_matrix, + ); + let far = vec4::new((x as f64 - 400.) / 400., (y as f64 - 400.) / 400., 1., 0.); + let near = vec4::new((x as f64 - 400.) / 400., (y as f64 - 400.) / 400., 0., 0.); + let mut new_far = vec4::new_zero(); + let mut new_near = vec4::new_zero(); + vec4::transform_mat4(&mut new_far, &far, &inverse_view_projection_matrix); + vec4::transform_mat4(&mut new_near, &near, &inverse_view_projection_matrix); + new_far[0] /= new_far[3]; + new_far[1] /= new_far[3]; + new_far[2] /= new_far[3]; + new_far[3] /= new_far[3]; + new_near[0] /= new_near[3]; + new_near[1] /= new_near[3]; + new_near[2] /= new_near[3]; + new_near[3] /= new_near[3]; + // let mut ray = Ray { + // origin: [view_matrix[3], view_matrix[7], view_matrix[11]], + // direction: [ + // new_far[0] - new_near[0], + // new_far[1] - new_near[1], + // new_far[2] - new_near[2], + // ], + // }; let mut ray = Ray { - origin: [0., 0., 0.], - direction: [0., 0., 1.], + origin: [view_matrix[12], view_matrix[13], view_matrix[14]], + direction: [ + new_far[0] - new_near[0], + new_far[1] - new_near[1], + new_far[2] - new_near[2], + ], }; - ray.direction[0] += (x as f64 - 400.) / 800.; - ray.direction[1] += (y as f64 - 300.) / 800.; - let mut n = - ray.direction[0].powi(2) + ray.direction[1].powi(2) + ray.direction[2].powi(2); - n = n.sqrt(); - ray.direction[0] /= n; - ray.direction[1] /= n; - ray.direction[2] /= n; + let scalar = + (ray.direction[0].powi(2) + ray.direction[1].powi(2) + ray.direction[2].powi(2)) + .sqrt(); + ray.direction = [ + ray.direction[0] / scalar, + ray.direction[1] / scalar, + ray.direction[2] / scalar, + ]; + if x == 0 && y == 0 { + println!("{:?}", ray); + } // let ray2 = Box::clone(&Box::new(ray)); // vec3::transform_mat4(&mut ray.direction, &ray2.direction, &projection_matrix); - let ray2 = Box::clone(&Box::new(ray)); - vec3::transform_mat4(&mut ray.origin, &ray2.origin, &view_matrix); - let ray2 = Box::clone(&Box::new(ray)); - vec3::transform_mat4(&mut ray.origin, &ray2.origin, &model_matrix); + //let ray2 = Box::clone(&Box::new(ray)); + //vec3::transform_mat4(&mut ray.origin, &ray2.origin, &view_matrix); + // let ray2 = Box::clone(&Box::new(ray)); + // vec3::transform_mat4(&mut ray.origin, &ray2.origin, &model_matrix); match sphere.get_intersection(ray) { Some(dist) => { let n = [ @@ -59,7 +183,7 @@ pub fn render(data: &mut [u8]) { ray.origin[2] + ray.direction[2] * dist, ]; let normal = sphere.get_normal(n); - let light = [n[0] - 10., n[1] - 10., n[2] - 10.]; + let light = [n[0] - 10., n[1] - 10., n[2] + 10.]; let scalar = (light[0].powi(2) + light[1].powi(2) + light[2].powi(2)).sqrt(); let light_d = [light[0] / scalar, light[1] / scalar, light[2] / scalar]; let mut diffuse = @@ -72,9 +196,9 @@ pub fn render(data: &mut [u8]) { x, y, Color { - r: (diffuse * 255.) as u8, - g: (diffuse * 255.) as u8, - b: (diffuse * 255.) as u8, + r: (diffuse * 255. * 0.9 + 0.1 * 255.) as u8, + g: (diffuse * 255. * 0.9 + 0.1 * 255.) as u8, + b: (diffuse * 255. * 0.9 + 0.1 * 255.) as u8, a: 0, }, );