Line data Source code
1 :
2 : /* Copyright (c) 2006-2011, Stefan Eilemann <eile@equalizergraphics.com>
3 : *
4 : * This library is free software; you can redistribute it and/or modify it under
5 : * the terms of the GNU Lesser General Public License version 2.1 as published
6 : * by the Free Software Foundation.
7 : *
8 : * This library is distributed in the hope that it will be useful, but WITHOUT
9 : * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
10 : * FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
11 : * details.
12 : *
13 : * You should have received a copy of the GNU Lesser General Public License
14 : * along with this library; if not, write to the Free Software Foundation, Inc.,
15 : * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
16 : */
17 :
18 : #include "frustumData.h"
19 :
20 : #include <eq/fabric/projection.h>
21 : #include <eq/fabric/vmmlib.h>
22 : #include <eq/fabric/wall.h>
23 :
24 : #define DEG2RAD(angle) ((angle) * static_cast<float>(M_PI) / 180.f)
25 :
26 : namespace eq
27 : {
28 : namespace server
29 : {
30 12638 : FrustumData::FrustumData()
31 : : _width(0.f)
32 : , _height(0.f)
33 12638 : , _type(Wall::TYPE_FIXED)
34 : {
35 12638 : }
36 :
37 76 : void FrustumData::applyWall(const fabric::Wall& wall)
38 : {
39 76 : Vector3f u = wall.bottomRight - wall.bottomLeft;
40 76 : Vector3f v = wall.topLeft - wall.bottomLeft;
41 76 : Vector3f w = vmml::cross(u, v);
42 :
43 76 : _type = wall.type;
44 76 : _width = u.normalize();
45 76 : _height = v.normalize();
46 76 : w.normalize();
47 :
48 76 : _xfm.array[0] = u[0];
49 76 : _xfm.array[1] = v[0];
50 76 : _xfm.array[2] = w[0];
51 76 : _xfm.array[3] = 0.;
52 :
53 76 : _xfm.array[4] = u[1];
54 76 : _xfm.array[5] = v[1];
55 76 : _xfm.array[6] = w[1];
56 76 : _xfm.array[7] = 0.;
57 :
58 76 : _xfm.array[8] = u[2];
59 76 : _xfm.array[9] = v[2];
60 76 : _xfm.array[10] = w[2];
61 76 : _xfm.array[11] = 0.;
62 :
63 76 : const Vector3f center = (wall.bottomRight + wall.topLeft) * 0.5f;
64 76 : _xfm.array[12] = -u.dot(center);
65 76 : _xfm.array[13] = -v.dot(center);
66 76 : _xfm.array[14] = -w.dot(center);
67 76 : _xfm.array[15] = 1.;
68 76 : }
69 :
70 0 : void FrustumData::applyProjection(const fabric::Projection& projection)
71 : {
72 0 : const float cosH = cosf(DEG2RAD(projection.hpr[0]));
73 0 : const float sinH = sinf(DEG2RAD(projection.hpr[0]));
74 0 : const float cosP = cosf(DEG2RAD(projection.hpr[1]));
75 0 : const float sinP = sinf(DEG2RAD(projection.hpr[1]));
76 0 : const float cosR = cosf(DEG2RAD(projection.hpr[2]));
77 0 : const float sinR = sinf(DEG2RAD(projection.hpr[2]));
78 :
79 : // HPR Matrix = -roll[z-axis] * -pitch[x-axis] * -head[y-axis]
80 0 : const float rot[9] = {sinR * sinP * sinH + cosR * cosH,
81 0 : cosR * sinP * sinH - sinR * cosH,
82 0 : cosP * sinH,
83 0 : cosP * sinR,
84 0 : cosP * cosR,
85 0 : -sinP,
86 0 : sinR * sinP * cosH - cosR * sinH,
87 0 : cosR * sinP * cosH + sinR * sinH,
88 0 : cosP * cosH};
89 :
90 : // translation = HPR x -origin
91 0 : const Vector3f& origin = projection.origin;
92 0 : const float distance = projection.distance;
93 : const Vector3f trans(
94 0 : -(rot[0] * origin[0] + rot[3] * origin[1] + rot[6] * origin[2]),
95 0 : -(rot[1] * origin[0] + rot[4] * origin[1] + rot[7] * origin[2]),
96 0 : -(rot[2] * origin[0] + rot[5] * origin[1] + rot[8] * origin[2]));
97 :
98 0 : _xfm.array[0] = rot[0];
99 0 : _xfm.array[1] = rot[1];
100 0 : _xfm.array[2] = rot[2];
101 0 : _xfm.array[3] = 0.;
102 :
103 0 : _xfm.array[4] = rot[3];
104 0 : _xfm.array[5] = rot[4];
105 0 : _xfm.array[6] = rot[5];
106 0 : _xfm.array[7] = 0.;
107 :
108 0 : _xfm.array[8] = rot[6];
109 0 : _xfm.array[9] = rot[7];
110 0 : _xfm.array[10] = rot[8];
111 0 : _xfm.array[11] = 0.;
112 :
113 0 : _xfm.array[12] = trans[0];
114 0 : _xfm.array[13] = trans[1];
115 0 : _xfm.array[14] = trans[2] + distance;
116 0 : _xfm.array[15] = 1.;
117 :
118 0 : _width = distance * 2.f * tanf(DEG2RAD(.5f * projection.fov[0]));
119 0 : _height = distance * 2.f * tanf(DEG2RAD(.5f * projection.fov[1]));
120 0 : _type = Wall::TYPE_FIXED;
121 0 : }
122 :
123 0 : std::ostream& operator<<(std::ostream& os, const FrustumData& frustumData)
124 : {
125 0 : os << "size: " << frustumData.getWidth() << "x" << frustumData.getHeight()
126 0 : << " xfm: " << frustumData.getTransform() << std::endl;
127 0 : return os;
128 : }
129 : }
130 60 : }
|