Browse Source

Wed Dec 21 20:00:39 CET 2016

tags/v0.1.0
Jan Walter 2 years ago
parent
commit
51a42553e8

+ 1
- 0
.gitignore View File

@@ -0,0 +1 @@
target

+ 102
- 0
Cargo.lock View File

@@ -0,0 +1,102 @@
[root]
name = "pbrt"
version = "0.1.0"
dependencies = [
"num 0.1.36 (registry+https://github.com/rust-lang/crates.io-index)",
]

[[package]]
name = "libc"
version = "0.2.18"
source = "registry+https://github.com/rust-lang/crates.io-index"

[[package]]
name = "num"
version = "0.1.36"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"num-bigint 0.1.35 (registry+https://github.com/rust-lang/crates.io-index)",
"num-complex 0.1.35 (registry+https://github.com/rust-lang/crates.io-index)",
"num-integer 0.1.32 (registry+https://github.com/rust-lang/crates.io-index)",
"num-iter 0.1.32 (registry+https://github.com/rust-lang/crates.io-index)",
"num-rational 0.1.35 (registry+https://github.com/rust-lang/crates.io-index)",
"num-traits 0.1.36 (registry+https://github.com/rust-lang/crates.io-index)",
]

[[package]]
name = "num-bigint"
version = "0.1.35"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"num-integer 0.1.32 (registry+https://github.com/rust-lang/crates.io-index)",
"num-traits 0.1.36 (registry+https://github.com/rust-lang/crates.io-index)",
"rand 0.3.15 (registry+https://github.com/rust-lang/crates.io-index)",
"rustc-serialize 0.3.22 (registry+https://github.com/rust-lang/crates.io-index)",
]

[[package]]
name = "num-complex"
version = "0.1.35"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"num-traits 0.1.36 (registry+https://github.com/rust-lang/crates.io-index)",
"rustc-serialize 0.3.22 (registry+https://github.com/rust-lang/crates.io-index)",
]

[[package]]
name = "num-integer"
version = "0.1.32"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"num-traits 0.1.36 (registry+https://github.com/rust-lang/crates.io-index)",
]

[[package]]
name = "num-iter"
version = "0.1.32"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"num-integer 0.1.32 (registry+https://github.com/rust-lang/crates.io-index)",
"num-traits 0.1.36 (registry+https://github.com/rust-lang/crates.io-index)",
]

[[package]]
name = "num-rational"
version = "0.1.35"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"num-bigint 0.1.35 (registry+https://github.com/rust-lang/crates.io-index)",
"num-integer 0.1.32 (registry+https://github.com/rust-lang/crates.io-index)",
"num-traits 0.1.36 (registry+https://github.com/rust-lang/crates.io-index)",
"rustc-serialize 0.3.22 (registry+https://github.com/rust-lang/crates.io-index)",
]

[[package]]
name = "num-traits"
version = "0.1.36"
source = "registry+https://github.com/rust-lang/crates.io-index"

[[package]]
name = "rand"
version = "0.3.15"
source = "registry+https://github.com/rust-lang/crates.io-index"
dependencies = [
"libc 0.2.18 (registry+https://github.com/rust-lang/crates.io-index)",
]

[[package]]
name = "rustc-serialize"
version = "0.3.22"
source = "registry+https://github.com/rust-lang/crates.io-index"

[metadata]
"checksum libc 0.2.18 (registry+https://github.com/rust-lang/crates.io-index)" = "a51822fc847e7a8101514d1d44e354ba2ffa7d4c194dcab48870740e327cac70"
"checksum num 0.1.36 (registry+https://github.com/rust-lang/crates.io-index)" = "bde7c03b09e7c6a301ee81f6ddf66d7a28ec305699e3d3b056d2fc56470e3120"
"checksum num-bigint 0.1.35 (registry+https://github.com/rust-lang/crates.io-index)" = "88b14378471f7c2adc5262f05b4701ef53e8da376453a8d8fee48e51db745e49"
"checksum num-complex 0.1.35 (registry+https://github.com/rust-lang/crates.io-index)" = "f0c78e054dd19c3fd03419ade63fa661e9c49bb890ce3beb4eee5b7baf93f92f"
"checksum num-integer 0.1.32 (registry+https://github.com/rust-lang/crates.io-index)" = "fb24d9bfb3f222010df27995441ded1e954f8f69cd35021f6bef02ca9552fb92"
"checksum num-iter 0.1.32 (registry+https://github.com/rust-lang/crates.io-index)" = "287a1c9969a847055e1122ec0ea7a5c5d6f72aad97934e131c83d5c08ab4e45c"
"checksum num-rational 0.1.35 (registry+https://github.com/rust-lang/crates.io-index)" = "54ff603b8334a72fbb27fe66948aac0abaaa40231b3cecd189e76162f6f38aaf"
"checksum num-traits 0.1.36 (registry+https://github.com/rust-lang/crates.io-index)" = "a16a42856a256b39c6d3484f097f6713e14feacd9bfb02290917904fae46c81c"
"checksum rand 0.3.15 (registry+https://github.com/rust-lang/crates.io-index)" = "022e0636ec2519ddae48154b028864bdce4eaf7d35226ab8e65c611be97b189d"
"checksum rustc-serialize 0.3.22 (registry+https://github.com/rust-lang/crates.io-index)" = "237546c689f20bb44980270c73c3b9edd0891c1be49cc1274406134a66d3957b"

