Merge branch 'debug-shadows'

Conflicts:
	graphics.cc
	graphics.hh
	object.cc
This commit is contained in:
Fabian Klemp 2015-02-13 16:02:12 +01:00
commit 599c849bb0
9 changed files with 226 additions and 72 deletions

View File

@ -69,7 +69,7 @@
</object> </object>
<light> <light>
<xOffset>0.0</xOffset> <xOffset>0.0</xOffset>
<yOffset>3</yOffset> <yOffset>2</yOffset>
<zOffset>0.0</zOffset> <zOffset>0.0</zOffset>
<rColour>1.0</rColour> <rColour>1.0</rColour>
<gColour>1.0</gColour> <gColour>1.0</gColour>

View File

@ -1,7 +1,7 @@
#version 150 #version 150
out float fragmentDepth; out float gl_FragDepth;
void main() { void main() {
fragmentDepth = gl_FragCoord.z; gl_FragDepth = gl_FragCoord.z;
} }

16
Shader/depth_cube.fsh Normal file
View File

@ -0,0 +1,16 @@
#version 150
in vec4 fragPosition;
uniform float farPlane;
out float gl_FragDepth;
void main() {
float nearPlane = 0.1;
float A = -(farPlane+nearPlane)/(farPlane-nearPlane);
float B = -2*(farPlane*nearPlane)/(farPlane - nearPlane);
float value = 0.5*(-A*length(fragPosition) + B)/length(fragPosition) + 0.5;
gl_FragDepth = value;
//gl_FragDepth = length(fragPosition)/farPlane;
}

15
Shader/depth_cube.vsh Normal file
View File

@ -0,0 +1,15 @@
#version 150
in vec3 aPosition;
in vec3 aNormal;
in vec3 aTexcoord;
uniform mat4 modelViewProjectionMatrix;
uniform mat4 modelViewMatrix;
out vec4 fragPosition;
void main() {
fragPosition = modelViewMatrix * vec4(aPosition, 1.0);
gl_Position = modelViewProjectionMatrix * vec4(aPosition, 1.0);
}

View File

