Related
I try to render a big block of individual cubes in OpenGL and i'm now experimenting with lighting.
It works quite good, but when viewing the cube from a certain angle, its shows highlights with shouldn't be there.
I altered the shader so the specular highlights are red.
I just expected them to not be there because the light comes from the direction with the all bright cubes and there should be no reflections from this lightsource on the side of the cube.
Another thing which bothers me is, that there is an edge(Pic 2) where color changes. This is also something i don't quite understand and seek help with.
This is present when I use a directional lightsource and view the big cube from a certain angle.
OpenGl Version ist 3.3, i'm on Windows and using c++ with cmake to build.
Here are some images:
Github Link, because SOT does not allow me to upload code becaues "it is not formatted"(trying like 20 min to format them to SOT likes).
Edit: It works now, who could have thought that it was the formatting of the images and not actually the cpp, glsl code.
Github
Important Files: light_proto.glsl, vertex.glsl, main.cpp
Files
main.cpp
// RENDER LOOP
while (!glfwWindowShouldClose(window))
{
// INPUT
//keysboard input, mouse input
processInput(window);
defaultShader.use();
// CAMERA
// model matrix set further down, dynamically for each object
//view matrix, transform world space to camera space
glm::mat4 view = glm::lookAt(cameraPos, cameraPos + cameraFront, cameraUp);
defaultShader.setMatrix4fv("view", view);
//projection matrix, view space to device cordinates
glm::mat4 projection = glm::perspective(glm::radians(fov), 800.0f / 600.0f, 0.1f, 100.0f);
defaultShader.setMatrix4fv("projection", projection);
// DRAWING
//clear color and depth buffer
glClearColor(0.2f, 0.3f, 0.3f, 1.0f);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
////vertex data, shaders
cube->use();
defaultShader.setVec3("viewPos", cameraPos.x, cameraPos.y, cameraPos.z);
defaultShader.setVec3("material.specular", 0.0f, 1.0f, 0.0f);
defaultShader.setFloat("material.shininess", 32.0f);
defaultShader.setVec3("dirLight.direction", -1.0f, -0.0f, 0.0f);
defaultShader.setVec3("dirLight.ambient", 0.2f, 0.2f, 0.2f);
defaultShader.setVec3("dirLight.diffuse", 0.8f, 0.8f, 0.8f); // darken diffuse light a bit
defaultShader.setVec3("dirLight.specular", 1.0f, 1.0f, 1.0f);
defaultShader.setVec3("pointLights[0].position", -1.0f, -1.0f, -1.0f);
defaultShader.setVec3("pointLights[0].ambient", 0.2f, 0.2f, 0.2f);
defaultShader.setVec3("pointLights[0].diffuse", 0.8f, 0.8f, 0.8f); // darken diffuse light a bit
defaultShader.setVec3("pointLights[0].specular", 1.0f, 1.0f, 1.0f);
defaultShader.setFloat("pointLights[0].constant", 1.0f);
defaultShader.setFloat("pointLights[0].linear", 0.045f);
defaultShader.setFloat("pointLights[0].quadratic", 0.0075f);
//defaultShader.setVec3("lightColor", 1.0f, 1.0f, 1.0f);
//defaultShader.setVec3("lightPos", -1.0f, lighty, -1.0f);
//defaultShader.setVec3("viewPos", cameraPos.x, cameraPos.y, cameraPos.z);
//defaultShader.setVec3("material.specular", 0.0f, 1.0f, 0.0f);
//defaultShader.setFloat("material.shininess", 128.0f);
//defaultShader.setVec3("light.direction", -10.0f, lighty, 10.0f);
//defaultShader.setBool("light.isDirectional", false);
//defaultShader.setVec3("light.ambient", 0.2f, 0.2f, 0.2f);
//defaultShader.setVec3("light.diffuse", 0.8f, 0.8f, 0.8f); // darken diffuse light a bit
//defaultShader.setVec3("light.specular", 1.0f, 1.0f, 1.0f);
//defaultShader.setFloat("light.constant", 1.0f);
//defaultShader.setFloat("light.linear", 0.045f);
//defaultShader.setFloat("light.quadratic", 0.0075f);
int cubesize = 30;
//draw cubes
for (float i = 0.0f; i < cubesize; i++) {
for (float j = 0.0f; j < cubesize; j++) {
for (float k = 0.0f; k < cubesize; k++) {
glm::mat4 model = glm::mat4(1.0f);
model = glm::translate(model, glm::vec3(i, j, k));
defaultShader.setMatrix4fv("model", model);
glDrawArrays(GL_TRIANGLES, 0, 36);
}
}
}
//DRAW LIGHT
light->use();
lightshader.use();
lightshader.setMatrix4fv("view", view);
lightshader.setMatrix4fv("projection", projection);
glm::mat4 model = glm::mat4(1.0f);
lighty += 0.1f * deltaTime;
model = glm::translate(model, glm::vec3(-1.0, -1.0, -1.0));
lightshader.setMatrix4fv("model", model);
glDrawArrays(GL_TRIANGLES, 0, 36);
//GLFW updating the window
glfwSwapBuffers(window);
glfwPollEvents();
}
Fragment Shader
#version 330 core
in vec2 TexCoord;
in vec3 Normal;
in vec3 FragPos;
struct DirLight {
vec3 direction;
vec3 ambient;
vec3 diffuse;
vec3 specular;
};
uniform DirLight dirLight;
vec3 CalcDirLight(DirLight light, vec3 normal, vec3 viewDir);
struct PointLight {
vec3 position;
float constant;
float linear;
float quadratic;
vec3 ambient;
vec3 diffuse;
vec3 specular;
};
#define NR_POINT_LIGHTS 1
uniform PointLight pointLights[NR_POINT_LIGHTS];
vec3 CalcPointLight(PointLight light, vec3 normal, vec3 fragPos, vec3 viewDir);
struct Material {
vec3 specular;
float shininess;
};
uniform Material material;
uniform sampler2D texture0;
uniform vec3 viewPos;
out vec4 FragColor;
void main()
{
// properties
vec3 norm = normalize(Normal);
vec3 viewDir = normalize(viewPos - FragPos);
// phase 1: Directional lighting
vec3 result = CalcDirLight(dirLight, norm, viewDir);
// phase 2: Point lights
for(int i = 0; i < NR_POINT_LIGHTS; i++)
//result += CalcPointLight(pointLights[i], norm, FragPos, viewDir);
FragColor = texture2D(texture0, TexCoord) * vec4(result, 1.0);
}
vec3 CalcDirLight(DirLight light, vec3 normal, vec3 viewDir)
{
vec3 lightDir = normalize(-light.direction);
// diffuse shading
float diff = max(dot(normal, lightDir), 0.0);
// specular shading
vec3 reflectDir = reflect(-lightDir, normal);
float spec = pow(max(dot(viewDir, reflectDir), 0.0), material.shininess);
// combine results
vec3 ambient = light.ambient * vec3(texture(texture0, TexCoord));
vec3 diffuse = light.diffuse * diff * vec3(texture(texture0, TexCoord));
vec3 specular = light.specular * spec * vec3(1.0f, 0.0f, 0.0f);
return (ambient + diffuse + specular);
}
vec3 CalcPointLight(PointLight light, vec3 normal, vec3 fragPos, vec3 viewDir)
{
vec3 lightDir = normalize(light.position - fragPos);
// diffuse shading
float diff = max(dot(normal, lightDir), 0.0);
// specular shading
vec3 reflectDir = reflect(-lightDir, normal);
float spec = pow(max(dot(viewDir, reflectDir), 0.0), material.shininess);
// attenuation
float distance = length(light.position - fragPos);
float attenuation = 1.0 / (light.constant + light.linear * distance +
light.quadratic * (distance * distance));
// combine results
vec3 ambient = light.ambient * vec3(texture(texture0, TexCoord));
vec3 diffuse = light.diffuse * diff * vec3(texture(texture0, TexCoord));
vec3 specular = light.specular * spec * vec3(1.0f, 1.0f, 1.0f);
ambient *= attenuation;
diffuse *= attenuation;
specular *= attenuation;
return (ambient + diffuse + specular);
}
Vertex Shader
#version 330 core
layout (location = 0) in vec3 aPos;
layout (location = 1) in vec2 aTexCoord;
layout (location = 2) in vec3 aNormal;
out vec2 TexCoord;
out vec3 Normal;
out vec3 FragPos;
uniform mat4 model;
uniform mat4 view;
uniform mat4 projection;
void main(){
gl_Position = projection * view * model * vec4(aPos, 1.0f);
FragPos = vec3(model * vec4(aPos, 1.0));
TexCoord = vec2(aTexCoord.x, aTexCoord.y);
Normal = aNormal;
};
It looks like you have one issue and a half
First in image 2 (and 3) the reason why there is a line in the diamond texture is due to texture filtering.
I checked your source code in Texture.cpp the Minification filter is set to GL_NEAREST_MIPMAP_NEAREST and you also generate the relative mipsmaps.
If you change
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST_MIPMAP_NEAREST);
to
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
at line 23 of Texture.cpp and remove
glGenerateMipmap(GL_TEXTURE_2D);
the line should disapper
I do not understand where the problem stands with the red specular light, if you could show the source of the light direction i think might be able to help
I am learning OpenGL from http://learnopengl.com and I have a problem with transformation based on this chapter Coordinate Systems...
I want to render something like this Movie but I have something like this Movie2 in 5 seconds its back on the screen. Sorry for many links but I think it's easier to show this by video.
It's my render loop:
const auto projection = glm::perspectiveFov(glm::radians(45.0f), 800.0f, 600.0f, 0.1f, 100.0f);
const auto view = glm::translate(glm::mat4(1.0f), glm::vec3(0.0f, 0.0f, -3.0f));
while (!glfwWindowShouldClose(window))
{
processInput(window);
glClearColor(0.2f, 0.3f, 0.3f, 1.0f);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
flatColorShader->bind();
flatColorShader->setMat4("u_Projection", projection);
flatColorShader->setMat4("u_View", view);
auto model = glm::mat4(1.0f);
model = glm::rotate(model, static_cast<float>(glfwGetTime()) * glm::radians(50.0f), glm::vec3(0.5f, 1.0f, 0.0f));
flatColorShader->setMat4("u_Model", model);
glDrawArrays(GL_TRIANGLES, 0, 36);
glBindVertexArray(vao);
glfwSwapBuffers(window);
glfwPollEvents();
}
Vaertex shader:
#version 460 core
layout (location = 0) in vec3 a_Pos;
layout (location = 1) in vec2 a_TexCoord;
out vec2 v_TexCoord;
uniform mat4 u_Projection;
uniform mat4 u_Model;
uniform mat4 u_View;
void main()
{
v_TexCoord = vec2(a_TexCoord.x, 1.0f - a_TexCoord.y);
gl_Position = u_Projection * u_Model * u_View * vec4(a_Pos, 1.0);
}
And Fragment shader:
#version 460 core
in vec2 v_TexCoord;
out vec4 color;
uniform sampler2D u_Texture;
void main()
{
color = texture(u_Texture, v_TexCoord);
}
I suppose it is a problem with the model matrix, but I don't known what. Can somebody help me with that's problem?
The order of the vertex transformations in the vertex shader is incorrect:
gl_Position = u_Projection * u_Model * u_View * vec4(a_Pos, 1.0);
gl_Position = u_Projection * u_View * u_Model * vec4(a_Pos, 1.0);
The order matters, because matrix multiplications are not commutative.
I am trying to build lighting using this tutorial. However, lighting appears on wrong side of human object and I do not know why.
Normals were created per triangle. Vertices of a triangle basically have the same normal:
glm::vec3 calculateNormal(glm::vec3 vertice_1, glm::vec3 vertice_2, glm::vec3 vertice_3)
{
glm::vec3 vector_1 = vertice_2 - vertice_1;
glm::vec3 vector_2 = vertice_3 - vertice_1;
return glm::normalize(glm::cross(vector_1, vector_2));
}
Here is code for vertex shader:
#version 330 core
layout (location = 0) in vec3 pos;
layout (location = 1) in vec3 normal;
out vec4 vert_color;
out vec3 Normal;
out vec3 FragPos;
uniform mat4 model;
uniform mat4 view;
uniform mat4 projection;
uniform mat4 transform;
uniform vec4 color;
void main()
{
vert_color = color;
gl_Position = projection * view * model * transform * vec4(pos.x, pos.y, pos.z, 1.0);
FragPos = vec3(model * transform * vec4(pos, 1.0));
Normal = normal;
}
Fragment shader:
#version 330 core
uniform vec3 cameraPos;
uniform vec3 lightPos;
uniform vec3 lightColor;
in vec4 vert_color;
in vec3 FragPos;
in vec3 Normal;
out vec4 frag_color;
void main()
{
float ambientStrength = 0.1;
float specularStrength = 0.5;
vec3 ambient = ambientStrength * lightColor;
vec3 lightDir = normalize(lightPos - FragPos);
float diff = max(dot(Normal, lightDir), 0.0);
vec3 diffuse = diff * lightColor;
vec3 viewDir = normalize(cameraPos - FragPos);
vec3 reflectDir = reflect(-lightDir, Normal);
float spec = pow(max(dot(viewDir, reflectDir), 0.0), 32);
vec3 specular = specularStrength * spec * lightColor;
vec3 result = (ambient + diffuse + specular) * vec3(vert_color.x, vert_color.y, vert_color.z);
frag_color = vec4(result, vert_color.w);
}
Main loop:
wxGLCanvas::SetCurrent(*glContext);
glClearDepth(1.0f);
glEnable(GL_BLEND);
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
glDepthFunc(GL_LEQUAL);
glEnable(GL_DEPTH_TEST);
glm::mat4 model, view, projection;
model = glm::translate(model, modelPos); // modelPos is
view = fpsCamera->getViewMatrix();
projection = fpsCamera->getProjectionMatrix(windowWidth, windowHeight);
color = glm::vec4(0.310f, 0.747f, 0.185f, 1.0f);
glm::vec3 lightPos = glm::vec3(0.0f, 1.0f, 0.0f);
glm::vec3 lightColor = glm::vec3(1.0f, 1.0f, 1.0f);
glm::mat4 phantomtTransformation;
phantomtTransformation = glm::rotate(phantomtTransformation, - glm::pi<float>() / 2.0f, glm::vec3(1.0f, 0.0f, 0.0f));
phantomtTransformation = glm::rotate(phantomtTransformation, - glm::pi<float>() , glm::vec3(0.0f, 0.0f, 1.0f));
ShaderProgram shaderProgram;
shaderProgram.loadShaders("Shaders/phantom.vert", "Shaders/phantom.frag");
glClearStencil(0);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT);
shaderProgram.use();
shaderProgram.setUniform("transform", phantomtTransformation);
shaderProgram.setUniform("model", model);
shaderProgram.setUniform("view", view);
shaderProgram.setUniform("projection", projection);
shaderProgram.setUniform("color", color);
shaderProgram.setUniform("lightColor", lightColor);
shaderProgram.setUniform("lightPos", lightPos);
shaderProgram.setUniform("cameraPos", fpsCamera->getPosition());
glStencilMask(0xFF); // Write to stencil buffer
glStencilOp(GL_KEEP, GL_KEEP, GL_REPLACE);
glStencilFunc(GL_ALWAYS, 0, 0xFF); // Set any stencil to 0
glStencilFunc(GL_ALWAYS, 1, 0xFF); // Set any stencil to object ID
m_pantomMesh->draw();
glStencilFunc(GL_ALWAYS, 0, 0xFF); // Set any stencil to 0 // no need for testing
glFlush();
wxGLCanvas::SwapBuffers();
View from front of the object:
View from back of the object:
EDIT:
In order to debug I removed object rotation matrix from main loop:
glm::mat4 phantomtTransformation;
phantomtTransformation = glm::rotate(phantomtTransformation, - glm::pi<float>() / 2.0f, glm::vec3(1.0f, 0.0f, 0.0f));
phantomtTransformation = glm::rotate(phantomtTransformation, - glm::pi<float>() , glm::vec3(0.0f, 0.0f, 1.0f));
shaderProgram.setUniform("transform", phantomtTransformation);
and changed line in fragment shader from
frag_color = vec4(result, vert_color.w);
to
frag_color = vec4(Normal, vert_color.w);
in order to visualize Normal values. As a result I noticed that when camera changes position phantom also changes color which means that normal values are also changing.
I think the cause of your problem is that you are not applying your model transformation to your normal vectors. Since you definitely do not want to skew them, you will have to create a special matrix for your normals.
As is explained further down the tutorial that you mentioned, the matrix can be constructed like this
Normal = mat3(transpose(inverse(model))) * aNormal;
in your vertex shader.
However, I highly recommend that you calculate the matrix in your application code instead, since you would calculate it per vertex in the above example.
Since you are using the glm library, it would look like this instead:
glm::mat3 model_normal = glm::mat3(glm::transpose(glm::inverse(model)));
You can then load your new model_normal matrix into the shader as a uniform mat3.
I am implementing a specular highlight in OpenGL as part of the phong model. Currently, the highlight moves when my camera moves rather that getting brighter or dimmer which obviously isn't the expected result. I have followed the tutorial on learnopengl.com
#version 330 core
in vec3 outColor;
in vec3 outNormal;
in vec3 fragPos;
out vec4 FragColor;
uniform vec3 lightPos = vec3(-2.0f, 0.0f, 0.0f);
uniform vec3 lightColor = vec3(1.0, 0.5f, 1.0f);
uniform vec3 viewPos;
float ambientStrength = 0.2;
float specularStrength = 0.5;
uniform sampler2D tex;
void main()
{
vec3 normal = normalize(outNormal);
vec3 lightDir = normalize(lightPos - fragPos);
//ambient lighitng
vec3 ambient = ambientStrength * lightColor;
//diffuse lighting
float diffuseFactor = max(dot(normal, lightDir), 0.0);
vec3 diffuse = diffuseFactor * lightColor;
//specular lighting
vec3 viewDir = normalize(viewPos - fragPos);
vec3 reflectDir = reflect(-lightDir, normal);
float spec = pow(max(dot(viewDir, reflectDir), 0.0), 128);
vec3 specular = specularStrength * spec * lightColor;
vec3 result = (ambient + diffuse + specular) * outColor;
FragColor = vec4(result, 1.0f);// texture(tex, outTexCoords);// vec4(0.0f, 1.0f, 0.0f, 1.0f);
}
I use vector as light position say (0.0f, 0.0f, 5.0f) and an object positioned at (0.0f, 0.0f, -10.0f) and a plane.
lightSpaceProjection = glm::ortho(-10.0f, 10.0f, -10.0f, 10.0f, 1.0f, 300.0f);
lightSpaceView= glm::lookAt(lightPosition, glm::vec3(0.0f), glm::vec3(0.0f, 1.0f, 0.0f));
lightSpaceMatrix = lightSpaceProjection * lightSpaceView;
I get a shadow moving with the camera everywhere, I want to know how to update the shadow map to render the right space shadow where the camera looks at.
I calculate the light space matrix as shown to send it to the vertex shader to render the shadow map from the light view, then send it again to the normal vertex shader to calculate which fragment is in shadow,
the light definition
DirectLight sun;
sun.direction = glm::vec3(0.0f, 10.0f, 5.0f);
sun.lightSpaceProjection = glm::ortho(-10.0f, 10.0f, -10.0f, 10.0f, 1.0f, 300.0f);
sun.lightSpaceView= glm::lookAt(sun.direction, glm::vec3(0.0f), glm::vec3(0.0f, 1.0f, 0.0f));
scene.addLight("sun", sun);
this is the render code
DirectLight& sun = dynamic_cast<DirectLight&>(this->getLight("sun", LIGHTTYPE_DIRECT));
glm::mat4 lightSpaceMatrix = (sun.lightSpaceProjection * sun.lightSpaceView);
glViewport(0, 0, SHADOW_WIDTH, SHADOW_HEIGHT);
glBindFramebuffer(GL_FRAMEBUFFER, depthMapFBO);
glClear(GL_DEPTH_BUFFER_BIT);
//glCullFace(GL_FRONT);
typedef std::map<std::string, Model>::iterator model_it;
depthShader.use();
glUniformMatrix4fv(glGetUniformLocation(depthShader.getProgramID(), "lightSpaceMatrix"), 1, GL_FALSE, glm::value_ptr(lightSpaceMatrix));
for (model_it it = phongModels.begin(); it != phongModels.end(); it++) {
((Model&) it->second).drawDepth(depthShader);
}
//glCullFace(GL_BACK);
glBindFramebuffer(GL_FRAMEBUFFER, 0);
// draw normal
glViewport(0, 0, WIDTH, HEIGHT);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
typedef std::map<std::string, Model>::iterator model_it;
phongShader.use();
glUniformMatrix4fv(glGetUniformLocation(phongShader.getProgramID(), "lightSpaceMatrix"), 1, GL_FALSE, glm::value_ptr(lightSpaceMatrix));
this->drawPhongLights(phongShader);
this->setViewUniforms(phongShader);
for (model_it it = phongModels.begin(); it != phongModels.end(); it++) {
glActiveTexture(GL_TEXTURE2);
glUniform1i(glGetUniformLocation(phongShader.getProgramID(), "shadowMap"), 2);
glBindTexture(GL_TEXTURE_2D, depthMap);
((Model&) it->second).drawPhong(phongShader, this->defCamera);
}
the depth vertex shader is
#version 330 core
layout (location = 0) in vec3 position;
uniform mat4 lightSpaceMatrix;
uniform mat4 model;
void main(){
gl_Position = lightSpaceMatrix * model * vec4(position, 1.0f);
}
and the normal vertex shader is
#version 330 core
layout (location = 0) in vec3 position;
layout (location = 2) in vec2 texCoord;
layout (location = 1) in vec3 normal;
out vec2 TexCoords;
out vec3 Normal;
out vec3 FragPos;
out vec3 LightPos;
out vec4 FragPosLightSpace;
uniform mat4 model;
uniform mat4 view;
uniform mat4 projection;
uniform vec3 lightPos;
uniform mat4 lightSpaceMatrix;
void main()
{
gl_Position = projection * view * model * vec4(position, 1.0f);
TexCoords = vec2(texCoord.s,1.0-texCoord.t);
Normal=normal;
FragPos = vec3(view * model * vec4(position, 1.0f));
LightPos = vec3(view * vec4(lightPos, 1.0));
FragPosLightSpace = lightSpaceMatrix * vec4(FragPos, 1.0);
}
and in fragment shader i calculate the shadow by this function
float directShadowCalculation(vec4 fragPosLightSpace,float bias){
vec3 projCoords = fragPosLightSpace.xyz / fragPosLightSpace.w;
projCoords = projCoords * 0.5 + 0.5;
float closestDepth = vec3(texture(shadowMap, projCoords.xy)).r;
float currentDepth = projCoords.z;
float shadow = 0.0;
vec2 texelSize = 1.0 / textureSize(shadowMap, 0);
for(int x = -1; x <= 1; ++x){
for(int y = -1; y <= 1; ++y){
float pcfDepth = texture(shadowMap, projCoords.xy + vec2(x, y) * texelSize).r;
shadow += currentDepth - bias > pcfDepth ? 1.0 : 0.0;
}
}
shadow /= 9.0;
if(projCoords.z > 1.0)
shadow = 0.0;
return shadow;
}
then apply the color by this one
vec3 calcDirectLight(DirectLight light){
vec3 color = vec3(texture(mat_diffuse, TexCoords));
vec3 norm = normalize(Normal);
vec3 lightDir = normalize( light.direction - FragPos);
float diff = max(dot(norm, lightDir), 0.0);
vec3 diffuse = light.diffuse * diff ;
vec3 viewDir = normalize(viewPos - FragPos);
vec3 reflectDir = reflect(-lightDir, norm);
float spec =0.0;
if(blinn){
vec3 halfwayDir = normalize(lightDir + viewDir);
spec = pow(max(dot(norm, halfwayDir), 0.0), 16.0);
}
else{
vec3 reflectDir = reflect(-lightDir, norm);
spec = pow(max(dot(viewDir, reflectDir), 0.0), 8.0);
}
//float spec = pow(max(dot(viewDir, reflectDir), 0.0), shininess);
vec3 specular = spec * light.specular;
float bias = max(0.05 * (1.0 - dot(norm, lightDir)), 0.005);
float shadow = directShadowCalculation(FragPosLightSpace,bias);
vec3 result =light.intensity* (light.ambient+ ((1.0 - shadow) * (diffuse + specular)))*color;
return result;
}
i don't know how to update the light space frustum with camera view
Solution:
the bug was in the vertex shader, this is the correct one:
#version 330 core
layout (location = 0) in vec3 position;
layout (location = 2) in vec2 texCoord;
layout (location = 1) in vec3 normal;
out vec2 TexCoords;
out vec3 Normal;
out vec3 FragPos;
out vec4 FragPosLightSpace;
uniform mat4 model;
uniform mat4 view;
uniform mat4 projection;
uniform vec3 lightPos;
uniform mat4 lightSpaceMatrix;
void main()
{
gl_Position = projection * view * model * vec4(position, 1.0f);
TexCoords = vec2(texCoord.s,1.0-texCoord.t);
Normal=transpose(inverse(mat3(model))) * normal;;
FragPos = vec3( model * vec4(position, 1.0f));
FragPosLightSpace = lightSpaceMatrix * vec4(FragPos, 1.0);
}