+ 8
- 0
Cargo.toml View File

@@ -0,0 +1,8 @@
[package]
name = "pbrt"
version = "0.1.0"
authors = ["Jan Walter <jan@janwalter.com>"]

[dependencies]

num="*"

+ 32
- 0
Makefile View File

@@ -0,0 +1,32 @@
all: release

clean:
-rm -f *~ examples/*~ src/*~ examples/*.rs.bk src/*.rs.bk

clobber: clean
-rm -fr target

doc:
cargo doc

browse: doc
firefox ./target/doc/pbrt/index.html

debug:
cargo test

release:
cargo test --release

examples: release
./target/release/examples/geometry_bounds2_unit_cube
./target/release/examples/geometry_bounds3_unit_cube
./target/release/examples/geometry_length
./target/release/examples/geometry_length_squared
./target/release/examples/geometry_matrix4x4_identity
./target/release/examples/geometry_normal3_null
./target/release/examples/geometry_point2_origin
./target/release/examples/geometry_point3_origin
./target/release/examples/geometry_ray_creation
./target/release/examples/geometry_vector2_null
./target/release/examples/geometry_vector3_null

+ 21
- 0
examples/geometry_bounds2_unit_cube.rs View File

@@ -0,0 +1,21 @@
extern crate pbrt;

use pbrt::{Bounds2, Point2};

fn main() {
let int_origin = Point2 { x: 0, y: 0 };
let int_xy11 = Point2 { x: 1, y: 1 };
let float_origin = Point2 { x: 0.0, y: 0.0 };
let float_xy11 = Point2 { x: 1.0, y: 1.0 };
let int_unit_cube = Bounds2 {
p_min: int_origin,
p_max: int_xy11,
};
let float_unit_cube = Bounds2 {
p_min: float_origin,
p_max: float_xy11,
};

println!("int {:?}", int_unit_cube);
println!("float {:?}", float_unit_cube);
}

+ 29
- 0
examples/geometry_bounds3_unit_cube.rs View File

@@ -0,0 +1,29 @@
extern crate pbrt;

use pbrt::{Bounds3, Point3};

fn main() {
let int_origin = Point3 { x: 0, y: 0, z: 0 };
let int_xyz111 = Point3 { x: 1, y: 1, z: 1 };
let float_origin = Point3 {
x: 0.0,
y: 0.0,
z: 0.0,
};
let float_xyz111 = Point3 {
x: 1.0,
y: 1.0,
z: 1.0,
};
let int_unit_cube = Bounds3 {
p_min: int_origin,
p_max: int_xyz111,
};
let float_unit_cube = Bounds3 {
p_min: float_origin,
p_max: float_xyz111,
};

println!("int {:?}", int_unit_cube);
println!("float {:?}", float_unit_cube);
}

+ 53
- 0
examples/geometry_length.rs View File

@@ -0,0 +1,53 @@
extern crate pbrt;

use pbrt::{Vector2, Vector3, Normal3};

fn main() {
let float_vec2_f32 = Vector2 {
x: 1.2_f32,
y: 2.3_f32,
};
let float_vec2_f64 = Vector2 {
x: 1.2_f64,
y: 2.3_f64,
};

println!("float_vec2_f32 = {:?}", float_vec2_f32);
println!("float_vec2_f32.length() = {:?}", float_vec2_f32.length());
println!("float_vec2_f64 = {:?}", float_vec2_f64);
println!("float_vec2_f64.length() = {:?}", float_vec2_f64.length());

let float_vec3_f32 = Vector3 {
x: 1.2_f32,
y: 2.3_f32,
z: 3.4_f32,
};
let float_vec3_f64 = Vector3 {
x: 1.2_f64,
y: 2.3_f64,
z: 3.4_f64,
};

println!("float_vec3_f32 = {:?}", float_vec3_f32);
println!("float_vec3_f32.length() = {:?}", float_vec3_f32.length());
println!("float_vec3_f64 = {:?}", float_vec3_f64);
println!("float_vec3_f64.length() = {:?}", float_vec3_f64.length());

let float_normal3_f32 = Normal3 {
x: 2.2_f32,
y: 3.3_f32,
z: 4.4_f32,
};
let float_normal3_f64 = Normal3 {
x: 2.2_f64,
y: 3.3_f64,
z: 4.4_f64,
};

println!("float_normal3_f32 = {:?}", float_normal3_f32);
println!("float_normal3_f32.length() = {:?}",
float_normal3_f32.length());
println!("float_normal3_f64 = {:?}", float_normal3_f64);
println!("float_normal3_f64.length() = {:?}",
float_normal3_f64.length());
}

+ 49
- 0
examples/geometry_length_squared.rs View File

@@ -0,0 +1,49 @@
extern crate pbrt;

use pbrt::{Vector2, Vector3, Normal3};

fn main() {
let int_vec2 = Vector2 { x: 1, y: 2 };

println!("int_vec2 = {:?}", int_vec2);
println!("int_vec2.length_squared() = {:?}",
int_vec2.length_squared());

let float_vec2 = Vector2 { x: 1.2, y: 2.3 };

println!("float_vec2 = {:?}", float_vec2);
println!("float_vec2.length_squared() = {:?}",
float_vec2.length_squared());

let int_vec3 = Vector3 { x: 1, y: 2, z: 3 };

println!("int_vec3 = {:?}", int_vec3);
println!("int_vec3.length_squared() = {:?}",
int_vec3.length_squared());

let float_vec3 = Vector3 {
x: 1.2,
y: 2.3,
z: 3.4,
};

println!("float_vec3 = {:?}", float_vec3);
println!("float_vec3.length_squared() = {:?}",
float_vec3.length_squared());

let int_normal3 = Normal3 { x: 2, y: 3, z: 4 };

println!("int_normal3 = {:?}", int_normal3);
println!("int_normal3.length_squared() = {:?}",
int_normal3.length_squared());

let float_normal3 = Normal3 {
x: 2.2,
y: 3.3,
z: 4.4,
};

println!("float_normal3 = {:?}", float_normal3);
println!("float_normal3.length_squared() = {:?}",
float_normal3.length_squared());
}

+ 9
- 0
examples/geometry_matrix4x4_identity.rs View File

@@ -0,0 +1,9 @@
extern crate pbrt;

use pbrt::Matrix4x4;

fn main() {
let identity: Matrix4x4 = Matrix4x4::new();

println!("identity matrix = {:?}", identity);
}

+ 15
- 0
examples/geometry_normal3_null.rs View File

@@ -0,0 +1,15 @@
extern crate pbrt;

use pbrt::Normal3;

fn main() {
let int_null = Normal3 { x: 0, y: 0, z: 0 };
let float_null = Normal3 {
x: 0.0,
y: 0.0,
z: 0.0,
};

println!("int {:?}", int_null);
println!("float {:?}", float_null);
}

+ 11
- 0
examples/geometry_point2_origin.rs View File

@@ -0,0 +1,11 @@
extern crate pbrt;

use pbrt::Point2;

fn main() {
let int_origin = Point2 { x: 0, y: 0 };
let float_origin = Point2 { x: 0.0, y: 0.0 };

println!("int {:?}", int_origin);
println!("float {:?}", float_origin);
}

+ 15
- 0
examples/geometry_point3_origin.rs View File

@@ -0,0 +1,15 @@
extern crate pbrt;

use pbrt::Point3;

fn main() {
let int_origin = Point3 { x: 0, y: 0, z: 0 };
let float_origin = Point3 {
x: 0.0,
y: 0.0,
z: 0.0,
};

println!("int {:?}", int_origin);
println!("float {:?}", float_origin);
}

+ 22
- 0
examples/geometry_ray_creation.rs View File

@@ -0,0 +1,22 @@
extern crate pbrt;

use pbrt::{Ray, Point3f, Vector3f};

fn main() {
let origin = Point3f {
x: -5.5,
y: 2.75,
z: 0.0,
};
let direction = Vector3f {
x: 1.0,
y: -8.75,
z: 2.25,
};
let ray = Ray {
o: origin,
d: direction,
};

println!("{:?}", ray);
}

+ 11
- 0
examples/geometry_vector2_null.rs View File

@@ -0,0 +1,11 @@
extern crate pbrt;

use pbrt::Vector2;

fn main() {
let int_null = Vector2 { x: 0, y: 0 };
let float_null = Vector2 { x: 0.0, y: 0.0 };

println!("int {:?}", int_null);
println!("float {:?}", float_null);
}

+ 15
- 0
examples/geometry_vector3_null.rs View File

@@ -0,0 +1,15 @@
extern crate pbrt;

use pbrt::Vector3;

fn main() {
let int_null = Vector3 { x: 0, y: 0, z: 0 };
let float_null = Vector3 {
x: 0.0,
y: 0.0,
z: 0.0,
};

println!("int {:?}", int_null);
println!("float {:?}", float_null);
}

+ 306
- 0
src/lib.rs View File

@@ -0,0 +1,306 @@
//! # pbrt
//!
//! ## Vectors
//!
//! **pbrt** provides both 2D and 3D **vector** classes. Both are
//! parameterized by the type of the underlying vector element, thus
//! making it easy to instantiate vectors of both integer and
//! floating-point types.
//!
//! ```rust
//! extern crate pbrt;
//!
//! use pbrt::Vector3;
//!
//! fn main() {
//! let int_null = Vector3 { x: 0, y: 0, z: 0 };
//! let float_null = Vector3 {
//! x: 0.0,
//! y: 0.0,
//! z: 0.0,
//! };
//!
//! println!("int {:?}", int_null);
//! println!("float {:?}", float_null);
//! }
//! ```
//!
//! ## Points
//!
//! A **point** is a zero-dimensional location in 2D or 3D space. The
//! **Point2** and **Point3** classes in **pbrt** represent points in
//! the obvious way: using x, y, z (in 3D) coordinates with respect to
//! a coordinate system. Although the same representation is used for
//! vectors, the fact that a point represents a position whereas a
//! vector represents a direction leads to a number of important
//! differences in how they are treated.
//!
//! ```rust
//! extern crate pbrt;
//!
//! use pbrt::Point3;
//!
//! fn main() {
//! let int_origin = Point3 { x: 0, y: 0, z: 0 };
//! let float_origin = Point3 {
//! x: 0.0,
//! y: 0.0,
//! z: 0.0,
//! };
//!
//! println!("int {:?}", int_origin);
//! println!("float {:?}", float_origin);
//! }
//! ```
//!
//! ## Normals
//!
//! A surface **normal** (or just normal) is a vector that is
//! perpendicular to a surface at a particular position. It can be
//! defined as the cross product of any two nonparallel vectors that
//! are tangent to the surface at a point. Although normals are
//! superficially similar to vectors, it is important to distinguish
//! between the two of them: because normals are defined in terms of
//! their relationship to a particular surface, they behave
//! differently than vectors in some situations, particularly when
//! applying transformations.
//!
//! ```rust
//! extern crate pbrt;
//!
//! use pbrt::Normal3;
//!
//! fn main() {
//! let int_null = Normal3 { x: 0, y: 0, z: 0 };
//! let float_null = Normal3 {
//! x: 0.0,
//! y: 0.0,
//! z: 0.0,
//! };
//!
//! println!("int {:?}", int_null);
//! println!("float {:?}", float_null);
//! }
//! ```
//!
//! ## Rays
//!
//! A **ray** is a semi-infinite line specified by its origin and
//! direction. **pbrt** represents a **Ray** with a **Point3f** for
//! the origin and a **Vector3f** for the direction. We only need rays
//! with floating-point origins and directions, so **Ray** isn't a
//! template class parameterized by an arbitrary type, as points,
//! vectors, and normals were.
//!
//! ```rust
//! extern crate pbrt;
//!
//! use pbrt::{Ray, Point3f, Vector3f};
//!
//! fn main() {
//! let origin = Point3f {
//! x: -5.5,
//! y: 2.75,
//! z: 0.0,
//! };
//! let direction = Vector3f {
//! x: 1.0,
//! y: -8.75,
//! z: 2.25,
//! };
//! let ray = Ray {
//! o: origin,
//! d: direction,
//! };
//!
//! println!("{:?}", ray);
//! }
//! ```
//!
//! ## Bounding Boxes
//!
//! Many parts of the system operate on axis-aligned regions of
//! space. For example, multi-threading in **pbrt** is implemented by
//! subdividing the image into rectangular tiles that can be processed
//! independently, and the bounding volume hierarchy uses 3D boxes to
//! bound geometric primitives in the scene. The **Bounds2** and
//! **Bounds3** template classes are used to represent the extent of
//! these sort of regions. Both are parameterized by a type T that is
//! used to represent the coordinates of its extents.
//!
//! ```rust
//! extern crate pbrt;
//!
//! use pbrt::{Bounds3, Point3};
//!
//! fn main() {
//! let int_origin = Point3 { x: 0, y: 0, z: 0 };
//! let int_xyz111 = Point3 { x: 1, y: 1, z: 1 };
//! let float_origin = Point3 {
//! x: 0.0,
//! y: 0.0,
//! z: 0.0,
//! };
//! let float_xyz111 = Point3 {
//! x: 1.0,
//! y: 1.0,
//! z: 1.0,
//! };
//! let int_unit_cube = Bounds3 {
//! p_min: int_origin,
//! p_max: int_xyz111,
//! };
//! let float_unit_cube = Bounds3 {
//! p_min: float_origin,
//! p_max: float_xyz111,
//! };
//!
//! println!("int {:?}", int_unit_cube);
//! println!("float {:?}", float_unit_cube);
//! }
//! ```
//!
//! ## 4 x 4 Matrices
//!
//! The **Matrix4x4** structure provides a low-level representation of
//! 4 x 4 matrices. It is an integral part of the **Transform** class.
//!
//! ```rust
//! extern crate pbrt;
//!
//! use pbrt::Matrix4x4;
//!
//! fn main() {
//! let identity: Matrix4x4 = Matrix4x4::new();
//!
//! println!("identity matrix = {:?}", identity);
//! }
//! ```

extern crate num;

use std::ops::{Add, Mul};

pub type Float = f64;
pub type Point3f = Point3<Float>;
pub type Vector3f = Vector3<Float>;

#[derive(Debug)]
pub struct Vector2<T> {
pub x: T,
pub y: T,
}

impl<T> Vector2<T> {
pub fn length_squared(&self) -> T
where T: Copy + Add<T, Output = T> + Mul<T, Output = T>
{
self.x * self.x + self.y * self.y
}
pub fn length(&self) -> T
where T: num::Float
{
self.length_squared().sqrt()
}
}

pub fn vec2_dot<T>(v1: Vector2<T>, v2: Vector2<T>) -> T
where T: Copy + Add<T, Output = T> + Mul<T, Output = T>
{
v1.x * v2.x + v1.y * v2.y
}

#[derive(Debug)]
pub struct Vector3<T> {
pub x: T,
pub y: T,
pub z: T,
}

impl<T> Vector3<T> {
pub fn length_squared(&self) -> T
where T: Copy + Add<T, Output = T> + Mul<T, Output = T>
{
self.x * self.x + self.y * self.y + self.z * self.z
}
pub fn length(&self) -> T
where T: num::Float
{
self.length_squared().sqrt()
}
}

pub fn vec3_dot<T>(v1: Vector3<T>, v2: Vector3<T>) -> T
where T: Copy + Add<T, Output = T> + Mul<T, Output = T>
{
v1.x * v2.x + v1.y * v2.y + v1.z * v2.z
}

#[derive(Debug)]
pub struct Point2<T> {
pub x: T,
pub y: T,
}

#[derive(Debug)]
pub struct Point3<T> {
pub x: T,
pub y: T,
pub z: T,
}

#[derive(Debug)]
pub struct Normal3<T> {
pub x: T,
pub y: T,
pub z: T,
}

impl<T> Normal3<T> {
pub fn length_squared(&self) -> T
where T: Copy + Add<T, Output = T> + Mul<T, Output = T>
{
self.x * self.x + self.y * self.y + self.z * self.z
}
pub fn length(&self) -> T
where T: num::Float
{
self.length_squared().sqrt()
}
}

#[derive(Debug)]
pub struct Bounds2<T> {
pub p_min: Point2<T>,
pub p_max: Point2<T>,
}

#[derive(Debug)]
pub struct Bounds3<T> {
pub p_min: Point3<T>,
pub p_max: Point3<T>,
}

#[derive(Debug)]
pub struct Ray {
/// origin
pub o: Point3f,
/// direction
pub d: Vector3f,
}

#[derive(Debug)]
pub struct Matrix4x4 {
pub m: [[Float; 4]; 4],
}

impl Matrix4x4 {
pub fn new() -> Matrix4x4 {
Matrix4x4 {
m: [[1.0, 0.0, 0.0, 0.0],
[0.0, 1.0, 0.0, 0.0],
[0.0, 0.0, 1.0, 0.0],
[0.0, 0.0, 0.0, 1.0]],
}
}
}

Loading…
Cancel
Save