General clean up

This commit is contained in:
2024-10-15 18:56:25 +02:00
parent 3cc58e0b4b
commit 5e402d9077
17 changed files with 657 additions and 829 deletions
+11 -11
View File
@@ -3,7 +3,7 @@ out vec2 FragColor;
in vec2 TexCoords; in vec2 TexCoords;
const float PI = 3.14159265359; const float PI = 3.14159265359;
// ----------------------------------------------------------------------------
// http://holger.dammertz.org/stuff/notes_HammersleyOnHemisphere.html // http://holger.dammertz.org/stuff/notes_HammersleyOnHemisphere.html
// efficient VanDerCorpus calculation. // efficient VanDerCorpus calculation.
float RadicalInverse_VdC(uint bits) float RadicalInverse_VdC(uint bits)
@@ -15,12 +15,12 @@ float RadicalInverse_VdC(uint bits)
bits = ((bits & 0x00FF00FFu) << 8u) | ((bits & 0xFF00FF00u) >> 8u); bits = ((bits & 0x00FF00FFu) << 8u) | ((bits & 0xFF00FF00u) >> 8u);
return float(bits) * 2.3283064365386963e-10; // / 0x100000000 return float(bits) * 2.3283064365386963e-10; // / 0x100000000
} }
// ----------------------------------------------------------------------------
vec2 Hammersley(uint i, uint N) vec2 Hammersley(uint i, uint N)
{ {
return vec2(float(i)/float(N), RadicalInverse_VdC(i)); return vec2(float(i)/float(N), RadicalInverse_VdC(i));
} }
// ----------------------------------------------------------------------------
vec3 ImportanceSampleGGX(vec2 Xi, vec3 N, float roughness) vec3 ImportanceSampleGGX(vec2 Xi, vec3 N, float roughness)
{ {
float a = roughness*roughness; float a = roughness*roughness;
@@ -43,7 +43,7 @@ vec3 ImportanceSampleGGX(vec2 Xi, vec3 N, float roughness)
vec3 sampleVec = tangent * H.x + bitangent * H.y + N * H.z; vec3 sampleVec = tangent * H.x + bitangent * H.y + N * H.z;
return normalize(sampleVec); return normalize(sampleVec);
} }
// ----------------------------------------------------------------------------
float GeometrySchlickGGX(float NdotV, float roughness) float GeometrySchlickGGX(float NdotV, float roughness)
{ {
// note that we use a different k for IBL // note that we use a different k for IBL
@@ -55,7 +55,7 @@ float GeometrySchlickGGX(float NdotV, float roughness)
return nom / denom; return nom / denom;
} }
// ----------------------------------------------------------------------------
float GeometrySmith(vec3 N, vec3 V, vec3 L, float roughness) float GeometrySmith(vec3 N, vec3 V, vec3 L, float roughness)
{ {
float NdotV = max(dot(N, V), 0.0); float NdotV = max(dot(N, V), 0.0);
@@ -65,7 +65,7 @@ float GeometrySmith(vec3 N, vec3 V, vec3 L, float roughness)
return ggx1 * ggx2; return ggx1 * ggx2;
} }
// ----------------------------------------------------------------------------
vec2 IntegrateBRDF(float NdotV, float roughness) vec2 IntegrateBRDF(float NdotV, float roughness)
{ {
vec3 V; vec3 V;
@@ -79,8 +79,8 @@ vec2 IntegrateBRDF(float NdotV, float roughness)
vec3 N = vec3(0.0, 0.0, 1.0); vec3 N = vec3(0.0, 0.0, 1.0);
const uint SAMPLE_COUNT = 1024u; const uint SAMPLE_COUNT = 1024u;
for(uint i = 0u; i < SAMPLE_COUNT; ++i) for(uint i = 0u; i < SAMPLE_COUNT; ++i) {
{
// generates a sample vector that's biased towards the // generates a sample vector that's biased towards the
// preferred alignment direction (importance sampling). // preferred alignment direction (importance sampling).
vec2 Xi = Hammersley(i, SAMPLE_COUNT); vec2 Xi = Hammersley(i, SAMPLE_COUNT);
@@ -91,8 +91,8 @@ vec2 IntegrateBRDF(float NdotV, float roughness)
float NdotH = max(H.z, 0.0); float NdotH = max(H.z, 0.0);
float VdotH = max(dot(V, H), 0.0); float VdotH = max(dot(V, H), 0.0);
if(NdotL > 0.0) if(NdotL > 0.0) {
{
float G = GeometrySmith(N, V, L, roughness); float G = GeometrySmith(N, V, L, roughness);
float G_Vis = (G * VdotH) / (NdotH * NdotV); float G_Vis = (G * VdotH) / (NdotH * NdotV);
float Fc = pow(1.0 - VdotH, 5.0); float Fc = pow(1.0 - VdotH, 5.0);
@@ -105,7 +105,7 @@ vec2 IntegrateBRDF(float NdotV, float roughness)
B /= float(SAMPLE_COUNT); B /= float(SAMPLE_COUNT);
return vec2(A, B); return vec2(A, B);
} }
// ----------------------------------------------------------------------------
void main() void main()
{ {
vec2 integratedBRDF = IntegrateBRDF(TexCoords.x, TexCoords.y); vec2 integratedBRDF = IntegrateBRDF(TexCoords.x, TexCoords.y);
+1
View File
@@ -1,4 +1,5 @@
#version 330 core #version 330 core
layout (location = 0) in vec3 aPos; layout (location = 0) in vec3 aPos;
layout (location = 1) in vec2 aTexCoords; layout (location = 1) in vec2 aTexCoords;
+1
View File
@@ -1,4 +1,5 @@
#version 330 core #version 330 core
layout (location = 0) in vec3 aPos; layout (location = 0) in vec3 aPos;
out vec3 WorldPos; out vec3 WorldPos;
@@ -1,10 +1,12 @@
#version 330 core #version 330 core
out vec4 FragColor; out vec4 FragColor;
in vec3 WorldPos; in vec3 WorldPos;
uniform sampler2D equirectangularMap; uniform sampler2D equirectangularMap;
const vec2 invAtan = vec2(0.1591, 0.3183); const vec2 invAtan = vec2(0.1591, 0.3183);
vec2 SampleSphericalMap(vec3 v) vec2 SampleSphericalMap(vec3 v)
{ {
vec2 uv = vec2(atan(v.z, v.x), asin(v.y)); vec2 uv = vec2(atan(v.z, v.x), asin(v.y));
+1
View File
@@ -131,6 +131,7 @@ float shadow_factor(vec4 frag_pos_light_space)
float closest_depth = texture(shadow_map, proj_coords.xy + vec2(i, j) * delta).r; float closest_depth = texture(shadow_map, proj_coords.xy + vec2(i, j) * delta).r;
shadow += (current_depth - bias > closest_depth) ? 1.0 : 0.0; shadow += (current_depth - bias > closest_depth) ? 1.0 : 0.0;
} }
shadow /= 9; shadow /= 9;
return shadow; return shadow;
} }
-105
View File
@@ -1,105 +0,0 @@
#version 330 core
struct Light {
vec3 direction;
vec3 ambient;
vec3 diffuse;
vec3 specular;
};
out vec4 FragColor;
in vec3 frag_normal;
in vec3 fragPos;
in vec4 frag_pos_light_space;
uniform sampler2D shadow_map;
uniform vec3 viewPos;
uniform float perceptualRoughness; // [0, 1]
uniform float metallic; // [0, 1]
uniform float reflectance; // [0, 1]
uniform vec3 baseColor;
uniform Light light;
float shadow_factor(vec4 frag_pos_light_space)
{
vec3 proj_coords = frag_pos_light_space.xyz / frag_pos_light_space.w;
proj_coords = proj_coords * 0.5 + 0.5;
float closest_depth = texture(shadow_map, proj_coords.xy).r;
float current_depth = proj_coords.z;
float bias = 0.005;
float shadow = 0;
vec2 delta = 1.0 / textureSize(shadow_map, 0);
for (int i = -1; i < 2; i++)
for (int j = -1; j < 2; j++) {
float closest_depth = texture(shadow_map, proj_coords.xy + vec2(i, j) * delta).r;
shadow += (current_depth - bias > closest_depth) ? 1.0 : 0.0;
}
shadow /= 9;
return shadow;
}
float D_GGX(float NoH, float a) {
float a2 = a * a;
float f = (NoH * a2 - NoH) * NoH + 1.0;
return a2 / (PI * f * f);
}
vec3 F_Schlick(float u, vec3 f0) {
return f0 + (vec3(1.0) - f0) * pow(1.0 - u, 5.0);
}
float V_SmithGGXCorrelated(float NoV, float NoL, float a) {
float a2 = a * a;
float GGXL = NoV * sqrt((-NoL * a2 + NoL) * NoL + a2);
float GGXV = NoL * sqrt((-NoV * a2 + NoV) * NoV + a2);
return 0.5 / (GGXV + GGXL);
}
float Fd_Lambert() {
return 1.0 / PI;
}
void main()
{
// NOTE: frag_normal is normalized by the vertex shader
/*
vec3 l = normalize(light.direction);
vec3 v = viewDir;
vec3 n = frag_normal;
vec3 h = normalize(v + l);
vec3 diffuseColor = (1.0 - metallic) * baseColor.rgb;
vec3 f0 = 0.16 * reflectance * reflectance * (1.0 - metallic) + baseColor * metallic;
float NoV = abs(dot(n, v)) + 1e-5;
float NoL = clamp(dot(n, l), 0.0, 1.0);
float NoH = clamp(dot(n, h), 0.0, 1.0);
float LoH = clamp(dot(l, h), 0.0, 1.0);
float roughness = perceptualRoughness * perceptualRoughness;
float D = D_GGX(NoH, roughness);
vec3 F = F_Schlick(LoH, f0);
float V = V_SmithGGXCorrelated(NoV, NoL, roughness);
// specular BRDF
vec3 Fr = (D * V) * F;
//vec3 energyCompensation = 1.0 + f0 * (1.0 / dfg.y - 1.0);
//// Scale the specular lobe to account for multiscattering
//Fr *= pixel.energyCompensation;
// diffuse BRDF
vec3 Fd = diffuseColor * Fd_Lambert();
// apply lighting...
float shadow = shadow_factor(frag_pos_light_space);
*/
vec3 result = vec3(1, 0, 0); // Fd + Fr * (1 - shadow);
FragColor = vec4(result, 1.0);
}
-113
View File
@@ -1,113 +0,0 @@
#version 330 core
// https://github.com/Nadrin/PBR/blob/master/data/shaders/glsl/pbr_fs.glsl
#define PI 3.1415926538
out vec4 FragColor;
in vec3 frag_normal;
in vec3 fragPos;
in vec4 frag_pos_light_space;
uniform sampler2D shadow_map;
uniform vec3 viewPos;
uniform float perceptualRoughness; // [0, 1]
uniform float metallic; // [0, 1]
uniform float reflectance; // [0, 1]
uniform vec3 baseColor;
uniform vec3 lightDir;
uniform vec3 lightColor;
float shadow_factor(vec4 frag_pos_light_space);
float D_GGX(float NoH, float a) {
float a2 = a * a;
float f = (NoH * a2 - NoH) * NoH + 1.0;
return a2 / (PI * f * f);
}
vec3 F_Schlick(float u, vec3 f0) {
return f0 + (vec3(1.0) - f0) * pow(1.0 - u, 5.0);
}
float V_SmithGGXCorrelated(float NoV, float NoL, float a) {
float a2 = a * a;
float GGXL = NoV * sqrt((-NoL * a2 + NoL) * NoL + a2);
float GGXV = NoL * sqrt((-NoV * a2 + NoV) * NoV + a2);
return 0.5 / (GGXV + GGXL);
}
float Fd_Lambert()
{
return 1.0 / PI;
}
void main()
{
vec3 l = normalize(lightDir);
vec3 v = normalize(viewPos - fragPos);
vec3 n = frag_normal;
vec3 h = normalize(v + l);
float light_intensity = 1;
vec3 albedo = baseColor;
vec3 diffuseColor = (1.0 - metallic) * baseColor;
vec3 f0 = 0.16 * reflectance * reflectance * (1.0 - metallic)
+ baseColor * metallic;
float NoV = abs(dot(n, v)) + 1e-5;
float NoL = clamp(dot(n, l), 0.0, 1.0);
float NoH = clamp(dot(n, h), 0.0, 1.0);
float LoH = clamp(dot(l, h), 0.0, 1.0);
float roughness = perceptualRoughness * perceptualRoughness;
float D = D_GGX(NoH, roughness);
vec3 F = F_Schlick(LoH, f0);
float V = V_SmithGGXCorrelated(NoV, NoL, roughness);
// specular BRDF
float denominator = 4.0 * max(dot(n, v), 0.0) * max(dot(n, l), 0.0) + 0.0001; // + 0.0001 to prevent divide by zero
vec3 Fr = (D * V) * F / denominator;
vec3 radiance = lightColor;
vec3 light = ((vec3(1.0) - F) * (1.0 - metallic) * albedo / PI + Fr) * radiance * NoL;
float shadow = shadow_factor(frag_pos_light_space);
vec3 ambient = vec3(0.03) * albedo;
vec3 color = (ambient + light) * (1 - shadow);
/*
// HDR tonemapping
color = color / (color + vec3(1.0));
// gamma correct
color = pow(color, vec3(1.0/2.2));
*/
FragColor = vec4(color, 1.0);
}
float shadow_factor(vec4 frag_pos_light_space)
{
vec3 proj_coords = frag_pos_light_space.xyz / frag_pos_light_space.w;
proj_coords = proj_coords * 0.5 + 0.5;
float closest_depth = texture(shadow_map, proj_coords.xy).r;
float current_depth = proj_coords.z;
float bias = 0.005;
float shadow = 0;
vec2 delta = 1.0 / textureSize(shadow_map, 0);
for (int i = -1; i < 2; i++)
for (int j = -1; j < 2; j++) {
float closest_depth = texture(shadow_map, proj_coords.xy + vec2(i, j) * delta).r;
shadow += (current_depth - bias > closest_depth) ? 1.0 : 0.0;
}
shadow /= 9;
return shadow;
}
+5 -5
View File
@@ -6,7 +6,7 @@ uniform samplerCube environmentMap;
uniform float roughness; uniform float roughness;
const float PI = 3.14159265359; const float PI = 3.14159265359;
// ----------------------------------------------------------------------------
float DistributionGGX(vec3 N, vec3 H, float roughness) float DistributionGGX(vec3 N, vec3 H, float roughness)
{ {
float a = roughness*roughness; float a = roughness*roughness;
@@ -20,7 +20,7 @@ float DistributionGGX(vec3 N, vec3 H, float roughness)
return nom / denom; return nom / denom;
} }
// ----------------------------------------------------------------------------
// http://holger.dammertz.org/stuff/notes_HammersleyOnHemisphere.html // http://holger.dammertz.org/stuff/notes_HammersleyOnHemisphere.html
// efficient VanDerCorpus calculation. // efficient VanDerCorpus calculation.
float RadicalInverse_VdC(uint bits) float RadicalInverse_VdC(uint bits)
@@ -32,12 +32,12 @@ float RadicalInverse_VdC(uint bits)
bits = ((bits & 0x00FF00FFu) << 8u) | ((bits & 0xFF00FF00u) >> 8u); bits = ((bits & 0x00FF00FFu) << 8u) | ((bits & 0xFF00FF00u) >> 8u);
return float(bits) * 2.3283064365386963e-10; // / 0x100000000 return float(bits) * 2.3283064365386963e-10; // / 0x100000000
} }
// ----------------------------------------------------------------------------
vec2 Hammersley(uint i, uint N) vec2 Hammersley(uint i, uint N)
{ {
return vec2(float(i)/float(N), RadicalInverse_VdC(i)); return vec2(float(i)/float(N), RadicalInverse_VdC(i));
} }
// ----------------------------------------------------------------------------
vec3 ImportanceSampleGGX(vec2 Xi, vec3 N, float roughness) vec3 ImportanceSampleGGX(vec2 Xi, vec3 N, float roughness)
{ {
float a = roughness*roughness; float a = roughness*roughness;
@@ -60,7 +60,7 @@ vec3 ImportanceSampleGGX(vec2 Xi, vec3 N, float roughness)
vec3 sampleVec = tangent * H.x + bitangent * H.y + N * H.z; vec3 sampleVec = tangent * H.x + bitangent * H.y + N * H.z;
return normalize(sampleVec); return normalize(sampleVec);
} }
// ----------------------------------------------------------------------------
void main() void main()
{ {
vec3 N = normalize(WorldPos); vec3 N = normalize(WorldPos);
+1
View File
@@ -1,4 +1,5 @@
#version 330 core #version 330 core
out vec4 FragColor; out vec4 FragColor;
in vec2 TexCoords; in vec2 TexCoords;
+1
View File
@@ -1,4 +1,5 @@
#version 330 core #version 330 core
layout (location=0) in vec3 aPos; layout (location=0) in vec3 aPos;
layout (location=1) in vec3 aNormal; layout (location=1) in vec3 aNormal;
layout (location=2) in vec2 aTexCoords; layout (location=2) in vec2 aTexCoords;
+51 -24
View File
@@ -34,9 +34,7 @@ static unsigned int irradianceMap;
static unsigned int prefilterMap; static unsigned int prefilterMap;
static unsigned int brdfLUTTexture; static unsigned int brdfLUTTexture;
/* // Shader program handles
* Shader program handles
*/
static unsigned int background_program; static unsigned int background_program;
static unsigned int shader_program; static unsigned int shader_program;
static unsigned int shadow_program; static unsigned int shadow_program;
@@ -45,8 +43,7 @@ static unsigned int skybox_program;
static GLFWwindow *window_; static GLFWwindow *window_;
static unsigned int static unsigned int
compile_shader(const char *vertex_file, compile_shader(const char *vertex_file, const char *fragment_file)
const char *fragment_file)
{ {
int success; int success;
char infolog[512]; char infolog[512];
@@ -239,9 +236,9 @@ unsigned int cubeVBO = 0;
void renderCube() void renderCube()
{ {
// initialize (if necessary) // initialize (if necessary)
if (cubeVAO == 0) if (cubeVAO == 0) {
{
float vertices[] = { float vertices[] = {
// back face // back face
-1.0f, -1.0f, -1.0f, 0.0f, 0.0f, -1.0f, 0.0f, 0.0f, // bottom-left -1.0f, -1.0f, -1.0f, 0.0f, 0.0f, -1.0f, 0.0f, 0.0f, // bottom-left
1.0f, 1.0f, -1.0f, 0.0f, 0.0f, -1.0f, 1.0f, 1.0f, // top-right 1.0f, 1.0f, -1.0f, 0.0f, 0.0f, -1.0f, 1.0f, 1.0f, // top-right
@@ -249,6 +246,7 @@ void renderCube()
1.0f, 1.0f, -1.0f, 0.0f, 0.0f, -1.0f, 1.0f, 1.0f, // top-right 1.0f, 1.0f, -1.0f, 0.0f, 0.0f, -1.0f, 1.0f, 1.0f, // top-right
-1.0f, -1.0f, -1.0f, 0.0f, 0.0f, -1.0f, 0.0f, 0.0f, // bottom-left -1.0f, -1.0f, -1.0f, 0.0f, 0.0f, -1.0f, 0.0f, 0.0f, // bottom-left
-1.0f, 1.0f, -1.0f, 0.0f, 0.0f, -1.0f, 0.0f, 1.0f, // top-left -1.0f, 1.0f, -1.0f, 0.0f, 0.0f, -1.0f, 0.0f, 1.0f, // top-left
// front face // front face
-1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, // bottom-left -1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, // bottom-left
1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 1.0f, 0.0f, // bottom-right 1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 1.0f, 0.0f, // bottom-right
@@ -256,6 +254,7 @@ void renderCube()
1.0f, 1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 1.0f, 1.0f, // top-right 1.0f, 1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 1.0f, 1.0f, // top-right
-1.0f, 1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 1.0f, // top-left -1.0f, 1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 1.0f, // top-left
-1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, // bottom-left -1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, // bottom-left
// left face // left face
-1.0f, 1.0f, 1.0f, -1.0f, 0.0f, 0.0f, 1.0f, 0.0f, // top-right -1.0f, 1.0f, 1.0f, -1.0f, 0.0f, 0.0f, 1.0f, 0.0f, // top-right
-1.0f, 1.0f, -1.0f, -1.0f, 0.0f, 0.0f, 1.0f, 1.0f, // top-left -1.0f, 1.0f, -1.0f, -1.0f, 0.0f, 0.0f, 1.0f, 1.0f, // top-left
@@ -263,6 +262,7 @@ void renderCube()
-1.0f, -1.0f, -1.0f, -1.0f, 0.0f, 0.0f, 0.0f, 1.0f, // bottom-left -1.0f, -1.0f, -1.0f, -1.0f, 0.0f, 0.0f, 0.0f, 1.0f, // bottom-left
-1.0f, -1.0f, 1.0f, -1.0f, 0.0f, 0.0f, 0.0f, 0.0f, // bottom-right -1.0f, -1.0f, 1.0f, -1.0f, 0.0f, 0.0f, 0.0f, 0.0f, // bottom-right
-1.0f, 1.0f, 1.0f, -1.0f, 0.0f, 0.0f, 1.0f, 0.0f, // top-right -1.0f, 1.0f, 1.0f, -1.0f, 0.0f, 0.0f, 1.0f, 0.0f, // top-right
// right face // right face
1.0f, 1.0f, 1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, // top-left 1.0f, 1.0f, 1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, // top-left
1.0f, -1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 0.0f, 1.0f, // bottom-right 1.0f, -1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 0.0f, 1.0f, // bottom-right
@@ -270,6 +270,7 @@ void renderCube()
1.0f, -1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 0.0f, 1.0f, // bottom-right 1.0f, -1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 0.0f, 1.0f, // bottom-right
1.0f, 1.0f, 1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, // top-left 1.0f, 1.0f, 1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, // top-left
1.0f, -1.0f, 1.0f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, // bottom-left 1.0f, -1.0f, 1.0f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, // bottom-left
// bottom face // bottom face
-1.0f, -1.0f, -1.0f, 0.0f, -1.0f, 0.0f, 0.0f, 1.0f, // top-right -1.0f, -1.0f, -1.0f, 0.0f, -1.0f, 0.0f, 0.0f, 1.0f, // top-right
1.0f, -1.0f, -1.0f, 0.0f, -1.0f, 0.0f, 1.0f, 1.0f, // top-left 1.0f, -1.0f, -1.0f, 0.0f, -1.0f, 0.0f, 1.0f, 1.0f, // top-left
@@ -277,6 +278,7 @@ void renderCube()
1.0f, -1.0f, 1.0f, 0.0f, -1.0f, 0.0f, 1.0f, 0.0f, // bottom-left 1.0f, -1.0f, 1.0f, 0.0f, -1.0f, 0.0f, 1.0f, 0.0f, // bottom-left
-1.0f, -1.0f, 1.0f, 0.0f, -1.0f, 0.0f, 0.0f, 0.0f, // bottom-right -1.0f, -1.0f, 1.0f, 0.0f, -1.0f, 0.0f, 0.0f, 0.0f, // bottom-right
-1.0f, -1.0f, -1.0f, 0.0f, -1.0f, 0.0f, 0.0f, 1.0f, // top-right -1.0f, -1.0f, -1.0f, 0.0f, -1.0f, 0.0f, 0.0f, 1.0f, // top-right
// top face // top face
-1.0f, 1.0f, -1.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, // top-left -1.0f, 1.0f, -1.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, // top-left
1.0f, 1.0f , 1.0f, 0.0f, 1.0f, 0.0f, 1.0f, 0.0f, // bottom-right 1.0f, 1.0f , 1.0f, 0.0f, 1.0f, 0.0f, 1.0f, 0.0f, // bottom-right
@@ -285,11 +287,14 @@ void renderCube()
-1.0f, 1.0f, -1.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, // top-left -1.0f, 1.0f, -1.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, // top-left
-1.0f, 1.0f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f // bottom-left -1.0f, 1.0f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f // bottom-left
}; };
glGenVertexArrays(1, &cubeVAO); glGenVertexArrays(1, &cubeVAO);
glGenBuffers(1, &cubeVBO); glGenBuffers(1, &cubeVBO);
// fill buffer // fill buffer
glBindBuffer(GL_ARRAY_BUFFER, cubeVBO); glBindBuffer(GL_ARRAY_BUFFER, cubeVBO);
glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW); glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);
// link vertex attributes // link vertex attributes
glBindVertexArray(cubeVAO); glBindVertexArray(cubeVAO);
glEnableVertexAttribArray(0); glEnableVertexAttribArray(0);
@@ -301,6 +306,7 @@ void renderCube()
glBindBuffer(GL_ARRAY_BUFFER, 0); glBindBuffer(GL_ARRAY_BUFFER, 0);
glBindVertexArray(0); glBindVertexArray(0);
} }
// render Cube // render Cube
glBindVertexArray(cubeVAO); glBindVertexArray(cubeVAO);
glDrawArrays(GL_TRIANGLES, 0, 36); glDrawArrays(GL_TRIANGLES, 0, 36);
@@ -313,8 +319,8 @@ unsigned int quadVAO = 0;
unsigned int quadVBO; unsigned int quadVBO;
void renderQuad() void renderQuad()
{ {
if (quadVAO == 0) if (quadVAO == 0) {
{
float quadVertices[] = { float quadVertices[] = {
// positions // texture Coords // positions // texture Coords
-1.0f, 1.0f, 0.0f, 0.0f, 1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 1.0f,
@@ -322,17 +328,24 @@ void renderQuad()
1.0f, 1.0f, 0.0f, 1.0f, 1.0f, 1.0f, 1.0f, 0.0f, 1.0f, 1.0f,
1.0f, -1.0f, 0.0f, 1.0f, 0.0f, 1.0f, -1.0f, 0.0f, 1.0f, 0.0f,
}; };
// setup plane VAO // setup plane VAO
glGenVertexArrays(1, &quadVAO); glGenVertexArrays(1, &quadVAO);
glGenBuffers(1, &quadVBO); glGenBuffers(1, &quadVBO);
glBindVertexArray(quadVAO); glBindVertexArray(quadVAO);
glBindBuffer(GL_ARRAY_BUFFER, quadVBO); glBindBuffer(GL_ARRAY_BUFFER, quadVBO);
glBufferData(GL_ARRAY_BUFFER, sizeof(quadVertices), &quadVertices, GL_STATIC_DRAW); glBufferData(GL_ARRAY_BUFFER, sizeof(quadVertices), &quadVertices, GL_STATIC_DRAW);
glEnableVertexAttribArray(0); glEnableVertexAttribArray(0);
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 5 * sizeof(float), (void*)0); glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 5 * sizeof(float), (void*)0);
glEnableVertexAttribArray(1); glEnableVertexAttribArray(1);
glVertexAttribPointer(1, 2, GL_FLOAT, GL_FALSE, 5 * sizeof(float), (void*)(3 * sizeof(float))); glVertexAttribPointer(1, 2, GL_FLOAT, GL_FALSE, 5 * sizeof(float), (void*)(3 * sizeof(float)));
} }
glBindVertexArray(quadVAO); glBindVertexArray(quadVAO);
glDrawArrays(GL_TRIANGLE_STRIP, 0, 4); glDrawArrays(GL_TRIANGLE_STRIP, 0, 4);
glBindVertexArray(0); glBindVertexArray(0);
@@ -342,19 +355,40 @@ void init_graphics(void *window)
{ {
window_ = window; window_ = window;
shader_program = compile_shader("assets/shaders/vertex.glsl", "assets/shaders/fragment.glsl"); // Compile the main shaders
shadow_program = compile_shader("assets/shaders/shadow_vertex.glsl", "assets/shaders/shadow_fragment.glsl"); shader_program = compile_shader(
"assets/shaders/vertex.glsl",
"assets/shaders/fragment.glsl");
unsigned int equirectangular_to_cubemap_program = compile_shader("assets/shaders/cubemap_vertex.glsl", "assets/shaders/equirectangular_to_cubemap_fragment.glsl"); // The program which calculates the shadow map
unsigned int irradiance_convolution_program = compile_shader("assets/shaders/cubemap_vertex.glsl", "assets/shaders/irradiance_convolution_fragment.glsl"); shadow_program = compile_shader(
background_program = compile_shader("assets/shaders/background_vertex.glsl", "assets/shaders/background_fragment.glsl"); "assets/shaders/shadow_vertex.glsl",
"assets/shaders/shadow_fragment.glsl");
// Program to compute a cubemap from an image (only necessary at startup)
unsigned int equirectangular_to_cubemap_program = compile_shader(
"assets/shaders/cubemap_vertex.glsl",
"assets/shaders/equirectangular_to_cubemap_fragment.glsl");
// Apply a low pass filter on the cubemap based on the roughness
// parameter (only necessary at startup)
unsigned int irradiance_convolution_program = compile_shader(
"assets/shaders/cubemap_vertex.glsl",
"assets/shaders/irradiance_convolution_fragment.glsl");
// Render the high resolution cubemap
background_program = compile_shader(
"assets/shaders/background_vertex.glsl",
"assets/shaders/background_fragment.glsl");
// Load the sphere mesh from memory
{ {
VertexArray vertices = make_sphere_mesh(0.5); VertexArray vertices = make_sphere_mesh(0.5);
mesh_buffers[MODEL_SPHERE-1] = create_gpu_mesh_buffer(vertices); mesh_buffers[MODEL_SPHERE-1] = create_gpu_mesh_buffer(vertices);
free(vertices.data); free(vertices.data);
} }
// Load the cube mesh from memory
{ {
VertexArray vertices = make_cube_mesh(); VertexArray vertices = make_cube_mesh();
mesh_buffers[MODEL_CUBE-1] = create_gpu_mesh_buffer(vertices); mesh_buffers[MODEL_CUBE-1] = create_gpu_mesh_buffer(vertices);
@@ -392,8 +426,7 @@ void init_graphics(void *window)
stbi_image_free(data); stbi_image_free(data);
} }
// pbr: set up projection and view matrices for capturing data onto the 6 cubemap face directions // Set up projection and view matrices for capturing data onto the 6 cubemap face directions
// ----------------------------------------------------------------------------------------------
Matrix4 captureProjection = perspective_matrix(deg2rad(90.0f), 1.0f, 0.1f, 10.0f); Matrix4 captureProjection = perspective_matrix(deg2rad(90.0f), 1.0f, 0.1f, 10.0f);
Matrix4 captureViews[] = { Matrix4 captureViews[] = {
lookat_matrix((Vector3) {0.0f, 0.0f, 0.0f}, (Vector3) {1.0f, 0.0f, 0.0f}, (Vector3) {0.0f, -1.0f, 0.0f}), lookat_matrix((Vector3) {0.0f, 0.0f, 0.0f}, (Vector3) {1.0f, 0.0f, 0.0f}, (Vector3) {0.0f, -1.0f, 0.0f}),
@@ -425,7 +458,7 @@ void init_graphics(void *window)
glViewport(0, 0, 512, 512); // don't forget to configure the viewport to the capture dimensions. glViewport(0, 0, 512, 512); // don't forget to configure the viewport to the capture dimensions.
glBindFramebuffer(GL_FRAMEBUFFER, captureFBO); glBindFramebuffer(GL_FRAMEBUFFER, captureFBO);
for (unsigned int i = 0; i < 6; ++i) { for (unsigned int i = 0; i < 6; i++) {
glUniformMatrix4fv(glGetUniformLocation(equirectangular_to_cubemap_program, "view"), 1, false, (float*) &captureViews[i]); glUniformMatrix4fv(glGetUniformLocation(equirectangular_to_cubemap_program, "view"), 1, false, (float*) &captureViews[i]);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, envCubemap, 0); glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, envCubemap, 0);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
@@ -437,13 +470,11 @@ void init_graphics(void *window)
{ {
// pbr: create an irradiance cubemap, and re-scale capture FBO to irradiance scale. // pbr: create an irradiance cubemap, and re-scale capture FBO to irradiance scale.
// --------------------------------------------------------------------------------
glGenTextures(1, &irradianceMap); glGenTextures(1, &irradianceMap);
glBindTexture(GL_TEXTURE_CUBE_MAP, irradianceMap); glBindTexture(GL_TEXTURE_CUBE_MAP, irradianceMap);
for (unsigned int i = 0; i < 6; ++i) for (unsigned int i = 0; i < 6; ++i)
{
glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, 0, GL_RGB16F, 32, 32, 0, GL_RGB, GL_FLOAT, NULL); glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, 0, GL_RGB16F, 32, 32, 0, GL_RGB, GL_FLOAT, NULL);
}
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_EDGE); glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_EDGE);
@@ -590,10 +621,6 @@ void init_graphics(void *window)
glEnable(GL_DEPTH_TEST); glEnable(GL_DEPTH_TEST);
glDepthFunc(GL_LEQUAL); glDepthFunc(GL_LEQUAL);
//glEnable(GL_DEPTH_TEST);
//glEnable(GL_CULL_FACE);
//glCullFace(GL_BACK);
} }
typedef struct { typedef struct {
+12
View File
@@ -174,6 +174,18 @@ int main(void)
draw_model(piece_models[board.pieces[i][j].type], (Vector3) {cell_w * (i + 0.5), 0, cell_d * (j + 0.5)}, (Vector3) {1, 1, 1}, (Vector3) {0, rotation, 0}, piece_material); draw_model(piece_models[board.pieces[i][j].type], (Vector3) {cell_w * (i + 0.5), 0, cell_d * (j + 0.5)}, (Vector3) {1, 1, 1}, (Vector3) {0, rotation, 0}, piece_material);
} }
{
Material material = {.baseColor={1, 1, 1}, .metallic=1.0, .perceptualRoughness=0, .reflectance=0};
Vector3 pos = {cell_w * (4 + 0.5), 0, cell_d * (4 + 0.5)};
draw_model(piece_models[PIECE_KING], pos, (Vector3) {1, 1, 1}, (Vector3) {0, 0, 0}, material);
}
{
Material material = {.baseColor={0, 0, 0}, .metallic=1.0, .perceptualRoughness=0, .reflectance=0};
Vector3 pos = {cell_w * (5 + 0.5), 0, cell_d * (4 + 0.5)};
draw_model(piece_models[PIECE_KING], pos, (Vector3) {1, 1, 1}, (Vector3) {0, 0, 0}, material);
}
update_graphics(); update_graphics();
glfwSwapBuffers(window); glfwSwapBuffers(window);
glfwPollEvents(); glfwPollEvents();