diff --git a/data/shaders/geometry.glsl b/data/shaders/geometry.glsl index 00c417a..1adbeff 100644 --- a/data/shaders/geometry.glsl +++ b/data/shaders/geometry.glsl @@ -7,6 +7,7 @@ uniform mat4 Model; in vec2 gtexCoord[]; in vec3 gnormCoord[]; in vec3 gWorldPos[]; +uniform mat4 MVP; out vec2 texCoord; out vec3 normCoord; @@ -21,18 +22,27 @@ out GS_OUT { vec3 tangentLightPos; vec3 tangentViewPos; vec3 tangentFragPos; + vec3 tangentNormPos; } gs_out; +in DATA { + vec3 normal; + vec2 texCoord; + mat4 camProj; + mat4 modelProj; + vec3 lightPos; + vec3 camPos; +} data_in[]; + void main(void) { // Calculate Normal Map stuff - // Edges of the triangle vec3 edge0 = gl_in[1].gl_Position.xyz - gl_in[0].gl_Position.xyz; vec3 edge1 = gl_in[2].gl_Position.xyz - gl_in[0].gl_Position.xyz; // Lengths of UV differences - vec2 deltaUV0 = gtexCoord[1] - gtexCoord[0]; - vec2 deltaUV1 = gtexCoord[2] - gtexCoord[0]; + vec2 deltaUV0 = data_in[1].texCoord - data_in[0].texCoord; + vec2 deltaUV1 = data_in[2].texCoord - data_in[0].texCoord; // one over the determinant float invDet = 1.0f / (deltaUV0.x * deltaUV1.y - deltaUV1.x * deltaUV0.y); @@ -40,41 +50,38 @@ void main(void) vec3 tangent = vec3(invDet * (deltaUV1.y * edge0 - deltaUV0.y * edge1)); vec3 bitangent = vec3(invDet * (-deltaUV1.x * edge0 + deltaUV0.x * edge1)); - //Calculate TBN - //mat3 normalMatrix = transpose(inverse(mat3(Model))); + vec3 T = normalize(vec3(data_in[0].modelProj * vec4(tangent, 0.0f))); + vec3 B = normalize(vec3(data_in[0].modelProj * vec4(bitangent, 0.0f))); + vec3 N = normalize(vec3(data_in[0].modelProj * vec4(cross(edge0, edge1), 0.0f))); - vec3 T = normalize(vec3(Model * vec4(tangent, 0.0f))); - vec3 B = normalize(vec3(Model * vec4(bitangent, 0.0f))); - vec3 N = normalize(vec3(Model * vec4(cross(edge1, edge0), 0.0f))); - - mat3 TBN = transpose(mat3(T, B, N)); + mat3 TBN = mat3(T, B, N); + // TBN is an orthogonal matrix and so its inverse is equal to its transpose + TBN = transpose(TBN); gs_out.TBN = TBN; - gs_out.tangentLightPos = TBN * lightPosition; - gs_out.tangentViewPos = TBN * CameraPos; - gs_out.tangentFragPos = TBN * gWorldPos[0]; - // send data to Fragment Shader - gl_Position = gl_in[0].gl_Position; - texCoord = gtexCoord[0]; - normCoord = gnormCoord[0]; - WorldPos = gWorldPos[0]; + gl_Position = data_in[0].camProj * gl_in[0].gl_Position; + gs_out.tangentNormPos = data_in[0].normal; + texCoord = data_in[0].texCoord; + gs_out.tangentFragPos = TBN * gl_in[0].gl_Position.xyz; + gs_out.tangentViewPos = TBN * data_in[0].camPos; + gs_out.tangentLightPos = TBN * data_in[0].lightPos; EmitVertex(); - gl_Position = gl_in[1].gl_Position; - texCoord = gtexCoord[1]; - normCoord = gnormCoord[1]; - WorldPos = gWorldPos[1]; - - gs_out.tangentFragPos = TBN * gWorldPos[1]; + gl_Position = data_in[1].camProj * gl_in[1].gl_Position; + gs_out.tangentNormPos = data_in[1].normal; + texCoord = data_in[1].texCoord; + gs_out.tangentFragPos = TBN * gl_in[1].gl_Position.xyz; + gs_out.tangentViewPos = TBN * data_in[1].camPos; + gs_out.tangentLightPos = TBN * data_in[1].lightPos; EmitVertex(); - gl_Position = gl_in[2].gl_Position; - texCoord = gtexCoord[2]; - normCoord = gnormCoord[2]; - WorldPos = gWorldPos[2]; - - gs_out.tangentFragPos = TBN * gWorldPos[2]; + gl_Position = data_in[2].camProj * gl_in[2].gl_Position; + gs_out.tangentNormPos = data_in[2].normal; + texCoord = data_in[2].texCoord; + gs_out.tangentFragPos = TBN * gl_in[2].gl_Position.xyz; + gs_out.tangentViewPos = TBN * data_in[2].camPos; + gs_out.tangentLightPos = TBN * data_in[2].lightPos; EmitVertex(); EndPrimitive(); }; diff --git a/data/shaders/pbrFragment.glsl b/data/shaders/pbrFragment.glsl index 2952df1..69df047 100644 --- a/data/shaders/pbrFragment.glsl +++ b/data/shaders/pbrFragment.glsl @@ -1,4 +1,5 @@ #version 330 core +uniform mat4 MVP; out vec4 FragColor; in vec2 texCoord; @@ -10,6 +11,7 @@ in GS_OUT { vec3 tangentLightPos; vec3 tangentViewPos; vec3 tangentFragPos; + vec3 tangentNormPos; } from_gs; in mat3 TBN; @@ -17,7 +19,7 @@ in mat3 TBN; // TODO: make temporary hard coded world/camera pos dynamic //uniform vec3 WorldPos ; uniform vec3 CameraPos; -uniform int tick; +//uniform int tick; //vec3 WorldPos = vec3(0.0f, 0.0f, 0.0f); //vec3 CameraPos = vec3(0.0f, 0.0f, -1.0f); //TODO: make these values rely on associated textures. @@ -89,7 +91,7 @@ vec3 normalMapNormal(){ vec3 halfwayDir = normalize(lightDir + viewDir); float spec = pow(max(dot(normal, halfwayDir), 0.0),32.0); - vec3 normMapSpecular = vec3(0.2) * spec; + vec3 normMapSpecular = vec3(1.0) * spec; return normMapSpecular; } @@ -98,13 +100,24 @@ vec3 normalMapNormal(){ vec3 PBR(vec3 albedo, float roughness, float metallic, float ao) { // Establish a temporary hard coded light position - vec3 lightPosition = vec3(1, 1, 2); + //vec3 lightPosition = vec3(1, 1, 2); + //vec3 lightPosition = vec3(1, 1, 2); + vec3 lightPosition = from_gs.tangentLightPos; //vec3 lightPosition = vec3( (sin(tick / 1000.0)*2), 1 + sin(tick / 600.0)*2, 2.0); //vec3 lightColor = vec3(1.0, 1.0, 1.0) - sin(tick / 90); vec3 lightColor = vec3(13.47, 11.31, 10.79); - vec3 N = normalize(normCoord); - vec3 V = normalize(CameraPos - WorldPos); + //vec3 camPos = CameraPos; + vec3 camPos = from_gs.tangentViewPos; + //vec3 fragPos = WorldPos; + vec3 fragPos = from_gs.tangentFragPos; + + //vec3 N = normalize(normCoord); + //vec3 N = normalize(from_gs.tangentNormPos); + vec3 N = normalize(texture(texture_normal1, texCoord).xyz * 2.0 - 1.0); + vec3 V = normalize(camPos - fragPos); + //N = (N + normalize(texture(texture_normal1, texCoord).xyz * 2.0 - 1.0))/2; + //N = (N + normalize(texture(texture_normal1, texCoord).zyx * 2.0 - 1.0))/2; //N = (N + normalMapNormal()) / 2; //N = normalMapNormal(); //For seeing if normal map tracks with light. @@ -114,9 +127,9 @@ vec3 PBR(vec3 albedo, float roughness, float metallic, float ao) // reflectance equation vec3 Lo = vec3(0.0); // calculate per-light radiance - vec3 L = normalize(lightPosition - WorldPos); + vec3 L = normalize(lightPosition - fragPos); vec3 H = normalize(V + L); - float distance = length(lightPosition - WorldPos); + float distance = length(lightPosition - fragPos); float attenuation = 1.0 / (distance * distance); vec3 radiance = lightColor * attenuation; @@ -154,9 +167,9 @@ void main() float metallic = texture(texture_rma1, texCoord).g; float ao = texture(texture_rma1, texCoord).b; - //FragColor = vec4(PBR(albedo, roughness, metallic, ao), 1.0); + FragColor = vec4(PBR(albedo, roughness, metallic, ao), 1.0); //FragColor = vec4(PBR(albedo, roughness, metallic, ao) + normalMapNormal(), 1.0); //FragColor = vec4(normalMapNormal(), 1.0); - FragColor = vec4(vec3(0.1) + normalMapNormal()*5, 1.0); + //FragColor = vec4(vec3(0.1) + normalMapNormal()*5, 1.0); //FragColor = vec4(vec3(0.5), 1.0); } diff --git a/data/shaders/pbrVertex.glsl b/data/shaders/pbrVertex.glsl index 5cf8bae..cdd0145 100644 --- a/data/shaders/pbrVertex.glsl +++ b/data/shaders/pbrVertex.glsl @@ -5,19 +5,40 @@ layout (location = 2) in vec2 aTexCoord; uniform mat4 MVP; uniform mat4 Model; +uniform vec3 CameraPos; +uniform int tick; out vec2 gtexCoord; out vec3 gnormCoord; + + //Pbr out vec3 gWorldPos; +out DATA { + vec3 normal; + vec2 texCoord; + mat4 camProj; + mat4 modelProj; + vec3 lightPos; + vec3 camPos; +} data_out; + void main() { - gl_Position = MVP * Model * vec4(aPos, 1.0); + // Saving camera projection until geometry shader. + gl_Position = Model * vec4(aPos, 1.0); gnormCoord = aNormal; gtexCoord = aTexCoord; + data_out.normal = aNormal; + data_out.texCoord = aTexCoord; + data_out.camProj = MVP; + data_out.modelProj = Model; + data_out.lightPos = vec3( (sin(tick / 1000.0)*2), 1 + sin(tick / 600.0)*2, 2.0); + data_out.camPos = CameraPos; + // Calculate position of fragment gWorldPos = vec3(Model * vec4(aPos, 1.0)); }; diff --git a/src/Model.cpp b/src/Model.cpp index 9c67d49..c821790 100644 --- a/src/Model.cpp +++ b/src/Model.cpp @@ -21,7 +21,6 @@ void Model::translate(glm::vec3 translation) { this->model = glm::translate(glm::mat4(1.0f), glm::vec3(position)); // set position based on the current model - // TODO: turn this into a function if readability becomes an issue this->position = model * glm::vec4(0.0f, 0.0f, 0.0f, 1.0f); } void Model::resize(glm::vec3 scale) { diff --git a/src/PlayerCamera.cpp b/src/PlayerCamera.cpp index c14f46d..750020b 100644 --- a/src/PlayerCamera.cpp +++ b/src/PlayerCamera.cpp @@ -45,16 +45,18 @@ void PlayerCamera::tick() { glm::vec3 cameraTarget = cameraPosition + cameraForward; // MVP stuff - glm::mat4 model = glm::mat4(1.0f); + model = glm::mat4(1.0f); - glm::mat4 view; view = glm::lookAt(cameraPosition, cameraTarget, up); - glm::mat4 projection = glm::perspective( - glm::radians(45.0f), (float)800 / (float)600, 0.1f, 100.0f); + projection = glm::perspective(glm::radians(45.0f), (float)800 / (float)600, + 0.1f, 100.0f); MVP = projection * view * model; } glm::mat4 PlayerCamera::getMVP() { return MVP; } +glm::mat4 PlayerCamera::getModel() { return model; } +glm::mat4 PlayerCamera::getView() { return view; } +glm::mat4 PlayerCamera::getProjection() { return projection; } glm::vec3 PlayerCamera::getCameraPosition() { return cameraPosition; } diff --git a/src/PlayerCamera.h b/src/PlayerCamera.h index 3b4df32..ee8a0c6 100644 --- a/src/PlayerCamera.h +++ b/src/PlayerCamera.h @@ -26,8 +26,11 @@ private: // Mouse position int mouseX, mouseY; - // Camera position + // Camera matrix glm::mat4 MVP; + glm::mat4 model; + glm::mat4 view; + glm::mat4 projection; public: PlayerCamera(); @@ -37,5 +40,8 @@ public: void tick(); glm::mat4 getMVP(); + glm::mat4 getModel(); + glm::mat4 getView(); + glm::mat4 getProjection(); glm::vec3 getCameraPosition(); }; diff --git a/src/main.cpp b/src/main.cpp index 83ca4ff..d58208c 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -125,9 +125,13 @@ int main(int argc, char **argv) { // Send our glsl shader our camera information shader.setMat4("MVP", camera.getMVP()); + // shader.setMat4("Model", camera.getModel()); + // shader.setMat4("View", camera.getView()); + // shader.setMat4("Projection", camera.getProjection()); + shader.setVec3("CameraPos", camera.getCameraPosition()); shader.setInt("tick", SDL_GetTicks()); - boxbarrel.rotate(0.001, glm::vec3(0, 1, 0)); + // boxbarrel.rotate(0.001, glm::vec3(0, 1, 0)); // Draw Meshes // cube.draw(shader);