#![deny(missing_docs)]
extern crate piston;
extern crate vecmath;
extern crate wavefront_obj;
extern crate image;
#[cfg(any(feature = "dx12", feature = "metal", feature = "vulkan"))]
mod rendy_backend;
#[cfg(not(any(feature = "dx12", feature = "metal", feature = "vulkan")))]
mod gl_backend;
#[cfg(any(feature = "dx12", feature = "metal", feature = "vulkan"))]
pub use rendy_backend::Scene;
#[cfg(not(any(feature = "dx12", feature = "metal", feature = "vulkan")))]
pub use gl_backend::Scene;
use std::path::Path;
use std::io;
use vecmath::*;
#[derive(Copy, Clone, Debug, PartialEq)]
pub enum Command {
UseProgram(Program),
SetModelViewProjection(Matrix4Uniform),
SetModel(Matrix4Uniform),
SetView(Matrix4Uniform),
SetTexture(Texture),
SetF32(F32Uniform, f32),
SetVector2(Vector2Uniform, Vector2<f32>),
SetVector3(Vector3Uniform, Vector3<f32>),
SetMatrix4(Matrix4Uniform, Matrix4<f32>),
EnableFrameBufferSRGB,
DisableFrameBufferSRGB,
EnableBlend,
DisableBlend,
EnableCullFace,
DisableCullFace,
CullFaceFront,
CullFaceBack,
CullFaceFrontAndBack,
DrawTriangles(VertexArray, usize),
DrawTriangleStrip(VertexArray, usize),
DrawLines(VertexArray, usize),
DrawPoints(VertexArray, usize),
Translate(Vector3<f32>),
TranslateGlobal(Vector3<f32>),
Scale(Vector3<f32>),
RotateXDeg(f32),
RotateYDeg(f32),
RotateZDeg(f32),
RotateAxisDeg(Vector3<f32>, f32),
PushTransform,
PopTransform,
Draw(CommandList),
}
#[derive(Debug)]
pub struct FrameGraph {
command_lists: Vec<Vec<Command>>,
}
impl FrameGraph {
pub fn new() -> FrameGraph {
FrameGraph {
command_lists: vec![]
}
}
pub fn command_list(&mut self, commands: Vec<Command>) -> CommandList {
let id = self.command_lists.len();
self.command_lists.push(commands);
CommandList(id)
}
}
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
pub struct VertexShader(usize);
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
pub struct FragmentShader(usize);
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
pub struct Program(usize);
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
pub struct Matrix4Uniform(usize);
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
pub struct Vector2Uniform(usize);
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
pub struct Vector3Uniform(usize);
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
pub struct F32Uniform(usize);
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
pub struct VertexArray(usize);
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
pub struct ColorBuffer(usize, usize);
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
pub struct VertexBuffer3(usize, usize);
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
pub struct VertexBuffer2(usize, usize);
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
pub struct UVBuffer(usize, usize);
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
pub struct NormalBuffer(usize, usize);
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
pub struct CommandList(usize);
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
pub struct Texture(usize);
impl ColorBuffer {
pub fn len(&self) -> usize {self.1}
}
impl VertexBuffer3 {
pub fn len(&self) -> usize {self.1}
}
impl VertexBuffer2 {
pub fn len(&self) -> usize {self.1}
}
pub struct ObjMesh {
pub vertices: Vec<f32>,
pub uvs: Vec<f32>,
pub normals: Vec<f32>,
}
impl ObjMesh {
pub fn load<P: AsRef<Path>>(path: P) -> Result<ObjMesh, io::Error> {
use std::fs::File;
use std::io::Read;
let mut obj_file = File::open(path)?;
let mut data = String::new();
obj_file.read_to_string(&mut data)?;
let obj_set = wavefront_obj::obj::parse(data).unwrap();
let obj = &obj_set.objects[0];
let temp_vertices = {
let mut res = vec![];
for v in &obj.vertices {
res.push(v.x as f32);
res.push(v.y as f32);
res.push(v.z as f32);
}
res
};
let temp_uvs = {
let mut res = vec![];
for uv in &obj.tex_vertices {
res.push(uv.u as f32);
res.push(1.0 - uv.v as f32);
}
res
};
let temp_normals = {
let mut res = vec![];
for normal in &obj.normals {
res.push(normal.x as gl::types::GLfloat);
res.push(normal.y as gl::types::GLfloat);
res.push(normal.z as gl::types::GLfloat);
}
res
};
let mut vertices = vec![];
let mut uvs = vec![];
let mut normals = vec![];
for geom in &obj.geometry {
for shape in &geom.shapes {
use wavefront_obj::obj::Primitive;
if let Primitive::Triangle(
(a_v, Some(a_uv), Some(a_n)),
(b_v, Some(b_uv), Some(b_n)),
(c_v, Some(c_uv), Some(c_n))
) = shape.primitive {
vertices.push(temp_vertices[a_v * 3 + 0]);
vertices.push(temp_vertices[a_v * 3 + 1]);
vertices.push(temp_vertices[a_v * 3 + 2]);
vertices.push(temp_vertices[b_v * 3 + 0]);
vertices.push(temp_vertices[b_v * 3 + 1]);
vertices.push(temp_vertices[b_v * 3 + 2]);
vertices.push(temp_vertices[c_v * 3 + 0]);
vertices.push(temp_vertices[c_v * 3 + 1]);
vertices.push(temp_vertices[c_v * 3 + 2]);
uvs.push(temp_uvs[a_uv * 2 + 0]);
uvs.push(temp_uvs[a_uv * 2 + 1]);
uvs.push(temp_uvs[b_uv * 2 + 0]);
uvs.push(temp_uvs[b_uv * 2 + 1]);
uvs.push(temp_uvs[c_uv * 2 + 0]);
uvs.push(temp_uvs[c_uv * 2 + 1]);
normals.push(temp_normals[a_n * 3 + 0]);
normals.push(temp_normals[a_n * 3 + 1]);
normals.push(temp_normals[a_n * 3 + 2]);
normals.push(temp_normals[b_n * 3 + 0]);
normals.push(temp_normals[b_n * 3 + 1]);
normals.push(temp_normals[b_n * 3 + 2]);
normals.push(temp_normals[c_n * 3 + 0]);
normals.push(temp_normals[c_n * 3 + 1]);
normals.push(temp_normals[c_n * 3 + 2]);
}
}
}
Ok(ObjMesh {
vertices,
uvs,
normals
})
}
}
#[derive(Clone)]
pub struct SceneSettings {
clear_depth_buffer: bool,
clear_enable_depth_test: bool,
}
impl SceneSettings {
pub fn new() -> SceneSettings {
SceneSettings {
clear_depth_buffer: true,
clear_enable_depth_test: true,
}
}
pub fn clear_depth_buffer(mut self, val: bool) -> Self {
self.clear_depth_buffer = val;
self
}
pub fn clear_enable_depth_test(mut self, val: bool) -> Self {
self.clear_enable_depth_test = val;
self
}
}
impl Default for SceneSettings {
fn default() -> Self {SceneSettings::new()}
}
#[cfg(test)]
mod tests {
#[test]
fn it_works() {
assert_eq!(2 + 2, 4);
}
}