Skip to content

Commit

Permalink
more careful rounding
Browse files Browse the repository at this point in the history
  • Loading branch information
ssloy committed Jan 22, 2015
1 parent cbfbce6 commit 5ff999c
Show file tree
Hide file tree
Showing 4 changed files with 34 additions and 23 deletions.
4 changes: 2 additions & 2 deletions Makefile
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
SYSCONF_LINK = g++
CPPFLAGS =
LDFLAGS =
CPPFLAGS = -O3
LDFLAGS = -O3
LIBS = -lm

DESTDIR = ./
Expand Down
12 changes: 12 additions & 0 deletions geometry.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
#include <vector>
#include <cassert>
#include <cmath>
#include <iostream>
#include "geometry.h"

template <> template <> Vec3<int>::Vec3<>(const Vec3<float> &v) : x(int(v.x+.5)), y(int(v.y+.5)), z(int(v.z+.5)) {
}

template <> template <> Vec3<float>::Vec3<>(const Vec3<int> &v) : x(v.x), y(v.y), z(v.z) {
}

30 changes: 15 additions & 15 deletions geometry.h
Original file line number Diff line number Diff line change
Expand Up @@ -4,12 +4,10 @@
#include <cmath>

template <class t> struct Vec2 {
t raw[2];
t& x;
t& y;
Vec2<t>() : raw(), x(raw[0]), y(raw[1]) { x = y = t(); }
Vec2<t>(t _x, t _y) : raw(), x(raw[0]), y(raw[1]) { x=_x; y=_y; }
Vec2<t>(const Vec2<t> &v) : raw(), x(raw[0]), y(raw[1]) { *this = v; }
t x, y;
Vec2<t>() : x(t()), y(t()) {}
Vec2<t>(t _x, t _y) : x(_x), y(_y) {}
Vec2<t>(const Vec2<t> &v) : x(t()), y(t()) { *this = v; }
Vec2<t> & operator =(const Vec2<t> &v) {
if (this != &v) {
x = v.x;
Expand All @@ -20,18 +18,16 @@ template <class t> struct Vec2 {
Vec2<t> operator +(const Vec2<t> &V) const { return Vec2<t>(x+V.x, y+V.y); }
Vec2<t> operator -(const Vec2<t> &V) const { return Vec2<t>(x-V.x, y-V.y); }
Vec2<t> operator *(float f) const { return Vec2<t>(x*f, y*f); }
t& operator[](const int i) {return raw[i];}
t& operator[](const int i) { if (x<=0) return x; else return y; }
template <class > friend std::ostream& operator<<(std::ostream& s, Vec2<t>& v);
};

template <class t> struct Vec3 {
t raw[3];
t& x;
t& y;
t& z;
Vec3<t>() : raw(), x(raw[0]), y(raw[1]), z(raw[2]) { x = y = z = t(); }
Vec3<t>(t _x, t _y, t _z) : raw(), x(raw[0]), y(raw[1]), z(raw[2]) { x=_x; y=_y; z=_z; }
Vec3<t>(const Vec3<t> &v) : raw(), x(raw[0]), y(raw[1]), z(raw[2]) { *this = v; }
t x, y, z;
Vec3<t>() : x(t()), y(t()), z(t()) { }
Vec3<t>(t _x, t _y, t _z) : x(_x), y(_y), z(_z) {}
template <class u> Vec3<t>(const Vec3<u> &v);
Vec3<t>(const Vec3<t> &v) : x(t()), y(t()), z(t()) { *this = v; }
Vec3<t> & operator =(const Vec3<t> &v) {
if (this != &v) {
x = v.x;
Expand All @@ -47,7 +43,7 @@ template <class t> struct Vec3 {
t operator *(const Vec3<t> &v) const { return x*v.x + y*v.y + z*v.z; }
float norm () const { return std::sqrt(x*x+y*y+z*z); }
Vec3<t> & normalize(t l=1) { *this = (*this)*(l/norm()); return *this; }
t& operator[](const int i) {return raw[i];}
t& operator[](const int i) { if (i<=0) return x; else if (i==1) return y; else return z; }
template <class > friend std::ostream& operator<<(std::ostream& s, Vec3<t>& v);
};

Expand All @@ -56,6 +52,10 @@ typedef Vec2<int> Vec2i;
typedef Vec3<float> Vec3f;
typedef Vec3<int> Vec3i;

template <> template <> Vec3<int>::Vec3(const Vec3<float> &v);
template <> template <> Vec3<float>::Vec3(const Vec3<int> &v);


template <class t> std::ostream& operator<<(std::ostream& s, Vec2<t>& v) {
s << "(" << v.x << ", " << v.y << ")\n";
return s;
Expand Down
11 changes: 5 additions & 6 deletions main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -24,17 +24,16 @@ void triangle(Vec3i t0, Vec3i t1, Vec3i t2, TGAImage &image, TGAColor color, int
int segment_height = second_half ? t2.y-t1.y : t1.y-t0.y;
float alpha = (float)i/total_height;
float beta = (float)(i-(second_half ? t1.y-t0.y : 0))/segment_height; // be careful: with above conditions no division by zero here
Vec3i A = t0 + (t2-t0)*alpha;
Vec3i B = second_half ? t1 + (t2-t1)*beta : t0 + (t1-t0)*beta;
Vec3i A = t0 + Vec3f(t2-t0)*alpha;
Vec3i B = second_half ? t1 + Vec3f(t2-t1)*beta : t0 + Vec3f(t1-t0)*beta;
if (A.x>B.x) std::swap(A, B);
for (int j=A.x; j<=B.x; j++) {
float phi = B.x==A.x ? 1. : (float)(j-A.x)/(float)(B.x-A.x);
Vec3i P = A + (B-A)*phi;
P.x = j; P.y = t0.y+i; // a hack to fill holes (due to int cast precision problems)
int idx = j+(t0.y+i)*width;
Vec3i P = Vec3f(A) + Vec3f(B-A)*phi;
int idx = P.x+P.y*width;
if (zbuffer[idx]<P.z) {
zbuffer[idx] = P.z;
image.set(P.x, P.y, color); // attention, due to int casts t0.y+i != A.y
image.set(P.x, P.y, color);
}
}
}
Expand Down

0 comments on commit 5ff999c

Please sign in to comment.