mirror of
https://github.com/ApfelTeeSaft/vb01.git
synced 2026-08-26 19:33:45 +00:00
improved reflections
minor code improvements and bugfixes
This commit is contained in:
@@ -65,15 +65,15 @@ namespace vb01{
|
|||||||
irradianceShader = new Shader(libPath + "irradiance");
|
irradianceShader = new Shader(libPath + "irradiance");
|
||||||
brdfIntegrationShader = new Shader(libPath + "brdfIntegration");
|
brdfIntegrationShader = new Shader(libPath + "brdfIntegration");
|
||||||
|
|
||||||
prefilterMap = new Texture(reflectionSize, false);
|
prefilterMap = new Texture(preFilterMapSize, false);
|
||||||
irradianceMap = new Texture(reflectionSize, false);
|
irradianceMap = new Texture(irradianceMapSize, false);
|
||||||
postfilterMap = new Texture(reflectionSize, false, 5);
|
postfilterMap = new Texture(environmentMapSize, false, 5);
|
||||||
brdfIntegrationMap = new Texture(reflectionSize, reflectionSize, false);
|
brdfIntegrationMap = new Texture(brdfMapSize, brdfMapSize, false);
|
||||||
|
|
||||||
initFramebuffer(preFilterFramebuffer, preFilterRenderbuffer, reflectionSize);
|
initFramebuffer(preFilterFramebuffer, preFilterRenderbuffer, preFilterMapSize);
|
||||||
initFramebuffer(irrandianceFramebuffer, irradianceRenderbuffer, reflectionSize);
|
initFramebuffer(irrandianceFramebuffer, irradianceRenderbuffer, irradianceMapSize);
|
||||||
initFramebuffer(postFilterFramebuffer, postFilterRenderbuffer, reflectionSize);
|
initFramebuffer(postFilterFramebuffer, postFilterRenderbuffer, environmentMapSize);
|
||||||
initFramebuffer(brdfFramebuffer, brdfRenderbuffer, reflectionSize);
|
initFramebuffer(brdfFramebuffer, brdfRenderbuffer, brdfMapSize);
|
||||||
|
|
||||||
initMesh();
|
initMesh();
|
||||||
}
|
}
|
||||||
@@ -280,7 +280,8 @@ namespace vb01{
|
|||||||
*/
|
*/
|
||||||
glBindFramebuffer(GL_FRAMEBUFFER, preFilterFramebuffer);
|
glBindFramebuffer(GL_FRAMEBUFFER, preFilterFramebuffer);
|
||||||
|
|
||||||
glViewport(0, 0, reflectionSize, reflectionSize);
|
int width = prefilterMap->getWidth();
|
||||||
|
glViewport(0, 0, width, width);
|
||||||
|
|
||||||
Root *root = Root::getSingleton();
|
Root *root = Root::getSingleton();
|
||||||
Mesh *skybox = root->getSkybox();
|
Mesh *skybox = root->getSkybox();
|
||||||
@@ -314,7 +315,8 @@ namespace vb01{
|
|||||||
glBindFramebuffer(GL_FRAMEBUFFER, irrandianceFramebuffer);
|
glBindFramebuffer(GL_FRAMEBUFFER, irrandianceFramebuffer);
|
||||||
glBindRenderbuffer(GL_RENDERBUFFER, irradianceRenderbuffer);
|
glBindRenderbuffer(GL_RENDERBUFFER, irradianceRenderbuffer);
|
||||||
|
|
||||||
glViewport(0, 0, reflectionSize, reflectionSize);
|
int width = irradianceMapSize;
|
||||||
|
glViewport(0, 0, width, width);
|
||||||
irradianceShader->use();
|
irradianceShader->use();
|
||||||
irradianceShader->setMat4(proj, "proj");
|
irradianceShader->setMat4(proj, "proj");
|
||||||
irradianceShader->setInt(0, "environmentMap");
|
irradianceShader->setInt(0, "environmentMap");
|
||||||
@@ -348,13 +350,13 @@ namespace vb01{
|
|||||||
environmentShader->setMat4(proj, "proj");
|
environmentShader->setMat4(proj, "proj");
|
||||||
environmentShader->setInt(0, "environmentMap");
|
environmentShader->setInt(0, "environmentMap");
|
||||||
|
|
||||||
prefilterMap->select(0);
|
prefilterMap->select();
|
||||||
|
|
||||||
Root *root = Root::getSingleton();
|
Root *root = Root::getSingleton();
|
||||||
int numMipmaps = postfilterMap->getMipmapLevel();
|
int numMipmaps = postfilterMap->getMipmapLevel();
|
||||||
|
|
||||||
for(int i = 0; i < numMipmaps; ++i){
|
for(int i = 0; i < numMipmaps; ++i){
|
||||||
u32 width = reflectionSize * pow(0.5, i);
|
u32 width = environmentMapSize * pow(0.5, i);
|
||||||
glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT24, width, width);
|
glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT24, width, width);
|
||||||
glViewport(0, 0, width, width);
|
glViewport(0, 0, width, width);
|
||||||
|
|
||||||
@@ -382,11 +384,11 @@ namespace vb01{
|
|||||||
void Mesh::updateBrdfLut(){
|
void Mesh::updateBrdfLut(){
|
||||||
glBindFramebuffer(GL_FRAMEBUFFER, brdfFramebuffer);
|
glBindFramebuffer(GL_FRAMEBUFFER, brdfFramebuffer);
|
||||||
|
|
||||||
|
int width = brdfMapSize;
|
||||||
|
glViewport(0, 0, width, width);
|
||||||
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT);
|
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT);
|
||||||
glViewport(0, 0, reflectionSize, reflectionSize);
|
|
||||||
|
|
||||||
glBindRenderbuffer(GL_RENDERBUFFER, brdfRenderbuffer);
|
glBindRenderbuffer(GL_RENDERBUFFER, brdfRenderbuffer);
|
||||||
glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT24, reflectionSize, reflectionSize);
|
|
||||||
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, *brdfIntegrationMap->getTexture(), 0);
|
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, *brdfIntegrationMap->getTexture(), 0);
|
||||||
|
|
||||||
brdfIntegrationShader->use();
|
brdfIntegrationShader->use();
|
||||||
@@ -414,12 +416,12 @@ namespace vb01{
|
|||||||
int irradianceId = 10, brdfId = 11, postFilterId = 12;
|
int irradianceId = 10, brdfId = 11, postFilterId = 12;
|
||||||
|
|
||||||
shader->setInt(irradianceId, "irradianceMap");
|
shader->setInt(irradianceId, "irradianceMap");
|
||||||
shader->setInt(postFilterId, "postFilterMap");
|
|
||||||
shader->setInt(brdfId, "brdfIntegrationMap");
|
shader->setInt(brdfId, "brdfIntegrationMap");
|
||||||
|
shader->setInt(postFilterId, "postFilterMap");
|
||||||
|
|
||||||
irradianceMap->select(irradianceId);
|
irradianceMap->select(irradianceId);
|
||||||
postfilterMap->select(postFilterId);
|
|
||||||
brdfIntegrationMap->select(brdfId);
|
brdfIntegrationMap->select(brdfId);
|
||||||
|
postfilterMap->select(postFilterId);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Mesh::render(){
|
void Mesh::render(){
|
||||||
|
|||||||
@@ -73,7 +73,7 @@ namespace vb01{
|
|||||||
void updateShapeKeys(Shader*);
|
void updateShapeKeys(Shader*);
|
||||||
inline glm::vec3 getUpVec(glm::vec3 dir){return (fabs(dir.y) == 1 ? glm::vec3(0, 0, -1) : glm::vec3(0, 1, 0));}
|
inline glm::vec3 getUpVec(glm::vec3 dir){return (fabs(dir.y) == 1 ? glm::vec3(0, 0, -1) : glm::vec3(0, 1, 0));}
|
||||||
|
|
||||||
int reflectionSize = 512;
|
int irradianceMapSize = 32, preFilterMapSize = 512, environmentMapSize = 128, brdfMapSize = 512;
|
||||||
Texture *prefilterMap = nullptr, *irradianceMap = nullptr, *postfilterMap = nullptr, *brdfIntegrationMap = nullptr;
|
Texture *prefilterMap = nullptr, *irradianceMap = nullptr, *postfilterMap = nullptr, *brdfIntegrationMap = nullptr;
|
||||||
Shader *environmentShader = nullptr, *irradianceShader = nullptr, *brdfIntegrationShader = nullptr;
|
Shader *environmentShader = nullptr, *irradianceShader = nullptr, *brdfIntegrationShader = nullptr;
|
||||||
u32 preFilterFramebuffer, preFilterRenderbuffer, irrandianceFramebuffer, irradianceRenderbuffer, postFilterFramebuffer, postFilterRenderbuffer, brdfFramebuffer, brdfRenderbuffer;
|
u32 preFilterFramebuffer, preFilterRenderbuffer, irrandianceFramebuffer, irradianceRenderbuffer, postFilterFramebuffer, postFilterRenderbuffer, brdfFramebuffer, brdfRenderbuffer;
|
||||||
|
|||||||
@@ -37,7 +37,7 @@ uniform sampler2D brdfIntegrationMap;
|
|||||||
uniform bool albedoMapEnabled;
|
uniform bool albedoMapEnabled;
|
||||||
uniform bool normalMapEnabled;
|
uniform bool normalMapEnabled;
|
||||||
uniform bool roughnessMapEnabled;
|
uniform bool roughnessMapEnabled;
|
||||||
uniform bool metallnessMapEnabled;
|
uniform bool metalnessMapEnabled;
|
||||||
uniform bool ambientOcclutionMapEnabled;
|
uniform bool ambientOcclutionMapEnabled;
|
||||||
uniform bool environmentMapEnabled;
|
uniform bool environmentMapEnabled;
|
||||||
uniform vec4 albedoColor;
|
uniform vec4 albedoColor;
|
||||||
@@ -96,7 +96,7 @@ void main() {
|
|||||||
|
|
||||||
float metalness = metalnessVal;
|
float metalness = metalnessVal;
|
||||||
|
|
||||||
if(metallnessMapEnabled)
|
if(metalnessMapEnabled)
|
||||||
metalness = texture(textures[3].pastTexture, texCoords).r;
|
metalness = texture(textures[3].pastTexture, texCoords).r;
|
||||||
|
|
||||||
vec3 f0 = mix(vec3(.04), albedo.rgb, metalness);
|
vec3 f0 = mix(vec3(.04), albedo.rgb, metalness);
|
||||||
@@ -121,7 +121,7 @@ void main() {
|
|||||||
vec3 halfVec = normalize(lightDir + normal);
|
vec3 halfVec = normalize(lightDir + normal);
|
||||||
|
|
||||||
float D = trowbridgeReitz(normal, halfVec, roughness * roughness);
|
float D = trowbridgeReitz(normal, halfVec, roughness * roughness);
|
||||||
float k = pow(roughness * roughness + 1, 2) / 8.0;
|
float k = pow(roughness + 1, 2) / 8.0;
|
||||||
float G = geoSmith(normal, viewDir, lightDir, k);
|
float G = geoSmith(normal, viewDir, lightDir, k);
|
||||||
vec3 F = fresnelSchlick(viewDir, halfVec, f0);
|
vec3 F = fresnelSchlick(viewDir, halfVec, f0);
|
||||||
float nDotV = max(dot(viewDir, normal), 0);
|
float nDotV = max(dot(viewDir, normal), 0);
|
||||||
@@ -134,21 +134,25 @@ void main() {
|
|||||||
totalLightColor += (kDiff * fDiff + cookTor) * lights[i].color * attenuation * nDotL;
|
totalLightColor += (kDiff * fDiff + cookTor) * lights[i].color * attenuation * nDotL;
|
||||||
}
|
}
|
||||||
|
|
||||||
vec3 specular = vec3(.03);
|
vec3 specular = vec3(.03), F = vec3(0);
|
||||||
|
|
||||||
if(environmentMapEnabled){
|
if(environmentMapEnabled){
|
||||||
// sample both the pre-filter map and the BRDF lut and combine them together as per the Split-Sum approximation to get the IBL specular part.
|
// sample both the pre-filter map and the BRDF lut and combine them together as per the Split-Sum approximation to get the IBL specular part.
|
||||||
vec3 reflVec = reflect(-viewDir, normal);
|
vec3 reflVec = reflect(-viewDir, normalize(fragPos + normal));
|
||||||
const float MAX_REFLECTION_LOD = 4.0;
|
const float MAX_REFLECTION_LOD = 4.0;
|
||||||
vec3 prefilteredColor = textureLod(postFilterMap, reflVec, roughness * MAX_REFLECTION_LOD).rgb;
|
vec3 prefilteredColor = textureLod(postFilterMap, reflVec, roughness * MAX_REFLECTION_LOD).rgb;
|
||||||
vec2 brdf = texture(brdfIntegrationMap, vec2(max(dot(normal, viewDir), 0.0), roughness)).rg;
|
vec2 brdf = texture(brdfIntegrationMap, vec2(max(dot(normal, viewDir), 0.0), roughness)).rg;
|
||||||
vec3 F = fresnelSchlickRoughness(normal, viewDir, f0, roughness);
|
F = fresnelSchlickRoughness(normal, viewDir, f0, roughness);
|
||||||
|
specular = prefilteredColor;
|
||||||
specular = prefilteredColor * (F * brdf.x + brdf.y);
|
specular = prefilteredColor * (F * brdf.x + brdf.y);
|
||||||
}
|
}
|
||||||
|
|
||||||
float ao = ambientOcclusion;
|
float ao = ambientOcclusion;
|
||||||
|
|
||||||
vec3 totalAmbientColor = (albedo.rgb + specular) * ao;
|
vec3 irradiance = texture(irradianceMap, normal).rgb;
|
||||||
|
vec3 diffuse = irradiance * albedo.rgb;
|
||||||
|
vec3 kD = (vec3(1) - F) * (1 - metalness);
|
||||||
|
vec3 totalAmbientColor = (kD * diffuse + specular) * ao;
|
||||||
|
|
||||||
vec4 finalColor = vec4(totalLightColor + totalAmbientColor, 1);
|
vec4 finalColor = vec4(totalLightColor + totalAmbientColor, 1);
|
||||||
|
|
||||||
|
|||||||
@@ -28,10 +28,10 @@ uniform mat4 proj;
|
|||||||
uniform float[numShapeKeys] shapeKeyFactors;
|
uniform float[numShapeKeys] shapeKeyFactors;
|
||||||
|
|
||||||
void main(){
|
void main(){
|
||||||
mat3 normalMat = mat3(transpose(inverse(model)));
|
mat3 normalMat = mat3(model);
|
||||||
norm = (normalMat * aNorm);
|
norm = mat3(normalMat) * aNorm;
|
||||||
tan = (normalMat * aTan);
|
tan = mat3(normalMat) * aTan;
|
||||||
biTan = (normalMat * aBiTan);
|
biTan = mat3(normalMat) * aBiTan;
|
||||||
fragPos = vec3(model * vec4(aPos, 1));
|
fragPos = vec3(model * vec4(aPos, 1));
|
||||||
texCoords = aTexCoords;
|
texCoords = aTexCoords;
|
||||||
|
|
||||||
|
|||||||
+9
-4
@@ -107,7 +107,7 @@ namespace vb01{
|
|||||||
data = stbi_load(paths[i].c_str(), &width, &height, &numChannels, 0);
|
data = stbi_load(paths[i].c_str(), &width, &height, &numChannels, 0);
|
||||||
|
|
||||||
if(data){
|
if(data){
|
||||||
glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, 0, GL_RGB, width, width, 0, GL_RGB, GL_UNSIGNED_BYTE, data);
|
glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, 0, GL_RGB16F, width, width, 0, GL_RGB, GL_UNSIGNED_BYTE, data);
|
||||||
stbi_image_free(data);
|
stbi_image_free(data);
|
||||||
}
|
}
|
||||||
else{
|
else{
|
||||||
@@ -116,7 +116,7 @@ namespace vb01{
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, 0, GL_RGB, width, width, 0, GL_RGB, GL_UNSIGNED_INT, NULL);
|
glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, 0, GL_RGB16F, width, width, 0, GL_RGB, GL_UNSIGNED_INT, NULL);
|
||||||
}
|
}
|
||||||
else{
|
else{
|
||||||
glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, 0, GL_DEPTH_COMPONENT, width, width, 0, GL_DEPTH_COMPONENT, GL_FLOAT, NULL);
|
glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, 0, GL_DEPTH_COMPONENT, width, width, 0, GL_DEPTH_COMPONENT, GL_FLOAT, NULL);
|
||||||
@@ -126,9 +126,14 @@ namespace vb01{
|
|||||||
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);
|
||||||
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
|
|
||||||
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
|
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
|
||||||
glGenerateMipmap(GL_TEXTURE_CUBE_MAP);
|
|
||||||
|
if(mipmapLevel > 0){
|
||||||
|
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR);
|
||||||
|
glGenerateMipmap(GL_TEXTURE_CUBE_MAP);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
|
||||||
}
|
}
|
||||||
|
|
||||||
Texture::Texture(FT_Face &face, char ch){
|
Texture::Texture(FT_Face &face, char ch){
|
||||||
|
|||||||
@@ -22,6 +22,8 @@ namespace vb01{
|
|||||||
void animate(float, KeyframeChannel);
|
void animate(float, KeyframeChannel);
|
||||||
inline u32* getTexture(int i = 0){return &(texture[i]);}
|
inline u32* getTexture(int i = 0){return &(texture[i]);}
|
||||||
inline std::string* getPath(){return paths;}
|
inline std::string* getPath(){return paths;}
|
||||||
|
inline int getWidth(){return width;}
|
||||||
|
inline int getHeight(){return height;}
|
||||||
inline int getNumFrames(){return numFrames;}
|
inline int getNumFrames(){return numFrames;}
|
||||||
inline int getMipmapLevel(){return mipmapLevel;}
|
inline int getMipmapLevel(){return mipmapLevel;}
|
||||||
inline float getMixRatio(){return mixRatio;}
|
inline float getMixRatio(){return mixRatio;}
|
||||||
|
|||||||
Reference in New Issue
Block a user