aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/libraries/irrlicht-1.8/source/Irrlicht/CSoftwareDriver2.cpp
diff options
context:
space:
mode:
authorDavid Walter Seikel2013-01-13 18:54:10 +1000
committerDavid Walter Seikel2013-01-13 18:54:10 +1000
commit959831f4ef5a3e797f576c3de08cd65032c997ad (patch)
treee7351908be5995f0b325b2ebeaa02d5a34b82583 /libraries/irrlicht-1.8/source/Irrlicht/CSoftwareDriver2.cpp
parentAdd info about changes to Irrlicht. (diff)
downloadSledjHamr-959831f4ef5a3e797f576c3de08cd65032c997ad.zip
SledjHamr-959831f4ef5a3e797f576c3de08cd65032c997ad.tar.gz
SledjHamr-959831f4ef5a3e797f576c3de08cd65032c997ad.tar.bz2
SledjHamr-959831f4ef5a3e797f576c3de08cd65032c997ad.tar.xz
Remove damned ancient DOS line endings from Irrlicht. Hopefully I did not go overboard.
Diffstat (limited to '')
-rw-r--r--libraries/irrlicht-1.8/source/Irrlicht/CSoftwareDriver2.cpp5444
1 files changed, 2722 insertions, 2722 deletions
diff --git a/libraries/irrlicht-1.8/source/Irrlicht/CSoftwareDriver2.cpp b/libraries/irrlicht-1.8/source/Irrlicht/CSoftwareDriver2.cpp
index bdde929..9f0015f 100644
--- a/libraries/irrlicht-1.8/source/Irrlicht/CSoftwareDriver2.cpp
+++ b/libraries/irrlicht-1.8/source/Irrlicht/CSoftwareDriver2.cpp
@@ -1,2722 +1,2722 @@
1// Copyright (C) 2002-2012 Nikolaus Gebhardt / Thomas Alten 1// Copyright (C) 2002-2012 Nikolaus Gebhardt / Thomas Alten
2// This file is part of the "Irrlicht Engine". 2// This file is part of the "Irrlicht Engine".
3// For conditions of distribution and use, see copyright notice in irrlicht.h 3// For conditions of distribution and use, see copyright notice in irrlicht.h
4 4
5#include "IrrCompileConfig.h" 5#include "IrrCompileConfig.h"
6#include "CSoftwareDriver2.h" 6#include "CSoftwareDriver2.h"
7 7
8#ifdef _IRR_COMPILE_WITH_BURNINGSVIDEO_ 8#ifdef _IRR_COMPILE_WITH_BURNINGSVIDEO_
9 9
10#include "SoftwareDriver2_helper.h" 10#include "SoftwareDriver2_helper.h"
11#include "CSoftwareTexture2.h" 11#include "CSoftwareTexture2.h"
12#include "CSoftware2MaterialRenderer.h" 12#include "CSoftware2MaterialRenderer.h"
13#include "S3DVertex.h" 13#include "S3DVertex.h"
14#include "S4DVertex.h" 14#include "S4DVertex.h"
15#include "CBlit.h" 15#include "CBlit.h"
16 16
17 17
18#define MAT_TEXTURE(tex) ( (video::CSoftwareTexture2*) Material.org.getTexture ( tex ) ) 18#define MAT_TEXTURE(tex) ( (video::CSoftwareTexture2*) Material.org.getTexture ( tex ) )
19 19
20 20
21namespace irr 21namespace irr
22{ 22{
23namespace video 23namespace video
24{ 24{
25 25
26namespace glsl 26namespace glsl
27{ 27{
28 28
29typedef sVec4 vec4; 29typedef sVec4 vec4;
30typedef sVec3 vec3; 30typedef sVec3 vec3;
31typedef sVec2 vec2; 31typedef sVec2 vec2;
32 32
33#define in 33#define in
34#define uniform 34#define uniform
35#define attribute 35#define attribute
36#define varying 36#define varying
37 37
38#ifdef _MSC_VER 38#ifdef _MSC_VER
39#pragma warning(disable:4244) 39#pragma warning(disable:4244)
40#endif 40#endif
41 41
42struct mat4{ 42struct mat4{
43 float m[4][4]; 43 float m[4][4];
44 44
45 vec4 operator* ( const vec4 &in ) const 45 vec4 operator* ( const vec4 &in ) const
46 { 46 {
47 vec4 out; 47 vec4 out;
48 return out; 48 return out;
49 } 49 }
50 50
51}; 51};
52 52
53struct mat3{ 53struct mat3{
54 float m[3][3]; 54 float m[3][3];
55 55
56 vec3 operator* ( const vec3 &in ) const 56 vec3 operator* ( const vec3 &in ) const
57 { 57 {
58 vec3 out; 58 vec3 out;
59 return out; 59 return out;
60 } 60 }
61}; 61};
62 62
63const int gl_MaxLights = 8; 63const int gl_MaxLights = 8;
64 64
65 65
66inline float dot (float x, float y) { return x * y; } 66inline float dot (float x, float y) { return x * y; }
67inline float dot ( const vec2 &x, const vec2 &y) { return x.x * y.x + x.y * y.y; } 67inline float dot ( const vec2 &x, const vec2 &y) { return x.x * y.x + x.y * y.y; }
68inline float dot ( const vec3 &x, const vec3 &y) { return x.x * y.x + x.y * y.y + x.z * y.z; } 68inline float dot ( const vec3 &x, const vec3 &y) { return x.x * y.x + x.y * y.y + x.z * y.z; }
69inline float dot ( const vec4 &x, const vec4 &y) { return x.x * y.x + x.y * y.y + x.z * y.z + x.w * y.w; } 69inline float dot ( const vec4 &x, const vec4 &y) { return x.x * y.x + x.y * y.y + x.z * y.z + x.w * y.w; }
70 70
71inline float reflect (float I, float N) { return I - 2.0 * dot (N, I) * N; } 71inline float reflect (float I, float N) { return I - 2.0 * dot (N, I) * N; }
72inline vec2 reflect (const vec2 &I, const vec2 &N) { return I - N * 2.0 * dot (N, I); } 72inline vec2 reflect (const vec2 &I, const vec2 &N) { return I - N * 2.0 * dot (N, I); }
73inline vec3 reflect (const vec3 &I, const vec3 &N) { return I - N * 2.0 * dot (N, I); } 73inline vec3 reflect (const vec3 &I, const vec3 &N) { return I - N * 2.0 * dot (N, I); }
74inline vec4 reflect (const vec4 &I, const vec4 &N) { return I - N * 2.0 * dot (N, I); } 74inline vec4 reflect (const vec4 &I, const vec4 &N) { return I - N * 2.0 * dot (N, I); }
75 75
76 76
77inline float refract (float I, float N, float eta){ 77inline float refract (float I, float N, float eta){
78 const float k = 1.0 - eta * eta * (1.0 - dot (N, I) * dot (N, I)); 78 const float k = 1.0 - eta * eta * (1.0 - dot (N, I) * dot (N, I));
79 if (k < 0.0) 79 if (k < 0.0)
80 return 0.0; 80 return 0.0;
81 return eta * I - (eta * dot (N, I) + sqrt (k)) * N; 81 return eta * I - (eta * dot (N, I) + sqrt (k)) * N;
82} 82}
83 83
84inline vec2 refract (const vec2 &I, const vec2 &N, float eta){ 84inline vec2 refract (const vec2 &I, const vec2 &N, float eta){
85 const float k = 1.0 - eta * eta * (1.0 - dot (N, I) * dot (N, I)); 85 const float k = 1.0 - eta * eta * (1.0 - dot (N, I) * dot (N, I));
86 if (k < 0.0) 86 if (k < 0.0)
87 return vec2 (0.0); 87 return vec2 (0.0);
88 return I * eta - N * (eta * dot (N, I) + sqrt (k)); 88 return I * eta - N * (eta * dot (N, I) + sqrt (k));
89} 89}
90 90
91inline vec3 refract (const vec3 &I, const vec3 &N, float eta) { 91inline vec3 refract (const vec3 &I, const vec3 &N, float eta) {
92 const float k = 1.0 - eta * eta * (1.0 - dot (N, I) * dot (N, I)); 92 const float k = 1.0 - eta * eta * (1.0 - dot (N, I) * dot (N, I));
93 if (k < 0.0) 93 if (k < 0.0)
94 return vec3 (0.0); 94 return vec3 (0.0);
95 return I * eta - N * (eta * dot (N, I) + sqrt (k)); 95 return I * eta - N * (eta * dot (N, I) + sqrt (k));
96} 96}
97 97
98inline vec4 refract (const vec4 &I, const vec4 &N, float eta) { 98inline vec4 refract (const vec4 &I, const vec4 &N, float eta) {
99 const float k = 1.0 - eta * eta * (1.0 - dot (N, I) * dot (N, I)); 99 const float k = 1.0 - eta * eta * (1.0 - dot (N, I) * dot (N, I));
100 if (k < 0.0) 100 if (k < 0.0)
101 return vec4 (0.0); 101 return vec4 (0.0);
102 return I * eta - N * (eta * dot (N, I) + sqrt (k)); 102 return I * eta - N * (eta * dot (N, I) + sqrt (k));
103} 103}
104 104
105 105
106inline float length ( const vec3 &v ) { return sqrtf ( v.x * v.x + v.y * v.y + v.z * v.z ); } 106inline float length ( const vec3 &v ) { return sqrtf ( v.x * v.x + v.y * v.y + v.z * v.z ); }
107vec3 normalize ( const vec3 &v ) { float l = 1.f / length ( v ); return vec3 ( v.x * l, v.y * l, v.z * l ); } 107vec3 normalize ( const vec3 &v ) { float l = 1.f / length ( v ); return vec3 ( v.x * l, v.y * l, v.z * l ); }
108float max ( float a, float b ) { return a > b ? a : b; } 108float max ( float a, float b ) { return a > b ? a : b; }
109float min ( float a, float b ) { return a < b ? a : b; } 109float min ( float a, float b ) { return a < b ? a : b; }
110vec4 clamp ( const vec4 &a, f32 low, f32 high ) { return vec4 ( min (max(a.x,low), high), min (max(a.y,low), high), min (max(a.z,low), high), min (max(a.w,low), high) ); } 110vec4 clamp ( const vec4 &a, f32 low, f32 high ) { return vec4 ( min (max(a.x,low), high), min (max(a.y,low), high), min (max(a.z,low), high), min (max(a.w,low), high) ); }
111 111
112 112
113 113
114typedef int sampler2D; 114typedef int sampler2D;
115sampler2D texUnit0; 115sampler2D texUnit0;
116 116
117vec4 texture2D (sampler2D sampler, const vec2 &coord) { return vec4 (0.0); } 117vec4 texture2D (sampler2D sampler, const vec2 &coord) { return vec4 (0.0); }
118 118
119struct gl_LightSourceParameters { 119struct gl_LightSourceParameters {
120 vec4 ambient; // Acli 120 vec4 ambient; // Acli
121 vec4 diffuse; // Dcli 121 vec4 diffuse; // Dcli
122 vec4 specular; // Scli 122 vec4 specular; // Scli
123 vec4 position; // Ppli 123 vec4 position; // Ppli
124 vec4 halfVector; // Derived: Hi 124 vec4 halfVector; // Derived: Hi
125 vec3 spotDirection; // Sdli 125 vec3 spotDirection; // Sdli
126 float spotExponent; // Srli 126 float spotExponent; // Srli
127 float spotCutoff; // Crli 127 float spotCutoff; // Crli
128 // (range: [0.0,90.0], 180.0) 128 // (range: [0.0,90.0], 180.0)
129 float spotCosCutoff; // Derived: cos(Crli) 129 float spotCosCutoff; // Derived: cos(Crli)
130 // (range: [1.0,0.0],-1.0) 130 // (range: [1.0,0.0],-1.0)
131 float constantAttenuation; // K0 131 float constantAttenuation; // K0
132 float linearAttenuation; // K1 132 float linearAttenuation; // K1
133 float quadraticAttenuation;// K2 133 float quadraticAttenuation;// K2
134}; 134};
135 135
136uniform gl_LightSourceParameters gl_LightSource[gl_MaxLights]; 136uniform gl_LightSourceParameters gl_LightSource[gl_MaxLights];
137 137
138struct gl_LightModelParameters { 138struct gl_LightModelParameters {
139 vec4 ambient; 139 vec4 ambient;
140}; 140};
141uniform gl_LightModelParameters gl_LightModel; 141uniform gl_LightModelParameters gl_LightModel;
142 142
143struct gl_LightModelProducts { 143struct gl_LightModelProducts {
144 vec4 sceneColor; 144 vec4 sceneColor;
145}; 145};
146 146
147uniform gl_LightModelProducts gl_FrontLightModelProduct; 147uniform gl_LightModelProducts gl_FrontLightModelProduct;
148uniform gl_LightModelProducts gl_BackLightModelProduct; 148uniform gl_LightModelProducts gl_BackLightModelProduct;
149 149
150struct gl_LightProducts { 150struct gl_LightProducts {
151 vec4 ambient; 151 vec4 ambient;
152 vec4 diffuse; 152 vec4 diffuse;
153 vec4 specular; 153 vec4 specular;
154}; 154};
155 155
156uniform gl_LightProducts gl_FrontLightProduct[gl_MaxLights]; 156uniform gl_LightProducts gl_FrontLightProduct[gl_MaxLights];
157uniform gl_LightProducts gl_BackLightProduct[gl_MaxLights]; 157uniform gl_LightProducts gl_BackLightProduct[gl_MaxLights];
158 158
159struct gl_MaterialParameters 159struct gl_MaterialParameters
160{ 160{
161 vec4 emission; // Ecm 161 vec4 emission; // Ecm
162 vec4 ambient; // Acm 162 vec4 ambient; // Acm
163 vec4 diffuse; // Dcm 163 vec4 diffuse; // Dcm
164 vec4 specular; // Scm 164 vec4 specular; // Scm
165 float shininess; // Srm 165 float shininess; // Srm
166}; 166};
167uniform gl_MaterialParameters gl_FrontMaterial; 167uniform gl_MaterialParameters gl_FrontMaterial;
168uniform gl_MaterialParameters gl_BackMaterial; 168uniform gl_MaterialParameters gl_BackMaterial;
169 169
170// GLSL has some built-in attributes in a vertex shader: 170// GLSL has some built-in attributes in a vertex shader:
171attribute vec4 gl_Vertex; // 4D vector representing the vertex position 171attribute vec4 gl_Vertex; // 4D vector representing the vertex position
172attribute vec3 gl_Normal; // 3D vector representing the vertex normal 172attribute vec3 gl_Normal; // 3D vector representing the vertex normal
173attribute vec4 gl_Color; // 4D vector representing the vertex color 173attribute vec4 gl_Color; // 4D vector representing the vertex color
174attribute vec4 gl_MultiTexCoord0; // 4D vector representing the texture coordinate of texture unit X 174attribute vec4 gl_MultiTexCoord0; // 4D vector representing the texture coordinate of texture unit X
175attribute vec4 gl_MultiTexCoord1; // 4D vector representing the texture coordinate of texture unit X 175attribute vec4 gl_MultiTexCoord1; // 4D vector representing the texture coordinate of texture unit X
176 176
177uniform mat4 gl_ModelViewMatrix; //4x4 Matrix representing the model-view matrix. 177uniform mat4 gl_ModelViewMatrix; //4x4 Matrix representing the model-view matrix.
178uniform mat4 gl_ModelViewProjectionMatrix; //4x4 Matrix representing the model-view-projection matrix. 178uniform mat4 gl_ModelViewProjectionMatrix; //4x4 Matrix representing the model-view-projection matrix.
179uniform mat3 gl_NormalMatrix; //3x3 Matrix representing the inverse transpose model-view matrix. This matrix is used for normal transformation. 179uniform mat3 gl_NormalMatrix; //3x3 Matrix representing the inverse transpose model-view matrix. This matrix is used for normal transformation.
180 180
181 181
182varying vec4 gl_FrontColor; // 4D vector representing the primitives front color 182varying vec4 gl_FrontColor; // 4D vector representing the primitives front color
183varying vec4 gl_FrontSecondaryColor; // 4D vector representing the primitives second front color 183varying vec4 gl_FrontSecondaryColor; // 4D vector representing the primitives second front color
184varying vec4 gl_BackColor; // 4D vector representing the primitives back color 184varying vec4 gl_BackColor; // 4D vector representing the primitives back color
185varying vec4 gl_TexCoord[4]; // 4D vector representing the Xth texture coordinate 185varying vec4 gl_TexCoord[4]; // 4D vector representing the Xth texture coordinate
186 186
187// shader output 187// shader output
188varying vec4 gl_Position; // 4D vector representing the final processed vertex position. Only available in vertex shader. 188varying vec4 gl_Position; // 4D vector representing the final processed vertex position. Only available in vertex shader.
189varying vec4 gl_FragColor; // 4D vector representing the final color which is written in the frame buffer. Only available in fragment shader. 189varying vec4 gl_FragColor; // 4D vector representing the final color which is written in the frame buffer. Only available in fragment shader.
190varying float gl_FragDepth; // float representing the depth which is written in the depth buffer. Only available in fragment shader. 190varying float gl_FragDepth; // float representing the depth which is written in the depth buffer. Only available in fragment shader.
191 191
192varying vec4 gl_SecondaryColor; 192varying vec4 gl_SecondaryColor;
193varying float gl_FogFragCoord; 193varying float gl_FogFragCoord;
194 194
195 195
196vec4 ftransform(void) 196vec4 ftransform(void)
197{ 197{
198 return gl_ModelViewProjectionMatrix * gl_Vertex; 198 return gl_ModelViewProjectionMatrix * gl_Vertex;
199} 199}
200 200
201vec3 fnormal(void) 201vec3 fnormal(void)
202{ 202{
203 //Compute the normal 203 //Compute the normal
204 vec3 normal = gl_NormalMatrix * gl_Normal; 204 vec3 normal = gl_NormalMatrix * gl_Normal;
205 normal = normalize(normal); 205 normal = normalize(normal);
206 return normal; 206 return normal;
207} 207}
208 208
209 209
210struct program1 210struct program1
211{ 211{
212 vec4 Ambient; 212 vec4 Ambient;
213 vec4 Diffuse; 213 vec4 Diffuse;
214 vec4 Specular; 214 vec4 Specular;
215 215
216 void pointLight(in int i, in vec3 normal, in vec3 eye, in vec3 ecPosition3) 216 void pointLight(in int i, in vec3 normal, in vec3 eye, in vec3 ecPosition3)
217 { 217 {
218 float nDotVP; // normal . light direction 218 float nDotVP; // normal . light direction
219 float nDotHV; // normal . light half vector 219 float nDotHV; // normal . light half vector
220 float pf; // power factor 220 float pf; // power factor
221 float attenuation; // computed attenuation factor 221 float attenuation; // computed attenuation factor
222 float d; // distance from surface to light source 222 float d; // distance from surface to light source
223 vec3 VP; // direction from surface to light position 223 vec3 VP; // direction from surface to light position
224 vec3 halfVector; // direction of maximum highlights 224 vec3 halfVector; // direction of maximum highlights
225 225
226 // Compute vector from surface to light position 226 // Compute vector from surface to light position
227 VP = vec3 (gl_LightSource[i].position) - ecPosition3; 227 VP = vec3 (gl_LightSource[i].position) - ecPosition3;
228 228
229 // Compute distance between surface and light position 229 // Compute distance between surface and light position
230 d = length(VP); 230 d = length(VP);
231 231
232 // Normalize the vector from surface to light position 232 // Normalize the vector from surface to light position
233 VP = normalize(VP); 233 VP = normalize(VP);
234 234
235 // Compute attenuation 235 // Compute attenuation
236 attenuation = 1.0 / (gl_LightSource[i].constantAttenuation + 236 attenuation = 1.0 / (gl_LightSource[i].constantAttenuation +
237 gl_LightSource[i].linearAttenuation * d + 237 gl_LightSource[i].linearAttenuation * d +
238 gl_LightSource[i].quadraticAttenuation * d * d); 238 gl_LightSource[i].quadraticAttenuation * d * d);
239 239
240 halfVector = normalize(VP + eye); 240 halfVector = normalize(VP + eye);
241 241
242 nDotVP = max(0.0, dot(normal, VP)); 242 nDotVP = max(0.0, dot(normal, VP));
243 nDotHV = max(0.0, dot(normal, halfVector)); 243 nDotHV = max(0.0, dot(normal, halfVector));
244 244
245 if (nDotVP == 0.0) 245 if (nDotVP == 0.0)
246 { 246 {
247 pf = 0.0; 247 pf = 0.0;
248 } 248 }
249 else 249 else
250 { 250 {
251 pf = pow(nDotHV, gl_FrontMaterial.shininess); 251 pf = pow(nDotHV, gl_FrontMaterial.shininess);
252 252
253 } 253 }
254 Ambient += gl_LightSource[i].ambient * attenuation; 254 Ambient += gl_LightSource[i].ambient * attenuation;
255 Diffuse += gl_LightSource[i].diffuse * nDotVP * attenuation; 255 Diffuse += gl_LightSource[i].diffuse * nDotVP * attenuation;
256 Specular += gl_LightSource[i].specular * pf * attenuation; 256 Specular += gl_LightSource[i].specular * pf * attenuation;
257 } 257 }
258 258
259 vec3 fnormal(void) 259 vec3 fnormal(void)
260 { 260 {
261 //Compute the normal 261 //Compute the normal
262 vec3 normal = gl_NormalMatrix * gl_Normal; 262 vec3 normal = gl_NormalMatrix * gl_Normal;
263 normal = normalize(normal); 263 normal = normalize(normal);
264 return normal; 264 return normal;
265 } 265 }
266 266
267 void ftexgen(in vec3 normal, in vec4 ecPosition) 267 void ftexgen(in vec3 normal, in vec4 ecPosition)
268 { 268 {
269 269
270 gl_TexCoord[0] = gl_MultiTexCoord0; 270 gl_TexCoord[0] = gl_MultiTexCoord0;
271 } 271 }
272 272
273 void flight(in vec3 normal, in vec4 ecPosition, float alphaFade) 273 void flight(in vec3 normal, in vec4 ecPosition, float alphaFade)
274 { 274 {
275 vec4 color; 275 vec4 color;
276 vec3 ecPosition3; 276 vec3 ecPosition3;
277 vec3 eye; 277 vec3 eye;
278 278
279 ecPosition3 = (vec3 (ecPosition)) / ecPosition.w; 279 ecPosition3 = (vec3 (ecPosition)) / ecPosition.w;
280 eye = vec3 (0.0, 0.0, 1.0); 280 eye = vec3 (0.0, 0.0, 1.0);
281 281
282 // Clear the light intensity accumulators 282 // Clear the light intensity accumulators
283 Ambient = vec4 (0.0); 283 Ambient = vec4 (0.0);
284 Diffuse = vec4 (0.0); 284 Diffuse = vec4 (0.0);
285 Specular = vec4 (0.0); 285 Specular = vec4 (0.0);
286 286
287 pointLight(0, normal, eye, ecPosition3); 287 pointLight(0, normal, eye, ecPosition3);
288 288
289 pointLight(1, normal, eye, ecPosition3); 289 pointLight(1, normal, eye, ecPosition3);
290 290
291 color = gl_FrontLightModelProduct.sceneColor + 291 color = gl_FrontLightModelProduct.sceneColor +
292 Ambient * gl_FrontMaterial.ambient + 292 Ambient * gl_FrontMaterial.ambient +
293 Diffuse * gl_FrontMaterial.diffuse; 293 Diffuse * gl_FrontMaterial.diffuse;
294 gl_FrontSecondaryColor = Specular * gl_FrontMaterial.specular; 294 gl_FrontSecondaryColor = Specular * gl_FrontMaterial.specular;
295 color = clamp( color, 0.0, 1.0 ); 295 color = clamp( color, 0.0, 1.0 );
296 gl_FrontColor = color; 296 gl_FrontColor = color;
297 297
298 gl_FrontColor.a *= alphaFade; 298 gl_FrontColor.a *= alphaFade;
299 } 299 }
300 300
301 301
302 void vertexshader_main (void) 302 void vertexshader_main (void)
303 { 303 {
304 vec3 transformedNormal; 304 vec3 transformedNormal;
305 float alphaFade = 1.0; 305 float alphaFade = 1.0;
306 306
307 // Eye-coordinate position of vertex, needed in various calculations 307 // Eye-coordinate position of vertex, needed in various calculations
308 vec4 ecPosition = gl_ModelViewMatrix * gl_Vertex; 308 vec4 ecPosition = gl_ModelViewMatrix * gl_Vertex;
309 309
310 // Do fixed functionality vertex transform 310 // Do fixed functionality vertex transform
311 gl_Position = ftransform(); 311 gl_Position = ftransform();
312 transformedNormal = fnormal(); 312 transformedNormal = fnormal();
313 flight(transformedNormal, ecPosition, alphaFade); 313 flight(transformedNormal, ecPosition, alphaFade);
314 ftexgen(transformedNormal, ecPosition); 314 ftexgen(transformedNormal, ecPosition);
315 } 315 }
316 316
317 void fragmentshader_main (void) 317 void fragmentshader_main (void)
318 { 318 {
319 vec4 color; 319 vec4 color;
320 320
321 color = gl_Color; 321 color = gl_Color;
322 322
323 color *= texture2D(texUnit0, vec2(gl_TexCoord[0].x, gl_TexCoord[0].y) ); 323 color *= texture2D(texUnit0, vec2(gl_TexCoord[0].x, gl_TexCoord[0].y) );
324 324
325 color += gl_SecondaryColor; 325 color += gl_SecondaryColor;
326 color = clamp(color, 0.0, 1.0); 326 color = clamp(color, 0.0, 1.0);
327 327
328 gl_FragColor = color; 328 gl_FragColor = color;
329 } 329 }
330}; 330};
331 331
332} 332}
333 333
334//! constructor 334//! constructor
335CBurningVideoDriver::CBurningVideoDriver(const irr::SIrrlichtCreationParameters& params, io::IFileSystem* io, video::IImagePresenter* presenter) 335CBurningVideoDriver::CBurningVideoDriver(const irr::SIrrlichtCreationParameters& params, io::IFileSystem* io, video::IImagePresenter* presenter)
336: CNullDriver(io, params.WindowSize), BackBuffer(0), Presenter(presenter), 336: CNullDriver(io, params.WindowSize), BackBuffer(0), Presenter(presenter),
337 WindowId(0), SceneSourceRect(0), 337 WindowId(0), SceneSourceRect(0),
338 RenderTargetTexture(0), RenderTargetSurface(0), CurrentShader(0), 338 RenderTargetTexture(0), RenderTargetSurface(0), CurrentShader(0),
339 DepthBuffer(0), StencilBuffer ( 0 ), 339 DepthBuffer(0), StencilBuffer ( 0 ),
340 CurrentOut ( 12 * 2, 128 ), Temp ( 12 * 2, 128 ) 340 CurrentOut ( 12 * 2, 128 ), Temp ( 12 * 2, 128 )
341{ 341{
342 #ifdef _DEBUG 342 #ifdef _DEBUG
343 setDebugName("CBurningVideoDriver"); 343 setDebugName("CBurningVideoDriver");
344 #endif 344 #endif
345 345
346 // create backbuffer 346 // create backbuffer
347 BackBuffer = new CImage(BURNINGSHADER_COLOR_FORMAT, params.WindowSize); 347 BackBuffer = new CImage(BURNINGSHADER_COLOR_FORMAT, params.WindowSize);
348 if (BackBuffer) 348 if (BackBuffer)
349 { 349 {
350 BackBuffer->fill(SColor(0)); 350 BackBuffer->fill(SColor(0));
351 351
352 // create z buffer 352 // create z buffer
353 if ( params.ZBufferBits ) 353 if ( params.ZBufferBits )
354 DepthBuffer = video::createDepthBuffer(BackBuffer->getDimension()); 354 DepthBuffer = video::createDepthBuffer(BackBuffer->getDimension());
355 355
356 // create stencil buffer 356 // create stencil buffer
357 if ( params.Stencilbuffer ) 357 if ( params.Stencilbuffer )
358 StencilBuffer = video::createStencilBuffer(BackBuffer->getDimension()); 358 StencilBuffer = video::createStencilBuffer(BackBuffer->getDimension());
359 } 359 }
360 360
361 DriverAttributes->setAttribute("MaxTextures", 2); 361 DriverAttributes->setAttribute("MaxTextures", 2);
362 DriverAttributes->setAttribute("MaxIndices", 1<<16); 362 DriverAttributes->setAttribute("MaxIndices", 1<<16);
363 DriverAttributes->setAttribute("MaxTextureSize", 1024); 363 DriverAttributes->setAttribute("MaxTextureSize", 1024);
364 DriverAttributes->setAttribute("MaxLights", glsl::gl_MaxLights); 364 DriverAttributes->setAttribute("MaxLights", glsl::gl_MaxLights);
365 DriverAttributes->setAttribute("MaxTextureLODBias", 16.f); 365 DriverAttributes->setAttribute("MaxTextureLODBias", 16.f);
366 DriverAttributes->setAttribute("Version", 47); 366 DriverAttributes->setAttribute("Version", 47);
367 367
368 // create triangle renderers 368 // create triangle renderers
369 369
370 irr::memset32 ( BurningShader, 0, sizeof ( BurningShader ) ); 370 irr::memset32 ( BurningShader, 0, sizeof ( BurningShader ) );
371 //BurningShader[ETR_FLAT] = createTRFlat2(DepthBuffer); 371 //BurningShader[ETR_FLAT] = createTRFlat2(DepthBuffer);
372 //BurningShader[ETR_FLAT_WIRE] = createTRFlatWire2(DepthBuffer); 372 //BurningShader[ETR_FLAT_WIRE] = createTRFlatWire2(DepthBuffer);
373 BurningShader[ETR_GOURAUD] = createTriangleRendererGouraud2(this); 373 BurningShader[ETR_GOURAUD] = createTriangleRendererGouraud2(this);
374 BurningShader[ETR_GOURAUD_ALPHA] = createTriangleRendererGouraudAlpha2(this ); 374 BurningShader[ETR_GOURAUD_ALPHA] = createTriangleRendererGouraudAlpha2(this );
375 BurningShader[ETR_GOURAUD_ALPHA_NOZ] = createTRGouraudAlphaNoZ2(this ); 375 BurningShader[ETR_GOURAUD_ALPHA_NOZ] = createTRGouraudAlphaNoZ2(this );
376 //BurningShader[ETR_GOURAUD_WIRE] = createTriangleRendererGouraudWire2(DepthBuffer); 376 //BurningShader[ETR_GOURAUD_WIRE] = createTriangleRendererGouraudWire2(DepthBuffer);
377 //BurningShader[ETR_TEXTURE_FLAT] = createTriangleRendererTextureFlat2(DepthBuffer); 377 //BurningShader[ETR_TEXTURE_FLAT] = createTriangleRendererTextureFlat2(DepthBuffer);
378 //BurningShader[ETR_TEXTURE_FLAT_WIRE] = createTriangleRendererTextureFlatWire2(DepthBuffer); 378 //BurningShader[ETR_TEXTURE_FLAT_WIRE] = createTriangleRendererTextureFlatWire2(DepthBuffer);
379 BurningShader[ETR_TEXTURE_GOURAUD] = createTriangleRendererTextureGouraud2(this); 379 BurningShader[ETR_TEXTURE_GOURAUD] = createTriangleRendererTextureGouraud2(this);
380 BurningShader[ETR_TEXTURE_GOURAUD_LIGHTMAP_M1] = createTriangleRendererTextureLightMap2_M1(this); 380 BurningShader[ETR_TEXTURE_GOURAUD_LIGHTMAP_M1] = createTriangleRendererTextureLightMap2_M1(this);
381 BurningShader[ETR_TEXTURE_GOURAUD_LIGHTMAP_M2] = createTriangleRendererTextureLightMap2_M2(this); 381 BurningShader[ETR_TEXTURE_GOURAUD_LIGHTMAP_M2] = createTriangleRendererTextureLightMap2_M2(this);
382 BurningShader[ETR_TEXTURE_GOURAUD_LIGHTMAP_M4] = createTriangleRendererGTextureLightMap2_M4(this); 382 BurningShader[ETR_TEXTURE_GOURAUD_LIGHTMAP_M4] = createTriangleRendererGTextureLightMap2_M4(this);
383 BurningShader[ETR_TEXTURE_LIGHTMAP_M4] = createTriangleRendererTextureLightMap2_M4(this); 383 BurningShader[ETR_TEXTURE_LIGHTMAP_M4] = createTriangleRendererTextureLightMap2_M4(this);
384 BurningShader[ETR_TEXTURE_GOURAUD_LIGHTMAP_ADD] = createTriangleRendererTextureLightMap2_Add(this); 384 BurningShader[ETR_TEXTURE_GOURAUD_LIGHTMAP_ADD] = createTriangleRendererTextureLightMap2_Add(this);
385 BurningShader[ETR_TEXTURE_GOURAUD_DETAIL_MAP] = createTriangleRendererTextureDetailMap2(this); 385 BurningShader[ETR_TEXTURE_GOURAUD_DETAIL_MAP] = createTriangleRendererTextureDetailMap2(this);
386 386
387 BurningShader[ETR_TEXTURE_GOURAUD_WIRE] = createTriangleRendererTextureGouraudWire2(this); 387 BurningShader[ETR_TEXTURE_GOURAUD_WIRE] = createTriangleRendererTextureGouraudWire2(this);
388 BurningShader[ETR_TEXTURE_GOURAUD_NOZ] = createTRTextureGouraudNoZ2(this); 388 BurningShader[ETR_TEXTURE_GOURAUD_NOZ] = createTRTextureGouraudNoZ2(this);
389 BurningShader[ETR_TEXTURE_GOURAUD_ADD] = createTRTextureGouraudAdd2(this); 389 BurningShader[ETR_TEXTURE_GOURAUD_ADD] = createTRTextureGouraudAdd2(this);
390 BurningShader[ETR_TEXTURE_GOURAUD_ADD_NO_Z] = createTRTextureGouraudAddNoZ2(this); 390 BurningShader[ETR_TEXTURE_GOURAUD_ADD_NO_Z] = createTRTextureGouraudAddNoZ2(this);
391 BurningShader[ETR_TEXTURE_GOURAUD_VERTEX_ALPHA] = createTriangleRendererTextureVertexAlpha2 ( this ); 391 BurningShader[ETR_TEXTURE_GOURAUD_VERTEX_ALPHA] = createTriangleRendererTextureVertexAlpha2 ( this );
392 392
393 BurningShader[ETR_TEXTURE_GOURAUD_ALPHA] = createTRTextureGouraudAlpha(this ); 393 BurningShader[ETR_TEXTURE_GOURAUD_ALPHA] = createTRTextureGouraudAlpha(this );
394 BurningShader[ETR_TEXTURE_GOURAUD_ALPHA_NOZ] = createTRTextureGouraudAlphaNoZ( this ); 394 BurningShader[ETR_TEXTURE_GOURAUD_ALPHA_NOZ] = createTRTextureGouraudAlphaNoZ( this );
395 395
396 BurningShader[ETR_NORMAL_MAP_SOLID] = createTRNormalMap ( this ); 396 BurningShader[ETR_NORMAL_MAP_SOLID] = createTRNormalMap ( this );
397 BurningShader[ETR_STENCIL_SHADOW] = createTRStencilShadow ( this ); 397 BurningShader[ETR_STENCIL_SHADOW] = createTRStencilShadow ( this );
398 BurningShader[ETR_TEXTURE_BLEND] = createTRTextureBlend( this ); 398 BurningShader[ETR_TEXTURE_BLEND] = createTRTextureBlend( this );
399 399
400 BurningShader[ETR_REFERENCE] = createTriangleRendererReference ( this ); 400 BurningShader[ETR_REFERENCE] = createTriangleRendererReference ( this );
401 401
402 402
403 // add the same renderer for all solid types 403 // add the same renderer for all solid types
404 CSoftware2MaterialRenderer_SOLID* smr = new CSoftware2MaterialRenderer_SOLID( this); 404 CSoftware2MaterialRenderer_SOLID* smr = new CSoftware2MaterialRenderer_SOLID( this);
405 CSoftware2MaterialRenderer_TRANSPARENT_ADD_COLOR* tmr = new CSoftware2MaterialRenderer_TRANSPARENT_ADD_COLOR( this); 405 CSoftware2MaterialRenderer_TRANSPARENT_ADD_COLOR* tmr = new CSoftware2MaterialRenderer_TRANSPARENT_ADD_COLOR( this);
406 CSoftware2MaterialRenderer_UNSUPPORTED * umr = new CSoftware2MaterialRenderer_UNSUPPORTED ( this ); 406 CSoftware2MaterialRenderer_UNSUPPORTED * umr = new CSoftware2MaterialRenderer_UNSUPPORTED ( this );
407 407
408 //!TODO: addMaterialRenderer depends on pushing order.... 408 //!TODO: addMaterialRenderer depends on pushing order....
409 addMaterialRenderer ( smr ); // EMT_SOLID 409 addMaterialRenderer ( smr ); // EMT_SOLID
410 addMaterialRenderer ( smr ); // EMT_SOLID_2_LAYER, 410 addMaterialRenderer ( smr ); // EMT_SOLID_2_LAYER,
411 addMaterialRenderer ( smr ); // EMT_LIGHTMAP, 411 addMaterialRenderer ( smr ); // EMT_LIGHTMAP,
412 addMaterialRenderer ( tmr ); // EMT_LIGHTMAP_ADD, 412 addMaterialRenderer ( tmr ); // EMT_LIGHTMAP_ADD,
413 addMaterialRenderer ( smr ); // EMT_LIGHTMAP_M2, 413 addMaterialRenderer ( smr ); // EMT_LIGHTMAP_M2,
414 addMaterialRenderer ( smr ); // EMT_LIGHTMAP_M4, 414 addMaterialRenderer ( smr ); // EMT_LIGHTMAP_M4,
415 addMaterialRenderer ( smr ); // EMT_LIGHTMAP_LIGHTING, 415 addMaterialRenderer ( smr ); // EMT_LIGHTMAP_LIGHTING,
416 addMaterialRenderer ( smr ); // EMT_LIGHTMAP_LIGHTING_M2, 416 addMaterialRenderer ( smr ); // EMT_LIGHTMAP_LIGHTING_M2,
417 addMaterialRenderer ( smr ); // EMT_LIGHTMAP_LIGHTING_M4, 417 addMaterialRenderer ( smr ); // EMT_LIGHTMAP_LIGHTING_M4,
418 addMaterialRenderer ( smr ); // EMT_DETAIL_MAP, 418 addMaterialRenderer ( smr ); // EMT_DETAIL_MAP,
419 addMaterialRenderer ( umr ); // EMT_SPHERE_MAP, 419 addMaterialRenderer ( umr ); // EMT_SPHERE_MAP,
420 addMaterialRenderer ( smr ); // EMT_REFLECTION_2_LAYER, 420 addMaterialRenderer ( smr ); // EMT_REFLECTION_2_LAYER,
421 addMaterialRenderer ( tmr ); // EMT_TRANSPARENT_ADD_COLOR, 421 addMaterialRenderer ( tmr ); // EMT_TRANSPARENT_ADD_COLOR,
422 addMaterialRenderer ( tmr ); // EMT_TRANSPARENT_ALPHA_CHANNEL, 422 addMaterialRenderer ( tmr ); // EMT_TRANSPARENT_ALPHA_CHANNEL,
423 addMaterialRenderer ( tmr ); // EMT_TRANSPARENT_ALPHA_CHANNEL_REF, 423 addMaterialRenderer ( tmr ); // EMT_TRANSPARENT_ALPHA_CHANNEL_REF,
424 addMaterialRenderer ( tmr ); // EMT_TRANSPARENT_VERTEX_ALPHA, 424 addMaterialRenderer ( tmr ); // EMT_TRANSPARENT_VERTEX_ALPHA,
425 addMaterialRenderer ( smr ); // EMT_TRANSPARENT_REFLECTION_2_LAYER, 425 addMaterialRenderer ( smr ); // EMT_TRANSPARENT_REFLECTION_2_LAYER,
426 addMaterialRenderer ( smr ); // EMT_NORMAL_MAP_SOLID, 426 addMaterialRenderer ( smr ); // EMT_NORMAL_MAP_SOLID,
427 addMaterialRenderer ( umr ); // EMT_NORMAL_MAP_TRANSPARENT_ADD_COLOR, 427 addMaterialRenderer ( umr ); // EMT_NORMAL_MAP_TRANSPARENT_ADD_COLOR,
428 addMaterialRenderer ( tmr ); // EMT_NORMAL_MAP_TRANSPARENT_VERTEX_ALPHA, 428 addMaterialRenderer ( tmr ); // EMT_NORMAL_MAP_TRANSPARENT_VERTEX_ALPHA,
429 addMaterialRenderer ( smr ); // EMT_PARALLAX_MAP_SOLID, 429 addMaterialRenderer ( smr ); // EMT_PARALLAX_MAP_SOLID,
430 addMaterialRenderer ( tmr ); // EMT_PARALLAX_MAP_TRANSPARENT_ADD_COLOR, 430 addMaterialRenderer ( tmr ); // EMT_PARALLAX_MAP_TRANSPARENT_ADD_COLOR,
431 addMaterialRenderer ( tmr ); // EMT_PARALLAX_MAP_TRANSPARENT_VERTEX_ALPHA, 431 addMaterialRenderer ( tmr ); // EMT_PARALLAX_MAP_TRANSPARENT_VERTEX_ALPHA,
432 addMaterialRenderer ( tmr ); // EMT_ONETEXTURE_BLEND 432 addMaterialRenderer ( tmr ); // EMT_ONETEXTURE_BLEND
433 433
434 smr->drop (); 434 smr->drop ();
435 tmr->drop (); 435 tmr->drop ();
436 umr->drop (); 436 umr->drop ();
437 437
438 // select render target 438 // select render target
439 setRenderTarget(BackBuffer); 439 setRenderTarget(BackBuffer);
440 440
441 //reset Lightspace 441 //reset Lightspace
442 LightSpace.reset (); 442 LightSpace.reset ();
443 443
444 // select the right renderer 444 // select the right renderer
445 setCurrentShader(); 445 setCurrentShader();
446} 446}
447 447
448 448
449//! destructor 449//! destructor
450CBurningVideoDriver::~CBurningVideoDriver() 450CBurningVideoDriver::~CBurningVideoDriver()
451{ 451{
452 // delete Backbuffer 452 // delete Backbuffer
453 if (BackBuffer) 453 if (BackBuffer)
454 BackBuffer->drop(); 454 BackBuffer->drop();
455 455
456 // delete triangle renderers 456 // delete triangle renderers
457 457
458 for (s32 i=0; i<ETR2_COUNT; ++i) 458 for (s32 i=0; i<ETR2_COUNT; ++i)
459 { 459 {
460 if (BurningShader[i]) 460 if (BurningShader[i])
461 BurningShader[i]->drop(); 461 BurningShader[i]->drop();
462 } 462 }
463 463
464 // delete Additional buffer 464 // delete Additional buffer
465 if (StencilBuffer) 465 if (StencilBuffer)
466 StencilBuffer->drop(); 466 StencilBuffer->drop();
467 467
468 if (DepthBuffer) 468 if (DepthBuffer)
469 DepthBuffer->drop(); 469 DepthBuffer->drop();
470 470
471 if (RenderTargetTexture) 471 if (RenderTargetTexture)
472 RenderTargetTexture->drop(); 472 RenderTargetTexture->drop();
473 473
474 if (RenderTargetSurface) 474 if (RenderTargetSurface)
475 RenderTargetSurface->drop(); 475 RenderTargetSurface->drop();
476} 476}
477 477
478 478
479/*! 479/*!
480 selects the right triangle renderer based on the render states. 480 selects the right triangle renderer based on the render states.
481*/ 481*/
482void CBurningVideoDriver::setCurrentShader() 482void CBurningVideoDriver::setCurrentShader()
483{ 483{
484 ITexture *texture0 = Material.org.getTexture(0); 484 ITexture *texture0 = Material.org.getTexture(0);
485 ITexture *texture1 = Material.org.getTexture(1); 485 ITexture *texture1 = Material.org.getTexture(1);
486 486
487 bool zMaterialTest = Material.org.ZBuffer != ECFN_NEVER && 487 bool zMaterialTest = Material.org.ZBuffer != ECFN_NEVER &&
488 Material.org.ZWriteEnable && 488 Material.org.ZWriteEnable &&
489 ( AllowZWriteOnTransparent || !Material.org.isTransparent() ); 489 ( AllowZWriteOnTransparent || !Material.org.isTransparent() );
490 490
491 EBurningFFShader shader = zMaterialTest ? ETR_TEXTURE_GOURAUD : ETR_TEXTURE_GOURAUD_NOZ; 491 EBurningFFShader shader = zMaterialTest ? ETR_TEXTURE_GOURAUD : ETR_TEXTURE_GOURAUD_NOZ;
492 492
493 TransformationFlag[ ETS_TEXTURE_0] &= ~(ETF_TEXGEN_CAMERA_NORMAL|ETF_TEXGEN_CAMERA_REFLECTION); 493 TransformationFlag[ ETS_TEXTURE_0] &= ~(ETF_TEXGEN_CAMERA_NORMAL|ETF_TEXGEN_CAMERA_REFLECTION);
494 LightSpace.Flags &= ~VERTEXTRANSFORM; 494 LightSpace.Flags &= ~VERTEXTRANSFORM;
495 495
496 switch ( Material.org.MaterialType ) 496 switch ( Material.org.MaterialType )
497 { 497 {
498 case EMT_ONETEXTURE_BLEND: 498 case EMT_ONETEXTURE_BLEND:
499 shader = ETR_TEXTURE_BLEND; 499 shader = ETR_TEXTURE_BLEND;
500 break; 500 break;
501 501
502 case EMT_TRANSPARENT_ALPHA_CHANNEL_REF: 502 case EMT_TRANSPARENT_ALPHA_CHANNEL_REF:
503 Material.org.MaterialTypeParam = 0.5f; 503 Material.org.MaterialTypeParam = 0.5f;
504 // fall through 504 // fall through
505 case EMT_TRANSPARENT_ALPHA_CHANNEL: 505 case EMT_TRANSPARENT_ALPHA_CHANNEL:
506 if ( texture0 && texture0->hasAlpha () ) 506 if ( texture0 && texture0->hasAlpha () )
507 { 507 {
508 shader = zMaterialTest ? ETR_TEXTURE_GOURAUD_ALPHA : ETR_TEXTURE_GOURAUD_ALPHA_NOZ; 508 shader = zMaterialTest ? ETR_TEXTURE_GOURAUD_ALPHA : ETR_TEXTURE_GOURAUD_ALPHA_NOZ;
509 break; 509 break;
510 } 510 }
511 // fall through 511 // fall through
512 512
513 case EMT_TRANSPARENT_ADD_COLOR: 513 case EMT_TRANSPARENT_ADD_COLOR:
514 shader = zMaterialTest ? ETR_TEXTURE_GOURAUD_ADD : ETR_TEXTURE_GOURAUD_ADD_NO_Z; 514 shader = zMaterialTest ? ETR_TEXTURE_GOURAUD_ADD : ETR_TEXTURE_GOURAUD_ADD_NO_Z;
515 break; 515 break;
516 516
517 case EMT_TRANSPARENT_VERTEX_ALPHA: 517 case EMT_TRANSPARENT_VERTEX_ALPHA:
518 shader = ETR_TEXTURE_GOURAUD_VERTEX_ALPHA; 518 shader = ETR_TEXTURE_GOURAUD_VERTEX_ALPHA;
519 break; 519 break;
520 520
521 case EMT_LIGHTMAP: 521 case EMT_LIGHTMAP:
522 case EMT_LIGHTMAP_LIGHTING: 522 case EMT_LIGHTMAP_LIGHTING:
523 shader = ETR_TEXTURE_GOURAUD_LIGHTMAP_M1; 523 shader = ETR_TEXTURE_GOURAUD_LIGHTMAP_M1;
524 break; 524 break;
525 525
526 case EMT_LIGHTMAP_M2: 526 case EMT_LIGHTMAP_M2:
527 case EMT_LIGHTMAP_LIGHTING_M2: 527 case EMT_LIGHTMAP_LIGHTING_M2:
528 shader = ETR_TEXTURE_GOURAUD_LIGHTMAP_M2; 528 shader = ETR_TEXTURE_GOURAUD_LIGHTMAP_M2;
529 break; 529 break;
530 530
531 case EMT_LIGHTMAP_LIGHTING_M4: 531 case EMT_LIGHTMAP_LIGHTING_M4:
532 if ( texture1 ) 532 if ( texture1 )
533 shader = ETR_TEXTURE_GOURAUD_LIGHTMAP_M4; 533 shader = ETR_TEXTURE_GOURAUD_LIGHTMAP_M4;
534 break; 534 break;
535 case EMT_LIGHTMAP_M4: 535 case EMT_LIGHTMAP_M4:
536 if ( texture1 ) 536 if ( texture1 )
537 shader = ETR_TEXTURE_LIGHTMAP_M4; 537 shader = ETR_TEXTURE_LIGHTMAP_M4;
538 break; 538 break;
539 539
540 case EMT_LIGHTMAP_ADD: 540 case EMT_LIGHTMAP_ADD:
541 if ( texture1 ) 541 if ( texture1 )
542 shader = ETR_TEXTURE_GOURAUD_LIGHTMAP_ADD; 542 shader = ETR_TEXTURE_GOURAUD_LIGHTMAP_ADD;
543 break; 543 break;
544 544
545 case EMT_DETAIL_MAP: 545 case EMT_DETAIL_MAP:
546 shader = ETR_TEXTURE_GOURAUD_DETAIL_MAP; 546 shader = ETR_TEXTURE_GOURAUD_DETAIL_MAP;
547 break; 547 break;
548 548
549 case EMT_SPHERE_MAP: 549 case EMT_SPHERE_MAP:
550 TransformationFlag[ ETS_TEXTURE_0] |= ETF_TEXGEN_CAMERA_REFLECTION; // ETF_TEXGEN_CAMERA_NORMAL; 550 TransformationFlag[ ETS_TEXTURE_0] |= ETF_TEXGEN_CAMERA_REFLECTION; // ETF_TEXGEN_CAMERA_NORMAL;
551 LightSpace.Flags |= VERTEXTRANSFORM; 551 LightSpace.Flags |= VERTEXTRANSFORM;
552 break; 552 break;
553 case EMT_REFLECTION_2_LAYER: 553 case EMT_REFLECTION_2_LAYER:
554 shader = ETR_TEXTURE_GOURAUD_LIGHTMAP_M1; 554 shader = ETR_TEXTURE_GOURAUD_LIGHTMAP_M1;
555 TransformationFlag[ ETS_TEXTURE_1] |= ETF_TEXGEN_CAMERA_REFLECTION; 555 TransformationFlag[ ETS_TEXTURE_1] |= ETF_TEXGEN_CAMERA_REFLECTION;
556 LightSpace.Flags |= VERTEXTRANSFORM; 556 LightSpace.Flags |= VERTEXTRANSFORM;
557 break; 557 break;
558 558
559 case EMT_NORMAL_MAP_TRANSPARENT_VERTEX_ALPHA: 559 case EMT_NORMAL_MAP_TRANSPARENT_VERTEX_ALPHA:
560 case EMT_NORMAL_MAP_SOLID: 560 case EMT_NORMAL_MAP_SOLID:
561 case EMT_PARALLAX_MAP_SOLID: 561 case EMT_PARALLAX_MAP_SOLID:
562 case EMT_PARALLAX_MAP_TRANSPARENT_VERTEX_ALPHA: 562 case EMT_PARALLAX_MAP_TRANSPARENT_VERTEX_ALPHA:
563 shader = ETR_NORMAL_MAP_SOLID; 563 shader = ETR_NORMAL_MAP_SOLID;
564 LightSpace.Flags |= VERTEXTRANSFORM; 564 LightSpace.Flags |= VERTEXTRANSFORM;
565 break; 565 break;
566 566
567 default: 567 default:
568 break; 568 break;
569 569
570 } 570 }
571 571
572 if ( !texture0 ) 572 if ( !texture0 )
573 { 573 {
574 shader = ETR_GOURAUD; 574 shader = ETR_GOURAUD;
575 } 575 }
576 576
577 if ( Material.org.Wireframe ) 577 if ( Material.org.Wireframe )
578 { 578 {
579 shader = ETR_TEXTURE_GOURAUD_WIRE; 579 shader = ETR_TEXTURE_GOURAUD_WIRE;
580 } 580 }
581 581
582 //shader = ETR_REFERENCE; 582 //shader = ETR_REFERENCE;
583 583
584 // switchToTriangleRenderer 584 // switchToTriangleRenderer
585 CurrentShader = BurningShader[shader]; 585 CurrentShader = BurningShader[shader];
586 if ( CurrentShader ) 586 if ( CurrentShader )
587 { 587 {
588 CurrentShader->setZCompareFunc ( Material.org.ZBuffer ); 588 CurrentShader->setZCompareFunc ( Material.org.ZBuffer );
589 CurrentShader->setRenderTarget(RenderTargetSurface, ViewPort); 589 CurrentShader->setRenderTarget(RenderTargetSurface, ViewPort);
590 CurrentShader->setMaterial ( Material ); 590 CurrentShader->setMaterial ( Material );
591 591
592 switch ( shader ) 592 switch ( shader )
593 { 593 {
594 case ETR_TEXTURE_GOURAUD_ALPHA: 594 case ETR_TEXTURE_GOURAUD_ALPHA:
595 case ETR_TEXTURE_GOURAUD_ALPHA_NOZ: 595 case ETR_TEXTURE_GOURAUD_ALPHA_NOZ:
596 case ETR_TEXTURE_BLEND: 596 case ETR_TEXTURE_BLEND:
597 CurrentShader->setParam ( 0, Material.org.MaterialTypeParam ); 597 CurrentShader->setParam ( 0, Material.org.MaterialTypeParam );
598 break; 598 break;
599 default: 599 default:
600 break; 600 break;
601 } 601 }
602 } 602 }
603 603
604} 604}
605 605
606 606
607 607
608//! queries the features of the driver, returns true if feature is available 608//! queries the features of the driver, returns true if feature is available
609bool CBurningVideoDriver::queryFeature(E_VIDEO_DRIVER_FEATURE feature) const 609bool CBurningVideoDriver::queryFeature(E_VIDEO_DRIVER_FEATURE feature) const
610{ 610{
611 if (!FeatureEnabled[feature]) 611 if (!FeatureEnabled[feature])
612 return false; 612 return false;
613 613
614 switch (feature) 614 switch (feature)
615 { 615 {
616#ifdef SOFTWARE_DRIVER_2_BILINEAR 616#ifdef SOFTWARE_DRIVER_2_BILINEAR
617 case EVDF_BILINEAR_FILTER: 617 case EVDF_BILINEAR_FILTER:
618 return true; 618 return true;
619#endif 619#endif
620#ifdef SOFTWARE_DRIVER_2_MIPMAPPING 620#ifdef SOFTWARE_DRIVER_2_MIPMAPPING
621 case EVDF_MIP_MAP: 621 case EVDF_MIP_MAP:
622 return true; 622 return true;
623#endif 623#endif
624 case EVDF_STENCIL_BUFFER: 624 case EVDF_STENCIL_BUFFER:
625 case EVDF_RENDER_TO_TARGET: 625 case EVDF_RENDER_TO_TARGET:
626 case EVDF_MULTITEXTURE: 626 case EVDF_MULTITEXTURE:
627 case EVDF_HARDWARE_TL: 627 case EVDF_HARDWARE_TL:
628 case EVDF_TEXTURE_NSQUARE: 628 case EVDF_TEXTURE_NSQUARE:
629 return true; 629 return true;
630 630
631 default: 631 default:
632 return false; 632 return false;
633 } 633 }
634} 634}
635 635
636 636
637 637
638//! sets transformation 638//! sets transformation
639void CBurningVideoDriver::setTransform(E_TRANSFORMATION_STATE state, const core::matrix4& mat) 639void CBurningVideoDriver::setTransform(E_TRANSFORMATION_STATE state, const core::matrix4& mat)
640{ 640{
641 Transformation[state] = mat; 641 Transformation[state] = mat;
642 core::setbit_cond ( TransformationFlag[state], mat.isIdentity(), ETF_IDENTITY ); 642 core::setbit_cond ( TransformationFlag[state], mat.isIdentity(), ETF_IDENTITY );
643 643
644 switch ( state ) 644 switch ( state )
645 { 645 {
646 case ETS_VIEW: 646 case ETS_VIEW:
647 Transformation[ETS_VIEW_PROJECTION].setbyproduct_nocheck ( 647 Transformation[ETS_VIEW_PROJECTION].setbyproduct_nocheck (
648 Transformation[ETS_PROJECTION], 648 Transformation[ETS_PROJECTION],
649 Transformation[ETS_VIEW] 649 Transformation[ETS_VIEW]
650 ); 650 );
651 getCameraPosWorldSpace (); 651 getCameraPosWorldSpace ();
652 break; 652 break;
653 653
654 case ETS_WORLD: 654 case ETS_WORLD:
655 if ( TransformationFlag[state] & ETF_IDENTITY ) 655 if ( TransformationFlag[state] & ETF_IDENTITY )
656 { 656 {
657 Transformation[ETS_WORLD_INVERSE] = Transformation[ETS_WORLD]; 657 Transformation[ETS_WORLD_INVERSE] = Transformation[ETS_WORLD];
658 TransformationFlag[ETS_WORLD_INVERSE] |= ETF_IDENTITY; 658 TransformationFlag[ETS_WORLD_INVERSE] |= ETF_IDENTITY;
659 Transformation[ETS_CURRENT] = Transformation[ETS_VIEW_PROJECTION]; 659 Transformation[ETS_CURRENT] = Transformation[ETS_VIEW_PROJECTION];
660 } 660 }
661 else 661 else
662 { 662 {
663 //Transformation[ETS_WORLD].getInversePrimitive ( Transformation[ETS_WORLD_INVERSE] ); 663 //Transformation[ETS_WORLD].getInversePrimitive ( Transformation[ETS_WORLD_INVERSE] );
664 Transformation[ETS_CURRENT].setbyproduct_nocheck ( 664 Transformation[ETS_CURRENT].setbyproduct_nocheck (
665 Transformation[ETS_VIEW_PROJECTION], 665 Transformation[ETS_VIEW_PROJECTION],
666 Transformation[ETS_WORLD] 666 Transformation[ETS_WORLD]
667 ); 667 );
668 } 668 }
669 TransformationFlag[ETS_CURRENT] = 0; 669 TransformationFlag[ETS_CURRENT] = 0;
670 //getLightPosObjectSpace (); 670 //getLightPosObjectSpace ();
671 break; 671 break;
672 case ETS_TEXTURE_0: 672 case ETS_TEXTURE_0:
673 case ETS_TEXTURE_1: 673 case ETS_TEXTURE_1:
674 case ETS_TEXTURE_2: 674 case ETS_TEXTURE_2:
675 case ETS_TEXTURE_3: 675 case ETS_TEXTURE_3:
676 if ( 0 == (TransformationFlag[state] & ETF_IDENTITY ) ) 676 if ( 0 == (TransformationFlag[state] & ETF_IDENTITY ) )
677 LightSpace.Flags |= VERTEXTRANSFORM; 677 LightSpace.Flags |= VERTEXTRANSFORM;
678 default: 678 default:
679 break; 679 break;
680 } 680 }
681} 681}
682 682
683 683
684//! clears the zbuffer 684//! clears the zbuffer
685bool CBurningVideoDriver::beginScene(bool backBuffer, bool zBuffer, 685bool CBurningVideoDriver::beginScene(bool backBuffer, bool zBuffer,
686 SColor color, const SExposedVideoData& videoData, 686 SColor color, const SExposedVideoData& videoData,
687 core::rect<s32>* sourceRect) 687 core::rect<s32>* sourceRect)
688{ 688{
689 CNullDriver::beginScene(backBuffer, zBuffer, color, videoData, sourceRect); 689 CNullDriver::beginScene(backBuffer, zBuffer, color, videoData, sourceRect);
690 WindowId = videoData.D3D9.HWnd; 690 WindowId = videoData.D3D9.HWnd;
691 SceneSourceRect = sourceRect; 691 SceneSourceRect = sourceRect;
692 692
693 if (backBuffer && BackBuffer) 693 if (backBuffer && BackBuffer)
694 BackBuffer->fill(color); 694 BackBuffer->fill(color);
695 695
696 if (zBuffer && DepthBuffer) 696 if (zBuffer && DepthBuffer)
697 DepthBuffer->clear(); 697 DepthBuffer->clear();
698 698
699 memset ( TransformationFlag, 0, sizeof ( TransformationFlag ) ); 699 memset ( TransformationFlag, 0, sizeof ( TransformationFlag ) );
700 return true; 700 return true;
701} 701}
702 702
703 703
704//! presents the rendered scene on the screen, returns false if failed 704//! presents the rendered scene on the screen, returns false if failed
705bool CBurningVideoDriver::endScene() 705bool CBurningVideoDriver::endScene()
706{ 706{
707 CNullDriver::endScene(); 707 CNullDriver::endScene();
708 708
709 return Presenter->present(BackBuffer, WindowId, SceneSourceRect); 709 return Presenter->present(BackBuffer, WindowId, SceneSourceRect);
710} 710}
711 711
712 712
713//! sets a render target 713//! sets a render target
714bool CBurningVideoDriver::setRenderTarget(video::ITexture* texture, bool clearBackBuffer, 714bool CBurningVideoDriver::setRenderTarget(video::ITexture* texture, bool clearBackBuffer,
715 bool clearZBuffer, SColor color) 715 bool clearZBuffer, SColor color)
716{ 716{
717 if (texture && texture->getDriverType() != EDT_BURNINGSVIDEO) 717 if (texture && texture->getDriverType() != EDT_BURNINGSVIDEO)
718 { 718 {
719 os::Printer::log("Fatal Error: Tried to set a texture not owned by this driver.", ELL_ERROR); 719 os::Printer::log("Fatal Error: Tried to set a texture not owned by this driver.", ELL_ERROR);
720 return false; 720 return false;
721 } 721 }
722 722
723 if (RenderTargetTexture) 723 if (RenderTargetTexture)
724 RenderTargetTexture->drop(); 724 RenderTargetTexture->drop();
725 725
726 RenderTargetTexture = texture; 726 RenderTargetTexture = texture;
727 727
728 if (RenderTargetTexture) 728 if (RenderTargetTexture)
729 { 729 {
730 RenderTargetTexture->grab(); 730 RenderTargetTexture->grab();
731 setRenderTarget(((CSoftwareTexture2*)RenderTargetTexture)->getTexture()); 731 setRenderTarget(((CSoftwareTexture2*)RenderTargetTexture)->getTexture());
732 } 732 }
733 else 733 else
734 { 734 {
735 setRenderTarget(BackBuffer); 735 setRenderTarget(BackBuffer);
736 } 736 }
737 737
738 if (RenderTargetSurface && (clearBackBuffer || clearZBuffer)) 738 if (RenderTargetSurface && (clearBackBuffer || clearZBuffer))
739 { 739 {
740 if (clearZBuffer) 740 if (clearZBuffer)
741 DepthBuffer->clear(); 741 DepthBuffer->clear();
742 742
743 if (clearBackBuffer) 743 if (clearBackBuffer)
744 RenderTargetSurface->fill( color ); 744 RenderTargetSurface->fill( color );
745 } 745 }
746 746
747 return true; 747 return true;
748} 748}
749 749
750 750
751//! sets a render target 751//! sets a render target
752void CBurningVideoDriver::setRenderTarget(video::CImage* image) 752void CBurningVideoDriver::setRenderTarget(video::CImage* image)
753{ 753{
754 if (RenderTargetSurface) 754 if (RenderTargetSurface)
755 RenderTargetSurface->drop(); 755 RenderTargetSurface->drop();
756 756
757 RenderTargetSurface = image; 757 RenderTargetSurface = image;
758 RenderTargetSize.Width = 0; 758 RenderTargetSize.Width = 0;
759 RenderTargetSize.Height = 0; 759 RenderTargetSize.Height = 0;
760 760
761 if (RenderTargetSurface) 761 if (RenderTargetSurface)
762 { 762 {
763 RenderTargetSurface->grab(); 763 RenderTargetSurface->grab();
764 RenderTargetSize = RenderTargetSurface->getDimension(); 764 RenderTargetSize = RenderTargetSurface->getDimension();
765 } 765 }
766 766
767 setViewPort(core::rect<s32>(0,0,RenderTargetSize.Width,RenderTargetSize.Height)); 767 setViewPort(core::rect<s32>(0,0,RenderTargetSize.Width,RenderTargetSize.Height));
768 768
769 if (DepthBuffer) 769 if (DepthBuffer)
770 DepthBuffer->setSize(RenderTargetSize); 770 DepthBuffer->setSize(RenderTargetSize);
771 771
772 if (StencilBuffer) 772 if (StencilBuffer)
773 StencilBuffer->setSize(RenderTargetSize); 773 StencilBuffer->setSize(RenderTargetSize);
774} 774}
775 775
776 776
777 777
778//! sets a viewport 778//! sets a viewport
779void CBurningVideoDriver::setViewPort(const core::rect<s32>& area) 779void CBurningVideoDriver::setViewPort(const core::rect<s32>& area)
780{ 780{
781 ViewPort = area; 781 ViewPort = area;
782 782
783 core::rect<s32> rendert(0,0,RenderTargetSize.Width,RenderTargetSize.Height); 783 core::rect<s32> rendert(0,0,RenderTargetSize.Width,RenderTargetSize.Height);
784 ViewPort.clipAgainst(rendert); 784 ViewPort.clipAgainst(rendert);
785 785
786 Transformation [ ETS_CLIPSCALE ].buildNDCToDCMatrix ( ViewPort, 1 ); 786 Transformation [ ETS_CLIPSCALE ].buildNDCToDCMatrix ( ViewPort, 1 );
787 787
788 if (CurrentShader) 788 if (CurrentShader)
789 CurrentShader->setRenderTarget(RenderTargetSurface, ViewPort); 789 CurrentShader->setRenderTarget(RenderTargetSurface, ViewPort);
790} 790}
791 791
792/* 792/*
793 generic plane clipping in homogenous coordinates 793 generic plane clipping in homogenous coordinates
794 special case ndc frustum <-w,w>,<-w,w>,<-w,w> 794 special case ndc frustum <-w,w>,<-w,w>,<-w,w>
795 can be rewritten with compares e.q near plane, a.z < -a.w and b.z < -b.w 795 can be rewritten with compares e.q near plane, a.z < -a.w and b.z < -b.w
796*/ 796*/
797 797
798const sVec4 CBurningVideoDriver::NDCPlane[6] = 798const sVec4 CBurningVideoDriver::NDCPlane[6] =
799{ 799{
800 sVec4( 0.f, 0.f, -1.f, -1.f ), // near 800 sVec4( 0.f, 0.f, -1.f, -1.f ), // near
801 sVec4( 0.f, 0.f, 1.f, -1.f ), // far 801 sVec4( 0.f, 0.f, 1.f, -1.f ), // far
802 sVec4( 1.f, 0.f, 0.f, -1.f ), // left 802 sVec4( 1.f, 0.f, 0.f, -1.f ), // left
803 sVec4( -1.f, 0.f, 0.f, -1.f ), // right 803 sVec4( -1.f, 0.f, 0.f, -1.f ), // right
804 sVec4( 0.f, 1.f, 0.f, -1.f ), // bottom 804 sVec4( 0.f, 1.f, 0.f, -1.f ), // bottom
805 sVec4( 0.f, -1.f, 0.f, -1.f ) // top 805 sVec4( 0.f, -1.f, 0.f, -1.f ) // top
806}; 806};
807 807
808 808
809 809
810/* 810/*
811 test a vertex if it's inside the standard frustum 811 test a vertex if it's inside the standard frustum
812 812
813 this is the generic one.. 813 this is the generic one..
814 814
815 f32 dotPlane; 815 f32 dotPlane;
816 for ( u32 i = 0; i!= 6; ++i ) 816 for ( u32 i = 0; i!= 6; ++i )
817 { 817 {
818 dotPlane = v->Pos.dotProduct ( NDCPlane[i] ); 818 dotPlane = v->Pos.dotProduct ( NDCPlane[i] );
819 core::setbit_cond( flag, dotPlane <= 0.f, 1 << i ); 819 core::setbit_cond( flag, dotPlane <= 0.f, 1 << i );
820 } 820 }
821 821
822 // this is the base for ndc frustum <-w,w>,<-w,w>,<-w,w> 822 // this is the base for ndc frustum <-w,w>,<-w,w>,<-w,w>
823 core::setbit_cond( flag, ( v->Pos.z - v->Pos.w ) <= 0.f, 1 ); 823 core::setbit_cond( flag, ( v->Pos.z - v->Pos.w ) <= 0.f, 1 );
824 core::setbit_cond( flag, (-v->Pos.z - v->Pos.w ) <= 0.f, 2 ); 824 core::setbit_cond( flag, (-v->Pos.z - v->Pos.w ) <= 0.f, 2 );
825 core::setbit_cond( flag, ( v->Pos.x - v->Pos.w ) <= 0.f, 4 ); 825 core::setbit_cond( flag, ( v->Pos.x - v->Pos.w ) <= 0.f, 4 );
826 core::setbit_cond( flag, (-v->Pos.x - v->Pos.w ) <= 0.f, 8 ); 826 core::setbit_cond( flag, (-v->Pos.x - v->Pos.w ) <= 0.f, 8 );
827 core::setbit_cond( flag, ( v->Pos.y - v->Pos.w ) <= 0.f, 16 ); 827 core::setbit_cond( flag, ( v->Pos.y - v->Pos.w ) <= 0.f, 16 );
828 core::setbit_cond( flag, (-v->Pos.y - v->Pos.w ) <= 0.f, 32 ); 828 core::setbit_cond( flag, (-v->Pos.y - v->Pos.w ) <= 0.f, 32 );
829 829
830*/ 830*/
831#ifdef IRRLICHT_FAST_MATH 831#ifdef IRRLICHT_FAST_MATH
832 832
833REALINLINE u32 CBurningVideoDriver::clipToFrustumTest ( const s4DVertex * v ) const 833REALINLINE u32 CBurningVideoDriver::clipToFrustumTest ( const s4DVertex * v ) const
834{ 834{
835 f32 test[6]; 835 f32 test[6];
836 u32 flag; 836 u32 flag;
837 const f32 w = - v->Pos.w; 837 const f32 w = - v->Pos.w;
838 838
839 // a conditional move is needed....FCOMI ( but we don't have it ) 839 // a conditional move is needed....FCOMI ( but we don't have it )
840 // so let the fpu calculate and write it back. 840 // so let the fpu calculate and write it back.
841 // cpu makes the compare, interleaving 841 // cpu makes the compare, interleaving
842 842
843 test[0] = v->Pos.z + w; 843 test[0] = v->Pos.z + w;
844 test[1] = -v->Pos.z + w; 844 test[1] = -v->Pos.z + w;
845 test[2] = v->Pos.x + w; 845 test[2] = v->Pos.x + w;
846 test[3] = -v->Pos.x + w; 846 test[3] = -v->Pos.x + w;
847 test[4] = v->Pos.y + w; 847 test[4] = v->Pos.y + w;
848 test[5] = -v->Pos.y + w; 848 test[5] = -v->Pos.y + w;
849 849
850 flag = (IR ( test[0] ) ) >> 31; 850 flag = (IR ( test[0] ) ) >> 31;
851 flag |= (IR ( test[1] ) & 0x80000000 ) >> 30; 851 flag |= (IR ( test[1] ) & 0x80000000 ) >> 30;
852 flag |= (IR ( test[2] ) & 0x80000000 ) >> 29; 852 flag |= (IR ( test[2] ) & 0x80000000 ) >> 29;
853 flag |= (IR ( test[3] ) & 0x80000000 ) >> 28; 853 flag |= (IR ( test[3] ) & 0x80000000 ) >> 28;
854 flag |= (IR ( test[4] ) & 0x80000000 ) >> 27; 854 flag |= (IR ( test[4] ) & 0x80000000 ) >> 27;
855 flag |= (IR ( test[5] ) & 0x80000000 ) >> 26; 855 flag |= (IR ( test[5] ) & 0x80000000 ) >> 26;
856 856
857/* 857/*
858 flag = F32_LOWER_EQUAL_0 ( test[0] ); 858 flag = F32_LOWER_EQUAL_0 ( test[0] );
859 flag |= F32_LOWER_EQUAL_0 ( test[1] ) << 1; 859 flag |= F32_LOWER_EQUAL_0 ( test[1] ) << 1;
860 flag |= F32_LOWER_EQUAL_0 ( test[2] ) << 2; 860 flag |= F32_LOWER_EQUAL_0 ( test[2] ) << 2;
861 flag |= F32_LOWER_EQUAL_0 ( test[3] ) << 3; 861 flag |= F32_LOWER_EQUAL_0 ( test[3] ) << 3;
862 flag |= F32_LOWER_EQUAL_0 ( test[4] ) << 4; 862 flag |= F32_LOWER_EQUAL_0 ( test[4] ) << 4;
863 flag |= F32_LOWER_EQUAL_0 ( test[5] ) << 5; 863 flag |= F32_LOWER_EQUAL_0 ( test[5] ) << 5;
864*/ 864*/
865 return flag; 865 return flag;
866} 866}
867 867
868#else 868#else
869 869
870 870
871REALINLINE u32 CBurningVideoDriver::clipToFrustumTest ( const s4DVertex * v ) const 871REALINLINE u32 CBurningVideoDriver::clipToFrustumTest ( const s4DVertex * v ) const
872{ 872{
873 u32 flag = 0; 873 u32 flag = 0;
874 874
875 if ( v->Pos.z <= v->Pos.w ) flag |= 1; 875 if ( v->Pos.z <= v->Pos.w ) flag |= 1;
876 if (-v->Pos.z <= v->Pos.w ) flag |= 2; 876 if (-v->Pos.z <= v->Pos.w ) flag |= 2;
877 877
878 if ( v->Pos.x <= v->Pos.w ) flag |= 4; 878 if ( v->Pos.x <= v->Pos.w ) flag |= 4;
879 if (-v->Pos.x <= v->Pos.w ) flag |= 8; 879 if (-v->Pos.x <= v->Pos.w ) flag |= 8;
880 880
881 if ( v->Pos.y <= v->Pos.w ) flag |= 16; 881 if ( v->Pos.y <= v->Pos.w ) flag |= 16;
882 if (-v->Pos.y <= v->Pos.w ) flag |= 32; 882 if (-v->Pos.y <= v->Pos.w ) flag |= 32;
883 883
884/* 884/*
885 for ( u32 i = 0; i!= 6; ++i ) 885 for ( u32 i = 0; i!= 6; ++i )
886 { 886 {
887 core::setbit_cond( flag, v->Pos.dotProduct ( NDCPlane[i] ) <= 0.f, 1 << i ); 887 core::setbit_cond( flag, v->Pos.dotProduct ( NDCPlane[i] ) <= 0.f, 1 << i );
888 } 888 }
889*/ 889*/
890 return flag; 890 return flag;
891} 891}
892 892
893#endif // _MSC_VER 893#endif // _MSC_VER
894 894
895u32 CBurningVideoDriver::clipToHyperPlane ( s4DVertex * dest, const s4DVertex * source, u32 inCount, const sVec4 &plane ) 895u32 CBurningVideoDriver::clipToHyperPlane ( s4DVertex * dest, const s4DVertex * source, u32 inCount, const sVec4 &plane )
896{ 896{
897 u32 outCount = 0; 897 u32 outCount = 0;
898 s4DVertex * out = dest; 898 s4DVertex * out = dest;
899 899
900 const s4DVertex * a; 900 const s4DVertex * a;
901 const s4DVertex * b = source; 901 const s4DVertex * b = source;
902 902
903 f32 bDotPlane; 903 f32 bDotPlane;
904 904
905 bDotPlane = b->Pos.dotProduct ( plane ); 905 bDotPlane = b->Pos.dotProduct ( plane );
906 906
907 for( u32 i = 1; i < inCount + 1; ++i) 907 for( u32 i = 1; i < inCount + 1; ++i)
908 { 908 {
909 const s32 condition = i - inCount; 909 const s32 condition = i - inCount;
910 const s32 index = (( ( condition >> 31 ) & ( i ^ condition ) ) ^ condition ) << 1; 910 const s32 index = (( ( condition >> 31 ) & ( i ^ condition ) ) ^ condition ) << 1;
911 911
912 a = &source[ index ]; 912 a = &source[ index ];
913 913
914 // current point inside 914 // current point inside
915 if ( a->Pos.dotProduct ( plane ) <= 0.f ) 915 if ( a->Pos.dotProduct ( plane ) <= 0.f )
916 { 916 {
917 // last point outside 917 // last point outside
918 if ( F32_GREATER_0 ( bDotPlane ) ) 918 if ( F32_GREATER_0 ( bDotPlane ) )
919 { 919 {
920 // intersect line segment with plane 920 // intersect line segment with plane
921 out->interpolate ( *b, *a, bDotPlane / (b->Pos - a->Pos).dotProduct ( plane ) ); 921 out->interpolate ( *b, *a, bDotPlane / (b->Pos - a->Pos).dotProduct ( plane ) );
922 out += 2; 922 out += 2;
923 outCount += 1; 923 outCount += 1;
924 } 924 }
925 925
926 // copy current to out 926 // copy current to out
927 //*out = *a; 927 //*out = *a;
928 irr::memcpy32_small ( out, a, SIZEOF_SVERTEX * 2 ); 928 irr::memcpy32_small ( out, a, SIZEOF_SVERTEX * 2 );
929 b = out; 929 b = out;
930 930
931 out += 2; 931 out += 2;
932 outCount += 1; 932 outCount += 1;
933 } 933 }
934 else 934 else
935 { 935 {
936 // current point outside 936 // current point outside
937 937
938 if ( F32_LOWER_EQUAL_0 ( bDotPlane ) ) 938 if ( F32_LOWER_EQUAL_0 ( bDotPlane ) )
939 { 939 {
940 // previous was inside 940 // previous was inside
941 // intersect line segment with plane 941 // intersect line segment with plane
942 out->interpolate ( *b, *a, bDotPlane / (b->Pos - a->Pos).dotProduct ( plane ) ); 942 out->interpolate ( *b, *a, bDotPlane / (b->Pos - a->Pos).dotProduct ( plane ) );
943 out += 2; 943 out += 2;
944 outCount += 1; 944 outCount += 1;
945 } 945 }
946 // pointer 946 // pointer
947 b = a; 947 b = a;
948 } 948 }
949 949
950 bDotPlane = b->Pos.dotProduct ( plane ); 950 bDotPlane = b->Pos.dotProduct ( plane );
951 951
952 } 952 }
953 953
954 return outCount; 954 return outCount;
955} 955}
956 956
957 957
958u32 CBurningVideoDriver::clipToFrustum ( s4DVertex *v0, s4DVertex * v1, const u32 vIn ) 958u32 CBurningVideoDriver::clipToFrustum ( s4DVertex *v0, s4DVertex * v1, const u32 vIn )
959{ 959{
960 u32 vOut = vIn; 960 u32 vOut = vIn;
961 961
962 vOut = clipToHyperPlane ( v1, v0, vOut, NDCPlane[0] ); if ( vOut < vIn ) return vOut; 962 vOut = clipToHyperPlane ( v1, v0, vOut, NDCPlane[0] ); if ( vOut < vIn ) return vOut;
963 vOut = clipToHyperPlane ( v0, v1, vOut, NDCPlane[1] ); if ( vOut < vIn ) return vOut; 963 vOut = clipToHyperPlane ( v0, v1, vOut, NDCPlane[1] ); if ( vOut < vIn ) return vOut;
964 vOut = clipToHyperPlane ( v1, v0, vOut, NDCPlane[2] ); if ( vOut < vIn ) return vOut; 964 vOut = clipToHyperPlane ( v1, v0, vOut, NDCPlane[2] ); if ( vOut < vIn ) return vOut;
965 vOut = clipToHyperPlane ( v0, v1, vOut, NDCPlane[3] ); if ( vOut < vIn ) return vOut; 965 vOut = clipToHyperPlane ( v0, v1, vOut, NDCPlane[3] ); if ( vOut < vIn ) return vOut;
966 vOut = clipToHyperPlane ( v1, v0, vOut, NDCPlane[4] ); if ( vOut < vIn ) return vOut; 966 vOut = clipToHyperPlane ( v1, v0, vOut, NDCPlane[4] ); if ( vOut < vIn ) return vOut;
967 vOut = clipToHyperPlane ( v0, v1, vOut, NDCPlane[5] ); 967 vOut = clipToHyperPlane ( v0, v1, vOut, NDCPlane[5] );
968 return vOut; 968 return vOut;
969} 969}
970 970
971/*! 971/*!
972 Part I: 972 Part I:
973 apply Clip Scale matrix 973 apply Clip Scale matrix
974 From Normalized Device Coordiante ( NDC ) Space to Device Coordinate Space ( DC ) 974 From Normalized Device Coordiante ( NDC ) Space to Device Coordinate Space ( DC )
975 975
976 Part II: 976 Part II:
977 Project homogeneous vector 977 Project homogeneous vector
978 homogeneous to non-homogenous coordinates ( dividebyW ) 978 homogeneous to non-homogenous coordinates ( dividebyW )
979 979
980 Incoming: ( xw, yw, zw, w, u, v, 1, R, G, B, A ) 980 Incoming: ( xw, yw, zw, w, u, v, 1, R, G, B, A )
981 Outgoing: ( xw/w, yw/w, zw/w, w/w, u/w, v/w, 1/w, R/w, G/w, B/w, A/w ) 981 Outgoing: ( xw/w, yw/w, zw/w, w/w, u/w, v/w, 1/w, R/w, G/w, B/w, A/w )
982 982
983 983
984 replace w/w by 1/w 984 replace w/w by 1/w
985*/ 985*/
986inline void CBurningVideoDriver::ndc_2_dc_and_project ( s4DVertex *dest,s4DVertex *source, u32 vIn ) const 986inline void CBurningVideoDriver::ndc_2_dc_and_project ( s4DVertex *dest,s4DVertex *source, u32 vIn ) const
987{ 987{
988 u32 g; 988 u32 g;
989 989
990 for ( g = 0; g != vIn; g += 2 ) 990 for ( g = 0; g != vIn; g += 2 )
991 { 991 {
992 if ( (dest[g].flag & VERTEX4D_PROJECTED ) == VERTEX4D_PROJECTED ) 992 if ( (dest[g].flag & VERTEX4D_PROJECTED ) == VERTEX4D_PROJECTED )
993 continue; 993 continue;
994 994
995 dest[g].flag = source[g].flag | VERTEX4D_PROJECTED; 995 dest[g].flag = source[g].flag | VERTEX4D_PROJECTED;
996 996
997 const f32 w = source[g].Pos.w; 997 const f32 w = source[g].Pos.w;
998 const f32 iw = core::reciprocal ( w ); 998 const f32 iw = core::reciprocal ( w );
999 999
1000 // to device coordinates 1000 // to device coordinates
1001 dest[g].Pos.x = iw * ( source[g].Pos.x * Transformation [ ETS_CLIPSCALE ][ 0] + w * Transformation [ ETS_CLIPSCALE ][12] ); 1001 dest[g].Pos.x = iw * ( source[g].Pos.x * Transformation [ ETS_CLIPSCALE ][ 0] + w * Transformation [ ETS_CLIPSCALE ][12] );
1002 dest[g].Pos.y = iw * ( source[g].Pos.y * Transformation [ ETS_CLIPSCALE ][ 5] + w * Transformation [ ETS_CLIPSCALE ][13] ); 1002 dest[g].Pos.y = iw * ( source[g].Pos.y * Transformation [ ETS_CLIPSCALE ][ 5] + w * Transformation [ ETS_CLIPSCALE ][13] );
1003 1003
1004#ifndef SOFTWARE_DRIVER_2_USE_WBUFFER 1004#ifndef SOFTWARE_DRIVER_2_USE_WBUFFER
1005 dest[g].Pos.z = iw * source[g].Pos.z; 1005 dest[g].Pos.z = iw * source[g].Pos.z;
1006#endif 1006#endif
1007 1007
1008 #ifdef SOFTWARE_DRIVER_2_USE_VERTEX_COLOR 1008 #ifdef SOFTWARE_DRIVER_2_USE_VERTEX_COLOR
1009 #ifdef SOFTWARE_DRIVER_2_PERSPECTIVE_CORRECT 1009 #ifdef SOFTWARE_DRIVER_2_PERSPECTIVE_CORRECT
1010 dest[g].Color[0] = source[g].Color[0] * iw; 1010 dest[g].Color[0] = source[g].Color[0] * iw;
1011 #else 1011 #else
1012 dest[g].Color[0] = source[g].Color[0]; 1012 dest[g].Color[0] = source[g].Color[0];
1013 #endif 1013 #endif
1014 1014
1015 #endif 1015 #endif
1016 dest[g].LightTangent[0] = source[g].LightTangent[0] * iw; 1016 dest[g].LightTangent[0] = source[g].LightTangent[0] * iw;
1017 dest[g].Pos.w = iw; 1017 dest[g].Pos.w = iw;
1018 } 1018 }
1019} 1019}
1020 1020
1021 1021
1022inline void CBurningVideoDriver::ndc_2_dc_and_project2 ( const s4DVertex **v, const u32 size ) const 1022inline void CBurningVideoDriver::ndc_2_dc_and_project2 ( const s4DVertex **v, const u32 size ) const
1023{ 1023{
1024 u32 g; 1024 u32 g;
1025 1025
1026 for ( g = 0; g != size; g += 1 ) 1026 for ( g = 0; g != size; g += 1 )
1027 { 1027 {
1028 s4DVertex * a = (s4DVertex*) v[g]; 1028 s4DVertex * a = (s4DVertex*) v[g];
1029 1029
1030 if ( (a[1].flag & VERTEX4D_PROJECTED ) == VERTEX4D_PROJECTED ) 1030 if ( (a[1].flag & VERTEX4D_PROJECTED ) == VERTEX4D_PROJECTED )
1031 continue; 1031 continue;
1032 1032
1033 a[1].flag = a->flag | VERTEX4D_PROJECTED; 1033 a[1].flag = a->flag | VERTEX4D_PROJECTED;
1034 1034
1035 // project homogenous vertex, store 1/w 1035 // project homogenous vertex, store 1/w
1036 const f32 w = a->Pos.w; 1036 const f32 w = a->Pos.w;
1037 const f32 iw = core::reciprocal ( w ); 1037 const f32 iw = core::reciprocal ( w );
1038 1038
1039 // to device coordinates 1039 // to device coordinates
1040 const f32 * p = Transformation [ ETS_CLIPSCALE ].pointer(); 1040 const f32 * p = Transformation [ ETS_CLIPSCALE ].pointer();
1041 a[1].Pos.x = iw * ( a->Pos.x * p[ 0] + w * p[12] ); 1041 a[1].Pos.x = iw * ( a->Pos.x * p[ 0] + w * p[12] );
1042 a[1].Pos.y = iw * ( a->Pos.y * p[ 5] + w * p[13] ); 1042 a[1].Pos.y = iw * ( a->Pos.y * p[ 5] + w * p[13] );
1043 1043
1044#ifndef SOFTWARE_DRIVER_2_USE_WBUFFER 1044#ifndef SOFTWARE_DRIVER_2_USE_WBUFFER
1045 a[1].Pos.z = a->Pos.z * iw; 1045 a[1].Pos.z = a->Pos.z * iw;
1046#endif 1046#endif
1047 1047
1048 #ifdef SOFTWARE_DRIVER_2_USE_VERTEX_COLOR 1048 #ifdef SOFTWARE_DRIVER_2_USE_VERTEX_COLOR
1049 #ifdef SOFTWARE_DRIVER_2_PERSPECTIVE_CORRECT 1049 #ifdef SOFTWARE_DRIVER_2_PERSPECTIVE_CORRECT
1050 a[1].Color[0] = a->Color[0] * iw; 1050 a[1].Color[0] = a->Color[0] * iw;
1051 #else 1051 #else
1052 a[1].Color[0] = a->Color[0]; 1052 a[1].Color[0] = a->Color[0];
1053 #endif 1053 #endif
1054 #endif 1054 #endif
1055 1055
1056 a[1].LightTangent[0] = a[0].LightTangent[0] * iw; 1056 a[1].LightTangent[0] = a[0].LightTangent[0] * iw;
1057 a[1].Pos.w = iw; 1057 a[1].Pos.w = iw;
1058 1058
1059 } 1059 }
1060 1060
1061} 1061}
1062 1062
1063 1063
1064/*! 1064/*!
1065 crossproduct in projected 2D -> screen area triangle 1065 crossproduct in projected 2D -> screen area triangle
1066*/ 1066*/
1067inline f32 CBurningVideoDriver::screenarea ( const s4DVertex *v ) const 1067inline f32 CBurningVideoDriver::screenarea ( const s4DVertex *v ) const
1068{ 1068{
1069 return ( ( v[3].Pos.x - v[1].Pos.x ) * ( v[5].Pos.y - v[1].Pos.y ) ) - 1069 return ( ( v[3].Pos.x - v[1].Pos.x ) * ( v[5].Pos.y - v[1].Pos.y ) ) -
1070 ( ( v[3].Pos.y - v[1].Pos.y ) * ( v[5].Pos.x - v[1].Pos.x ) ); 1070 ( ( v[3].Pos.y - v[1].Pos.y ) * ( v[5].Pos.x - v[1].Pos.x ) );
1071} 1071}
1072 1072
1073 1073
1074/*! 1074/*!
1075*/ 1075*/
1076inline f32 CBurningVideoDriver::texelarea ( const s4DVertex *v, int tex ) const 1076inline f32 CBurningVideoDriver::texelarea ( const s4DVertex *v, int tex ) const
1077{ 1077{
1078 f32 z; 1078 f32 z;
1079 1079
1080 z = ( (v[2].Tex[tex].x - v[0].Tex[tex].x ) * (v[4].Tex[tex].y - v[0].Tex[tex].y ) ) 1080 z = ( (v[2].Tex[tex].x - v[0].Tex[tex].x ) * (v[4].Tex[tex].y - v[0].Tex[tex].y ) )
1081 - ( (v[4].Tex[tex].x - v[0].Tex[tex].x ) * (v[2].Tex[tex].y - v[0].Tex[tex].y ) ); 1081 - ( (v[4].Tex[tex].x - v[0].Tex[tex].x ) * (v[2].Tex[tex].y - v[0].Tex[tex].y ) );
1082 1082
1083 return MAT_TEXTURE ( tex )->getLODFactor ( z ); 1083 return MAT_TEXTURE ( tex )->getLODFactor ( z );
1084} 1084}
1085 1085
1086/*! 1086/*!
1087 crossproduct in projected 2D 1087 crossproduct in projected 2D
1088*/ 1088*/
1089inline f32 CBurningVideoDriver::screenarea2 ( const s4DVertex **v ) const 1089inline f32 CBurningVideoDriver::screenarea2 ( const s4DVertex **v ) const
1090{ 1090{
1091 return ( (( v[1] + 1 )->Pos.x - (v[0] + 1 )->Pos.x ) * ( (v[2] + 1 )->Pos.y - (v[0] + 1 )->Pos.y ) ) - 1091 return ( (( v[1] + 1 )->Pos.x - (v[0] + 1 )->Pos.x ) * ( (v[2] + 1 )->Pos.y - (v[0] + 1 )->Pos.y ) ) -
1092 ( (( v[1] + 1 )->Pos.y - (v[0] + 1 )->Pos.y ) * ( (v[2] + 1 )->Pos.x - (v[0] + 1 )->Pos.x ) ); 1092 ( (( v[1] + 1 )->Pos.y - (v[0] + 1 )->Pos.y ) * ( (v[2] + 1 )->Pos.x - (v[0] + 1 )->Pos.x ) );
1093} 1093}
1094 1094
1095/*! 1095/*!
1096*/ 1096*/
1097inline f32 CBurningVideoDriver::texelarea2 ( const s4DVertex **v, s32 tex ) const 1097inline f32 CBurningVideoDriver::texelarea2 ( const s4DVertex **v, s32 tex ) const
1098{ 1098{
1099 f32 z; 1099 f32 z;
1100 z = ( (v[1]->Tex[tex].x - v[0]->Tex[tex].x ) * (v[2]->Tex[tex].y - v[0]->Tex[tex].y ) ) 1100 z = ( (v[1]->Tex[tex].x - v[0]->Tex[tex].x ) * (v[2]->Tex[tex].y - v[0]->Tex[tex].y ) )
1101 - ( (v[2]->Tex[tex].x - v[0]->Tex[tex].x ) * (v[1]->Tex[tex].y - v[0]->Tex[tex].y ) ); 1101 - ( (v[2]->Tex[tex].x - v[0]->Tex[tex].x ) * (v[1]->Tex[tex].y - v[0]->Tex[tex].y ) );
1102 1102
1103 return MAT_TEXTURE ( tex )->getLODFactor ( z ); 1103 return MAT_TEXTURE ( tex )->getLODFactor ( z );
1104} 1104}
1105 1105
1106 1106
1107/*! 1107/*!
1108*/ 1108*/
1109inline void CBurningVideoDriver::select_polygon_mipmap ( s4DVertex *v, u32 vIn, u32 tex, const core::dimension2du& texSize ) const 1109inline void CBurningVideoDriver::select_polygon_mipmap ( s4DVertex *v, u32 vIn, u32 tex, const core::dimension2du& texSize ) const
1110{ 1110{
1111 f32 f[2]; 1111 f32 f[2];
1112 1112
1113 f[0] = (f32) texSize.Width - 0.25f; 1113 f[0] = (f32) texSize.Width - 0.25f;
1114 f[1] = (f32) texSize.Height - 0.25f; 1114 f[1] = (f32) texSize.Height - 0.25f;
1115 1115
1116#ifdef SOFTWARE_DRIVER_2_PERSPECTIVE_CORRECT 1116#ifdef SOFTWARE_DRIVER_2_PERSPECTIVE_CORRECT
1117 for ( u32 g = 0; g != vIn; g += 2 ) 1117 for ( u32 g = 0; g != vIn; g += 2 )
1118 { 1118 {
1119 (v + g + 1 )->Tex[tex].x = (v + g + 0)->Tex[tex].x * ( v + g + 1 )->Pos.w * f[0]; 1119 (v + g + 1 )->Tex[tex].x = (v + g + 0)->Tex[tex].x * ( v + g + 1 )->Pos.w * f[0];
1120 (v + g + 1 )->Tex[tex].y = (v + g + 0)->Tex[tex].y * ( v + g + 1 )->Pos.w * f[1]; 1120 (v + g + 1 )->Tex[tex].y = (v + g + 0)->Tex[tex].y * ( v + g + 1 )->Pos.w * f[1];
1121 } 1121 }
1122#else 1122#else
1123 for ( u32 g = 0; g != vIn; g += 2 ) 1123 for ( u32 g = 0; g != vIn; g += 2 )
1124 { 1124 {
1125 (v + g + 1 )->Tex[tex].x = (v + g + 0)->Tex[tex].x * f[0]; 1125 (v + g + 1 )->Tex[tex].x = (v + g + 0)->Tex[tex].x * f[0];
1126 (v + g + 1 )->Tex[tex].y = (v + g + 0)->Tex[tex].y * f[1]; 1126 (v + g + 1 )->Tex[tex].y = (v + g + 0)->Tex[tex].y * f[1];
1127 } 1127 }
1128#endif 1128#endif
1129} 1129}
1130 1130
1131inline void CBurningVideoDriver::select_polygon_mipmap2 ( s4DVertex **v, u32 tex, const core::dimension2du& texSize ) const 1131inline void CBurningVideoDriver::select_polygon_mipmap2 ( s4DVertex **v, u32 tex, const core::dimension2du& texSize ) const
1132{ 1132{
1133 f32 f[2]; 1133 f32 f[2];
1134 1134
1135 f[0] = (f32) texSize.Width - 0.25f; 1135 f[0] = (f32) texSize.Width - 0.25f;
1136 f[1] = (f32) texSize.Height - 0.25f; 1136 f[1] = (f32) texSize.Height - 0.25f;
1137 1137
1138#ifdef SOFTWARE_DRIVER_2_PERSPECTIVE_CORRECT 1138#ifdef SOFTWARE_DRIVER_2_PERSPECTIVE_CORRECT
1139 (v[0] + 1 )->Tex[tex].x = v[0]->Tex[tex].x * ( v[0] + 1 )->Pos.w * f[0]; 1139 (v[0] + 1 )->Tex[tex].x = v[0]->Tex[tex].x * ( v[0] + 1 )->Pos.w * f[0];
1140 (v[0] + 1 )->Tex[tex].y = v[0]->Tex[tex].y * ( v[0] + 1 )->Pos.w * f[1]; 1140 (v[0] + 1 )->Tex[tex].y = v[0]->Tex[tex].y * ( v[0] + 1 )->Pos.w * f[1];
1141 1141
1142 (v[1] + 1 )->Tex[tex].x = v[1]->Tex[tex].x * ( v[1] + 1 )->Pos.w * f[0]; 1142 (v[1] + 1 )->Tex[tex].x = v[1]->Tex[tex].x * ( v[1] + 1 )->Pos.w * f[0];
1143 (v[1] + 1 )->Tex[tex].y = v[1]->Tex[tex].y * ( v[1] + 1 )->Pos.w * f[1]; 1143 (v[1] + 1 )->Tex[tex].y = v[1]->Tex[tex].y * ( v[1] + 1 )->Pos.w * f[1];
1144 1144
1145 (v[2] + 1 )->Tex[tex].x = v[2]->Tex[tex].x * ( v[2] + 1 )->Pos.w * f[0]; 1145 (v[2] + 1 )->Tex[tex].x = v[2]->Tex[tex].x * ( v[2] + 1 )->Pos.w * f[0];
1146 (v[2] + 1 )->Tex[tex].y = v[2]->Tex[tex].y * ( v[2] + 1 )->Pos.w * f[1]; 1146 (v[2] + 1 )->Tex[tex].y = v[2]->Tex[tex].y * ( v[2] + 1 )->Pos.w * f[1];
1147 1147
1148#else 1148#else
1149 (v[0] + 1 )->Tex[tex].x = v[0]->Tex[tex].x * f[0]; 1149 (v[0] + 1 )->Tex[tex].x = v[0]->Tex[tex].x * f[0];
1150 (v[0] + 1 )->Tex[tex].y = v[0]->Tex[tex].y * f[1]; 1150 (v[0] + 1 )->Tex[tex].y = v[0]->Tex[tex].y * f[1];
1151 1151
1152 (v[1] + 1 )->Tex[tex].x = v[1]->Tex[tex].x * f[0]; 1152 (v[1] + 1 )->Tex[tex].x = v[1]->Tex[tex].x * f[0];
1153 (v[1] + 1 )->Tex[tex].y = v[1]->Tex[tex].y * f[1]; 1153 (v[1] + 1 )->Tex[tex].y = v[1]->Tex[tex].y * f[1];
1154 1154
1155 (v[2] + 1 )->Tex[tex].x = v[2]->Tex[tex].x * f[0]; 1155 (v[2] + 1 )->Tex[tex].x = v[2]->Tex[tex].x * f[0];
1156 (v[2] + 1 )->Tex[tex].y = v[2]->Tex[tex].y * f[1]; 1156 (v[2] + 1 )->Tex[tex].y = v[2]->Tex[tex].y * f[1];
1157#endif 1157#endif
1158} 1158}
1159 1159
1160// Vertex Cache 1160// Vertex Cache
1161const SVSize CBurningVideoDriver::vSize[] = 1161const SVSize CBurningVideoDriver::vSize[] =
1162{ 1162{
1163 { VERTEX4D_FORMAT_TEXTURE_1 | VERTEX4D_FORMAT_COLOR_1, sizeof(S3DVertex), 1 }, 1163 { VERTEX4D_FORMAT_TEXTURE_1 | VERTEX4D_FORMAT_COLOR_1, sizeof(S3DVertex), 1 },
1164 { VERTEX4D_FORMAT_TEXTURE_2 | VERTEX4D_FORMAT_COLOR_1, sizeof(S3DVertex2TCoords),2 }, 1164 { VERTEX4D_FORMAT_TEXTURE_2 | VERTEX4D_FORMAT_COLOR_1, sizeof(S3DVertex2TCoords),2 },
1165 { VERTEX4D_FORMAT_TEXTURE_2 | VERTEX4D_FORMAT_COLOR_1 | VERTEX4D_FORMAT_BUMP_DOT3, sizeof(S3DVertexTangents),2 }, 1165 { VERTEX4D_FORMAT_TEXTURE_2 | VERTEX4D_FORMAT_COLOR_1 | VERTEX4D_FORMAT_BUMP_DOT3, sizeof(S3DVertexTangents),2 },
1166 { VERTEX4D_FORMAT_TEXTURE_2 | VERTEX4D_FORMAT_COLOR_1, sizeof(S3DVertex), 2 }, // reflection map 1166 { VERTEX4D_FORMAT_TEXTURE_2 | VERTEX4D_FORMAT_COLOR_1, sizeof(S3DVertex), 2 }, // reflection map
1167 { 0, sizeof(f32) * 3, 0 }, // core::vector3df* 1167 { 0, sizeof(f32) * 3, 0 }, // core::vector3df*
1168}; 1168};
1169 1169
1170 1170
1171 1171
1172/*! 1172/*!
1173 fill a cache line with transformed, light and clipp test triangles 1173 fill a cache line with transformed, light and clipp test triangles
1174*/ 1174*/
1175void CBurningVideoDriver::VertexCache_fill(const u32 sourceIndex, const u32 destIndex) 1175void CBurningVideoDriver::VertexCache_fill(const u32 sourceIndex, const u32 destIndex)
1176{ 1176{
1177 u8 * source; 1177 u8 * source;
1178 s4DVertex *dest; 1178 s4DVertex *dest;
1179 1179
1180 source = (u8*) VertexCache.vertices + ( sourceIndex * vSize[VertexCache.vType].Pitch ); 1180 source = (u8*) VertexCache.vertices + ( sourceIndex * vSize[VertexCache.vType].Pitch );
1181 1181
1182 // it's a look ahead so we never hit it.. 1182 // it's a look ahead so we never hit it..
1183 // but give priority... 1183 // but give priority...
1184 //VertexCache.info[ destIndex ].hit = hitCount; 1184 //VertexCache.info[ destIndex ].hit = hitCount;
1185 1185
1186 // store info 1186 // store info
1187 VertexCache.info[ destIndex ].index = sourceIndex; 1187 VertexCache.info[ destIndex ].index = sourceIndex;
1188 VertexCache.info[ destIndex ].hit = 0; 1188 VertexCache.info[ destIndex ].hit = 0;
1189 1189
1190 // destination Vertex 1190 // destination Vertex
1191 dest = (s4DVertex *) ( (u8*) VertexCache.mem.data + ( destIndex << ( SIZEOF_SVERTEX_LOG2 + 1 ) ) ); 1191 dest = (s4DVertex *) ( (u8*) VertexCache.mem.data + ( destIndex << ( SIZEOF_SVERTEX_LOG2 + 1 ) ) );
1192 1192
1193 // transform Model * World * Camera * Projection * NDCSpace matrix 1193 // transform Model * World * Camera * Projection * NDCSpace matrix
1194 const S3DVertex *base = ((S3DVertex*) source ); 1194 const S3DVertex *base = ((S3DVertex*) source );
1195 Transformation [ ETS_CURRENT].transformVect ( &dest->Pos.x, base->Pos ); 1195 Transformation [ ETS_CURRENT].transformVect ( &dest->Pos.x, base->Pos );
1196 1196
1197 //mhm ;-) maybe no goto 1197 //mhm ;-) maybe no goto
1198 if ( VertexCache.vType == 4 ) goto clipandproject; 1198 if ( VertexCache.vType == 4 ) goto clipandproject;
1199 1199
1200 1200
1201#if defined (SOFTWARE_DRIVER_2_LIGHTING) || defined ( SOFTWARE_DRIVER_2_TEXTURE_TRANSFORM ) 1201#if defined (SOFTWARE_DRIVER_2_LIGHTING) || defined ( SOFTWARE_DRIVER_2_TEXTURE_TRANSFORM )
1202 1202
1203 // vertex normal in light space 1203 // vertex normal in light space
1204 if ( Material.org.Lighting || (LightSpace.Flags & VERTEXTRANSFORM) ) 1204 if ( Material.org.Lighting || (LightSpace.Flags & VERTEXTRANSFORM) )
1205 { 1205 {
1206 if ( TransformationFlag[ETS_WORLD] & ETF_IDENTITY ) 1206 if ( TransformationFlag[ETS_WORLD] & ETF_IDENTITY )
1207 { 1207 {
1208 LightSpace.normal.set ( base->Normal.X, base->Normal.Y, base->Normal.Z, 1.f ); 1208 LightSpace.normal.set ( base->Normal.X, base->Normal.Y, base->Normal.Z, 1.f );
1209 LightSpace.vertex.set ( base->Pos.X, base->Pos.Y, base->Pos.Z, 1.f ); 1209 LightSpace.vertex.set ( base->Pos.X, base->Pos.Y, base->Pos.Z, 1.f );
1210 } 1210 }
1211 else 1211 else
1212 { 1212 {
1213 Transformation[ETS_WORLD].rotateVect ( &LightSpace.normal.x, base->Normal ); 1213 Transformation[ETS_WORLD].rotateVect ( &LightSpace.normal.x, base->Normal );
1214 1214
1215 // vertex in light space 1215 // vertex in light space
1216 if ( LightSpace.Flags & ( POINTLIGHT | FOG | SPECULAR | VERTEXTRANSFORM) ) 1216 if ( LightSpace.Flags & ( POINTLIGHT | FOG | SPECULAR | VERTEXTRANSFORM) )
1217 Transformation[ETS_WORLD].transformVect ( &LightSpace.vertex.x, base->Pos ); 1217 Transformation[ETS_WORLD].transformVect ( &LightSpace.vertex.x, base->Pos );
1218 } 1218 }
1219 1219
1220 if ( LightSpace.Flags & NORMALIZE ) 1220 if ( LightSpace.Flags & NORMALIZE )
1221 LightSpace.normal.normalize_xyz(); 1221 LightSpace.normal.normalize_xyz();
1222 1222
1223 } 1223 }
1224 1224
1225#endif 1225#endif
1226 1226
1227#if defined ( SOFTWARE_DRIVER_2_USE_VERTEX_COLOR ) 1227#if defined ( SOFTWARE_DRIVER_2_USE_VERTEX_COLOR )
1228 // apply lighting model 1228 // apply lighting model
1229 #if defined (SOFTWARE_DRIVER_2_LIGHTING) 1229 #if defined (SOFTWARE_DRIVER_2_LIGHTING)
1230 if ( Material.org.Lighting ) 1230 if ( Material.org.Lighting )
1231 { 1231 {
1232 lightVertex ( dest, base->Color.color ); 1232 lightVertex ( dest, base->Color.color );
1233 } 1233 }
1234 else 1234 else
1235 { 1235 {
1236 dest->Color[0].setA8R8G8B8 ( base->Color.color ); 1236 dest->Color[0].setA8R8G8B8 ( base->Color.color );
1237 } 1237 }
1238 #else 1238 #else
1239 dest->Color[0].setA8R8G8B8 ( base->Color.color ); 1239 dest->Color[0].setA8R8G8B8 ( base->Color.color );
1240 #endif 1240 #endif
1241#endif 1241#endif
1242 1242
1243 // Texture Transform 1243 // Texture Transform
1244#if !defined ( SOFTWARE_DRIVER_2_TEXTURE_TRANSFORM ) 1244#if !defined ( SOFTWARE_DRIVER_2_TEXTURE_TRANSFORM )
1245 irr::memcpy32_small ( &dest->Tex[0],&base->TCoords, 1245 irr::memcpy32_small ( &dest->Tex[0],&base->TCoords,
1246 vSize[VertexCache.vType].TexSize << 3 // * ( sizeof ( f32 ) * 2 ) 1246 vSize[VertexCache.vType].TexSize << 3 // * ( sizeof ( f32 ) * 2 )
1247 ); 1247 );
1248#else 1248#else
1249 1249
1250 if ( 0 == (LightSpace.Flags & VERTEXTRANSFORM) ) 1250 if ( 0 == (LightSpace.Flags & VERTEXTRANSFORM) )
1251 { 1251 {
1252 irr::memcpy32_small ( &dest->Tex[0],&base->TCoords, 1252 irr::memcpy32_small ( &dest->Tex[0],&base->TCoords,
1253 vSize[VertexCache.vType].TexSize << 3 // * ( sizeof ( f32 ) * 2 ) 1253 vSize[VertexCache.vType].TexSize << 3 // * ( sizeof ( f32 ) * 2 )
1254 ); 1254 );
1255 } 1255 }
1256 else 1256 else
1257 { 1257 {
1258 /* 1258 /*
1259 Generate texture coordinates as linear functions so that: 1259 Generate texture coordinates as linear functions so that:
1260 u = Ux*x + Uy*y + Uz*z + Uw 1260 u = Ux*x + Uy*y + Uz*z + Uw
1261 v = Vx*x + Vy*y + Vz*z + Vw 1261 v = Vx*x + Vy*y + Vz*z + Vw
1262 The matrix M for this case is: 1262 The matrix M for this case is:
1263 Ux Vx 0 0 1263 Ux Vx 0 0
1264 Uy Vy 0 0 1264 Uy Vy 0 0
1265 Uz Vz 0 0 1265 Uz Vz 0 0
1266 Uw Vw 0 0 1266 Uw Vw 0 0
1267 */ 1267 */
1268 1268
1269 u32 t; 1269 u32 t;
1270 sVec4 n; 1270 sVec4 n;
1271 sVec2 srcT; 1271 sVec2 srcT;
1272 1272
1273 for ( t = 0; t != vSize[VertexCache.vType].TexSize; ++t ) 1273 for ( t = 0; t != vSize[VertexCache.vType].TexSize; ++t )
1274 { 1274 {
1275 const core::matrix4& M = Transformation [ ETS_TEXTURE_0 + t ]; 1275 const core::matrix4& M = Transformation [ ETS_TEXTURE_0 + t ];
1276 1276
1277 // texgen 1277 // texgen
1278 if ( TransformationFlag [ ETS_TEXTURE_0 + t ] & (ETF_TEXGEN_CAMERA_NORMAL|ETF_TEXGEN_CAMERA_REFLECTION) ) 1278 if ( TransformationFlag [ ETS_TEXTURE_0 + t ] & (ETF_TEXGEN_CAMERA_NORMAL|ETF_TEXGEN_CAMERA_REFLECTION) )
1279 { 1279 {
1280 n.x = LightSpace.campos.x - LightSpace.vertex.x; 1280 n.x = LightSpace.campos.x - LightSpace.vertex.x;
1281 n.y = LightSpace.campos.x - LightSpace.vertex.y; 1281 n.y = LightSpace.campos.x - LightSpace.vertex.y;
1282 n.z = LightSpace.campos.x - LightSpace.vertex.z; 1282 n.z = LightSpace.campos.x - LightSpace.vertex.z;
1283 n.normalize_xyz(); 1283 n.normalize_xyz();
1284 n.x += LightSpace.normal.x; 1284 n.x += LightSpace.normal.x;
1285 n.y += LightSpace.normal.y; 1285 n.y += LightSpace.normal.y;
1286 n.z += LightSpace.normal.z; 1286 n.z += LightSpace.normal.z;
1287 n.normalize_xyz(); 1287 n.normalize_xyz();
1288 1288
1289 const f32 *view = Transformation[ETS_VIEW].pointer(); 1289 const f32 *view = Transformation[ETS_VIEW].pointer();
1290 1290
1291 if ( TransformationFlag [ ETS_TEXTURE_0 + t ] & ETF_TEXGEN_CAMERA_REFLECTION ) 1291 if ( TransformationFlag [ ETS_TEXTURE_0 + t ] & ETF_TEXGEN_CAMERA_REFLECTION )
1292 { 1292 {
1293 srcT.x = 0.5f * ( 1.f + (n.x * view[0] + n.y * view[4] + n.z * view[8] )); 1293 srcT.x = 0.5f * ( 1.f + (n.x * view[0] + n.y * view[4] + n.z * view[8] ));
1294 srcT.y = 0.5f * ( 1.f + (n.x * view[1] + n.y * view[5] + n.z * view[9] )); 1294 srcT.y = 0.5f * ( 1.f + (n.x * view[1] + n.y * view[5] + n.z * view[9] ));
1295 } 1295 }
1296 else 1296 else
1297 { 1297 {
1298 srcT.x = 0.5f * ( 1.f + (n.x * view[0] + n.y * view[1] + n.z * view[2] )); 1298 srcT.x = 0.5f * ( 1.f + (n.x * view[0] + n.y * view[1] + n.z * view[2] ));
1299 srcT.y = 0.5f * ( 1.f + (n.x * view[4] + n.y * view[5] + n.z * view[6] )); 1299 srcT.y = 0.5f * ( 1.f + (n.x * view[4] + n.y * view[5] + n.z * view[6] ));
1300 } 1300 }
1301 } 1301 }
1302 else 1302 else
1303 { 1303 {
1304 irr::memcpy32_small ( &srcT,(&base->TCoords) + t, 1304 irr::memcpy32_small ( &srcT,(&base->TCoords) + t,
1305 sizeof ( f32 ) * 2 ); 1305 sizeof ( f32 ) * 2 );
1306 } 1306 }
1307 1307
1308 switch ( Material.org.TextureLayer[t].TextureWrapU ) 1308 switch ( Material.org.TextureLayer[t].TextureWrapU )
1309 { 1309 {
1310 case ETC_CLAMP: 1310 case ETC_CLAMP:
1311 case ETC_CLAMP_TO_EDGE: 1311 case ETC_CLAMP_TO_EDGE:
1312 case ETC_CLAMP_TO_BORDER: 1312 case ETC_CLAMP_TO_BORDER:
1313 dest->Tex[t].x = core::clamp ( (f32) ( M[0] * srcT.x + M[4] * srcT.y + M[8] ), 0.f, 1.f ); 1313 dest->Tex[t].x = core::clamp ( (f32) ( M[0] * srcT.x + M[4] * srcT.y + M[8] ), 0.f, 1.f );
1314 break; 1314 break;
1315 case ETC_MIRROR: 1315 case ETC_MIRROR:
1316 dest->Tex[t].x = M[0] * srcT.x + M[4] * srcT.y + M[8]; 1316 dest->Tex[t].x = M[0] * srcT.x + M[4] * srcT.y + M[8];
1317 if (core::fract(dest->Tex[t].x)>0.5f) 1317 if (core::fract(dest->Tex[t].x)>0.5f)
1318 dest->Tex[t].x=1.f-dest->Tex[t].x; 1318 dest->Tex[t].x=1.f-dest->Tex[t].x;
1319 break; 1319 break;
1320 case ETC_MIRROR_CLAMP: 1320 case ETC_MIRROR_CLAMP:
1321 case ETC_MIRROR_CLAMP_TO_EDGE: 1321 case ETC_MIRROR_CLAMP_TO_EDGE:
1322 case ETC_MIRROR_CLAMP_TO_BORDER: 1322 case ETC_MIRROR_CLAMP_TO_BORDER:
1323 dest->Tex[t].x = core::clamp ( (f32) ( M[0] * srcT.x + M[4] * srcT.y + M[8] ), 0.f, 1.f ); 1323 dest->Tex[t].x = core::clamp ( (f32) ( M[0] * srcT.x + M[4] * srcT.y + M[8] ), 0.f, 1.f );
1324 if (core::fract(dest->Tex[t].x)>0.5f) 1324 if (core::fract(dest->Tex[t].x)>0.5f)
1325 dest->Tex[t].x=1.f-dest->Tex[t].x; 1325 dest->Tex[t].x=1.f-dest->Tex[t].x;
1326 break; 1326 break;
1327 case ETC_REPEAT: 1327 case ETC_REPEAT:
1328 default: 1328 default:
1329 dest->Tex[t].x = M[0] * srcT.x + M[4] * srcT.y + M[8]; 1329 dest->Tex[t].x = M[0] * srcT.x + M[4] * srcT.y + M[8];
1330 break; 1330 break;
1331 } 1331 }
1332 switch ( Material.org.TextureLayer[t].TextureWrapV ) 1332 switch ( Material.org.TextureLayer[t].TextureWrapV )
1333 { 1333 {
1334 case ETC_CLAMP: 1334 case ETC_CLAMP:
1335 case ETC_CLAMP_TO_EDGE: 1335 case ETC_CLAMP_TO_EDGE:
1336 case ETC_CLAMP_TO_BORDER: 1336 case ETC_CLAMP_TO_BORDER:
1337 dest->Tex[t].y = core::clamp ( (f32) ( M[1] * srcT.x + M[5] * srcT.y + M[9] ), 0.f, 1.f ); 1337 dest->Tex[t].y = core::clamp ( (f32) ( M[1] * srcT.x + M[5] * srcT.y + M[9] ), 0.f, 1.f );
1338 break; 1338 break;
1339 case ETC_MIRROR: 1339 case ETC_MIRROR:
1340 dest->Tex[t].y = M[1] * srcT.x + M[5] * srcT.y + M[9]; 1340 dest->Tex[t].y = M[1] * srcT.x + M[5] * srcT.y + M[9];
1341 if (core::fract(dest->Tex[t].y)>0.5f) 1341 if (core::fract(dest->Tex[t].y)>0.5f)
1342 dest->Tex[t].y=1.f-dest->Tex[t].y; 1342 dest->Tex[t].y=1.f-dest->Tex[t].y;
1343 break; 1343 break;
1344 case ETC_MIRROR_CLAMP: 1344 case ETC_MIRROR_CLAMP:
1345 case ETC_MIRROR_CLAMP_TO_EDGE: 1345 case ETC_MIRROR_CLAMP_TO_EDGE:
1346 case ETC_MIRROR_CLAMP_TO_BORDER: 1346 case ETC_MIRROR_CLAMP_TO_BORDER:
1347 dest->Tex[t].y = core::clamp ( (f32) ( M[1] * srcT.x + M[5] * srcT.y + M[9] ), 0.f, 1.f ); 1347 dest->Tex[t].y = core::clamp ( (f32) ( M[1] * srcT.x + M[5] * srcT.y + M[9] ), 0.f, 1.f );
1348 if (core::fract(dest->Tex[t].y)>0.5f) 1348 if (core::fract(dest->Tex[t].y)>0.5f)
1349 dest->Tex[t].y=1.f-dest->Tex[t].y; 1349 dest->Tex[t].y=1.f-dest->Tex[t].y;
1350 break; 1350 break;
1351 case ETC_REPEAT: 1351 case ETC_REPEAT:
1352 default: 1352 default:
1353 dest->Tex[t].y = M[1] * srcT.x + M[5] * srcT.y + M[9]; 1353 dest->Tex[t].y = M[1] * srcT.x + M[5] * srcT.y + M[9];
1354 break; 1354 break;
1355 } 1355 }
1356 } 1356 }
1357 } 1357 }
1358 1358
1359#if 0 1359#if 0
1360 // tangent space light vector, emboss 1360 // tangent space light vector, emboss
1361 if ( Lights.size () && ( vSize[VertexCache.vType].Format & VERTEX4D_FORMAT_BUMP_DOT3 ) ) 1361 if ( Lights.size () && ( vSize[VertexCache.vType].Format & VERTEX4D_FORMAT_BUMP_DOT3 ) )
1362 { 1362 {
1363 const S3DVertexTangents *tangent = ((S3DVertexTangents*) source ); 1363 const S3DVertexTangents *tangent = ((S3DVertexTangents*) source );
1364 const SBurningShaderLight &light = LightSpace.Light[0]; 1364 const SBurningShaderLight &light = LightSpace.Light[0];
1365 1365
1366 sVec4 vp; 1366 sVec4 vp;
1367 1367
1368 vp.x = light.pos.x - LightSpace.vertex.x; 1368 vp.x = light.pos.x - LightSpace.vertex.x;
1369 vp.y = light.pos.y - LightSpace.vertex.y; 1369 vp.y = light.pos.y - LightSpace.vertex.y;
1370 vp.z = light.pos.z - LightSpace.vertex.z; 1370 vp.z = light.pos.z - LightSpace.vertex.z;
1371 1371
1372 vp.normalize_xyz(); 1372 vp.normalize_xyz();
1373 1373
1374 LightSpace.tangent.x = vp.x * tangent->Tangent.X + vp.y * tangent->Tangent.Y + vp.z * tangent->Tangent.Z; 1374 LightSpace.tangent.x = vp.x * tangent->Tangent.X + vp.y * tangent->Tangent.Y + vp.z * tangent->Tangent.Z;
1375 LightSpace.tangent.y = vp.x * tangent->Binormal.X + vp.y * tangent->Binormal.Y + vp.z * tangent->Binormal.Z; 1375 LightSpace.tangent.y = vp.x * tangent->Binormal.X + vp.y * tangent->Binormal.Y + vp.z * tangent->Binormal.Z;
1376 //LightSpace.tangent.z = vp.x * tangent->Normal.X + vp.y * tangent->Normal.Y + vp.z * tangent->Normal.Z; 1376 //LightSpace.tangent.z = vp.x * tangent->Normal.X + vp.y * tangent->Normal.Y + vp.z * tangent->Normal.Z;
1377 LightSpace.tangent.z = 0.f; 1377 LightSpace.tangent.z = 0.f;
1378 LightSpace.tangent.normalize_xyz(); 1378 LightSpace.tangent.normalize_xyz();
1379 1379
1380 f32 scale = 1.f / 128.f; 1380 f32 scale = 1.f / 128.f;
1381 if ( Material.org.MaterialTypeParam > 0.f ) 1381 if ( Material.org.MaterialTypeParam > 0.f )
1382 scale = Material.org.MaterialTypeParam; 1382 scale = Material.org.MaterialTypeParam;
1383 1383
1384 // emboss, shift coordinates 1384 // emboss, shift coordinates
1385 dest->Tex[1].x = dest->Tex[0].x + LightSpace.tangent.x * scale; 1385 dest->Tex[1].x = dest->Tex[0].x + LightSpace.tangent.x * scale;
1386 dest->Tex[1].y = dest->Tex[0].y + LightSpace.tangent.y * scale; 1386 dest->Tex[1].y = dest->Tex[0].y + LightSpace.tangent.y * scale;
1387 //dest->Tex[1].z = LightSpace.tangent.z * scale; 1387 //dest->Tex[1].z = LightSpace.tangent.z * scale;
1388 } 1388 }
1389#endif 1389#endif
1390 1390
1391 if ( LightSpace.Light.size () && ( vSize[VertexCache.vType].Format & VERTEX4D_FORMAT_BUMP_DOT3 ) ) 1391 if ( LightSpace.Light.size () && ( vSize[VertexCache.vType].Format & VERTEX4D_FORMAT_BUMP_DOT3 ) )
1392 { 1392 {
1393 const S3DVertexTangents *tangent = ((S3DVertexTangents*) source ); 1393 const S3DVertexTangents *tangent = ((S3DVertexTangents*) source );
1394 1394
1395 sVec4 vp; 1395 sVec4 vp;
1396 1396
1397 dest->LightTangent[0].x = 0.f; 1397 dest->LightTangent[0].x = 0.f;
1398 dest->LightTangent[0].y = 0.f; 1398 dest->LightTangent[0].y = 0.f;
1399 dest->LightTangent[0].z = 0.f; 1399 dest->LightTangent[0].z = 0.f;
1400 for ( u32 i = 0; i < 2 && i < LightSpace.Light.size (); ++i ) 1400 for ( u32 i = 0; i < 2 && i < LightSpace.Light.size (); ++i )
1401 { 1401 {
1402 const SBurningShaderLight &light = LightSpace.Light[i]; 1402 const SBurningShaderLight &light = LightSpace.Light[i];
1403 1403
1404 if ( !light.LightIsOn ) 1404 if ( !light.LightIsOn )
1405 continue; 1405 continue;
1406 1406
1407 vp.x = light.pos.x - LightSpace.vertex.x; 1407 vp.x = light.pos.x - LightSpace.vertex.x;
1408 vp.y = light.pos.y - LightSpace.vertex.y; 1408 vp.y = light.pos.y - LightSpace.vertex.y;
1409 vp.z = light.pos.z - LightSpace.vertex.z; 1409 vp.z = light.pos.z - LightSpace.vertex.z;
1410 1410
1411 /* 1411 /*
1412 vp.x = light.pos_objectspace.x - base->Pos.X; 1412 vp.x = light.pos_objectspace.x - base->Pos.X;
1413 vp.y = light.pos_objectspace.y - base->Pos.Y; 1413 vp.y = light.pos_objectspace.y - base->Pos.Y;
1414 vp.z = light.pos_objectspace.z - base->Pos.Z; 1414 vp.z = light.pos_objectspace.z - base->Pos.Z;
1415 */ 1415 */
1416 1416
1417 vp.normalize_xyz(); 1417 vp.normalize_xyz();
1418 1418
1419 1419
1420 // transform by tangent matrix 1420 // transform by tangent matrix
1421 sVec3 l; 1421 sVec3 l;
1422 #if 1 1422 #if 1
1423 l.x = (vp.x * tangent->Tangent.X + vp.y * tangent->Tangent.Y + vp.z * tangent->Tangent.Z ); 1423 l.x = (vp.x * tangent->Tangent.X + vp.y * tangent->Tangent.Y + vp.z * tangent->Tangent.Z );
1424 l.y = (vp.x * tangent->Binormal.X + vp.y * tangent->Binormal.Y + vp.z * tangent->Binormal.Z ); 1424 l.y = (vp.x * tangent->Binormal.X + vp.y * tangent->Binormal.Y + vp.z * tangent->Binormal.Z );
1425 l.z = (vp.x * tangent->Normal.X + vp.y * tangent->Normal.Y + vp.z * tangent->Normal.Z ); 1425 l.z = (vp.x * tangent->Normal.X + vp.y * tangent->Normal.Y + vp.z * tangent->Normal.Z );
1426 #else 1426 #else
1427 l.x = (vp.x * tangent->Tangent.X + vp.y * tangent->Binormal.X + vp.z * tangent->Normal.X ); 1427 l.x = (vp.x * tangent->Tangent.X + vp.y * tangent->Binormal.X + vp.z * tangent->Normal.X );
1428 l.y = (vp.x * tangent->Tangent.Y + vp.y * tangent->Binormal.Y + vp.z * tangent->Normal.Y ); 1428 l.y = (vp.x * tangent->Tangent.Y + vp.y * tangent->Binormal.Y + vp.z * tangent->Normal.Y );
1429 l.z = (vp.x * tangent->Tangent.Z + vp.y * tangent->Binormal.Z + vp.z * tangent->Normal.Z ); 1429 l.z = (vp.x * tangent->Tangent.Z + vp.y * tangent->Binormal.Z + vp.z * tangent->Normal.Z );
1430 #endif 1430 #endif
1431 1431
1432 1432
1433 /* 1433 /*
1434 f32 scale = 1.f / 128.f; 1434 f32 scale = 1.f / 128.f;
1435 scale /= dest->LightTangent[0].b; 1435 scale /= dest->LightTangent[0].b;
1436 1436
1437 // emboss, shift coordinates 1437 // emboss, shift coordinates
1438 dest->Tex[1].x = dest->Tex[0].x + l.r * scale; 1438 dest->Tex[1].x = dest->Tex[0].x + l.r * scale;
1439 dest->Tex[1].y = dest->Tex[0].y + l.g * scale; 1439 dest->Tex[1].y = dest->Tex[0].y + l.g * scale;
1440 */ 1440 */
1441 dest->Tex[1].x = dest->Tex[0].x; 1441 dest->Tex[1].x = dest->Tex[0].x;
1442 dest->Tex[1].y = dest->Tex[0].y; 1442 dest->Tex[1].y = dest->Tex[0].y;
1443 1443
1444 // scale bias 1444 // scale bias
1445 dest->LightTangent[0].x += l.x; 1445 dest->LightTangent[0].x += l.x;
1446 dest->LightTangent[0].y += l.y; 1446 dest->LightTangent[0].y += l.y;
1447 dest->LightTangent[0].z += l.z; 1447 dest->LightTangent[0].z += l.z;
1448 } 1448 }
1449 dest->LightTangent[0].setLength ( 0.5f ); 1449 dest->LightTangent[0].setLength ( 0.5f );
1450 dest->LightTangent[0].x += 0.5f; 1450 dest->LightTangent[0].x += 0.5f;
1451 dest->LightTangent[0].y += 0.5f; 1451 dest->LightTangent[0].y += 0.5f;
1452 dest->LightTangent[0].z += 0.5f; 1452 dest->LightTangent[0].z += 0.5f;
1453 } 1453 }
1454 1454
1455 1455
1456#endif 1456#endif
1457 1457
1458clipandproject: 1458clipandproject:
1459 dest[0].flag = dest[1].flag = vSize[VertexCache.vType].Format; 1459 dest[0].flag = dest[1].flag = vSize[VertexCache.vType].Format;
1460 1460
1461 // test vertex 1461 // test vertex
1462 dest[0].flag |= clipToFrustumTest ( dest); 1462 dest[0].flag |= clipToFrustumTest ( dest);
1463 1463
1464 // to DC Space, project homogenous vertex 1464 // to DC Space, project homogenous vertex
1465 if ( (dest[0].flag & VERTEX4D_CLIPMASK ) == VERTEX4D_INSIDE ) 1465 if ( (dest[0].flag & VERTEX4D_CLIPMASK ) == VERTEX4D_INSIDE )
1466 { 1466 {
1467 ndc_2_dc_and_project2 ( (const s4DVertex**) &dest, 1 ); 1467 ndc_2_dc_and_project2 ( (const s4DVertex**) &dest, 1 );
1468 } 1468 }
1469 1469
1470 //return dest; 1470 //return dest;
1471} 1471}
1472 1472
1473// 1473//
1474 1474
1475REALINLINE s4DVertex * CBurningVideoDriver::VertexCache_getVertex ( const u32 sourceIndex ) 1475REALINLINE s4DVertex * CBurningVideoDriver::VertexCache_getVertex ( const u32 sourceIndex )
1476{ 1476{
1477 for ( s32 i = 0; i < VERTEXCACHE_ELEMENT; ++i ) 1477 for ( s32 i = 0; i < VERTEXCACHE_ELEMENT; ++i )
1478 { 1478 {
1479 if ( VertexCache.info[ i ].index == sourceIndex ) 1479 if ( VertexCache.info[ i ].index == sourceIndex )
1480 { 1480 {
1481 return (s4DVertex *) ( (u8*) VertexCache.mem.data + ( i << ( SIZEOF_SVERTEX_LOG2 + 1 ) ) ); 1481 return (s4DVertex *) ( (u8*) VertexCache.mem.data + ( i << ( SIZEOF_SVERTEX_LOG2 + 1 ) ) );
1482 } 1482 }
1483 } 1483 }
1484 return 0; 1484 return 0;
1485} 1485}
1486 1486
1487 1487
1488/* 1488/*
1489 Cache based on linear walk indices 1489 Cache based on linear walk indices
1490 fill blockwise on the next 16(Cache_Size) unique vertices in indexlist 1490 fill blockwise on the next 16(Cache_Size) unique vertices in indexlist
1491 merge the next 16 vertices with the current 1491 merge the next 16 vertices with the current
1492*/ 1492*/
1493REALINLINE void CBurningVideoDriver::VertexCache_get(const s4DVertex ** face) 1493REALINLINE void CBurningVideoDriver::VertexCache_get(const s4DVertex ** face)
1494{ 1494{
1495 SCacheInfo info[VERTEXCACHE_ELEMENT]; 1495 SCacheInfo info[VERTEXCACHE_ELEMENT];
1496 1496
1497 // next primitive must be complete in cache 1497 // next primitive must be complete in cache
1498 if ( VertexCache.indicesIndex - VertexCache.indicesRun < 3 && 1498 if ( VertexCache.indicesIndex - VertexCache.indicesRun < 3 &&
1499 VertexCache.indicesIndex < VertexCache.indexCount 1499 VertexCache.indicesIndex < VertexCache.indexCount
1500 ) 1500 )
1501 { 1501 {
1502 // rewind to start of primitive 1502 // rewind to start of primitive
1503 VertexCache.indicesIndex = VertexCache.indicesRun; 1503 VertexCache.indicesIndex = VertexCache.indicesRun;
1504 1504
1505 irr::memset32 ( info, VERTEXCACHE_MISS, sizeof ( info ) ); 1505 irr::memset32 ( info, VERTEXCACHE_MISS, sizeof ( info ) );
1506 1506
1507 // get the next unique vertices cache line 1507 // get the next unique vertices cache line
1508 u32 fillIndex = 0; 1508 u32 fillIndex = 0;
1509 u32 dIndex; 1509 u32 dIndex;
1510 u32 i; 1510 u32 i;
1511 u32 sourceIndex; 1511 u32 sourceIndex;
1512 1512
1513 while ( VertexCache.indicesIndex < VertexCache.indexCount && 1513 while ( VertexCache.indicesIndex < VertexCache.indexCount &&
1514 fillIndex < VERTEXCACHE_ELEMENT 1514 fillIndex < VERTEXCACHE_ELEMENT
1515 ) 1515 )
1516 { 1516 {
1517 switch ( VertexCache.iType ) 1517 switch ( VertexCache.iType )
1518 { 1518 {
1519 case 1: 1519 case 1:
1520 sourceIndex = ((u16*)VertexCache.indices) [ VertexCache.indicesIndex ]; 1520 sourceIndex = ((u16*)VertexCache.indices) [ VertexCache.indicesIndex ];
1521 break; 1521 break;
1522 case 2: 1522 case 2:
1523 sourceIndex = ((u32*)VertexCache.indices) [ VertexCache.indicesIndex ]; 1523 sourceIndex = ((u32*)VertexCache.indices) [ VertexCache.indicesIndex ];
1524 break; 1524 break;
1525 case 4: 1525 case 4:
1526 sourceIndex = VertexCache.indicesIndex; 1526 sourceIndex = VertexCache.indicesIndex;
1527 break; 1527 break;
1528 } 1528 }
1529 1529
1530 VertexCache.indicesIndex += 1; 1530 VertexCache.indicesIndex += 1;
1531 1531
1532 // if not exist, push back 1532 // if not exist, push back
1533 s32 exist = 0; 1533 s32 exist = 0;
1534 for ( dIndex = 0; dIndex < fillIndex; ++dIndex ) 1534 for ( dIndex = 0; dIndex < fillIndex; ++dIndex )
1535 { 1535 {
1536 if ( info[ dIndex ].index == sourceIndex ) 1536 if ( info[ dIndex ].index == sourceIndex )
1537 { 1537 {
1538 exist = 1; 1538 exist = 1;
1539 break; 1539 break;
1540 } 1540 }
1541 } 1541 }
1542 1542
1543 if ( 0 == exist ) 1543 if ( 0 == exist )
1544 { 1544 {
1545 info[fillIndex++].index = sourceIndex; 1545 info[fillIndex++].index = sourceIndex;
1546 } 1546 }
1547 } 1547 }
1548 1548
1549 // clear marks 1549 // clear marks
1550 for ( i = 0; i!= VERTEXCACHE_ELEMENT; ++i ) 1550 for ( i = 0; i!= VERTEXCACHE_ELEMENT; ++i )
1551 { 1551 {
1552 VertexCache.info[i].hit = 0; 1552 VertexCache.info[i].hit = 0;
1553 } 1553 }
1554 1554
1555 // mark all existing 1555 // mark all existing
1556 for ( i = 0; i!= fillIndex; ++i ) 1556 for ( i = 0; i!= fillIndex; ++i )
1557 { 1557 {
1558 for ( dIndex = 0; dIndex < VERTEXCACHE_ELEMENT; ++dIndex ) 1558 for ( dIndex = 0; dIndex < VERTEXCACHE_ELEMENT; ++dIndex )
1559 { 1559 {
1560 if ( VertexCache.info[ dIndex ].index == info[i].index ) 1560 if ( VertexCache.info[ dIndex ].index == info[i].index )
1561 { 1561 {
1562 info[i].hit = dIndex; 1562 info[i].hit = dIndex;
1563 VertexCache.info[ dIndex ].hit = 1; 1563 VertexCache.info[ dIndex ].hit = 1;
1564 break; 1564 break;
1565 } 1565 }
1566 } 1566 }
1567 } 1567 }
1568 1568
1569 // fill new 1569 // fill new
1570 for ( i = 0; i!= fillIndex; ++i ) 1570 for ( i = 0; i!= fillIndex; ++i )
1571 { 1571 {
1572 if ( info[i].hit != VERTEXCACHE_MISS ) 1572 if ( info[i].hit != VERTEXCACHE_MISS )
1573 continue; 1573 continue;
1574 1574
1575 for ( dIndex = 0; dIndex < VERTEXCACHE_ELEMENT; ++dIndex ) 1575 for ( dIndex = 0; dIndex < VERTEXCACHE_ELEMENT; ++dIndex )
1576 { 1576 {
1577 if ( 0 == VertexCache.info[dIndex].hit ) 1577 if ( 0 == VertexCache.info[dIndex].hit )
1578 { 1578 {
1579 VertexCache_fill ( info[i].index, dIndex ); 1579 VertexCache_fill ( info[i].index, dIndex );
1580 VertexCache.info[dIndex].hit += 1; 1580 VertexCache.info[dIndex].hit += 1;
1581 info[i].hit = dIndex; 1581 info[i].hit = dIndex;
1582 break; 1582 break;
1583 } 1583 }
1584 } 1584 }
1585 } 1585 }
1586 } 1586 }
1587 1587
1588 const u32 i0 = core::if_c_a_else_0 ( VertexCache.pType != scene::EPT_TRIANGLE_FAN, VertexCache.indicesRun ); 1588 const u32 i0 = core::if_c_a_else_0 ( VertexCache.pType != scene::EPT_TRIANGLE_FAN, VertexCache.indicesRun );
1589 1589
1590 switch ( VertexCache.iType ) 1590 switch ( VertexCache.iType )
1591 { 1591 {
1592 case 1: 1592 case 1:
1593 { 1593 {
1594 const u16 *p = (const u16 *) VertexCache.indices; 1594 const u16 *p = (const u16 *) VertexCache.indices;
1595 face[0] = VertexCache_getVertex ( p[ i0 ] ); 1595 face[0] = VertexCache_getVertex ( p[ i0 ] );
1596 face[1] = VertexCache_getVertex ( p[ VertexCache.indicesRun + 1] ); 1596 face[1] = VertexCache_getVertex ( p[ VertexCache.indicesRun + 1] );
1597 face[2] = VertexCache_getVertex ( p[ VertexCache.indicesRun + 2] ); 1597 face[2] = VertexCache_getVertex ( p[ VertexCache.indicesRun + 2] );
1598 } 1598 }
1599 break; 1599 break;
1600 1600
1601 case 2: 1601 case 2:
1602 { 1602 {
1603 const u32 *p = (const u32 *) VertexCache.indices; 1603 const u32 *p = (const u32 *) VertexCache.indices;
1604 face[0] = VertexCache_getVertex ( p[ i0 ] ); 1604 face[0] = VertexCache_getVertex ( p[ i0 ] );
1605 face[1] = VertexCache_getVertex ( p[ VertexCache.indicesRun + 1] ); 1605 face[1] = VertexCache_getVertex ( p[ VertexCache.indicesRun + 1] );
1606 face[2] = VertexCache_getVertex ( p[ VertexCache.indicesRun + 2] ); 1606 face[2] = VertexCache_getVertex ( p[ VertexCache.indicesRun + 2] );
1607 } 1607 }
1608 break; 1608 break;
1609 1609
1610 case 4: 1610 case 4:
1611 face[0] = VertexCache_getVertex ( VertexCache.indicesRun + 0 ); 1611 face[0] = VertexCache_getVertex ( VertexCache.indicesRun + 0 );
1612 face[1] = VertexCache_getVertex ( VertexCache.indicesRun + 1 ); 1612 face[1] = VertexCache_getVertex ( VertexCache.indicesRun + 1 );
1613 face[2] = VertexCache_getVertex ( VertexCache.indicesRun + 2 ); 1613 face[2] = VertexCache_getVertex ( VertexCache.indicesRun + 2 );
1614 break; 1614 break;
1615 default: 1615 default:
1616 face[0] = face[1] = face[2] = VertexCache_getVertex(VertexCache.indicesRun + 0); 1616 face[0] = face[1] = face[2] = VertexCache_getVertex(VertexCache.indicesRun + 0);
1617 break; 1617 break;
1618 } 1618 }
1619 1619
1620 VertexCache.indicesRun += VertexCache.primitivePitch; 1620 VertexCache.indicesRun += VertexCache.primitivePitch;
1621} 1621}
1622 1622
1623/*! 1623/*!
1624*/ 1624*/
1625REALINLINE void CBurningVideoDriver::VertexCache_getbypass ( s4DVertex ** face ) 1625REALINLINE void CBurningVideoDriver::VertexCache_getbypass ( s4DVertex ** face )
1626{ 1626{
1627 const u32 i0 = core::if_c_a_else_0 ( VertexCache.pType != scene::EPT_TRIANGLE_FAN, VertexCache.indicesRun ); 1627 const u32 i0 = core::if_c_a_else_0 ( VertexCache.pType != scene::EPT_TRIANGLE_FAN, VertexCache.indicesRun );
1628 1628
1629 if ( VertexCache.iType == 1 ) 1629 if ( VertexCache.iType == 1 )
1630 { 1630 {
1631 const u16 *p = (const u16 *) VertexCache.indices; 1631 const u16 *p = (const u16 *) VertexCache.indices;
1632 VertexCache_fill ( p[ i0 ], 0 ); 1632 VertexCache_fill ( p[ i0 ], 0 );
1633 VertexCache_fill ( p[ VertexCache.indicesRun + 1], 1 ); 1633 VertexCache_fill ( p[ VertexCache.indicesRun + 1], 1 );
1634 VertexCache_fill ( p[ VertexCache.indicesRun + 2], 2 ); 1634 VertexCache_fill ( p[ VertexCache.indicesRun + 2], 2 );
1635 } 1635 }
1636 else 1636 else
1637 { 1637 {
1638 const u32 *p = (const u32 *) VertexCache.indices; 1638 const u32 *p = (const u32 *) VertexCache.indices;
1639 VertexCache_fill ( p[ i0 ], 0 ); 1639 VertexCache_fill ( p[ i0 ], 0 );
1640 VertexCache_fill ( p[ VertexCache.indicesRun + 1], 1 ); 1640 VertexCache_fill ( p[ VertexCache.indicesRun + 1], 1 );
1641 VertexCache_fill ( p[ VertexCache.indicesRun + 2], 2 ); 1641 VertexCache_fill ( p[ VertexCache.indicesRun + 2], 2 );
1642 } 1642 }
1643 1643
1644 VertexCache.indicesRun += VertexCache.primitivePitch; 1644 VertexCache.indicesRun += VertexCache.primitivePitch;
1645 1645
1646 face[0] = (s4DVertex *) ( (u8*) VertexCache.mem.data + ( 0 << ( SIZEOF_SVERTEX_LOG2 + 1 ) ) ); 1646 face[0] = (s4DVertex *) ( (u8*) VertexCache.mem.data + ( 0 << ( SIZEOF_SVERTEX_LOG2 + 1 ) ) );
1647 face[1] = (s4DVertex *) ( (u8*) VertexCache.mem.data + ( 1 << ( SIZEOF_SVERTEX_LOG2 + 1 ) ) ); 1647 face[1] = (s4DVertex *) ( (u8*) VertexCache.mem.data + ( 1 << ( SIZEOF_SVERTEX_LOG2 + 1 ) ) );
1648 face[2] = (s4DVertex *) ( (u8*) VertexCache.mem.data + ( 2 << ( SIZEOF_SVERTEX_LOG2 + 1 ) ) ); 1648 face[2] = (s4DVertex *) ( (u8*) VertexCache.mem.data + ( 2 << ( SIZEOF_SVERTEX_LOG2 + 1 ) ) );
1649 1649
1650} 1650}
1651 1651
1652/*! 1652/*!
1653*/ 1653*/
1654void CBurningVideoDriver::VertexCache_reset ( const void* vertices, u32 vertexCount, 1654void CBurningVideoDriver::VertexCache_reset ( const void* vertices, u32 vertexCount,
1655 const void* indices, u32 primitiveCount, 1655 const void* indices, u32 primitiveCount,
1656 E_VERTEX_TYPE vType, 1656 E_VERTEX_TYPE vType,
1657 scene::E_PRIMITIVE_TYPE pType, 1657 scene::E_PRIMITIVE_TYPE pType,
1658 E_INDEX_TYPE iType) 1658 E_INDEX_TYPE iType)
1659{ 1659{
1660 VertexCache.vertices = vertices; 1660 VertexCache.vertices = vertices;
1661 VertexCache.vertexCount = vertexCount; 1661 VertexCache.vertexCount = vertexCount;
1662 1662
1663 VertexCache.indices = indices; 1663 VertexCache.indices = indices;
1664 VertexCache.indicesIndex = 0; 1664 VertexCache.indicesIndex = 0;
1665 VertexCache.indicesRun = 0; 1665 VertexCache.indicesRun = 0;
1666 1666
1667 if ( Material.org.MaterialType == video::EMT_REFLECTION_2_LAYER ) 1667 if ( Material.org.MaterialType == video::EMT_REFLECTION_2_LAYER )
1668 VertexCache.vType = 3; 1668 VertexCache.vType = 3;
1669 else 1669 else
1670 VertexCache.vType = vType; 1670 VertexCache.vType = vType;
1671 VertexCache.pType = pType; 1671 VertexCache.pType = pType;
1672 1672
1673 switch ( iType ) 1673 switch ( iType )
1674 { 1674 {
1675 case EIT_16BIT: VertexCache.iType = 1; break; 1675 case EIT_16BIT: VertexCache.iType = 1; break;
1676 case EIT_32BIT: VertexCache.iType = 2; break; 1676 case EIT_32BIT: VertexCache.iType = 2; break;
1677 default: 1677 default:
1678 VertexCache.iType = iType; break; 1678 VertexCache.iType = iType; break;
1679 } 1679 }
1680 1680
1681 switch ( VertexCache.pType ) 1681 switch ( VertexCache.pType )
1682 { 1682 {
1683 // most types here will not work as expected, only triangles/triangle_fan 1683 // most types here will not work as expected, only triangles/triangle_fan
1684 // is known to work. 1684 // is known to work.
1685 case scene::EPT_POINTS: 1685 case scene::EPT_POINTS:
1686 VertexCache.indexCount = primitiveCount; 1686 VertexCache.indexCount = primitiveCount;
1687 VertexCache.primitivePitch = 1; 1687 VertexCache.primitivePitch = 1;
1688 break; 1688 break;
1689 case scene::EPT_LINE_STRIP: 1689 case scene::EPT_LINE_STRIP:
1690 VertexCache.indexCount = primitiveCount+1; 1690 VertexCache.indexCount = primitiveCount+1;
1691 VertexCache.primitivePitch = 1; 1691 VertexCache.primitivePitch = 1;
1692 break; 1692 break;
1693 case scene::EPT_LINE_LOOP: 1693 case scene::EPT_LINE_LOOP:
1694 VertexCache.indexCount = primitiveCount+1; 1694 VertexCache.indexCount = primitiveCount+1;
1695 VertexCache.primitivePitch = 1; 1695 VertexCache.primitivePitch = 1;
1696 break; 1696 break;
1697 case scene::EPT_LINES: 1697 case scene::EPT_LINES:
1698 VertexCache.indexCount = 2*primitiveCount; 1698 VertexCache.indexCount = 2*primitiveCount;
1699 VertexCache.primitivePitch = 2; 1699 VertexCache.primitivePitch = 2;
1700 break; 1700 break;
1701 case scene::EPT_TRIANGLE_STRIP: 1701 case scene::EPT_TRIANGLE_STRIP:
1702 VertexCache.indexCount = primitiveCount+2; 1702 VertexCache.indexCount = primitiveCount+2;
1703 VertexCache.primitivePitch = 1; 1703 VertexCache.primitivePitch = 1;
1704 break; 1704 break;
1705 case scene::EPT_TRIANGLES: 1705 case scene::EPT_TRIANGLES:
1706 VertexCache.indexCount = primitiveCount + primitiveCount + primitiveCount; 1706 VertexCache.indexCount = primitiveCount + primitiveCount + primitiveCount;
1707 VertexCache.primitivePitch = 3; 1707 VertexCache.primitivePitch = 3;
1708 break; 1708 break;
1709 case scene::EPT_TRIANGLE_FAN: 1709 case scene::EPT_TRIANGLE_FAN:
1710 VertexCache.indexCount = primitiveCount + 2; 1710 VertexCache.indexCount = primitiveCount + 2;
1711 VertexCache.primitivePitch = 1; 1711 VertexCache.primitivePitch = 1;
1712 break; 1712 break;
1713 case scene::EPT_QUAD_STRIP: 1713 case scene::EPT_QUAD_STRIP:
1714 VertexCache.indexCount = 2*primitiveCount + 2; 1714 VertexCache.indexCount = 2*primitiveCount + 2;
1715 VertexCache.primitivePitch = 2; 1715 VertexCache.primitivePitch = 2;
1716 break; 1716 break;
1717 case scene::EPT_QUADS: 1717 case scene::EPT_QUADS:
1718 VertexCache.indexCount = 4*primitiveCount; 1718 VertexCache.indexCount = 4*primitiveCount;
1719 VertexCache.primitivePitch = 4; 1719 VertexCache.primitivePitch = 4;
1720 break; 1720 break;
1721 case scene::EPT_POLYGON: 1721 case scene::EPT_POLYGON:
1722 VertexCache.indexCount = primitiveCount+1; 1722 VertexCache.indexCount = primitiveCount+1;
1723 VertexCache.primitivePitch = 1; 1723 VertexCache.primitivePitch = 1;
1724 break; 1724 break;
1725 case scene::EPT_POINT_SPRITES: 1725 case scene::EPT_POINT_SPRITES:
1726 VertexCache.indexCount = primitiveCount; 1726 VertexCache.indexCount = primitiveCount;
1727 VertexCache.primitivePitch = 1; 1727 VertexCache.primitivePitch = 1;
1728 break; 1728 break;
1729 } 1729 }
1730 1730
1731 irr::memset32 ( VertexCache.info, VERTEXCACHE_MISS, sizeof ( VertexCache.info ) ); 1731 irr::memset32 ( VertexCache.info, VERTEXCACHE_MISS, sizeof ( VertexCache.info ) );
1732} 1732}
1733 1733
1734 1734
1735void CBurningVideoDriver::drawVertexPrimitiveList(const void* vertices, u32 vertexCount, 1735void CBurningVideoDriver::drawVertexPrimitiveList(const void* vertices, u32 vertexCount,
1736 const void* indexList, u32 primitiveCount, 1736 const void* indexList, u32 primitiveCount,
1737 E_VERTEX_TYPE vType, scene::E_PRIMITIVE_TYPE pType, E_INDEX_TYPE iType) 1737 E_VERTEX_TYPE vType, scene::E_PRIMITIVE_TYPE pType, E_INDEX_TYPE iType)
1738 1738
1739{ 1739{
1740 if (!checkPrimitiveCount(primitiveCount)) 1740 if (!checkPrimitiveCount(primitiveCount))
1741 return; 1741 return;
1742 1742
1743 CNullDriver::drawVertexPrimitiveList(vertices, vertexCount, indexList, primitiveCount, vType, pType, iType); 1743 CNullDriver::drawVertexPrimitiveList(vertices, vertexCount, indexList, primitiveCount, vType, pType, iType);
1744 1744
1745 // These calls would lead to crashes due to wrong index usage. 1745 // These calls would lead to crashes due to wrong index usage.
1746 // The vertex cache needs to be rewritten for these primitives. 1746 // The vertex cache needs to be rewritten for these primitives.
1747 if (pType==scene::EPT_POINTS || pType==scene::EPT_LINE_STRIP || 1747 if (pType==scene::EPT_POINTS || pType==scene::EPT_LINE_STRIP ||
1748 pType==scene::EPT_LINE_LOOP || pType==scene::EPT_LINES || pType==scene::EPT_POLYGON || 1748 pType==scene::EPT_LINE_LOOP || pType==scene::EPT_LINES || pType==scene::EPT_POLYGON ||
1749 pType==scene::EPT_POINT_SPRITES) 1749 pType==scene::EPT_POINT_SPRITES)
1750 return; 1750 return;
1751 1751
1752 if ( 0 == CurrentShader ) 1752 if ( 0 == CurrentShader )
1753 return; 1753 return;
1754 1754
1755 VertexCache_reset ( vertices, vertexCount, indexList, primitiveCount, vType, pType, iType ); 1755 VertexCache_reset ( vertices, vertexCount, indexList, primitiveCount, vType, pType, iType );
1756 1756
1757 const s4DVertex * face[3]; 1757 const s4DVertex * face[3];
1758 1758
1759 f32 dc_area; 1759 f32 dc_area;
1760 s32 lodLevel; 1760 s32 lodLevel;
1761 u32 i; 1761 u32 i;
1762 u32 g; 1762 u32 g;
1763 u32 m; 1763 u32 m;
1764 video::CSoftwareTexture2* tex; 1764 video::CSoftwareTexture2* tex;
1765 1765
1766 for ( i = 0; i < (u32) primitiveCount; ++i ) 1766 for ( i = 0; i < (u32) primitiveCount; ++i )
1767 { 1767 {
1768 VertexCache_get(face); 1768 VertexCache_get(face);
1769 1769
1770 // if fully outside or outside on same side 1770 // if fully outside or outside on same side
1771 if ( ( (face[0]->flag | face[1]->flag | face[2]->flag) & VERTEX4D_CLIPMASK ) 1771 if ( ( (face[0]->flag | face[1]->flag | face[2]->flag) & VERTEX4D_CLIPMASK )
1772 != VERTEX4D_INSIDE 1772 != VERTEX4D_INSIDE
1773 ) 1773 )
1774 continue; 1774 continue;
1775 1775
1776 // if fully inside 1776 // if fully inside
1777 if ( ( face[0]->flag & face[1]->flag & face[2]->flag & VERTEX4D_CLIPMASK ) == VERTEX4D_INSIDE ) 1777 if ( ( face[0]->flag & face[1]->flag & face[2]->flag & VERTEX4D_CLIPMASK ) == VERTEX4D_INSIDE )
1778 { 1778 {
1779 dc_area = screenarea2 ( face ); 1779 dc_area = screenarea2 ( face );
1780 if ( Material.org.BackfaceCulling && F32_LOWER_EQUAL_0( dc_area ) ) 1780 if ( Material.org.BackfaceCulling && F32_LOWER_EQUAL_0( dc_area ) )
1781 continue; 1781 continue;
1782 else 1782 else
1783 if ( Material.org.FrontfaceCulling && F32_GREATER_EQUAL_0( dc_area ) ) 1783 if ( Material.org.FrontfaceCulling && F32_GREATER_EQUAL_0( dc_area ) )
1784 continue; 1784 continue;
1785 1785
1786 // select mipmap 1786 // select mipmap
1787 dc_area = core::reciprocal ( dc_area ); 1787 dc_area = core::reciprocal ( dc_area );
1788 for ( m = 0; m != vSize[VertexCache.vType].TexSize; ++m ) 1788 for ( m = 0; m != vSize[VertexCache.vType].TexSize; ++m )
1789 { 1789 {
1790 if ( 0 == (tex = MAT_TEXTURE ( m )) ) 1790 if ( 0 == (tex = MAT_TEXTURE ( m )) )
1791 { 1791 {
1792 CurrentShader->setTextureParam(m, 0, 0); 1792 CurrentShader->setTextureParam(m, 0, 0);
1793 continue; 1793 continue;
1794 } 1794 }
1795 1795
1796 lodLevel = s32_log2_f32 ( texelarea2 ( face, m ) * dc_area ); 1796 lodLevel = s32_log2_f32 ( texelarea2 ( face, m ) * dc_area );
1797 CurrentShader->setTextureParam(m, tex, lodLevel ); 1797 CurrentShader->setTextureParam(m, tex, lodLevel );
1798 select_polygon_mipmap2 ( (s4DVertex**) face, m, tex->getSize() ); 1798 select_polygon_mipmap2 ( (s4DVertex**) face, m, tex->getSize() );
1799 } 1799 }
1800 1800
1801 // rasterize 1801 // rasterize
1802 CurrentShader->drawTriangle ( face[0] + 1, face[1] + 1, face[2] + 1 ); 1802 CurrentShader->drawTriangle ( face[0] + 1, face[1] + 1, face[2] + 1 );
1803 continue; 1803 continue;
1804 } 1804 }
1805 1805
1806 // else if not complete inside clipping necessary 1806 // else if not complete inside clipping necessary
1807 irr::memcpy32_small ( ( (u8*) CurrentOut.data + ( 0 << ( SIZEOF_SVERTEX_LOG2 + 1 ) ) ), face[0], SIZEOF_SVERTEX * 2 ); 1807 irr::memcpy32_small ( ( (u8*) CurrentOut.data + ( 0 << ( SIZEOF_SVERTEX_LOG2 + 1 ) ) ), face[0], SIZEOF_SVERTEX * 2 );
1808 irr::memcpy32_small ( ( (u8*) CurrentOut.data + ( 1 << ( SIZEOF_SVERTEX_LOG2 + 1 ) ) ), face[1], SIZEOF_SVERTEX * 2 ); 1808 irr::memcpy32_small ( ( (u8*) CurrentOut.data + ( 1 << ( SIZEOF_SVERTEX_LOG2 + 1 ) ) ), face[1], SIZEOF_SVERTEX * 2 );
1809 irr::memcpy32_small ( ( (u8*) CurrentOut.data + ( 2 << ( SIZEOF_SVERTEX_LOG2 + 1 ) ) ), face[2], SIZEOF_SVERTEX * 2 ); 1809 irr::memcpy32_small ( ( (u8*) CurrentOut.data + ( 2 << ( SIZEOF_SVERTEX_LOG2 + 1 ) ) ), face[2], SIZEOF_SVERTEX * 2 );
1810 1810
1811 const u32 flag = CurrentOut.data->flag & VERTEX4D_FORMAT_MASK; 1811 const u32 flag = CurrentOut.data->flag & VERTEX4D_FORMAT_MASK;
1812 1812
1813 for ( g = 0; g != CurrentOut.ElementSize; ++g ) 1813 for ( g = 0; g != CurrentOut.ElementSize; ++g )
1814 { 1814 {
1815 CurrentOut.data[g].flag = flag; 1815 CurrentOut.data[g].flag = flag;
1816 Temp.data[g].flag = flag; 1816 Temp.data[g].flag = flag;
1817 } 1817 }
1818 1818
1819 u32 vOut; 1819 u32 vOut;
1820 vOut = clipToFrustum ( CurrentOut.data, Temp.data, 3 ); 1820 vOut = clipToFrustum ( CurrentOut.data, Temp.data, 3 );
1821 if ( vOut < 3 ) 1821 if ( vOut < 3 )
1822 continue; 1822 continue;
1823 1823
1824 vOut <<= 1; 1824 vOut <<= 1;
1825 1825
1826 // to DC Space, project homogenous vertex 1826 // to DC Space, project homogenous vertex
1827 ndc_2_dc_and_project ( CurrentOut.data + 1, CurrentOut.data, vOut ); 1827 ndc_2_dc_and_project ( CurrentOut.data + 1, CurrentOut.data, vOut );
1828 1828
1829/* 1829/*
1830 // TODO: don't stick on 32 Bit Pointer 1830 // TODO: don't stick on 32 Bit Pointer
1831 #define PointerAsValue(x) ( (u32) (u32*) (x) ) 1831 #define PointerAsValue(x) ( (u32) (u32*) (x) )
1832 1832
1833 // if not complete inside clipping necessary 1833 // if not complete inside clipping necessary
1834 if ( ( test & VERTEX4D_INSIDE ) != VERTEX4D_INSIDE ) 1834 if ( ( test & VERTEX4D_INSIDE ) != VERTEX4D_INSIDE )
1835 { 1835 {
1836 u32 v[2] = { PointerAsValue ( Temp ) , PointerAsValue ( CurrentOut ) }; 1836 u32 v[2] = { PointerAsValue ( Temp ) , PointerAsValue ( CurrentOut ) };
1837 for ( g = 0; g != 6; ++g ) 1837 for ( g = 0; g != 6; ++g )
1838 { 1838 {
1839 vOut = clipToHyperPlane ( (s4DVertex*) v[0], (s4DVertex*) v[1], vOut, NDCPlane[g] ); 1839 vOut = clipToHyperPlane ( (s4DVertex*) v[0], (s4DVertex*) v[1], vOut, NDCPlane[g] );
1840 if ( vOut < 3 ) 1840 if ( vOut < 3 )
1841 break; 1841 break;
1842 1842
1843 v[0] ^= v[1]; 1843 v[0] ^= v[1];
1844 v[1] ^= v[0]; 1844 v[1] ^= v[0];
1845 v[0] ^= v[1]; 1845 v[0] ^= v[1];
1846 } 1846 }
1847 1847
1848 if ( vOut < 3 ) 1848 if ( vOut < 3 )
1849 continue; 1849 continue;
1850 1850
1851 } 1851 }
1852*/ 1852*/
1853 1853
1854 // check 2d backface culling on first 1854 // check 2d backface culling on first
1855 dc_area = screenarea ( CurrentOut.data ); 1855 dc_area = screenarea ( CurrentOut.data );
1856 if ( Material.org.BackfaceCulling && F32_LOWER_EQUAL_0 ( dc_area ) ) 1856 if ( Material.org.BackfaceCulling && F32_LOWER_EQUAL_0 ( dc_area ) )
1857 continue; 1857 continue;
1858 else if ( Material.org.FrontfaceCulling && F32_GREATER_EQUAL_0( dc_area ) ) 1858 else if ( Material.org.FrontfaceCulling && F32_GREATER_EQUAL_0( dc_area ) )
1859 continue; 1859 continue;
1860 1860
1861 // select mipmap 1861 // select mipmap
1862 dc_area = core::reciprocal ( dc_area ); 1862 dc_area = core::reciprocal ( dc_area );
1863 for ( m = 0; m != vSize[VertexCache.vType].TexSize; ++m ) 1863 for ( m = 0; m != vSize[VertexCache.vType].TexSize; ++m )
1864 { 1864 {
1865 if ( 0 == (tex = MAT_TEXTURE ( m )) ) 1865 if ( 0 == (tex = MAT_TEXTURE ( m )) )
1866 { 1866 {
1867 CurrentShader->setTextureParam(m, 0, 0); 1867 CurrentShader->setTextureParam(m, 0, 0);
1868 continue; 1868 continue;
1869 } 1869 }
1870 1870
1871 lodLevel = s32_log2_f32 ( texelarea ( CurrentOut.data, m ) * dc_area ); 1871 lodLevel = s32_log2_f32 ( texelarea ( CurrentOut.data, m ) * dc_area );
1872 CurrentShader->setTextureParam(m, tex, lodLevel ); 1872 CurrentShader->setTextureParam(m, tex, lodLevel );
1873 select_polygon_mipmap ( CurrentOut.data, vOut, m, tex->getSize() ); 1873 select_polygon_mipmap ( CurrentOut.data, vOut, m, tex->getSize() );
1874 } 1874 }
1875 1875
1876 1876
1877 // re-tesselate ( triangle-fan, 0-1-2,0-2-3.. ) 1877 // re-tesselate ( triangle-fan, 0-1-2,0-2-3.. )
1878 for ( g = 0; g <= vOut - 6; g += 2 ) 1878 for ( g = 0; g <= vOut - 6; g += 2 )
1879 { 1879 {
1880 // rasterize 1880 // rasterize
1881 CurrentShader->drawTriangle ( CurrentOut.data + 0 + 1, 1881 CurrentShader->drawTriangle ( CurrentOut.data + 0 + 1,
1882 CurrentOut.data + g + 3, 1882 CurrentOut.data + g + 3,
1883 CurrentOut.data + g + 5); 1883 CurrentOut.data + g + 5);
1884 } 1884 }
1885 1885
1886 } 1886 }
1887 1887
1888 // dump statistics 1888 // dump statistics
1889/* 1889/*
1890 char buf [64]; 1890 char buf [64];
1891 sprintf ( buf,"VCount:%d PCount:%d CacheMiss: %d", 1891 sprintf ( buf,"VCount:%d PCount:%d CacheMiss: %d",
1892 vertexCount, primitiveCount, 1892 vertexCount, primitiveCount,
1893 VertexCache.CacheMiss 1893 VertexCache.CacheMiss
1894 ); 1894 );
1895 os::Printer::log( buf ); 1895 os::Printer::log( buf );
1896*/ 1896*/
1897 1897
1898} 1898}
1899 1899
1900 1900
1901//! Sets the dynamic ambient light color. The default color is 1901//! Sets the dynamic ambient light color. The default color is
1902//! (0,0,0,0) which means it is dark. 1902//! (0,0,0,0) which means it is dark.
1903//! \param color: New color of the ambient light. 1903//! \param color: New color of the ambient light.
1904void CBurningVideoDriver::setAmbientLight(const SColorf& color) 1904void CBurningVideoDriver::setAmbientLight(const SColorf& color)
1905{ 1905{
1906 LightSpace.Global_AmbientLight.setColorf ( color ); 1906 LightSpace.Global_AmbientLight.setColorf ( color );
1907} 1907}
1908 1908
1909 1909
1910//! adds a dynamic light 1910//! adds a dynamic light
1911s32 CBurningVideoDriver::addDynamicLight(const SLight& dl) 1911s32 CBurningVideoDriver::addDynamicLight(const SLight& dl)
1912{ 1912{
1913 (void) CNullDriver::addDynamicLight( dl ); 1913 (void) CNullDriver::addDynamicLight( dl );
1914 1914
1915 SBurningShaderLight l; 1915 SBurningShaderLight l;
1916// l.org = dl; 1916// l.org = dl;
1917 l.Type = dl.Type; 1917 l.Type = dl.Type;
1918 l.LightIsOn = true; 1918 l.LightIsOn = true;
1919 1919
1920 l.AmbientColor.setColorf ( dl.AmbientColor ); 1920 l.AmbientColor.setColorf ( dl.AmbientColor );
1921 l.DiffuseColor.setColorf ( dl.DiffuseColor ); 1921 l.DiffuseColor.setColorf ( dl.DiffuseColor );
1922 l.SpecularColor.setColorf ( dl.SpecularColor ); 1922 l.SpecularColor.setColorf ( dl.SpecularColor );
1923 1923
1924 switch ( dl.Type ) 1924 switch ( dl.Type )
1925 { 1925 {
1926 case video::ELT_DIRECTIONAL: 1926 case video::ELT_DIRECTIONAL:
1927 l.pos.x = -dl.Direction.X; 1927 l.pos.x = -dl.Direction.X;
1928 l.pos.y = -dl.Direction.Y; 1928 l.pos.y = -dl.Direction.Y;
1929 l.pos.z = -dl.Direction.Z; 1929 l.pos.z = -dl.Direction.Z;
1930 l.pos.w = 1.f; 1930 l.pos.w = 1.f;
1931 break; 1931 break;
1932 case ELT_POINT: 1932 case ELT_POINT:
1933 case ELT_SPOT: 1933 case ELT_SPOT:
1934 LightSpace.Flags |= POINTLIGHT; 1934 LightSpace.Flags |= POINTLIGHT;
1935 l.pos.x = dl.Position.X; 1935 l.pos.x = dl.Position.X;
1936 l.pos.y = dl.Position.Y; 1936 l.pos.y = dl.Position.Y;
1937 l.pos.z = dl.Position.Z; 1937 l.pos.z = dl.Position.Z;
1938 l.pos.w = 1.f; 1938 l.pos.w = 1.f;
1939/* 1939/*
1940 l.radius = (1.f / dl.Attenuation.Y) * (1.f / dl.Attenuation.Y); 1940 l.radius = (1.f / dl.Attenuation.Y) * (1.f / dl.Attenuation.Y);
1941 l.constantAttenuation = dl.Attenuation.X; 1941 l.constantAttenuation = dl.Attenuation.X;
1942 l.linearAttenuation = dl.Attenuation.Y; 1942 l.linearAttenuation = dl.Attenuation.Y;
1943 l.quadraticAttenuation = dl.Attenuation.Z; 1943 l.quadraticAttenuation = dl.Attenuation.Z;
1944*/ 1944*/
1945 l.radius = dl.Radius * dl.Radius; 1945 l.radius = dl.Radius * dl.Radius;
1946 l.constantAttenuation = dl.Attenuation.X; 1946 l.constantAttenuation = dl.Attenuation.X;
1947 l.linearAttenuation = 1.f / dl.Radius; 1947 l.linearAttenuation = 1.f / dl.Radius;
1948 l.quadraticAttenuation = dl.Attenuation.Z; 1948 l.quadraticAttenuation = dl.Attenuation.Z;
1949 1949
1950 break; 1950 break;
1951 default: 1951 default:
1952 break; 1952 break;
1953 } 1953 }
1954 1954
1955 LightSpace.Light.push_back ( l ); 1955 LightSpace.Light.push_back ( l );
1956 return LightSpace.Light.size() - 1; 1956 return LightSpace.Light.size() - 1;
1957} 1957}
1958 1958
1959//! Turns a dynamic light on or off 1959//! Turns a dynamic light on or off
1960void CBurningVideoDriver::turnLightOn(s32 lightIndex, bool turnOn) 1960void CBurningVideoDriver::turnLightOn(s32 lightIndex, bool turnOn)
1961{ 1961{
1962 if(lightIndex > -1 && lightIndex < (s32)LightSpace.Light.size()) 1962 if(lightIndex > -1 && lightIndex < (s32)LightSpace.Light.size())
1963 { 1963 {
1964 LightSpace.Light[lightIndex].LightIsOn = turnOn; 1964 LightSpace.Light[lightIndex].LightIsOn = turnOn;
1965 } 1965 }
1966} 1966}
1967 1967
1968//! deletes all dynamic lights there are 1968//! deletes all dynamic lights there are
1969void CBurningVideoDriver::deleteAllDynamicLights() 1969void CBurningVideoDriver::deleteAllDynamicLights()
1970{ 1970{
1971 LightSpace.reset (); 1971 LightSpace.reset ();
1972 CNullDriver::deleteAllDynamicLights(); 1972 CNullDriver::deleteAllDynamicLights();
1973 1973
1974} 1974}
1975 1975
1976//! returns the maximal amount of dynamic lights the device can handle 1976//! returns the maximal amount of dynamic lights the device can handle
1977u32 CBurningVideoDriver::getMaximalDynamicLightAmount() const 1977u32 CBurningVideoDriver::getMaximalDynamicLightAmount() const
1978{ 1978{
1979 return 8; 1979 return 8;
1980} 1980}
1981 1981
1982 1982
1983//! sets a material 1983//! sets a material
1984void CBurningVideoDriver::setMaterial(const SMaterial& material) 1984void CBurningVideoDriver::setMaterial(const SMaterial& material)
1985{ 1985{
1986 Material.org = material; 1986 Material.org = material;
1987 1987
1988#ifdef SOFTWARE_DRIVER_2_TEXTURE_TRANSFORM 1988#ifdef SOFTWARE_DRIVER_2_TEXTURE_TRANSFORM
1989 for (u32 i = 0; i < 2; ++i) 1989 for (u32 i = 0; i < 2; ++i)
1990 { 1990 {
1991 setTransform((E_TRANSFORMATION_STATE) (ETS_TEXTURE_0 + i), 1991 setTransform((E_TRANSFORMATION_STATE) (ETS_TEXTURE_0 + i),
1992 material.getTextureMatrix(i)); 1992 material.getTextureMatrix(i));
1993 } 1993 }
1994#endif 1994#endif
1995 1995
1996#ifdef SOFTWARE_DRIVER_2_LIGHTING 1996#ifdef SOFTWARE_DRIVER_2_LIGHTING
1997 Material.AmbientColor.setR8G8B8 ( Material.org.AmbientColor.color ); 1997 Material.AmbientColor.setR8G8B8 ( Material.org.AmbientColor.color );
1998 Material.DiffuseColor.setR8G8B8 ( Material.org.DiffuseColor.color ); 1998 Material.DiffuseColor.setR8G8B8 ( Material.org.DiffuseColor.color );
1999 Material.EmissiveColor.setR8G8B8 ( Material.org.EmissiveColor.color ); 1999 Material.EmissiveColor.setR8G8B8 ( Material.org.EmissiveColor.color );
2000 Material.SpecularColor.setR8G8B8 ( Material.org.SpecularColor.color ); 2000 Material.SpecularColor.setR8G8B8 ( Material.org.SpecularColor.color );
2001 2001
2002 core::setbit_cond ( LightSpace.Flags, Material.org.Shininess != 0.f, SPECULAR ); 2002 core::setbit_cond ( LightSpace.Flags, Material.org.Shininess != 0.f, SPECULAR );
2003 core::setbit_cond ( LightSpace.Flags, Material.org.FogEnable, FOG ); 2003 core::setbit_cond ( LightSpace.Flags, Material.org.FogEnable, FOG );
2004 core::setbit_cond ( LightSpace.Flags, Material.org.NormalizeNormals, NORMALIZE ); 2004 core::setbit_cond ( LightSpace.Flags, Material.org.NormalizeNormals, NORMALIZE );
2005#endif 2005#endif
2006 2006
2007 setCurrentShader(); 2007 setCurrentShader();
2008} 2008}
2009 2009
2010 2010
2011/*! 2011/*!
2012 Camera Position in World Space 2012 Camera Position in World Space
2013*/ 2013*/
2014void CBurningVideoDriver::getCameraPosWorldSpace () 2014void CBurningVideoDriver::getCameraPosWorldSpace ()
2015{ 2015{
2016 Transformation[ETS_VIEW_INVERSE] = Transformation[ ETS_VIEW ]; 2016 Transformation[ETS_VIEW_INVERSE] = Transformation[ ETS_VIEW ];
2017 Transformation[ETS_VIEW_INVERSE].makeInverse (); 2017 Transformation[ETS_VIEW_INVERSE].makeInverse ();
2018 TransformationFlag[ETS_VIEW_INVERSE] = 0; 2018 TransformationFlag[ETS_VIEW_INVERSE] = 0;
2019 2019
2020 const f32 *M = Transformation[ETS_VIEW_INVERSE].pointer (); 2020 const f32 *M = Transformation[ETS_VIEW_INVERSE].pointer ();
2021 2021
2022 /* The viewpoint is at (0., 0., 0.) in eye space. 2022 /* The viewpoint is at (0., 0., 0.) in eye space.
2023 Turning this into a vector [0 0 0 1] and multiply it by 2023 Turning this into a vector [0 0 0 1] and multiply it by
2024 the inverse of the view matrix, the resulting vector is the 2024 the inverse of the view matrix, the resulting vector is the
2025 object space location of the camera. 2025 object space location of the camera.
2026 */ 2026 */
2027 2027
2028 LightSpace.campos.x = M[12]; 2028 LightSpace.campos.x = M[12];
2029 LightSpace.campos.y = M[13]; 2029 LightSpace.campos.y = M[13];
2030 LightSpace.campos.z = M[14]; 2030 LightSpace.campos.z = M[14];
2031 LightSpace.campos.w = 1.f; 2031 LightSpace.campos.w = 1.f;
2032} 2032}
2033 2033
2034void CBurningVideoDriver::getLightPosObjectSpace () 2034void CBurningVideoDriver::getLightPosObjectSpace ()
2035{ 2035{
2036 if ( TransformationFlag[ETS_WORLD] & ETF_IDENTITY ) 2036 if ( TransformationFlag[ETS_WORLD] & ETF_IDENTITY )
2037 { 2037 {
2038 Transformation[ETS_WORLD_INVERSE] = Transformation[ETS_WORLD]; 2038 Transformation[ETS_WORLD_INVERSE] = Transformation[ETS_WORLD];
2039 TransformationFlag[ETS_WORLD_INVERSE] |= ETF_IDENTITY; 2039 TransformationFlag[ETS_WORLD_INVERSE] |= ETF_IDENTITY;
2040 } 2040 }
2041 else 2041 else
2042 { 2042 {
2043 Transformation[ETS_WORLD].getInverse ( Transformation[ETS_WORLD_INVERSE] ); 2043 Transformation[ETS_WORLD].getInverse ( Transformation[ETS_WORLD_INVERSE] );
2044 TransformationFlag[ETS_WORLD_INVERSE] &= ~ETF_IDENTITY; 2044 TransformationFlag[ETS_WORLD_INVERSE] &= ~ETF_IDENTITY;
2045 } 2045 }
2046 2046
2047 for ( u32 i = 0; i < 1 && i < LightSpace.Light.size(); ++i ) 2047 for ( u32 i = 0; i < 1 && i < LightSpace.Light.size(); ++i )
2048 { 2048 {
2049 SBurningShaderLight &l = LightSpace.Light[i]; 2049 SBurningShaderLight &l = LightSpace.Light[i];
2050 2050
2051 Transformation[ETS_WORLD_INVERSE].transformVec3 ( &l.pos_objectspace.x, &l.pos.x ); 2051 Transformation[ETS_WORLD_INVERSE].transformVec3 ( &l.pos_objectspace.x, &l.pos.x );
2052 } 2052 }
2053} 2053}
2054 2054
2055 2055
2056#ifdef SOFTWARE_DRIVER_2_LIGHTING 2056#ifdef SOFTWARE_DRIVER_2_LIGHTING
2057 2057
2058//! Sets the fog mode. 2058//! Sets the fog mode.
2059void CBurningVideoDriver::setFog(SColor color, E_FOG_TYPE fogType, f32 start, 2059void CBurningVideoDriver::setFog(SColor color, E_FOG_TYPE fogType, f32 start,
2060 f32 end, f32 density, bool pixelFog, bool rangeFog) 2060 f32 end, f32 density, bool pixelFog, bool rangeFog)
2061{ 2061{
2062 CNullDriver::setFog(color, fogType, start, end, density, pixelFog, rangeFog); 2062 CNullDriver::setFog(color, fogType, start, end, density, pixelFog, rangeFog);
2063 LightSpace.FogColor.setA8R8G8B8 ( color.color ); 2063 LightSpace.FogColor.setA8R8G8B8 ( color.color );
2064} 2064}
2065 2065
2066/*! 2066/*!
2067 applies lighting model 2067 applies lighting model
2068*/ 2068*/
2069void CBurningVideoDriver::lightVertex ( s4DVertex *dest, u32 vertexargb ) 2069void CBurningVideoDriver::lightVertex ( s4DVertex *dest, u32 vertexargb )
2070{ 2070{
2071 sVec3 dColor; 2071 sVec3 dColor;
2072 2072
2073 dColor = LightSpace.Global_AmbientLight; 2073 dColor = LightSpace.Global_AmbientLight;
2074 dColor.add ( Material.EmissiveColor ); 2074 dColor.add ( Material.EmissiveColor );
2075 2075
2076 if ( Lights.size () == 0 ) 2076 if ( Lights.size () == 0 )
2077 { 2077 {
2078 dColor.saturate( dest->Color[0], vertexargb); 2078 dColor.saturate( dest->Color[0], vertexargb);
2079 return; 2079 return;
2080 } 2080 }
2081 2081
2082 sVec3 ambient; 2082 sVec3 ambient;
2083 sVec3 diffuse; 2083 sVec3 diffuse;
2084 sVec3 specular; 2084 sVec3 specular;
2085 2085
2086 2086
2087 // the universe started in darkness.. 2087 // the universe started in darkness..
2088 ambient.set ( 0.f, 0.f, 0.f ); 2088 ambient.set ( 0.f, 0.f, 0.f );
2089 diffuse.set ( 0.f, 0.f, 0.f ); 2089 diffuse.set ( 0.f, 0.f, 0.f );
2090 specular.set ( 0.f, 0.f, 0.f ); 2090 specular.set ( 0.f, 0.f, 0.f );
2091 2091
2092 2092
2093 u32 i; 2093 u32 i;
2094 f32 dot; 2094 f32 dot;
2095 f32 len; 2095 f32 len;
2096 f32 attenuation; 2096 f32 attenuation;
2097 sVec4 vp; // unit vector vertex to light 2097 sVec4 vp; // unit vector vertex to light
2098 sVec4 lightHalf; // blinn-phong reflection 2098 sVec4 lightHalf; // blinn-phong reflection
2099 2099
2100 for ( i = 0; i!= LightSpace.Light.size (); ++i ) 2100 for ( i = 0; i!= LightSpace.Light.size (); ++i )
2101 { 2101 {
2102 const SBurningShaderLight &light = LightSpace.Light[i]; 2102 const SBurningShaderLight &light = LightSpace.Light[i];
2103 2103
2104 if ( !light.LightIsOn ) 2104 if ( !light.LightIsOn )
2105 continue; 2105 continue;
2106 2106
2107 // accumulate ambient 2107 // accumulate ambient
2108 ambient.add ( light.AmbientColor ); 2108 ambient.add ( light.AmbientColor );
2109 2109
2110 switch ( light.Type ) 2110 switch ( light.Type )
2111 { 2111 {
2112 case video::ELT_SPOT: 2112 case video::ELT_SPOT:
2113 case video::ELT_POINT: 2113 case video::ELT_POINT:
2114 // surface to light 2114 // surface to light
2115 vp.x = light.pos.x - LightSpace.vertex.x; 2115 vp.x = light.pos.x - LightSpace.vertex.x;
2116 vp.y = light.pos.y - LightSpace.vertex.y; 2116 vp.y = light.pos.y - LightSpace.vertex.y;
2117 vp.z = light.pos.z - LightSpace.vertex.z; 2117 vp.z = light.pos.z - LightSpace.vertex.z;
2118 //vp.x = light.pos_objectspace.x - LightSpace.vertex.x; 2118 //vp.x = light.pos_objectspace.x - LightSpace.vertex.x;
2119 //vp.y = light.pos_objectspace.y - LightSpace.vertex.x; 2119 //vp.y = light.pos_objectspace.y - LightSpace.vertex.x;
2120 //vp.z = light.pos_objectspace.z - LightSpace.vertex.x; 2120 //vp.z = light.pos_objectspace.z - LightSpace.vertex.x;
2121 2121
2122 len = vp.get_length_xyz_square(); 2122 len = vp.get_length_xyz_square();
2123 if ( light.radius < len ) 2123 if ( light.radius < len )
2124 continue; 2124 continue;
2125 2125
2126 len = core::reciprocal_squareroot ( len ); 2126 len = core::reciprocal_squareroot ( len );
2127 2127
2128 // build diffuse reflection 2128 // build diffuse reflection
2129 2129
2130 //angle between normal and light vector 2130 //angle between normal and light vector
2131 vp.mul ( len ); 2131 vp.mul ( len );
2132 dot = LightSpace.normal.dot_xyz ( vp ); 2132 dot = LightSpace.normal.dot_xyz ( vp );
2133 if ( dot < 0.f ) 2133 if ( dot < 0.f )
2134 continue; 2134 continue;
2135 2135
2136 attenuation = light.constantAttenuation + ( 1.f - ( len * light.linearAttenuation ) ); 2136 attenuation = light.constantAttenuation + ( 1.f - ( len * light.linearAttenuation ) );
2137 2137
2138 // diffuse component 2138 // diffuse component
2139 diffuse.mulAdd ( light.DiffuseColor, 3.f * dot * attenuation ); 2139 diffuse.mulAdd ( light.DiffuseColor, 3.f * dot * attenuation );
2140 2140
2141 if ( !(LightSpace.Flags & SPECULAR) ) 2141 if ( !(LightSpace.Flags & SPECULAR) )
2142 continue; 2142 continue;
2143 2143
2144 // build specular 2144 // build specular
2145 // surface to view 2145 // surface to view
2146 lightHalf.x = LightSpace.campos.x - LightSpace.vertex.x; 2146 lightHalf.x = LightSpace.campos.x - LightSpace.vertex.x;
2147 lightHalf.y = LightSpace.campos.y - LightSpace.vertex.y; 2147 lightHalf.y = LightSpace.campos.y - LightSpace.vertex.y;
2148 lightHalf.z = LightSpace.campos.z - LightSpace.vertex.z; 2148 lightHalf.z = LightSpace.campos.z - LightSpace.vertex.z;
2149 lightHalf.normalize_xyz(); 2149 lightHalf.normalize_xyz();
2150 lightHalf += vp; 2150 lightHalf += vp;
2151 lightHalf.normalize_xyz(); 2151 lightHalf.normalize_xyz();
2152 2152
2153 // specular 2153 // specular
2154 dot = LightSpace.normal.dot_xyz ( lightHalf ); 2154 dot = LightSpace.normal.dot_xyz ( lightHalf );
2155 if ( dot < 0.f ) 2155 if ( dot < 0.f )
2156 continue; 2156 continue;
2157 2157
2158 //specular += light.SpecularColor * ( powf ( Material.org.Shininess ,dot ) * attenuation ); 2158 //specular += light.SpecularColor * ( powf ( Material.org.Shininess ,dot ) * attenuation );
2159 specular.mulAdd ( light.SpecularColor, dot * attenuation ); 2159 specular.mulAdd ( light.SpecularColor, dot * attenuation );
2160 break; 2160 break;
2161 2161
2162 case video::ELT_DIRECTIONAL: 2162 case video::ELT_DIRECTIONAL:
2163 2163
2164 //angle between normal and light vector 2164 //angle between normal and light vector
2165 dot = LightSpace.normal.dot_xyz ( light.pos ); 2165 dot = LightSpace.normal.dot_xyz ( light.pos );
2166 if ( dot < 0.f ) 2166 if ( dot < 0.f )
2167 continue; 2167 continue;
2168 2168
2169 // diffuse component 2169 // diffuse component
2170 diffuse.mulAdd ( light.DiffuseColor, dot ); 2170 diffuse.mulAdd ( light.DiffuseColor, dot );
2171 break; 2171 break;
2172 default: 2172 default:
2173 break; 2173 break;
2174 } 2174 }
2175 2175
2176 } 2176 }
2177 2177
2178 // sum up lights 2178 // sum up lights
2179 dColor.mulAdd (ambient, Material.AmbientColor ); 2179 dColor.mulAdd (ambient, Material.AmbientColor );
2180 dColor.mulAdd (diffuse, Material.DiffuseColor); 2180 dColor.mulAdd (diffuse, Material.DiffuseColor);
2181 dColor.mulAdd (specular, Material.SpecularColor); 2181 dColor.mulAdd (specular, Material.SpecularColor);
2182 2182
2183 dColor.saturate ( dest->Color[0], vertexargb ); 2183 dColor.saturate ( dest->Color[0], vertexargb );
2184} 2184}
2185 2185
2186#endif 2186#endif
2187 2187
2188 2188
2189//! draws an 2d image, using a color (if color is other then Color(255,255,255,255)) and the alpha channel of the texture if wanted. 2189//! draws an 2d image, using a color (if color is other then Color(255,255,255,255)) and the alpha channel of the texture if wanted.
2190void CBurningVideoDriver::draw2DImage(const video::ITexture* texture, const core::position2d<s32>& destPos, 2190void CBurningVideoDriver::draw2DImage(const video::ITexture* texture, const core::position2d<s32>& destPos,
2191 const core::rect<s32>& sourceRect, 2191 const core::rect<s32>& sourceRect,
2192 const core::rect<s32>* clipRect, SColor color, 2192 const core::rect<s32>* clipRect, SColor color,
2193 bool useAlphaChannelOfTexture) 2193 bool useAlphaChannelOfTexture)
2194{ 2194{
2195 if (texture) 2195 if (texture)
2196 { 2196 {
2197 if (texture->getDriverType() != EDT_BURNINGSVIDEO) 2197 if (texture->getDriverType() != EDT_BURNINGSVIDEO)
2198 { 2198 {
2199 os::Printer::log("Fatal Error: Tried to copy from a surface not owned by this driver.", ELL_ERROR); 2199 os::Printer::log("Fatal Error: Tried to copy from a surface not owned by this driver.", ELL_ERROR);
2200 return; 2200 return;
2201 } 2201 }
2202 2202
2203#if 0 2203#if 0
2204 // 2d methods don't use viewPort 2204 // 2d methods don't use viewPort
2205 core::position2di dest = destPos; 2205 core::position2di dest = destPos;
2206 core::recti clip=ViewPort; 2206 core::recti clip=ViewPort;
2207 if (ViewPort.getSize().Width != ScreenSize.Width) 2207 if (ViewPort.getSize().Width != ScreenSize.Width)
2208 { 2208 {
2209 dest.X=ViewPort.UpperLeftCorner.X+core::round32(destPos.X*ViewPort.getWidth()/(f32)ScreenSize.Width); 2209 dest.X=ViewPort.UpperLeftCorner.X+core::round32(destPos.X*ViewPort.getWidth()/(f32)ScreenSize.Width);
2210 dest.Y=ViewPort.UpperLeftCorner.Y+core::round32(destPos.Y*ViewPort.getHeight()/(f32)ScreenSize.Height); 2210 dest.Y=ViewPort.UpperLeftCorner.Y+core::round32(destPos.Y*ViewPort.getHeight()/(f32)ScreenSize.Height);
2211 if (clipRect) 2211 if (clipRect)
2212 { 2212 {
2213 clip.constrainTo(*clipRect); 2213 clip.constrainTo(*clipRect);
2214 } 2214 }
2215 clipRect = &clip; 2215 clipRect = &clip;
2216 } 2216 }
2217#endif 2217#endif
2218 if (useAlphaChannelOfTexture) 2218 if (useAlphaChannelOfTexture)
2219 ((CSoftwareTexture2*)texture)->getImage()->copyToWithAlpha( 2219 ((CSoftwareTexture2*)texture)->getImage()->copyToWithAlpha(
2220 RenderTargetSurface, destPos, sourceRect, color, clipRect); 2220 RenderTargetSurface, destPos, sourceRect, color, clipRect);
2221 else 2221 else
2222 ((CSoftwareTexture2*)texture)->getImage()->copyTo( 2222 ((CSoftwareTexture2*)texture)->getImage()->copyTo(
2223 RenderTargetSurface, destPos, sourceRect, clipRect); 2223 RenderTargetSurface, destPos, sourceRect, clipRect);
2224 } 2224 }
2225} 2225}
2226 2226
2227 2227
2228//! Draws a part of the texture into the rectangle. 2228//! Draws a part of the texture into the rectangle.
2229void CBurningVideoDriver::draw2DImage(const video::ITexture* texture, const core::rect<s32>& destRect, 2229void CBurningVideoDriver::draw2DImage(const video::ITexture* texture, const core::rect<s32>& destRect,
2230 const core::rect<s32>& sourceRect, const core::rect<s32>* clipRect, 2230 const core::rect<s32>& sourceRect, const core::rect<s32>* clipRect,
2231 const video::SColor* const colors, bool useAlphaChannelOfTexture) 2231 const video::SColor* const colors, bool useAlphaChannelOfTexture)
2232{ 2232{
2233 if (texture) 2233 if (texture)
2234 { 2234 {
2235 if (texture->getDriverType() != EDT_BURNINGSVIDEO) 2235 if (texture->getDriverType() != EDT_BURNINGSVIDEO)
2236 { 2236 {
2237 os::Printer::log("Fatal Error: Tried to copy from a surface not owned by this driver.", ELL_ERROR); 2237 os::Printer::log("Fatal Error: Tried to copy from a surface not owned by this driver.", ELL_ERROR);
2238 return; 2238 return;
2239 } 2239 }
2240 2240
2241 if (useAlphaChannelOfTexture) 2241 if (useAlphaChannelOfTexture)
2242 StretchBlit(BLITTER_TEXTURE_ALPHA_BLEND, RenderTargetSurface, &destRect, &sourceRect, 2242 StretchBlit(BLITTER_TEXTURE_ALPHA_BLEND, RenderTargetSurface, &destRect, &sourceRect,
2243 ((CSoftwareTexture2*)texture)->getImage(), (colors ? colors[0].color : 0)); 2243 ((CSoftwareTexture2*)texture)->getImage(), (colors ? colors[0].color : 0));
2244 else 2244 else
2245 StretchBlit(BLITTER_TEXTURE, RenderTargetSurface, &destRect, &sourceRect, 2245 StretchBlit(BLITTER_TEXTURE, RenderTargetSurface, &destRect, &sourceRect,
2246 ((CSoftwareTexture2*)texture)->getImage(), (colors ? colors[0].color : 0)); 2246 ((CSoftwareTexture2*)texture)->getImage(), (colors ? colors[0].color : 0));
2247 } 2247 }
2248} 2248}
2249 2249
2250//! Draws a 2d line. 2250//! Draws a 2d line.
2251void CBurningVideoDriver::draw2DLine(const core::position2d<s32>& start, 2251void CBurningVideoDriver::draw2DLine(const core::position2d<s32>& start,
2252 const core::position2d<s32>& end, 2252 const core::position2d<s32>& end,
2253 SColor color) 2253 SColor color)
2254{ 2254{
2255 drawLine(BackBuffer, start, end, color ); 2255 drawLine(BackBuffer, start, end, color );
2256} 2256}
2257 2257
2258 2258
2259//! Draws a pixel 2259//! Draws a pixel
2260void CBurningVideoDriver::drawPixel(u32 x, u32 y, const SColor & color) 2260void CBurningVideoDriver::drawPixel(u32 x, u32 y, const SColor & color)
2261{ 2261{
2262 BackBuffer->setPixel(x, y, color, true); 2262 BackBuffer->setPixel(x, y, color, true);
2263} 2263}
2264 2264
2265 2265
2266//! draw an 2d rectangle 2266//! draw an 2d rectangle
2267void CBurningVideoDriver::draw2DRectangle(SColor color, const core::rect<s32>& pos, 2267void CBurningVideoDriver::draw2DRectangle(SColor color, const core::rect<s32>& pos,
2268 const core::rect<s32>* clip) 2268 const core::rect<s32>* clip)
2269{ 2269{
2270 if (clip) 2270 if (clip)
2271 { 2271 {
2272 core::rect<s32> p(pos); 2272 core::rect<s32> p(pos);
2273 2273
2274 p.clipAgainst(*clip); 2274 p.clipAgainst(*clip);
2275 2275
2276 if(!p.isValid()) 2276 if(!p.isValid())
2277 return; 2277 return;
2278 2278
2279 drawRectangle(BackBuffer, p, color); 2279 drawRectangle(BackBuffer, p, color);
2280 } 2280 }
2281 else 2281 else
2282 { 2282 {
2283 if(!pos.isValid()) 2283 if(!pos.isValid())
2284 return; 2284 return;
2285 2285
2286 drawRectangle(BackBuffer, pos, color); 2286 drawRectangle(BackBuffer, pos, color);
2287 } 2287 }
2288} 2288}
2289 2289
2290 2290
2291//! Only used by the internal engine. Used to notify the driver that 2291//! Only used by the internal engine. Used to notify the driver that
2292//! the window was resized. 2292//! the window was resized.
2293void CBurningVideoDriver::OnResize(const core::dimension2d<u32>& size) 2293void CBurningVideoDriver::OnResize(const core::dimension2d<u32>& size)
2294{ 2294{
2295 // make sure width and height are multiples of 2 2295 // make sure width and height are multiples of 2
2296 core::dimension2d<u32> realSize(size); 2296 core::dimension2d<u32> realSize(size);
2297 2297
2298 if (realSize.Width % 2) 2298 if (realSize.Width % 2)
2299 realSize.Width += 1; 2299 realSize.Width += 1;
2300 2300
2301 if (realSize.Height % 2) 2301 if (realSize.Height % 2)
2302 realSize.Height += 1; 2302 realSize.Height += 1;
2303 2303
2304 if (ScreenSize != realSize) 2304 if (ScreenSize != realSize)
2305 { 2305 {
2306 if (ViewPort.getWidth() == (s32)ScreenSize.Width && 2306 if (ViewPort.getWidth() == (s32)ScreenSize.Width &&
2307 ViewPort.getHeight() == (s32)ScreenSize.Height) 2307 ViewPort.getHeight() == (s32)ScreenSize.Height)
2308 { 2308 {
2309 ViewPort.UpperLeftCorner.X = 0; 2309 ViewPort.UpperLeftCorner.X = 0;
2310 ViewPort.UpperLeftCorner.Y = 0; 2310 ViewPort.UpperLeftCorner.Y = 0;
2311 ViewPort.LowerRightCorner.X = realSize.Width; 2311 ViewPort.LowerRightCorner.X = realSize.Width;
2312 ViewPort.LowerRightCorner.X = realSize.Height; 2312 ViewPort.LowerRightCorner.X = realSize.Height;
2313 } 2313 }
2314 2314
2315 ScreenSize = realSize; 2315 ScreenSize = realSize;
2316 2316
2317 bool resetRT = (RenderTargetSurface == BackBuffer); 2317 bool resetRT = (RenderTargetSurface == BackBuffer);
2318 2318
2319 if (BackBuffer) 2319 if (BackBuffer)
2320 BackBuffer->drop(); 2320 BackBuffer->drop();
2321 BackBuffer = new CImage(BURNINGSHADER_COLOR_FORMAT, realSize); 2321 BackBuffer = new CImage(BURNINGSHADER_COLOR_FORMAT, realSize);
2322 2322
2323 if (resetRT) 2323 if (resetRT)
2324 setRenderTarget(BackBuffer); 2324 setRenderTarget(BackBuffer);
2325 } 2325 }
2326} 2326}
2327 2327
2328 2328
2329//! returns the current render target size 2329//! returns the current render target size
2330const core::dimension2d<u32>& CBurningVideoDriver::getCurrentRenderTargetSize() const 2330const core::dimension2d<u32>& CBurningVideoDriver::getCurrentRenderTargetSize() const
2331{ 2331{
2332 return RenderTargetSize; 2332 return RenderTargetSize;
2333} 2333}
2334 2334
2335 2335
2336//!Draws an 2d rectangle with a gradient. 2336//!Draws an 2d rectangle with a gradient.
2337void CBurningVideoDriver::draw2DRectangle(const core::rect<s32>& position, 2337void CBurningVideoDriver::draw2DRectangle(const core::rect<s32>& position,
2338 SColor colorLeftUp, SColor colorRightUp, SColor colorLeftDown, SColor colorRightDown, 2338 SColor colorLeftUp, SColor colorRightUp, SColor colorLeftDown, SColor colorRightDown,
2339 const core::rect<s32>* clip) 2339 const core::rect<s32>* clip)
2340{ 2340{
2341#ifdef SOFTWARE_DRIVER_2_USE_VERTEX_COLOR 2341#ifdef SOFTWARE_DRIVER_2_USE_VERTEX_COLOR
2342 2342
2343 core::rect<s32> pos = position; 2343 core::rect<s32> pos = position;
2344 2344
2345 if (clip) 2345 if (clip)
2346 pos.clipAgainst(*clip); 2346 pos.clipAgainst(*clip);
2347 2347
2348 if (!pos.isValid()) 2348 if (!pos.isValid())
2349 return; 2349 return;
2350 2350
2351 const core::dimension2d<s32> renderTargetSize ( ViewPort.getSize() ); 2351 const core::dimension2d<s32> renderTargetSize ( ViewPort.getSize() );
2352 2352
2353 const s32 xPlus = -(renderTargetSize.Width>>1); 2353 const s32 xPlus = -(renderTargetSize.Width>>1);
2354 const f32 xFact = 1.0f / (renderTargetSize.Width>>1); 2354 const f32 xFact = 1.0f / (renderTargetSize.Width>>1);
2355 2355
2356 const s32 yPlus = renderTargetSize.Height-(renderTargetSize.Height>>1); 2356 const s32 yPlus = renderTargetSize.Height-(renderTargetSize.Height>>1);
2357 const f32 yFact = 1.0f / (renderTargetSize.Height>>1); 2357 const f32 yFact = 1.0f / (renderTargetSize.Height>>1);
2358 2358
2359 // fill VertexCache direct 2359 // fill VertexCache direct
2360 s4DVertex *v; 2360 s4DVertex *v;
2361 2361
2362 VertexCache.vertexCount = 4; 2362 VertexCache.vertexCount = 4;
2363 2363
2364 VertexCache.info[0].index = 0; 2364 VertexCache.info[0].index = 0;
2365 VertexCache.info[1].index = 1; 2365 VertexCache.info[1].index = 1;
2366 VertexCache.info[2].index = 2; 2366 VertexCache.info[2].index = 2;
2367 VertexCache.info[3].index = 3; 2367 VertexCache.info[3].index = 3;
2368 2368
2369 v = &VertexCache.mem.data [ 0 ]; 2369 v = &VertexCache.mem.data [ 0 ];
2370 2370
2371 v[0].Pos.set ( (f32)(pos.UpperLeftCorner.X+xPlus) * xFact, (f32)(yPlus-pos.UpperLeftCorner.Y) * yFact, 0.f, 1.f ); 2371 v[0].Pos.set ( (f32)(pos.UpperLeftCorner.X+xPlus) * xFact, (f32)(yPlus-pos.UpperLeftCorner.Y) * yFact, 0.f, 1.f );
2372 v[0].Color[0].setA8R8G8B8 ( colorLeftUp.color ); 2372 v[0].Color[0].setA8R8G8B8 ( colorLeftUp.color );
2373 2373
2374 v[2].Pos.set ( (f32)(pos.LowerRightCorner.X+xPlus) * xFact, (f32)(yPlus- pos.UpperLeftCorner.Y) * yFact, 0.f, 1.f ); 2374 v[2].Pos.set ( (f32)(pos.LowerRightCorner.X+xPlus) * xFact, (f32)(yPlus- pos.UpperLeftCorner.Y) * yFact, 0.f, 1.f );
2375 v[2].Color[0].setA8R8G8B8 ( colorRightUp.color ); 2375 v[2].Color[0].setA8R8G8B8 ( colorRightUp.color );
2376 2376
2377 v[4].Pos.set ( (f32)(pos.LowerRightCorner.X+xPlus) * xFact, (f32)(yPlus-pos.LowerRightCorner.Y) * yFact, 0.f ,1.f ); 2377 v[4].Pos.set ( (f32)(pos.LowerRightCorner.X+xPlus) * xFact, (f32)(yPlus-pos.LowerRightCorner.Y) * yFact, 0.f ,1.f );
2378 v[4].Color[0].setA8R8G8B8 ( colorRightDown.color ); 2378 v[4].Color[0].setA8R8G8B8 ( colorRightDown.color );
2379 2379
2380 v[6].Pos.set ( (f32)(pos.UpperLeftCorner.X+xPlus) * xFact, (f32)(yPlus-pos.LowerRightCorner.Y) * yFact, 0.f, 1.f ); 2380 v[6].Pos.set ( (f32)(pos.UpperLeftCorner.X+xPlus) * xFact, (f32)(yPlus-pos.LowerRightCorner.Y) * yFact, 0.f, 1.f );
2381 v[6].Color[0].setA8R8G8B8 ( colorLeftDown.color ); 2381 v[6].Color[0].setA8R8G8B8 ( colorLeftDown.color );
2382 2382
2383 s32 i; 2383 s32 i;
2384 u32 g; 2384 u32 g;
2385 2385
2386 for ( i = 0; i!= 8; i += 2 ) 2386 for ( i = 0; i!= 8; i += 2 )
2387 { 2387 {
2388 v[i + 0].flag = clipToFrustumTest ( v + i ); 2388 v[i + 0].flag = clipToFrustumTest ( v + i );
2389 v[i + 1].flag = 0; 2389 v[i + 1].flag = 0;
2390 if ( (v[i].flag & VERTEX4D_INSIDE ) == VERTEX4D_INSIDE ) 2390 if ( (v[i].flag & VERTEX4D_INSIDE ) == VERTEX4D_INSIDE )
2391 { 2391 {
2392 ndc_2_dc_and_project ( v + i + 1, v + i, 2 ); 2392 ndc_2_dc_and_project ( v + i + 1, v + i, 2 );
2393 } 2393 }
2394 } 2394 }
2395 2395
2396 2396
2397 IBurningShader * render; 2397 IBurningShader * render;
2398 2398
2399 render = BurningShader [ ETR_GOURAUD_ALPHA_NOZ ]; 2399 render = BurningShader [ ETR_GOURAUD_ALPHA_NOZ ];
2400 render->setRenderTarget(RenderTargetSurface, ViewPort); 2400 render->setRenderTarget(RenderTargetSurface, ViewPort);
2401 2401
2402 static const s16 indexList[6] = {0,1,2,0,2,3}; 2402 static const s16 indexList[6] = {0,1,2,0,2,3};
2403 2403
2404 s4DVertex * face[3]; 2404 s4DVertex * face[3];
2405 2405
2406 for ( i = 0; i!= 6; i += 3 ) 2406 for ( i = 0; i!= 6; i += 3 )
2407 { 2407 {
2408 face[0] = VertexCache_getVertex ( indexList [ i + 0 ] ); 2408 face[0] = VertexCache_getVertex ( indexList [ i + 0 ] );
2409 face[1] = VertexCache_getVertex ( indexList [ i + 1 ] ); 2409 face[1] = VertexCache_getVertex ( indexList [ i + 1 ] );
2410 face[2] = VertexCache_getVertex ( indexList [ i + 2 ] ); 2410 face[2] = VertexCache_getVertex ( indexList [ i + 2 ] );
2411 2411
2412 // test clipping 2412 // test clipping
2413 u32 test = face[0]->flag & face[1]->flag & face[2]->flag & VERTEX4D_INSIDE; 2413 u32 test = face[0]->flag & face[1]->flag & face[2]->flag & VERTEX4D_INSIDE;
2414 2414
2415 if ( test == VERTEX4D_INSIDE ) 2415 if ( test == VERTEX4D_INSIDE )
2416 { 2416 {
2417 render->drawTriangle ( face[0] + 1, face[1] + 1, face[2] + 1 ); 2417 render->drawTriangle ( face[0] + 1, face[1] + 1, face[2] + 1 );
2418 continue; 2418 continue;
2419 } 2419 }
2420 // Todo: all vertices are clipped in 2d.. 2420 // Todo: all vertices are clipped in 2d..
2421 // is this true ? 2421 // is this true ?
2422 u32 vOut = 6; 2422 u32 vOut = 6;
2423 memcpy ( CurrentOut.data + 0, face[0], sizeof ( s4DVertex ) * 2 ); 2423 memcpy ( CurrentOut.data + 0, face[0], sizeof ( s4DVertex ) * 2 );
2424 memcpy ( CurrentOut.data + 2, face[1], sizeof ( s4DVertex ) * 2 ); 2424 memcpy ( CurrentOut.data + 2, face[1], sizeof ( s4DVertex ) * 2 );
2425 memcpy ( CurrentOut.data + 4, face[2], sizeof ( s4DVertex ) * 2 ); 2425 memcpy ( CurrentOut.data + 4, face[2], sizeof ( s4DVertex ) * 2 );
2426 2426
2427 vOut = clipToFrustum ( CurrentOut.data, Temp.data, 3 ); 2427 vOut = clipToFrustum ( CurrentOut.data, Temp.data, 3 );
2428 if ( vOut < 3 ) 2428 if ( vOut < 3 )
2429 continue; 2429 continue;
2430 2430
2431 vOut <<= 1; 2431 vOut <<= 1;
2432 // to DC Space, project homogenous vertex 2432 // to DC Space, project homogenous vertex
2433 ndc_2_dc_and_project ( CurrentOut.data + 1, CurrentOut.data, vOut ); 2433 ndc_2_dc_and_project ( CurrentOut.data + 1, CurrentOut.data, vOut );
2434 2434
2435 // re-tesselate ( triangle-fan, 0-1-2,0-2-3.. ) 2435 // re-tesselate ( triangle-fan, 0-1-2,0-2-3.. )
2436 for ( g = 0; g <= vOut - 6; g += 2 ) 2436 for ( g = 0; g <= vOut - 6; g += 2 )
2437 { 2437 {
2438 // rasterize 2438 // rasterize
2439 render->drawTriangle ( CurrentOut.data + 1, &CurrentOut.data[g + 3], &CurrentOut.data[g + 5] ); 2439 render->drawTriangle ( CurrentOut.data + 1, &CurrentOut.data[g + 3], &CurrentOut.data[g + 5] );
2440 } 2440 }
2441 2441
2442 } 2442 }
2443#else 2443#else
2444 draw2DRectangle ( colorLeftUp, position, clip ); 2444 draw2DRectangle ( colorLeftUp, position, clip );
2445#endif 2445#endif
2446} 2446}
2447 2447
2448 2448
2449//! Draws a 3d line. 2449//! Draws a 3d line.
2450void CBurningVideoDriver::draw3DLine(const core::vector3df& start, 2450void CBurningVideoDriver::draw3DLine(const core::vector3df& start,
2451 const core::vector3df& end, SColor color) 2451 const core::vector3df& end, SColor color)
2452{ 2452{
2453 Transformation [ ETS_CURRENT].transformVect ( &CurrentOut.data[0].Pos.x, start ); 2453 Transformation [ ETS_CURRENT].transformVect ( &CurrentOut.data[0].Pos.x, start );
2454 Transformation [ ETS_CURRENT].transformVect ( &CurrentOut.data[2].Pos.x, end ); 2454 Transformation [ ETS_CURRENT].transformVect ( &CurrentOut.data[2].Pos.x, end );
2455 2455
2456 u32 g; 2456 u32 g;
2457 u32 vOut; 2457 u32 vOut;
2458 2458
2459 // no clipping flags 2459 // no clipping flags
2460 for ( g = 0; g != CurrentOut.ElementSize; ++g ) 2460 for ( g = 0; g != CurrentOut.ElementSize; ++g )
2461 { 2461 {
2462 CurrentOut.data[g].flag = 0; 2462 CurrentOut.data[g].flag = 0;
2463 Temp.data[g].flag = 0; 2463 Temp.data[g].flag = 0;
2464 } 2464 }
2465 2465
2466 // vertices count per line 2466 // vertices count per line
2467 vOut = clipToFrustum ( CurrentOut.data, Temp.data, 2 ); 2467 vOut = clipToFrustum ( CurrentOut.data, Temp.data, 2 );
2468 if ( vOut < 2 ) 2468 if ( vOut < 2 )
2469 return; 2469 return;
2470 2470
2471 vOut <<= 1; 2471 vOut <<= 1;
2472 2472
2473 IBurningShader * line; 2473 IBurningShader * line;
2474 line = BurningShader [ ETR_TEXTURE_GOURAUD_WIRE ]; 2474 line = BurningShader [ ETR_TEXTURE_GOURAUD_WIRE ];
2475 line->setRenderTarget(RenderTargetSurface, ViewPort); 2475 line->setRenderTarget(RenderTargetSurface, ViewPort);
2476 2476
2477 // to DC Space, project homogenous vertex 2477 // to DC Space, project homogenous vertex
2478 ndc_2_dc_and_project ( CurrentOut.data + 1, CurrentOut.data, vOut ); 2478 ndc_2_dc_and_project ( CurrentOut.data + 1, CurrentOut.data, vOut );
2479 2479
2480 // unproject vertex color 2480 // unproject vertex color
2481#ifdef SOFTWARE_DRIVER_2_USE_VERTEX_COLOR 2481#ifdef SOFTWARE_DRIVER_2_USE_VERTEX_COLOR
2482 for ( g = 0; g != vOut; g+= 2 ) 2482 for ( g = 0; g != vOut; g+= 2 )
2483 { 2483 {
2484 CurrentOut.data[ g + 1].Color[0].setA8R8G8B8 ( color.color ); 2484 CurrentOut.data[ g + 1].Color[0].setA8R8G8B8 ( color.color );
2485 } 2485 }
2486#endif 2486#endif
2487 2487
2488 2488
2489 for ( g = 0; g <= vOut - 4; g += 2 ) 2489 for ( g = 0; g <= vOut - 4; g += 2 )
2490 { 2490 {
2491 // rasterize 2491 // rasterize
2492 line->drawLine ( CurrentOut.data + 1, CurrentOut.data + g + 3 ); 2492 line->drawLine ( CurrentOut.data + 1, CurrentOut.data + g + 3 );
2493 } 2493 }
2494} 2494}
2495 2495
2496 2496
2497//! \return Returns the name of the video driver. Example: In case of the DirectX8 2497//! \return Returns the name of the video driver. Example: In case of the DirectX8
2498//! driver, it would return "Direct3D8.1". 2498//! driver, it would return "Direct3D8.1".
2499const wchar_t* CBurningVideoDriver::getName() const 2499const wchar_t* CBurningVideoDriver::getName() const
2500{ 2500{
2501#ifdef BURNINGVIDEO_RENDERER_BEAUTIFUL 2501#ifdef BURNINGVIDEO_RENDERER_BEAUTIFUL
2502 return L"Burning's Video 0.47 beautiful"; 2502 return L"Burning's Video 0.47 beautiful";
2503#elif defined ( BURNINGVIDEO_RENDERER_ULTRA_FAST ) 2503#elif defined ( BURNINGVIDEO_RENDERER_ULTRA_FAST )
2504 return L"Burning's Video 0.47 ultra fast"; 2504 return L"Burning's Video 0.47 ultra fast";
2505#elif defined ( BURNINGVIDEO_RENDERER_FAST ) 2505#elif defined ( BURNINGVIDEO_RENDERER_FAST )
2506 return L"Burning's Video 0.47 fast"; 2506 return L"Burning's Video 0.47 fast";
2507#else 2507#else
2508 return L"Burning's Video 0.47"; 2508 return L"Burning's Video 0.47";
2509#endif 2509#endif
2510} 2510}
2511 2511
2512//! Returns the graphics card vendor name. 2512//! Returns the graphics card vendor name.
2513core::stringc CBurningVideoDriver::getVendorInfo() 2513core::stringc CBurningVideoDriver::getVendorInfo()
2514{ 2514{
2515 return "Burning's Video: Ing. Thomas Alten (c) 2006-2012"; 2515 return "Burning's Video: Ing. Thomas Alten (c) 2006-2012";
2516} 2516}
2517 2517
2518 2518
2519//! Returns type of video driver 2519//! Returns type of video driver
2520E_DRIVER_TYPE CBurningVideoDriver::getDriverType() const 2520E_DRIVER_TYPE CBurningVideoDriver::getDriverType() const
2521{ 2521{
2522 return EDT_BURNINGSVIDEO; 2522 return EDT_BURNINGSVIDEO;
2523} 2523}
2524 2524
2525 2525
2526//! returns color format 2526//! returns color format
2527ECOLOR_FORMAT CBurningVideoDriver::getColorFormat() const 2527ECOLOR_FORMAT CBurningVideoDriver::getColorFormat() const
2528{ 2528{
2529 return BURNINGSHADER_COLOR_FORMAT; 2529 return BURNINGSHADER_COLOR_FORMAT;
2530} 2530}
2531 2531
2532 2532
2533//! Returns the transformation set by setTransform 2533//! Returns the transformation set by setTransform
2534const core::matrix4& CBurningVideoDriver::getTransform(E_TRANSFORMATION_STATE state) const 2534const core::matrix4& CBurningVideoDriver::getTransform(E_TRANSFORMATION_STATE state) const
2535{ 2535{
2536 return Transformation[state]; 2536 return Transformation[state];
2537} 2537}
2538 2538
2539 2539
2540//! Creates a render target texture. 2540//! Creates a render target texture.
2541ITexture* CBurningVideoDriver::addRenderTargetTexture(const core::dimension2d<u32>& size, 2541ITexture* CBurningVideoDriver::addRenderTargetTexture(const core::dimension2d<u32>& size,
2542 const io::path& name, const ECOLOR_FORMAT format) 2542 const io::path& name, const ECOLOR_FORMAT format)
2543{ 2543{
2544 IImage* img = createImage(BURNINGSHADER_COLOR_FORMAT, size); 2544 IImage* img = createImage(BURNINGSHADER_COLOR_FORMAT, size);
2545 ITexture* tex = new CSoftwareTexture2(img, name, CSoftwareTexture2::IS_RENDERTARGET ); 2545 ITexture* tex = new CSoftwareTexture2(img, name, CSoftwareTexture2::IS_RENDERTARGET );
2546 img->drop(); 2546 img->drop();
2547 addTexture(tex); 2547 addTexture(tex);
2548 tex->drop(); 2548 tex->drop();
2549 return tex; 2549 return tex;
2550} 2550}
2551 2551
2552 2552
2553//! Clears the DepthBuffer. 2553//! Clears the DepthBuffer.
2554void CBurningVideoDriver::clearZBuffer() 2554void CBurningVideoDriver::clearZBuffer()
2555{ 2555{
2556 if (DepthBuffer) 2556 if (DepthBuffer)
2557 DepthBuffer->clear(); 2557 DepthBuffer->clear();
2558} 2558}
2559 2559
2560 2560
2561//! Returns an image created from the last rendered frame. 2561//! Returns an image created from the last rendered frame.
2562IImage* CBurningVideoDriver::createScreenShot(video::ECOLOR_FORMAT format, video::E_RENDER_TARGET target) 2562IImage* CBurningVideoDriver::createScreenShot(video::ECOLOR_FORMAT format, video::E_RENDER_TARGET target)
2563{ 2563{
2564 if (target != video::ERT_FRAME_BUFFER) 2564 if (target != video::ERT_FRAME_BUFFER)
2565 return 0; 2565 return 0;
2566 2566
2567 if (BackBuffer) 2567 if (BackBuffer)
2568 { 2568 {
2569 IImage* tmp = createImage(BackBuffer->getColorFormat(), BackBuffer->getDimension()); 2569 IImage* tmp = createImage(BackBuffer->getColorFormat(), BackBuffer->getDimension());
2570 BackBuffer->copyTo(tmp); 2570 BackBuffer->copyTo(tmp);
2571 return tmp; 2571 return tmp;
2572 } 2572 }
2573 else 2573 else
2574 return 0; 2574 return 0;
2575} 2575}
2576 2576
2577 2577
2578//! returns a device dependent texture from a software surface (IImage) 2578//! returns a device dependent texture from a software surface (IImage)
2579//! THIS METHOD HAS TO BE OVERRIDDEN BY DERIVED DRIVERS WITH OWN TEXTURES 2579//! THIS METHOD HAS TO BE OVERRIDDEN BY DERIVED DRIVERS WITH OWN TEXTURES
2580ITexture* CBurningVideoDriver::createDeviceDependentTexture(IImage* surface, const io::path& name, void* mipmapData) 2580ITexture* CBurningVideoDriver::createDeviceDependentTexture(IImage* surface, const io::path& name, void* mipmapData)
2581{ 2581{
2582 return new CSoftwareTexture2( 2582 return new CSoftwareTexture2(
2583 surface, name, 2583 surface, name,
2584 (getTextureCreationFlag(ETCF_CREATE_MIP_MAPS) ? CSoftwareTexture2::GEN_MIPMAP : 0 ) | 2584 (getTextureCreationFlag(ETCF_CREATE_MIP_MAPS) ? CSoftwareTexture2::GEN_MIPMAP : 0 ) |
2585 (getTextureCreationFlag(ETCF_ALLOW_NON_POWER_2) ? 0 : CSoftwareTexture2::NP2_SIZE ), mipmapData); 2585 (getTextureCreationFlag(ETCF_ALLOW_NON_POWER_2) ? 0 : CSoftwareTexture2::NP2_SIZE ), mipmapData);
2586 2586
2587} 2587}
2588 2588
2589 2589
2590//! Returns the maximum amount of primitives (mostly vertices) which 2590//! Returns the maximum amount of primitives (mostly vertices) which
2591//! the device is able to render with one drawIndexedTriangleList 2591//! the device is able to render with one drawIndexedTriangleList
2592//! call. 2592//! call.
2593u32 CBurningVideoDriver::getMaximalPrimitiveCount() const 2593u32 CBurningVideoDriver::getMaximalPrimitiveCount() const
2594{ 2594{
2595 return 0xFFFFFFFF; 2595 return 0xFFFFFFFF;
2596} 2596}
2597 2597
2598 2598
2599//! Draws a shadow volume into the stencil buffer. To draw a stencil shadow, do 2599//! Draws a shadow volume into the stencil buffer. To draw a stencil shadow, do
2600//! this: First, draw all geometry. Then use this method, to draw the shadow 2600//! this: First, draw all geometry. Then use this method, to draw the shadow
2601//! volume. Next use IVideoDriver::drawStencilShadow() to visualize the shadow. 2601//! volume. Next use IVideoDriver::drawStencilShadow() to visualize the shadow.
2602void CBurningVideoDriver::drawStencilShadowVolume(const core::array<core::vector3df>& triangles, bool zfail, u32 debugDataVisible) 2602void CBurningVideoDriver::drawStencilShadowVolume(const core::array<core::vector3df>& triangles, bool zfail, u32 debugDataVisible)
2603{ 2603{
2604 const u32 count = triangles.size(); 2604 const u32 count = triangles.size();
2605 IBurningShader *shader = BurningShader [ ETR_STENCIL_SHADOW ]; 2605 IBurningShader *shader = BurningShader [ ETR_STENCIL_SHADOW ];
2606 2606
2607 CurrentShader = shader; 2607 CurrentShader = shader;
2608 shader->setRenderTarget(RenderTargetSurface, ViewPort); 2608 shader->setRenderTarget(RenderTargetSurface, ViewPort);
2609 2609
2610 Material.org.MaterialType = video::EMT_SOLID; 2610 Material.org.MaterialType = video::EMT_SOLID;
2611 Material.org.Lighting = false; 2611 Material.org.Lighting = false;
2612 Material.org.ZWriteEnable = false; 2612 Material.org.ZWriteEnable = false;
2613 Material.org.ZBuffer = ECFN_LESSEQUAL; 2613 Material.org.ZBuffer = ECFN_LESSEQUAL;
2614 LightSpace.Flags &= ~VERTEXTRANSFORM; 2614 LightSpace.Flags &= ~VERTEXTRANSFORM;
2615 2615
2616 //glStencilMask(~0); 2616 //glStencilMask(~0);
2617 //glStencilFunc(GL_ALWAYS, 0, ~0); 2617 //glStencilFunc(GL_ALWAYS, 0, ~0);
2618 2618
2619 if (true)// zpass does not work yet 2619 if (true)// zpass does not work yet
2620 { 2620 {
2621 Material.org.BackfaceCulling = true; 2621 Material.org.BackfaceCulling = true;
2622 Material.org.FrontfaceCulling = false; 2622 Material.org.FrontfaceCulling = false;
2623 shader->setParam ( 0, 0 ); 2623 shader->setParam ( 0, 0 );
2624 shader->setParam ( 1, 1 ); 2624 shader->setParam ( 1, 1 );
2625 shader->setParam ( 2, 0 ); 2625 shader->setParam ( 2, 0 );
2626 drawVertexPrimitiveList (triangles.const_pointer(), count, 0, count/3, (video::E_VERTEX_TYPE) 4, scene::EPT_TRIANGLES, (video::E_INDEX_TYPE) 4 ); 2626 drawVertexPrimitiveList (triangles.const_pointer(), count, 0, count/3, (video::E_VERTEX_TYPE) 4, scene::EPT_TRIANGLES, (video::E_INDEX_TYPE) 4 );
2627 //glStencilOp(GL_KEEP, incr, GL_KEEP); 2627 //glStencilOp(GL_KEEP, incr, GL_KEEP);
2628 //glDrawArrays(GL_TRIANGLES,0,count); 2628 //glDrawArrays(GL_TRIANGLES,0,count);
2629 2629
2630 Material.org.BackfaceCulling = false; 2630 Material.org.BackfaceCulling = false;
2631 Material.org.FrontfaceCulling = true; 2631 Material.org.FrontfaceCulling = true;
2632 shader->setParam ( 0, 0 ); 2632 shader->setParam ( 0, 0 );
2633 shader->setParam ( 1, 2 ); 2633 shader->setParam ( 1, 2 );
2634 shader->setParam ( 2, 0 ); 2634 shader->setParam ( 2, 0 );
2635 drawVertexPrimitiveList (triangles.const_pointer(), count, 0, count/3, (video::E_VERTEX_TYPE) 4, scene::EPT_TRIANGLES, (video::E_INDEX_TYPE) 4 ); 2635 drawVertexPrimitiveList (triangles.const_pointer(), count, 0, count/3, (video::E_VERTEX_TYPE) 4, scene::EPT_TRIANGLES, (video::E_INDEX_TYPE) 4 );
2636 //glStencilOp(GL_KEEP, decr, GL_KEEP); 2636 //glStencilOp(GL_KEEP, decr, GL_KEEP);
2637 //glDrawArrays(GL_TRIANGLES,0,count); 2637 //glDrawArrays(GL_TRIANGLES,0,count);
2638 } 2638 }
2639 else // zpass 2639 else // zpass
2640 { 2640 {
2641 Material.org.BackfaceCulling = true; 2641 Material.org.BackfaceCulling = true;
2642 Material.org.FrontfaceCulling = false; 2642 Material.org.FrontfaceCulling = false;
2643 shader->setParam ( 0, 0 ); 2643 shader->setParam ( 0, 0 );
2644 shader->setParam ( 1, 0 ); 2644 shader->setParam ( 1, 0 );
2645 shader->setParam ( 2, 1 ); 2645 shader->setParam ( 2, 1 );
2646 //glStencilOp(GL_KEEP, GL_KEEP, incr); 2646 //glStencilOp(GL_KEEP, GL_KEEP, incr);
2647 //glDrawArrays(GL_TRIANGLES,0,count); 2647 //glDrawArrays(GL_TRIANGLES,0,count);
2648 2648
2649 Material.org.BackfaceCulling = false; 2649 Material.org.BackfaceCulling = false;
2650 Material.org.FrontfaceCulling = true; 2650 Material.org.FrontfaceCulling = true;
2651 shader->setParam ( 0, 0 ); 2651 shader->setParam ( 0, 0 );
2652 shader->setParam ( 1, 0 ); 2652 shader->setParam ( 1, 0 );
2653 shader->setParam ( 2, 2 ); 2653 shader->setParam ( 2, 2 );
2654 //glStencilOp(GL_KEEP, GL_KEEP, decr); 2654 //glStencilOp(GL_KEEP, GL_KEEP, decr);
2655 //glDrawArrays(GL_TRIANGLES,0,count); 2655 //glDrawArrays(GL_TRIANGLES,0,count);
2656 } 2656 }
2657} 2657}
2658 2658
2659//! Fills the stencil shadow with color. After the shadow volume has been drawn 2659//! Fills the stencil shadow with color. After the shadow volume has been drawn
2660//! into the stencil buffer using IVideoDriver::drawStencilShadowVolume(), use this 2660//! into the stencil buffer using IVideoDriver::drawStencilShadowVolume(), use this
2661//! to draw the color of the shadow. 2661//! to draw the color of the shadow.
2662void CBurningVideoDriver::drawStencilShadow(bool clearStencilBuffer, video::SColor leftUpEdge, 2662void CBurningVideoDriver::drawStencilShadow(bool clearStencilBuffer, video::SColor leftUpEdge,
2663 video::SColor rightUpEdge, video::SColor leftDownEdge, video::SColor rightDownEdge) 2663 video::SColor rightUpEdge, video::SColor leftDownEdge, video::SColor rightDownEdge)
2664{ 2664{
2665 if (!StencilBuffer) 2665 if (!StencilBuffer)
2666 return; 2666 return;
2667 // draw a shadow rectangle covering the entire screen using stencil buffer 2667 // draw a shadow rectangle covering the entire screen using stencil buffer
2668 const u32 h = RenderTargetSurface->getDimension().Height; 2668 const u32 h = RenderTargetSurface->getDimension().Height;
2669 const u32 w = RenderTargetSurface->getDimension().Width; 2669 const u32 w = RenderTargetSurface->getDimension().Width;
2670 tVideoSample *dst; 2670 tVideoSample *dst;
2671 u32 *stencil; 2671 u32 *stencil;
2672 u32* const stencilBase=(u32*) StencilBuffer->lock(); 2672 u32* const stencilBase=(u32*) StencilBuffer->lock();
2673 2673
2674 for ( u32 y = 0; y < h; ++y ) 2674 for ( u32 y = 0; y < h; ++y )
2675 { 2675 {
2676 dst = (tVideoSample*)RenderTargetSurface->lock() + ( y * w ); 2676 dst = (tVideoSample*)RenderTargetSurface->lock() + ( y * w );
2677 stencil = stencilBase + ( y * w ); 2677 stencil = stencilBase + ( y * w );
2678 2678
2679 for ( u32 x = 0; x < w; ++x ) 2679 for ( u32 x = 0; x < w; ++x )
2680 { 2680 {
2681 if ( stencil[x] > 1 ) 2681 if ( stencil[x] > 1 )
2682 { 2682 {
2683 dst[x] = PixelBlend32 ( dst[x], leftUpEdge.color ); 2683 dst[x] = PixelBlend32 ( dst[x], leftUpEdge.color );
2684 } 2684 }
2685 } 2685 }
2686 } 2686 }
2687 2687
2688 StencilBuffer->clear(); 2688 StencilBuffer->clear();
2689} 2689}
2690 2690
2691 2691
2692core::dimension2du CBurningVideoDriver::getMaxTextureSize() const 2692core::dimension2du CBurningVideoDriver::getMaxTextureSize() const
2693{ 2693{
2694 return core::dimension2du(SOFTWARE_DRIVER_2_TEXTURE_MAXSIZE, SOFTWARE_DRIVER_2_TEXTURE_MAXSIZE); 2694 return core::dimension2du(SOFTWARE_DRIVER_2_TEXTURE_MAXSIZE, SOFTWARE_DRIVER_2_TEXTURE_MAXSIZE);
2695} 2695}
2696 2696
2697 2697
2698} // end namespace video 2698} // end namespace video
2699} // end namespace irr 2699} // end namespace irr
2700 2700
2701#endif // _IRR_COMPILE_WITH_BURNINGSVIDEO_ 2701#endif // _IRR_COMPILE_WITH_BURNINGSVIDEO_
2702 2702
2703namespace irr 2703namespace irr
2704{ 2704{
2705namespace video 2705namespace video
2706{ 2706{
2707 2707
2708//! creates a video driver 2708//! creates a video driver
2709IVideoDriver* createBurningVideoDriver(const irr::SIrrlichtCreationParameters& params, io::IFileSystem* io, video::IImagePresenter* presenter) 2709IVideoDriver* createBurningVideoDriver(const irr::SIrrlichtCreationParameters& params, io::IFileSystem* io, video::IImagePresenter* presenter)
2710{ 2710{
2711 #ifdef _IRR_COMPILE_WITH_BURNINGSVIDEO_ 2711 #ifdef _IRR_COMPILE_WITH_BURNINGSVIDEO_
2712 return new CBurningVideoDriver(params, io, presenter); 2712 return new CBurningVideoDriver(params, io, presenter);
2713 #else 2713 #else
2714 return 0; 2714 return 0;
2715 #endif // _IRR_COMPILE_WITH_BURNINGSVIDEO_ 2715 #endif // _IRR_COMPILE_WITH_BURNINGSVIDEO_
2716} 2716}
2717 2717
2718 2718
2719 2719
2720} // end namespace video 2720} // end namespace video
2721} // end namespace irr 2721} // end namespace irr
2722 2722