Main Page | Namespace List | Class Hierarchy | Alphabetical List | Data Structures | File List | Namespace Members | Data Fields | Globals

/Users/blackie/Documents/myRepository/phobosengine-vc2005/phobosengine/phobosengine/SingleTexturedMesh.cpp

Go to the documentation of this file.
00001 
00002 
00003 #include "SingleTexturedMesh.h"
00004 
00005 #include "AABB.h"
00006 #include "Camera.h"
00007 #include "CoreEngine.h"
00008 #include "Renderer.h"
00009 #include "LightShader.h"
00010 #include "Sphere.h"
00011 #include "Texture.h"
00012 #include "TextureDatabase.h"
00013 #include "VBO.h"
00014 #include "World.h"
00015 
00016 
00017 namespace pge {
00018 
00019         //****************************************************************************
00020         //
00021         //
00022         //
00023         //****************************************************************************
00024         SingleTexturedMesh::SingleTexturedMesh(bool disableLightShader) : Mesh() {
00025                 m_texture = TextureDatabase::getInstance()->getDefaultTexture();
00026                 m_renderMode = Mesh::VertexBufferObject;
00027                 m_vbo = NULL;
00028                 m_vertexNum = 0;
00029                 m_disableLightShader = disableLightShader;
00030 
00031                 if(!m_disableLightShader) {
00032                         m_lightShader = new LightShader(CoreEngine::getInstance()->getCurrentWorld()->getLightProgram());
00033                 } else {
00034                         m_lightShader = NULL;
00035                 }
00036 
00037         }
00038 
00039 
00040         //****************************************************************************
00041         //
00042         //
00043         //
00044         //****************************************************************************
00045         SingleTexturedMesh::~SingleTexturedMesh(void) {
00046                 if(m_vbo != NULL) {
00047                         delete m_vbo;
00048                         m_vbo = NULL;
00049                 }
00050                 if(m_lightShader != NULL) {
00051                         delete m_lightShader;
00052                         m_lightShader = NULL;
00053                 }
00054         }
00055 
00056 
00057         //****************************************************************************
00058         //
00059         //
00060         //
00061         //****************************************************************************
00062         bool SingleTexturedMesh::init(void) {
00063                 Mesh::init();
00064                 buildVBO();
00065 
00066                 if(!m_disableLightShader && m_lightShader != NULL) {
00067                         getSurroundingLights();
00068                 }
00069 
00070                 return true;
00071         }
00072 
00073 
00074         //****************************************************************************
00075         //
00076         //
00077         //
00078         //****************************************************************************
00079         void SingleTexturedMesh::render(void) {
00080                 // Calculate alpha value based on distance to the camera.
00081                 Camera *camera = CoreEngine::getInstance()->getCurrentWorld()->getCamera();
00082                 float sqrDist = 0.0f;
00083                 float dist = 0.0f;
00084                 float maxDistance = 200.0f;
00085                 float minDistance = 180.0f;
00086 
00087                 // If the camera is inside of the mesh's sphere, then render without alpha.
00088                 if(m_boundingSphere->isIntersecting(*camera->getBoundingSphere())) {
00089                         m_alphaColor = 1.0f;
00090                 } else {
00091                         // Calculate distance to camera.
00092                         sqrDist = camera->getPosition().sqrDistance(m_boundingSphere->m_center);
00093                         if(sqrDist >= minDistance * minDistance) {
00094                                 if(sqrDist <= maxDistance * maxDistance) {
00095                                         // Calculate blend factor.
00096                                         dist = camera->getPosition().distance(m_boundingSphere->m_center) - minDistance;
00097                                         m_alphaColor = 1.0f - (dist / (maxDistance - minDistance));
00098                                 } else {
00099                                         m_alphaColor = 0.0f;
00100                                 }
00101                         } else {
00102                                 m_alphaColor = 1.0f;
00103                         }
00104                 }
00105                 if(m_alphaColor > 0.0f) {
00106                         renderVBO();
00107                 }
00108         }
00109 
00110 
00111         //****************************************************************************
00112         //
00113         //
00114         //
00115         //****************************************************************************
00116         void SingleTexturedMesh::setTexture(Texture *texture) {
00117                 if(texture != NULL) {
00118                         m_texture = texture;
00119                 }
00120         }
00121 
00122 
00123         //****************************************************************************
00124         //
00125         //
00126         //
00127         //****************************************************************************
00128         void SingleTexturedMesh::buildVBO(void) {
00129                 std::vector<Triangle*>::iterator it;
00130 
00131 
00132                 m_vertexNum = getVertexNum();
00133                 m_vbo = new VBO(m_vertexNum);
00134 
00135                 // Go through all triangles.
00136                 for(it = m_triangles->begin(); it != m_triangles->end(); it++) {
00137                         Triangle *triangle = *it;
00138 
00139                         m_vbo->addTriangle(triangle);
00140                 }
00141 
00142                 m_vbo->buildVBO();
00143         }
00144 
00145 
00146         //****************************************************************************
00147         //
00148         //
00149         //
00150         //****************************************************************************
00151         void SingleTexturedMesh::renderVBO(void) {
00152                 if(m_texture != NULL) {
00153                         // Enable alpha blending if the texture is set to it.
00154                         if(m_texture->hasAlphaBlending()) {
00155                                 renderer::setTextureAlphaBlendEnabled(true);
00156 
00157                         } else if(m_alphaColor < 1.0f) {
00158                                 renderer::setBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
00159                                 renderer::setBlendingEnabled(true);
00160                         }
00161                         renderer::setTexture(m_texture, GL_MODULATE);
00162                         renderer::color4f(1.0f, 1.0f, 1.0f, m_alphaColor);
00163 
00164                 } else {
00165                         glDisable(GL_TEXTURE_2D);
00166                 }
00167 
00168                 // Light shader.
00169                 if(!m_disableLightShader && m_lightShader != NULL) {
00170                         m_lightShader->preRender();
00171                 }
00172 
00173                 // Render.
00174                 m_vbo->renderVBO(0, m_vertexNum);
00175 
00176                 // Light shader.
00177                 if(!m_disableLightShader && m_lightShader != NULL) {
00178                         m_lightShader->postRender();
00179                 }
00180 
00181                 if(m_texture != NULL) {
00182                         // Disable alpha blending.
00183                         if(m_texture->hasAlphaBlending()) {
00184                                 renderer::setTextureAlphaBlendEnabled(false);
00185                         }
00186                 }
00187                 if(m_alphaColor < 1.0f) {
00188                         renderer::setBlendingEnabled(false);
00189                         // Reset alpha color.
00190                         renderer::color4f(1.0f, 1.0f, 1.0f, 1.0f);
00191                 }
00192         }
00193 
00194 
00195         //****************************************************************************
00196         //
00197         //
00198         //
00199         //****************************************************************************
00200         void SingleTexturedMesh::renderImmediate(void) {
00201         }
00202 
00203 
00204         //****************************************************************************
00205         //
00206         // TODO: What to do if there are less than 3 lights in the world?!
00207         //
00208         //****************************************************************************
00209         void SingleTexturedMesh::getSurroundingLights(void) {
00210                 int i;
00211                 World *world;
00212                 Light *light;
00213                 float distance;
00214                 float minDistance;
00215                 float tmpDistance;
00216                 Light *minLight1;
00217                 Light *minLight2;
00218                 Light *minLight3;
00219 
00220 
00221                 world = CoreEngine::getInstance()->getCurrentWorld();
00222 
00223                 // TODO: infinity for this map!
00224                 minDistance = 10000000.0f;
00225 
00226                 /*// Find the minimal distance light.
00227                 for(i = 0; i < world->getLightNum(); i++) {
00228                         light = world->getLightAt(i);
00229                         distance = Vector3f(light->m_position).distance(m_boundingBox->getCenter());
00230                         if(distance < minDistance) {
00231                                 minLight1 = light;
00232                                 minDistance = distance;
00233                         }
00234                 }
00235 
00236                 // TODO: infinity for this map!
00237                 tmpDistance = 10000000.0f;
00238 
00239                 // Find the second smallest distance light.
00240                 for(i = 0; i < world->getLightNum(); i++) {
00241                         light = world->getLightAt(i);
00242                         distance = Vector3f(light->m_position).distance(m_boundingBox->getCenter());
00243 
00244                         if(distance >= minDistance && distance < tmpDistance && light != minLight1) {
00245                                 minLight2 = light;
00246                                 tmpDistance = distance;
00247                         }
00248                 }
00249 
00250                 minDistance = tmpDistance;
00251 
00252                 // Find the third smallest distance light.
00253                 for(i = 0; i < world->getLightNum(); i++) {
00254                         light = world->getLightAt(i);
00255                         distance = Vector3f(light->m_position).distance(m_boundingBox->getCenter());
00256 
00257                         if(distance >= minDistance && distance < tmpDistance && light != minLight1 && light != minLight2) {
00258                                 minLight3 = light;
00259                                 tmpDistance = distance;
00260                         }
00261                 }*/
00262 
00263 
00264                 minLight1 = world->getLightAt(0);
00265                 minLight2 = world->getLightAt(1);
00266                 minLight3 = world->getLightAt(2);
00267 
00268                 m_lightShader->addActiveLight(minLight1);
00269                 m_lightShader->addActiveLight(minLight2);
00270                 m_lightShader->addActiveLight(minLight3);
00271         }
00272 };

Generated on Mon Oct 16 12:08:11 2006 for Phobosengine by doxygen 1.3.4