2020-02-13 10:42:52 +00:00
|
|
|
#![allow(clippy::suspicious_arithmetic_impl)]
|
|
|
|
|
|
|
|
mod camera;
|
2019-03-08 17:29:21 +00:00
|
|
|
mod demos;
|
2020-02-09 16:30:51 +00:00
|
|
|
mod types;
|
2019-03-07 00:33:46 +00:00
|
|
|
|
2020-02-13 10:42:52 +00:00
|
|
|
pub use camera::Camera;
|
|
|
|
|
2020-02-12 16:40:23 +00:00
|
|
|
use {
|
|
|
|
demos::Demo,
|
|
|
|
sdl2::{
|
|
|
|
event::{Event, WindowEvent},
|
|
|
|
keyboard::Keycode,
|
|
|
|
pixels::PixelFormatEnum,
|
|
|
|
},
|
2019-03-07 00:33:46 +00:00
|
|
|
};
|
|
|
|
|
2020-02-13 10:42:52 +00:00
|
|
|
const NUM_SAMPLES: u8 = 100;
|
2020-02-09 16:30:51 +00:00
|
|
|
|
2019-03-07 00:33:46 +00:00
|
|
|
fn main() -> Result<(), String> {
|
|
|
|
let sdl_ctx = sdl2::init()?;
|
|
|
|
let video_subsys = sdl_ctx.video()?;
|
|
|
|
|
2020-02-13 10:42:52 +00:00
|
|
|
let (mut width, mut height) = (1280, 640);
|
2019-03-07 00:33:46 +00:00
|
|
|
|
2019-06-25 17:44:37 +00:00
|
|
|
let window = video_subsys
|
2019-03-07 00:33:46 +00:00
|
|
|
.window("Ray tracing in a weekend", width as u32, height as u32)
|
|
|
|
.position_centered()
|
|
|
|
.build()
|
|
|
|
.map_err(|e| e.to_string())?;
|
|
|
|
|
|
|
|
let mut event_pump = sdl_ctx.event_pump()?;
|
|
|
|
|
|
|
|
let mut canvas = window
|
|
|
|
.into_canvas()
|
|
|
|
.target_texture()
|
|
|
|
.build()
|
|
|
|
.map_err(|e| e.to_string())?;
|
|
|
|
|
2019-06-24 16:40:45 +00:00
|
|
|
// RGBA framebuffer
|
2019-03-07 00:33:46 +00:00
|
|
|
let mut buffer = vec![0; height * width * 4];
|
|
|
|
|
|
|
|
let texture_creator = canvas.texture_creator();
|
|
|
|
let mut texture = texture_creator
|
2019-03-08 17:29:21 +00:00
|
|
|
.create_texture_static(PixelFormatEnum::BGR888, width as u32, height as u32)
|
2019-03-07 00:33:46 +00:00
|
|
|
.map_err(|e| e.to_string())?;
|
|
|
|
|
2019-03-08 17:29:21 +00:00
|
|
|
//println!("{:?} {:?} {:?}", texture.query(), texture.color_mod(), texture.alpha_mod());
|
2019-06-25 17:44:37 +00:00
|
|
|
|
2020-02-12 16:40:23 +00:00
|
|
|
let mut active_demo: Box<dyn Demo> = Box::new(demos::SimpleRectangle);
|
2019-06-25 17:44:37 +00:00
|
|
|
// TODO: Should update when window is unfocus since the project window retains
|
|
|
|
// data from overlapped window
|
|
|
|
// TODO: Maybe consider using condition variable to make loop {} not run at full
|
|
|
|
// speed at all times pinning a core at 100%
|
2019-06-24 16:40:45 +00:00
|
|
|
let mut should_update = true;
|
2019-03-07 00:33:46 +00:00
|
|
|
loop {
|
|
|
|
for event in event_pump.poll_iter() {
|
|
|
|
match event {
|
|
|
|
Event::Quit { .. }
|
|
|
|
| Event::KeyDown {
|
|
|
|
keycode: Some(Keycode::Escape),
|
|
|
|
..
|
|
|
|
} => return Ok(()),
|
2020-02-12 16:40:23 +00:00
|
|
|
Event::KeyUp { keycode, .. } => {
|
|
|
|
match keycode {
|
|
|
|
Some(Keycode::S) => active_demo.save_as_ppm(&buffer, width, height),
|
|
|
|
Some(Keycode::Num1) => active_demo = Box::new(demos::SimpleRectangle),
|
|
|
|
Some(Keycode::Num2) => {
|
|
|
|
active_demo = Box::new(demos::LinearGradientRectangle)
|
|
|
|
}
|
|
|
|
Some(Keycode::Num3) => active_demo = Box::new(demos::SimpleSphere),
|
|
|
|
Some(Keycode::Num4) => active_demo = Box::new(demos::SurfaceNormalSphere),
|
2020-02-13 10:42:52 +00:00
|
|
|
Some(Keycode::Num5) => active_demo = Box::new(demos::HitableSphere),
|
|
|
|
Some(Keycode::Num6) => active_demo = Box::new(demos::SimpleAntialiasing),
|
2020-02-12 16:40:23 +00:00
|
|
|
None => unreachable!(),
|
|
|
|
_ => (),
|
|
|
|
};
|
|
|
|
should_update = true;
|
|
|
|
}
|
2019-03-07 00:33:46 +00:00
|
|
|
Event::Window {
|
|
|
|
win_event: WindowEvent::Resized(w, h),
|
|
|
|
..
|
|
|
|
} => {
|
|
|
|
width = w as usize;
|
|
|
|
height = h as usize;
|
|
|
|
buffer.resize(width * height * 4, 0);
|
|
|
|
texture = texture_creator
|
2019-03-08 17:29:21 +00:00
|
|
|
.create_texture_static(PixelFormatEnum::BGR888, width as u32, height as u32)
|
2019-03-07 00:33:46 +00:00
|
|
|
.expect("error in resizing texture");
|
2019-06-24 16:40:45 +00:00
|
|
|
should_update = true;
|
2019-03-07 00:33:46 +00:00
|
|
|
}
|
|
|
|
_ => {}
|
|
|
|
};
|
|
|
|
}
|
2019-06-24 16:40:45 +00:00
|
|
|
if should_update {
|
2020-02-09 16:30:51 +00:00
|
|
|
active_demo.render(&mut buffer, width, height, NUM_SAMPLES);
|
2019-06-24 16:40:45 +00:00
|
|
|
texture.update(None, &buffer, width * 4);
|
|
|
|
canvas.copy(&texture, None, None);
|
|
|
|
canvas.present();
|
|
|
|
should_update = false;
|
|
|
|
}
|
2019-03-07 00:33:46 +00:00
|
|
|
}
|
|
|
|
}
|