@ -9,7 +9,16 @@ out vec4 oColor;
uniform sampler2D uTexture; uniform sampler2D uTexture;
uniform sampler2DShadow shadowMap; uniform sampler2DShadow shadowMap;
uniform samplerCubeShadow shadowMap_cube; uniform samplerCubeShadow shadowMap_cube0;
uniform samplerCubeShadow shadowMap_cube1;
uniform samplerCubeShadow shadowMap_cube2;
uniform samplerCubeShadow shadowMap_cube3;
uniform samplerCubeShadow shadowMap_cube4;
uniform samplerCubeShadow shadowMap_cube5;
uniform samplerCubeShadow shadowMap_cube6;
uniform samplerCubeShadow shadowMap_cube7;
uniform samplerCubeShadow shadowMap_cube8;
uniform samplerCubeShadow shadowMap_cube9;
uniform vec3 ambientColor; uniform vec3 ambientColor;
uniform float ambientFactor; uniform float ambientFactor;
uniform float diffuseFactor; uniform float diffuseFactor;
@ -70,9 +79,10 @@ float samplePointShadow(samplerCubeShadow shadowMap, vec3 lightDirection) {
float A = -(farPlane+nearPlane)/(farPlane-nearPlane); float A = -(farPlane+nearPlane)/(farPlane-nearPlane);
float B = -2*(farPlane*nearPlane)/(farPlane - nearPlane); float B = -2*(farPlane*nearPlane)/(farPlane - nearPlane);
float compValue = 0.5*(-A*length(lightDirection) + B)/length(lightDirection) + 0.5; float compValue = 0.5*(-A*length(lightDirection) + B)/length(lightDirection) + 0.5;
float bias = 0.005; float bias = 0.001*tan(acos(clamp(dot(vNormal, -directionalLightVector), 0.0, 1.0)));
vec3 vector = vec3(-lightDirection.x, -lightDirection.y, lightDirection.z); bias = clamp(bias, 0.0, 0.01);
return texture(shadowMap, vec4(vector , compValue - bias)); //return texture(shadowMap, vec4(lightDirection , length(lightDirection)/farPlane - bias));
return texture(shadowMap, vec4(lightDirection , compValue - bias));
} }
float distanceToBorder(vec2 vector) { float distanceToBorder(vec2 vector) {
@ -91,11 +101,13 @@ void main()
// direction lighting // direction lighting
if(length(directionalLightVector)>0.0f) { if(length(directionalLightVector)>0.0f) {
vec3 directionalVector = normalize(directionalLightVector); vec3 directionalVector = normalize(directionalLightVector);
float directionalVisibility = sampleDirectionalShadow(shadowMap, shadowCoord);
diffuseColor += clamp(dot(normalize(vNormal), directionalVector) diffuseColor += clamp(dot(normalize(vNormal), directionalVector)
*diffuseFactor*directionalIntensity*directionalColor, 0.0, 1.0); *diffuseFactor*directionalIntensity*directionalColor, 0.0, 1.0)*directionalVisibility;
vec3 cameraVector = normalize(camera - vec3(fragPosition)); vec3 cameraVector = normalize(camera - vec3(fragPosition));
specularColor += clamp(pow((dot((cameraVector+directionalVector),normalize(vNormal))/(length(cameraVector+directionalVector)*length(normalize(vNormal)))),shininess), 0.0, 1.0) specularColor += clamp(pow((dot((cameraVector+directionalVector),normalize(vNormal))/
*specularFactor*directionalIntensity*directionalColor; (length(cameraVector+directionalVector)*length(normalize(vNormal)))),shininess), 0.0, 1.0)
*specularFactor*directionalIntensity*directionalColor*directionalVisibility;
} }
// point lights // point lights
@ -103,24 +115,58 @@ void main()
for(int i = 0; i<lightCount; i++) { for(int i = 0; i<lightCount; i++) {
vec3 lightDirection = vec3(fragPosition) - lightSources[i]; vec3 lightDirection = vec3(fragPosition) - lightSources[i];
float distance = length(lightDirection); float distance = length(lightDirection);
float pointVisibility = 0.0f;
// only take lights into account with meaningful contribution // only take lights into account with meaningful contribution
if (distance > 0.001f) { if (distance < farPlane) {
if (i == 0) {
pointVisibility = samplePointShadow(shadowMap_cube0, lightDirection);
}
if (i == 1) {
pointVisibility = samplePointShadow(shadowMap_cube1, lightDirection);
}
if (i == 2) {
pointVisibility = samplePointShadow(shadowMap_cube2, lightDirection);
}
if (i == 3) {
pointVisibility = samplePointShadow(shadowMap_cube3, lightDirection);
}
if (i == 4) {
pointVisibility = samplePointShadow(shadowMap_cube4, lightDirection);
}
if (i == 5) {
pointVisibility = samplePointShadow(shadowMap_cube5, lightDirection);
}
if (i == 6) {
pointVisibility = samplePointShadow(shadowMap_cube6, lightDirection);
}
if (i == 7) {
pointVisibility = samplePointShadow(shadowMap_cube7, lightDirection);
}
if (i == 8) {
pointVisibility = samplePointShadow(shadowMap_cube8, lightDirection);
}
if (i == 9) {
pointVisibility = samplePointShadow(shadowMap_cube9, lightDirection);
}
vec3 lightVector = normalize(lightSources[i]-vec3(fragPosition)); vec3 lightVector = normalize(lightSources[i]-vec3(fragPosition));
float intensity = clamp(exp(-(1/lightIntensities[i])*distance), 0.0, 1.0); float intensity = clamp(exp(-(1/lightIntensities[i])*distance), 0.0, 1.0);
diffuseColor += clamp(dot(normalize(vNormal), lightVector) diffuseColor += clamp(dot(normalize(vNormal), lightVector)
*diffuseFactor*intensity*lightColors[i], 0.0, 1.0); *diffuseFactor*intensity*lightColors[i], 0.0, 1.0)*pointVisibility;
vec3 cameraVector = normalize(camera - vec3(fragPosition)); vec3 cameraVector = normalize(camera - vec3(fragPosition));
specularColor += clamp(pow((dot((cameraVector+lightVector),normalize(vNormal))/(length(cameraVector+lightVector)*length(normalize(vNormal)))),shininess), 0.0, 1.0) specularColor += clamp(pow((dot((cameraVector+lightVector),normalize(vNormal))/
*specularFactor*intensity*lightColors[i]; (length(cameraVector+lightVector)*length(normalize(vNormal)))),shininess), 0.0, 1.0)
visibility = samplePointShadow(shadowMap_cube, lightDirection); *specularFactor*intensity*lightColors[i]*pointVisibility;
} }
} }
// shadows
visibility *= sampleDirectionalShadow(shadowMap, shadowCoord);
specularColor *= visibility;
diffuseColor *= visibility;
vec3 finalColor = specularColor + diffuseColor + ambientColor; vec3 finalColor = specularColor + diffuseColor + ambientColor;
float distanceCameraCenter = distance(cameraCenter, vec3(fragPosition)); float distanceCameraCenter = distance(cameraCenter, vec3(fragPosition));

View File

@ -1,7 +1,9 @@
#include "graphics.hh" #include "graphics.hh"
#include "lodepng.h"
#include <iomanip> #include <iomanip>
#include <sstream> #include <sstream>
#include <functional>
#include <ACGL/OpenGL/Creator/ShaderProgramCreator.hh> #include <ACGL/OpenGL/Creator/ShaderProgramCreator.hh>
@ -41,7 +43,10 @@ void Graphics::init(Level* level) {
depthShader = ShaderProgramCreator("depth") depthShader = ShaderProgramCreator("depth")
.attributeLocations(vao->getAttributeLocations()).create(); .attributeLocations(vao->getAttributeLocations()).create();
depthTexture = SharedTexture2D( new Texture2D(windowSize, GL_DEPTH_COMPONENT16)); depthCubeShader = ShaderProgramCreator("depth_cube")
.attributeLocations(vao->getAttributeLocations()).create();
depthTexture = SharedTexture2D( new Texture2D(windowSize, GL_DEPTH_COMPONENT24));
depthTexture->setMinFilter(GL_NEAREST); depthTexture->setMinFilter(GL_NEAREST);
depthTexture->setMagFilter(GL_NEAREST); depthTexture->setMagFilter(GL_NEAREST);
depthTexture->setWrapS(GL_CLAMP_TO_EDGE); depthTexture->setWrapS(GL_CLAMP_TO_EDGE);
@ -52,11 +57,18 @@ void Graphics::init(Level* level) {
framebuffer->setDepthTexture(depthTexture); framebuffer->setDepthTexture(depthTexture);
framebuffer->validate(); framebuffer->validate();
/*depth_cubeMaps = std::vector<ACGL::OpenGL::SharedTextureCubeMap>(level->getLights()->size()); glGetIntegerv(GL_MAX_COMBINED_TEXTURE_IMAGE_UNITS, &number_of_texture_units);
for (unsigned int i = 0; i<depth_cubeMaps.size(); i++) {*/ printf("Your graphics card supports %d texture units.\n", number_of_texture_units);
depth_cubeMaps = std::vector<ACGL::OpenGL::SharedTextureCubeMap>(std::min(int(level->getLights()->size()), 1)); // Exit if we need more texture units
for (unsigned int i = 0; i<1 && i<depth_cubeMaps.size(); i++) { if (number_of_texture_units < 12) {
depth_cubeMaps.at(i) = SharedTextureCubeMap(new TextureCubeMap(glm::vec2(cube_size, cube_size), GL_DEPTH_COMPONENT16)); printf("You need at least 12 texture units to run this application. Exiting\n");
exit(-1);
}
// always generate and bind 32 cube maps, because otherwise the shader won't work
depth_cubeMaps = std::vector<ACGL::OpenGL::SharedTextureCubeMap>(10);
for (unsigned int i = 0; i<depth_cubeMaps.size(); i++) {
depth_cubeMaps.at(i) = SharedTextureCubeMap(new TextureCubeMap(glm::vec2(cube_size, cube_size), GL_DEPTH_COMPONENT24));
depth_cubeMaps.at(i)->setMinFilter(GL_NEAREST); depth_cubeMaps.at(i)->setMinFilter(GL_NEAREST);
depth_cubeMaps.at(i)->setMagFilter(GL_NEAREST); depth_cubeMaps.at(i)->setMagFilter(GL_NEAREST);
depth_cubeMaps.at(i)->setWrapS(GL_CLAMP_TO_EDGE); depth_cubeMaps.at(i)->setWrapS(GL_CLAMP_TO_EDGE);
@ -66,12 +78,17 @@ void Graphics::init(Level* level) {
framebuffer_cube = SharedFrameBufferObject(new FrameBufferObject()); framebuffer_cube = SharedFrameBufferObject(new FrameBufferObject());
depthTexture_cube = SharedTexture2D( new Texture2D(windowSize, GL_DEPTH_COMPONENT16)); lightingShader->use();
depthTexture_cube->setMinFilter(GL_NEAREST);
depthTexture_cube->setMagFilter(GL_NEAREST); lightingShader->setTexture("shadowMap", depthTexture, 1);
depthTexture_cube->setWrapS(GL_CLAMP_TO_EDGE);
depthTexture_cube->setWrapT(GL_CLAMP_TO_EDGE); if (level->getLights()->size() > 0) {
depthTexture_cube->setCompareMode(GL_COMPARE_REF_TO_TEXTURE); for(unsigned int i = 0; i<depth_cubeMaps.size(); i++){
// start with texture unit 2 because the first two are used by the texture and the directional shadow map
lightingShader->setTexture("shadowMap_cube" + std::to_string(i), depth_cubeMaps.at(i), i+2);
}
}
updateClosestLights();
} }
glm::uvec2 Graphics::getWindowSize() { glm::uvec2 Graphics::getWindowSize() {
@ -81,29 +98,35 @@ glm::uvec2 Graphics::getWindowSize() {
void Graphics::render(double time) void Graphics::render(double time)
{ {
// At first render shadows // At first render shadows
depthShader->use(); depthCubeShader->use();
depthCubeShader->setUniform("farPlane", farPlane);
// render depth textures for point lights // render depth textures for point lights
glViewport(0, 0, cube_size, cube_size); glViewport(0, 0, cube_size, cube_size);
glm::mat4 depthProjectionMatrix_pointlights = glm::perspective(1.571f, (float)cube_size/(float)cube_size, 0.1f, farPlane); glm::mat4 depthProjectionMatrix_pointlights = glm::perspective(1.571f, (float)cube_size/(float)cube_size, 0.1f, farPlane);
glm::vec3 looking_directions[6] = {glm::vec3(-1.0f, 0.0f, 0.0f), glm::vec3(1.0f, 0.0f, 0.0f), glm::vec3(0.0f, 1.0f, 0.0f), glm::vec3 looking_directions[6] = {glm::vec3(1.0f, 0.0f, 0.0f), glm::vec3(-1.0f, 0.0f, 0.0f), glm::vec3(0.0f, 1.0f, 0.0f),
glm::vec3(0.0f, -1.0f, 0.0f), glm::vec3(0.0f, 0.0f, 1.0f), glm::vec3(0.0f, 0.0f, -1.0f)}; glm::vec3(0.0f, -1.0f, 0.0f), glm::vec3(0.0f, 0.0f, 1.0f), glm::vec3(0.0f, 0.0f, -1.0f)};
glm::vec3 upvectors[6] = {glm::vec3(0.0f, -1.0f, 0.0f),glm::vec3(0.0f, -1.0f, 0.0f),glm::vec3(0.0f, 0.0f, -1.0f),
glm::vec3(0.0f, 0.0f, -1.0f),glm::vec3(0.0f, -1.0f, 0.0f),glm::vec3(0.0f, -1.0f, 0.0f)};
framebuffer_cube->bind(); framebuffer_cube->bind();
//for (unsigned int i_pointlight = 0; i_pointlight<level->getLights()->size(); i_pointlight++) { for (unsigned int i_pointlight = 0; i_pointlight<closestLights->size(); i_pointlight++) {
for (unsigned int i_pointlight = 0; i_pointlight<1 && i_pointlight<level->getLights()->size(); i_pointlight++) {
// render each side of the cube // render each side of the cube
for (int i_face = 0; i_face<6; i_face++) { for (int i_face = 0; i_face<6; i_face++) {
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_CUBE_MAP_POSITIVE_X + i_face, depth_cubeMaps.at(i_pointlight)->getObjectName(), 0); glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_CUBE_MAP_POSITIVE_X + i_face, depth_cubeMaps.at(i_pointlight)->getObjectName(), 0);
glClear(GL_DEPTH_BUFFER_BIT); glClear(GL_DEPTH_BUFFER_BIT);
glm::mat4 depthViewProjectionMatrix_face = depthProjectionMatrix_pointlights * glm::lookAt(level->getLights()->at(i_pointlight).getPosition(), glm::mat4 viewMatrix = glm::lookAt(closestLights->at(i_pointlight).getPosition(),
level->getLights()->at(i_pointlight).getPosition() + looking_directions[i_face], glm::vec3(0.0f, 1.0f, 0.0f)); closestLights->at(i_pointlight).getPosition() + looking_directions[i_face], upvectors[i_face]);
level->render(depthShader, false, &depthViewProjectionMatrix_face); glm::mat4 depthViewProjectionMatrix_face = depthProjectionMatrix_pointlights * viewMatrix;
std::vector<glm::mat4> viewMatrixVector = std::vector<glm::mat4>();
viewMatrixVector.push_back(viewMatrix);
level->render(depthCubeShader, false, &depthViewProjectionMatrix_face, &viewMatrixVector);
if (!framebuffer_cube->isFrameBufferObjectComplete()) { if (!framebuffer_cube->isFrameBufferObjectComplete()) {
printf("Framebuffer incomplete, unknown error occured during shadow generation!\n"); printf("Framebuffer incomplete, unknown error occured during shadow generation!\n");
} }
} }
} }
// render depth texture for sun // render depth texture for sun
depthShader->use();
glViewport(0, 0, windowSize.x, windowSize.y); glViewport(0, 0, windowSize.x, windowSize.y);
// far pass // far pass
@ -123,18 +146,15 @@ void Graphics::render(double time)
lightingShader->use(); lightingShader->use();
if (level->getLights()->size() > 0) {
lightingShader->setTexture("shadowMap_cube", depth_cubeMaps.at(0), 4);
}
//set lighting parameters //set lighting parameters
// TODO look into doing this less often, offload to another thread? // TODO look into doing this less often, offload to another thread?
// TODO figure out how to deal with bigger numbers of lights. load the nearest on demand? // TODO figure out how to deal with bigger numbers of lights. load the nearest on demand?
double nextUpdate = lastUpdate + lightUpdateDelay; double nextUpdate = lastUpdate + lightUpdateDelay;
if (time >= nextUpdate) if (time >= nextUpdate)
{ {
updateLights(); updateShaderLights();
lastUpdate = time; lastUpdate = time;
} }
@ -146,9 +166,6 @@ void Graphics::render(double time)
0.5, 0.5, 0.5, 1.0 0.5, 0.5, 0.5, 1.0
); );
glm::mat4 depthBiasVP = biasMatrix*depthViewProjectionMatrix; glm::mat4 depthBiasVP = biasMatrix*depthViewProjectionMatrix;
lightingShader->setTexture("shadowMap", depthTexture, 1);
lightingShader->setUniform("farPlane", farPlane); lightingShader->setUniform("farPlane", farPlane);
// set fog Parameters // set fog Parameters
@ -169,28 +186,54 @@ void Graphics::render(double time)
level->render(lightingShader, true, &lightingViewProjectionMatrix, &shadowVPs); level->render(lightingShader, true, &lightingViewProjectionMatrix, &shadowVPs);
} }
void Graphics::updateLights() { bool Graphics::compareLightDistances(Light a, Light b) {
if (level->getLights()->size() > 0) { if (glm::distance(this->level->getCameraCenter()->getPosition(), a.getPosition()) <
lightingShader->setUniform("lightCount", (int) level->getLights()->size()); glm::distance(this->level->getCameraCenter()->getPosition(), b.getPosition())) {
return true;
}
else {
return false;
}
}
void Graphics::updateClosestLights() {
if (level->getLights()->size() <= 32) {
this->closestLights = level->getLights();
}
else {
closestLightsVector = std::vector<Light>(*level->getLights());
std::sort(closestLightsVector.begin(),
closestLightsVector.end(),
[this](Light a, Light b) {return compareLightDistances(a, b); });
closestLightsVector = std::vector<Light>(&closestLightsVector[0],
&closestLightsVector[31]);
closestLights = &closestLightsVector;
}
}
void Graphics::updateShaderLights() {
updateClosestLights();
if (closestLights->size() > 0) {
lightingShader->setUniform("lightCount", (int) closestLights->size());
// Build light position array // Build light position array
glm::vec3 lightSources[level->getLights()->size()]; glm::vec3 lightSources[closestLights->size()];
for(unsigned int i = 0; i<level->getLights()->size(); i++) { for(unsigned int i = 0; i<closestLights->size(); i++) {
lightSources[i] = level->getLights()->at(i).getPosition(); lightSources[i] = closestLights->at(i).getPosition();
} }
glUniform3fv(lightingShader->getUniformLocation("lightSources"), glUniform3fv(lightingShader->getUniformLocation("lightSources"),
sizeof(lightSources), (GLfloat*) lightSources); sizeof(lightSources), (GLfloat*) lightSources);
// Build light colour array // Build light colour array
glm::vec3 lightColours[level->getLights()->size()]; glm::vec3 lightColours[closestLights->size()];
for(unsigned int i = 0; i<level->getLights()->size(); i++) { for(unsigned int i = 0; i<closestLights->size(); i++) {
lightColours[i] = level->getLights()->at(i).getColour(); lightColours[i] = closestLights->at(i).getColour();
} }
glUniform3fv(lightingShader->getUniformLocation("lightColors"), glUniform3fv(lightingShader->getUniformLocation("lightColors"),
sizeof(lightColours), (GLfloat*) lightColours); sizeof(lightColours), (GLfloat*) lightColours);
// Build light attenuation array // Build light attenuation array
float lightIntensities[level->getLights()->size()]; float lightIntensities[closestLights->size()];
for(unsigned int i = 0; i<level->getLights()->size(); i++) { for(unsigned int i = 0; i<closestLights->size(); i++) {
lightIntensities[i] = level->getLights()->at(i).getIntensity(); lightIntensities[i] = closestLights->at(i).getIntensity();
} }
glUniform1fv(lightingShader->getUniformLocation("lightIntensities"), glUniform1fv(lightingShader->getUniformLocation("lightIntensities"),
sizeof(lightIntensities), (GLfloat*) lightIntensities); sizeof(lightIntensities), (GLfloat*) lightIntensities);
@ -222,3 +265,25 @@ glm::mat4 Graphics::buildViewMatrix(Level* level) {
float Graphics::getFarPlane() { float Graphics::getFarPlane() {
return farPlane; return farPlane;
} }
void Graphics::saveDepthBufferToDisk(int face, std::string filename) {
printf("Starting saving of depth buffer...\n");
float *depthbuffer = new float[1024*1024];
std::vector<unsigned char> image (1024 * 1024 * 4);
glGetTexImage(GL_TEXTURE_CUBE_MAP_POSITIVE_X + face, 0, GL_DEPTH_COMPONENT, GL_FLOAT, depthbuffer);
for (unsigned int i = 0; i<1024*1024; i++) {
image[i * 4 + 0] = depthbuffer[i] * 255;
image[i * 4 + 1] = depthbuffer[i] * 255;
image[i * 4 + 2] = depthbuffer[i] * 255;
image[i * 4 + 3] = 255;
}
unsigned error = lodepng::encode(filename.c_str(), image, 1024, 1024);
if (error) {
std::cout << "Encoder error " << error << ": " << lodepng_error_text(error) << std::endl;
}
else {
printf("Saving complete!\n");
}
delete [] depthbuffer;
}

View File

@ -19,20 +19,27 @@ class Graphics {
void resize(glm::uvec2 windowSize); void resize(glm::uvec2 windowSize);
float getFarPlane(); float getFarPlane();
private: private:
void updateLights(); void updateShaderLights();
void updateClosestLights();
bool compareLightDistances(Light a, Light b);
void saveDepthBufferToDisk(int face, std::string);
double lastUpdate; double lastUpdate;
glm::uvec2 windowSize; glm::uvec2 windowSize;
float nearPlane; float nearPlane;
float farPlane; float farPlane;
// pointer to either use the vector from the level or from here
std::vector<Light>* closestLights;
std::vector<Light> closestLightsVector; // contains the 32 closest lights
ACGL::OpenGL::SharedShaderProgram lightingShader; ACGL::OpenGL::SharedShaderProgram lightingShader;
ACGL::OpenGL::SharedShaderProgram depthCubeShader;
ACGL::OpenGL::SharedShaderProgram depthShader; ACGL::OpenGL::SharedShaderProgram depthShader;
ACGL::OpenGL::SharedTexture2D depthTexture; ACGL::OpenGL::SharedTexture2D depthTexture;
ACGL::OpenGL::SharedFrameBufferObject framebuffer; ACGL::OpenGL::SharedFrameBufferObject framebuffer;
std::vector<ACGL::OpenGL::SharedTextureCubeMap> depth_cubeMaps; std::vector<ACGL::OpenGL::SharedTextureCubeMap> depth_cubeMaps;
ACGL::OpenGL::SharedFrameBufferObject framebuffer_cube; ACGL::OpenGL::SharedFrameBufferObject framebuffer_cube;
ACGL::OpenGL::SharedTexture2D depthTexture_cube;
int cube_size; int cube_size;
Level* level; Level* level;
int number_of_texture_units = 0;
}; };
#endif #endif

View File

@ -14,7 +14,7 @@ Object::~Object() {
} }
void Object::render(ACGL::OpenGL::SharedShaderProgram shader, bool lightingPass, void Object::render(ACGL::OpenGL::SharedShaderProgram shader, bool lightingPass,
glm::mat4* viewProjectionMatrix, std::vector<glm::mat4>* shadowVPs) { glm::mat4* viewProjectionMatrix, std::vector<glm::mat4>* additionalMatrices) {
if (!renderable) { if (!renderable) {
return; return;
} }
@ -27,15 +27,20 @@ void Object::render(ACGL::OpenGL::SharedShaderProgram shader, bool lightingPass,
shader->setUniform("shininess", material.getShininess()); shader->setUniform("shininess", material.getShininess());
shader->setTexture("uTexture", material.getReference(), 0); shader->setTexture("uTexture", material.getReference(), 0);
// set model matrix // set model matrix
shader->setUniform( "modelMatrix", modelMatrix); shader->setUniform("modelMatrix", modelMatrix);
// set shadowMVPs // set shadowMVPs
glm::mat4 shadowMVPs[5]; glm::mat4 shadowMVPs[5];
for(unsigned int i = 0; (i<shadowVPs->size() && i<5); i++) { for(unsigned int i = 0; (i<additionalMatrices->size() && i<5); i++) {
shadowMVPs[i] = shadowVPs->at(i) * modelMatrix; shadowMVPs[i] = additionalMatrices->at(i) * modelMatrix;
} }
glUniformMatrix4fv(shader->getUniformLocation("shadowMVPs"), glUniformMatrix4fv(shader->getUniformLocation("shadowMVPs"),
sizeof(shadowMVPs), false, (GLfloat*) shadowMVPs); sizeof(shadowMVPs), false, (GLfloat*) shadowMVPs);
} }
else {
if (additionalMatrices) {
shader->setUniform("modelViewMatrix", additionalMatrices->at(0) * modelMatrix);
}
}
glm::mat4 mvp = (*viewProjectionMatrix) * modelMatrix; glm::mat4 mvp = (*viewProjectionMatrix) * modelMatrix;
shader->setUniform("modelViewProjectionMatrix", mvp); shader->setUniform("modelViewProjectionMatrix", mvp);
// draw // draw

View File

@ -16,7 +16,7 @@ class Object : public Entity {
Object(); Object();
~Object(); ~Object();
void render(ACGL::OpenGL::SharedShaderProgram shader, bool lightingPass, void render(ACGL::OpenGL::SharedShaderProgram shader, bool lightingPass,
glm::mat4* viewProjcetionMatrix, std::vector<glm::mat4>* shadowVPs); glm::mat4* viewProjcetionMatrix, std::vector<glm::mat4>* additionalMatrices);
private: private:
Model model; Model model;
Material material; Material material;