00001
00002 #include "LightsConfig.h"
00003 #include "glwxOpenGL.h"
00004 #include "Lights.h"
00005
00006 #include <math.h>
00007
00008 Lights::Lights() {
00009
00010 numLights = 3;
00011 height = 0.9528;
00012 distance = 1.0;
00013 isWireframe = false;
00014 cameraPosition[0] = 0;
00015 cameraPosition[1] = 0.2;
00016 cameraPosition[2] = 8;
00017 lookPosition[0] = 0;
00018 lookPosition[1] = 0.2;
00019 lookPosition[2] = 0;
00020
00021 useDepthBuffer = true;
00022
00023 p1Brightness = 0;
00024 p2Brightness = 0;
00025 percentDifference = 0;
00026 }
00027
00028 bool Lights::Init() {
00029
00030
00031 glClearColor( 0.0f, 0.0f, 0.0f, 0.0f );
00032 glClearDepth( 1.0f );
00033
00034 glEnable( GL_DEPTH_TEST );
00035 glDepthFunc( GL_LEQUAL );
00036 glShadeModel( GL_SMOOTH );
00037
00038
00039 glBlendFunc( GL_SRC_ALPHA, GL_ONE );
00040 glLineStipple(1, 0x3F07);
00041
00042
00043 std::string texturePath = LIGHTS_DATA_DIR;
00044 texturePath += "/Textures/light.tga";
00045
00046
00047 lightTex.load2D(texturePath.c_str());
00048 lightTex.activate();
00049
00050
00051 GLfloat light_pos[] = {0.0, 1, 0, 1};
00052 GLfloat rgba_white[] = { 1.0f, 1.0f, 1.0f, 1.0f };
00053 GLfloat rgba_black[] = { 0.0f, 0.0f, 0.0f, 1.0f };
00054
00055
00056
00057 glLightfv( GL_LIGHT1, GL_AMBIENT, rgba_black );
00058 glLightfv( GL_LIGHT1, GL_DIFFUSE, rgba_white );
00059 glLightfv( GL_LIGHT1, GL_POSITION, light_pos );
00060
00061 glEnable(GL_LIGHT1);
00062
00063
00064 return true;
00065 }
00066
00067
00068 void Lights::Draw() {
00069
00070
00071 glClearColor( 0.1f, 0.1f, 0.15f, 1.0f );
00072 glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
00073 glLoadIdentity();
00074
00075
00076
00077 gluLookAt(cameraPosition[0], cameraPosition[1], cameraPosition[2],
00078 lookPosition[0], lookPosition[1], lookPosition[2], 0, 1, 0);
00079
00080
00081 GLfloat light_pos[] = {0.0, height + (numLights*distance)*0.1, 0.0, 1};
00082 glLightfv( GL_LIGHT1, GL_POSITION, light_pos );
00083
00084 DrawFloor();
00085 if (drawLines) DrawLines();
00086 DrawLights();
00087
00088 CalculateBrightness();
00089
00090 }
00091
00092 void Lights::DrawFloor() {
00093
00094
00095 float radius = 30;
00096
00097 int patches = 10;
00098 float step = (2*radius)/patches;
00099
00100 glDisable(GL_BLEND);
00101 glEnable(GL_LIGHTING);
00102 glEnable(GL_DEPTH_TEST);
00103
00104 glDisable(GL_TEXTURE_2D);
00105
00106 if (isWireframe) glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
00107
00108
00109 glBegin( GL_QUADS );
00110 float y = radius;
00111 for (int j = 0; j < patches; ++j) {
00112 float x = radius;
00113 for (int k = 0; k < patches; ++k) {
00114 glNormal3f(0,1,0);
00115 glVertex3f( x, 0.0f, y );
00116 glNormal3f(0,1,0);
00117 glVertex3f( x, 0.0f, y-step );
00118 glNormal3f(0,1,0);
00119 glVertex3f( x-step, 0.0f, y-step );
00120 glNormal3f(0,1,0);
00121 glVertex3f( x-step, 0.0f, y );
00122 x -= step;
00123 }
00124 y -= step;
00125 }
00126 glEnd( );
00127
00128 if (isWireframe) glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
00129
00130 }
00131
00132 void Lights::DrawLines() {
00133
00134
00135 glDisable(GL_DEPTH_TEST);
00136
00137 glLineWidth(1.0);
00138 glDisable(GL_LIGHTING);
00139
00140
00141
00142 glBegin( GL_LINES );
00143 double x = -(distance*(numLights-1))/2;
00144 for (int i = 0; i < numLights; ++i) {
00145 glVertex3f(x,height,0);
00146 glVertex3f(0,0,0);
00147 x += distance;
00148 }
00149 glEnd();
00150
00151
00152 glEnable(GL_LINE_STIPPLE);
00153 glBegin( GL_LINES );
00154 x = -(distance*(numLights-1))/2.0f;
00155 double offset = distance/2.0f;
00156 for (int i = 0; i < numLights; ++i) {
00157 glVertex3f(x,height,0);
00158 glVertex3f(offset,0,0);
00159 x += distance;
00160 }
00161 glEnd();
00162 glDisable(GL_LINE_STIPPLE);
00163
00164 }
00165
00166 void Lights::DrawLights() {
00167
00168 float radius = 0.25;
00169
00170 glEnable(GL_TEXTURE_2D);
00171 glBindTexture(GL_TEXTURE_2D, lightTex.getID() );
00172
00173 glEnable(GL_BLEND);
00174 glBlendFunc( GL_SRC_ALPHA, GL_ONE );
00175
00176 glDisable(GL_LIGHTING);
00177 if (useDepthBuffer) glEnable(GL_DEPTH_TEST);
00178 else glDisable(GL_DEPTH_TEST);
00179 glColor4f(1.0f,1.0f,1.0f,1.0f);
00180
00181
00182 glBegin( GL_QUADS );
00183
00184 double x = -(distance*(numLights-1))/2;
00185 for (int i = 0; i < numLights; ++i) {
00186
00187 glTexCoord2f(1.0f, 1.0f); glNormal3f(0,0,1); glVertex3f( radius+x, radius+height, 0 );
00188 glTexCoord2f(0.0f, 1.0f); glNormal3f(0,0,1); glVertex3f( -radius+x, radius+height, 0 );
00189 glTexCoord2f(0.0f, 0.0f); glNormal3f(0,0,1); glVertex3f( -radius+x, -radius+height, 0 );
00190 glTexCoord2f(1.0f, 0.0f); glNormal3f(0,0,1); glVertex3f( radius+x, -radius+height, 0 );
00191
00192 x += distance;
00193 }
00194
00195 glEnd();
00196
00197 }
00198
00199 void Lights::SetDrawLines(bool flag) { this->drawLines = flag; }
00200 void Lights::SetUseDepthBuffer(bool flag) { this->useDepthBuffer = flag; }
00201
00202 void Lights::SetNumberOfLights(int num) {
00203
00204 if (num < 0) return;
00205
00206
00207 if (num%2) this->numLights = num;
00208 else this->numLights = num+1;
00209
00210 }
00211
00212 void Lights::Reset() {
00213
00214 height = 0.9528;
00215 distance = 1.0;
00216 isWireframe = false;
00217 cameraPosition[0] = 0;
00218 cameraPosition[1] = 0.2;
00219 cameraPosition[2] = 8;
00220 lookPosition[0] = 0;
00221 lookPosition[1] = 0.2;
00222 lookPosition[2] = 0;
00223
00224 }
00225
00226
00227
00228
00229 void Lights::CalculateBrightness() {
00230
00231
00232 p1Brightness = 0;
00233 p2Brightness = 0;
00234 percentDifference = 0;
00235
00236
00237 double x = -(distance*(numLights-1))/2;
00238 double offset = distance/2.0f;
00239 double dx = 0;
00240 double dy = 0;
00241
00242 for (int i = 0; i < numLights; ++i) {
00243
00244
00245 dx = x;
00246 dy = height;
00247 p1Brightness += 1.0 / ( dx*dx + dy*dy );
00248
00249
00250 dx = offset - x;
00251 dy = height;
00252 p2Brightness += 1.0 / ( dx*dx + dy*dy );
00253
00254 x += distance;
00255 }
00256
00257 p1Brightness /= (double)numLights;
00258 p2Brightness /= (double)numLights;
00259
00260 if (p1Brightness + p2Brightness != 0) {
00261
00262 percentDifference = (2.0*abs(p1Brightness - p2Brightness))/(p1Brightness + p2Brightness);
00263 percentDifference *= 100.0;
00264
00265 }
00266
00267 }
00268
00269
00270 int Lights::GetNumberOfLights() { return numLights; }
00271 double Lights::GetDistanceBetweenLights() { return distance; }
00272 double Lights::GetHeightAboveGround() { return height; }
00273 double Lights::GetP1Brightness() { return p1Brightness;}
00274 double Lights::GetP2Brightness() { return p2Brightness; }
00275 double Lights::GetPercentDifference() { return percentDifference; }
00276
00277
00278 void Lights::SetDistanceBetweenLights(double distance) { this->distance = distance; }
00279 void Lights::SetHeightAboveGround(double height) { this->height = height; }
00280 void Lights::SetViewDistance(double distance) { this->cameraPosition[2] = -distance; }
00281
00282 void Lights::MouseDown() { mouseIsDown = true; }
00283 void Lights::MouseUp() { mouseIsDown = false; }
00284
00285 void Lights::MouseMove(int x, int y) {
00286
00287 if (mouseIsDown) {
00288 lookPosition[0] += x*cameraPosition[2]/200.0f;
00289
00290 lookPosition[1] -= y*abs(cameraPosition[2])/200.0f;
00291 }
00292
00293 }
00294
00295
00296