bloboland

diff src/camera.cc @ 1:cfe68befb7cc

some progress
author John Tsiombikas <nuclear@member.fsf.org>
date Sat, 15 Dec 2012 23:43:03 +0200
parents
children a39c301cdcce
line diff
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/src/camera.cc	Sat Dec 15 23:43:03 2012 +0200
     1.3 @@ -0,0 +1,237 @@
     1.4 +#include "opengl.h"
     1.5 +#include "camera.h"
     1.6 +
     1.7 +Camera::Camera()
     1.8 +{
     1.9 +	inval_cache();
    1.10 +}
    1.11 +
    1.12 +Camera::~Camera()
    1.13 +{
    1.14 +}
    1.15 +
    1.16 +void Camera::calc_inv_matrix(Matrix4x4 *mat) const
    1.17 +{
    1.18 +	*mat = matrix().inverse();
    1.19 +}
    1.20 +
    1.21 +void Camera::set_glmat(const Matrix4x4 &mat) const
    1.22 +{
    1.23 +#ifdef SINGLE_PRECISION_MATH
    1.24 +	if(glLoadTransposeMatrixfARB) {
    1.25 +		glLoadTransposeMatrixfARB((float*)&mat);
    1.26 +	} else {
    1.27 +		Matrix4x4 tmat = mat.transposed();
    1.28 +		glLoadMatrixf((float*)&tmat);
    1.29 +	}
    1.30 +#else
    1.31 +	if(glLoadTransposeMatrixdARB) {
    1.32 +		glLoadTransposeMatrixdARB((double*)&mat);
    1.33 +	} else {
    1.34 +		Matrix4x4 tmat = mat.transposed();
    1.35 +		glLoadMatrixd((double*)&tmat);
    1.36 +	}
    1.37 +#endif
    1.38 +}
    1.39 +
    1.40 +const Matrix4x4 &Camera::matrix() const
    1.41 +{
    1.42 +	if(!mcache.valid) {
    1.43 +		calc_matrix(&mcache.mat);
    1.44 +		mcache.valid = true;
    1.45 +	}
    1.46 +	return mcache.mat;
    1.47 +}
    1.48 +
    1.49 +const Matrix4x4 &Camera::inv_matrix() const
    1.50 +{
    1.51 +	if(!mcache_inv.valid) {
    1.52 +		calc_inv_matrix(&mcache_inv.mat);
    1.53 +		mcache_inv.valid = true;
    1.54 +	}
    1.55 +	return mcache_inv.mat;
    1.56 +}
    1.57 +
    1.58 +void Camera::use() const
    1.59 +{
    1.60 +	set_glmat(matrix());
    1.61 +}
    1.62 +
    1.63 +void Camera::use_inverse() const
    1.64 +{
    1.65 +	set_glmat(inv_matrix());
    1.66 +}
    1.67 +
    1.68 +void Camera::input_move(float x, float y, float z)
    1.69 +{
    1.70 +}
    1.71 +
    1.72 +void Camera::input_rotate(float x, float y, float z)
    1.73 +{
    1.74 +}
    1.75 +
    1.76 +void Camera::input_zoom(float factor)
    1.77 +{
    1.78 +}
    1.79 +
    1.80 +
    1.81 +// ---- orbit camera ----
    1.82 +
    1.83 +OrbitCamera::OrbitCamera()
    1.84 +{
    1.85 +	theta = 0.0;
    1.86 +	phi = 0.0;
    1.87 +	rad = 10.0;
    1.88 +
    1.89 +	min_phi = -M_PI / 2;
    1.90 +	max_phi = M_PI / 2;
    1.91 +}
    1.92 +
    1.93 +OrbitCamera::~OrbitCamera()
    1.94 +{
    1.95 +}
    1.96 +
    1.97 +void OrbitCamera::set_distance(float dist)
    1.98 +{
    1.99 +	rad = dist;
   1.100 +}
   1.101 +
   1.102 +#define MIN(a, b)	((a) < (b) ? (a) : (b))
   1.103 +#define MAX(a, b)	((a) > (b) ? (a) : (b))
   1.104 +void OrbitCamera::set_vertical_limits(float a, float b)
   1.105 +{
   1.106 +	a = M_PI * a / 180.0;
   1.107 +	b = M_PI * b / 180.0;
   1.108 +	min_phi = MIN(a, b);
   1.109 +	max_phi = MAX(a, b);
   1.110 +}
   1.111 +
   1.112 +void OrbitCamera::calc_matrix(Matrix4x4 *mat) const
   1.113 +{
   1.114 +	mat->reset_identity();
   1.115 +	mat->translate(Vector3(0, 0, -rad));
   1.116 +	mat->rotate(Vector3(phi, 0, 0));
   1.117 +	mat->rotate(Vector3(0, theta, 0));
   1.118 +}
   1.119 +
   1.120 +void OrbitCamera::calc_inv_matrix(Matrix4x4 *mat) const
   1.121 +{
   1.122 +	mat->reset_identity();
   1.123 +	mat->rotate(Vector3(0, theta, 0));
   1.124 +	mat->rotate(Vector3(phi, 0, 0));
   1.125 +	mat->translate(Vector3(0, 0, -rad));
   1.126 +}
   1.127 +
   1.128 +void OrbitCamera::input_rotate(float x, float y, float z)
   1.129 +{
   1.130 +	theta += x;
   1.131 +	phi += y;
   1.132 +
   1.133 +	if(phi < min_phi)
   1.134 +		phi = min_phi;
   1.135 +	if(phi > max_phi)
   1.136 +		phi = max_phi;
   1.137 +
   1.138 +	inval_cache();
   1.139 +}
   1.140 +
   1.141 +void OrbitCamera::input_zoom(float factor)
   1.142 +{
   1.143 +	rad += factor;
   1.144 +	if(rad < 0.0)
   1.145 +		rad = 0.0;
   1.146 +
   1.147 +	inval_cache();
   1.148 +}
   1.149 +
   1.150 +void FpsCamera::calc_matrix(Matrix4x4 *mat) const
   1.151 +{
   1.152 +	mat->reset_identity();
   1.153 +	mat->translate(Vector3(pos.x, pos.y, pos.z));
   1.154 +	mat->rotate(Vector3(0, theta, 0));
   1.155 +	mat->rotate(Vector3(phi, 0, 0));
   1.156 +}
   1.157 +
   1.158 +void FpsCamera::calc_inv_matrix(Matrix4x4 *mat) const
   1.159 +{
   1.160 +	mat->reset_identity();
   1.161 +	mat->rotate(Vector3(phi, 0, 0));
   1.162 +	mat->rotate(Vector3(0, theta, 0));
   1.163 +	mat->translate(Vector3(-pos.x, -pos.y, -pos.z));
   1.164 +}
   1.165 +
   1.166 +void FpsCamera::input_move(float x, float y, float z)
   1.167 +{
   1.168 +	pos.x += x * cos(theta) - z * sin(theta);
   1.169 +	pos.z += x * sin(theta) + z * cos(theta);
   1.170 +	pos.y += y;
   1.171 +	inval_cache();
   1.172 +}
   1.173 +
   1.174 +const Vector3 &FpsCamera::get_position() const
   1.175 +{
   1.176 +	return pos;
   1.177 +}
   1.178 +
   1.179 +
   1.180 +FlyCamera::FlyCamera()
   1.181 +{
   1.182 +	pos.z = 10.0f;
   1.183 +}
   1.184 +
   1.185 +void FlyCamera::calc_matrix(Matrix4x4 *mat) const
   1.186 +{
   1.187 +	/*mat->reset_identity();
   1.188 +	mat->translate(-pos);
   1.189 +	*mat = *mat * Matrix4x4(rot.get_rotation_matrix());
   1.190 +	mat->translate(pos);*/
   1.191 +	//mat->translate(-pos.transformed(rot));
   1.192 +
   1.193 +	Matrix3x3 qmat = rot.get_rotation_matrix();
   1.194 +
   1.195 +	Vector3 ivec = qmat.get_row_vector(0);
   1.196 +	Vector3 jvec = qmat.get_row_vector(1);
   1.197 +	Vector3 kvec = qmat.get_row_vector(2);
   1.198 +
   1.199 +	*mat = Matrix4x4(qmat);
   1.200 +	/*Vector3 trans_x = ivec * pos;
   1.201 +	Vector3 trans_y = jvec * pos;
   1.202 +	Vector3 trans_z = kvec * pos;
   1.203 +	Vector3 trans = trans_x + trans_y + trans_z;*/
   1.204 +	Vector3 trans;
   1.205 +	trans.x = dot_product(ivec, pos);
   1.206 +	trans.y = dot_product(jvec, pos);
   1.207 +	trans.z = dot_product(kvec, pos);
   1.208 +	mat->set_column_vector(-trans, 3);
   1.209 +}
   1.210 +
   1.211 +/*void FlyCamera::calc_inv_matrix(Matrix4x4 *mat) const
   1.212 +{
   1.213 +	mat->set_translation(pos);
   1.214 +	*mat = *mat * Matrix4x4(rot.get_rotation_matrix());
   1.215 +}*/
   1.216 +
   1.217 +const Vector3 &FlyCamera::get_position() const
   1.218 +{
   1.219 +	return pos;
   1.220 +}
   1.221 +
   1.222 +const Quaternion &FlyCamera::get_rotation() const
   1.223 +{
   1.224 +	return rot;
   1.225 +}
   1.226 +
   1.227 +void FlyCamera::input_move(float x, float y, float z)
   1.228 +{
   1.229 +	pos += Vector3(x, y, z);
   1.230 +	inval_cache();
   1.231 +}
   1.232 +
   1.233 +void FlyCamera::input_rotate(float x, float y, float z)
   1.234 +{
   1.235 +	Vector3 axis(x, y, z);
   1.236 +	float axis_len = axis.length();
   1.237 +	rot.rotate(axis / axis_len, axis_len);
   1.238 +	rot.normalize();
   1.239 +	inval_cache();
   1.240 +}