加入天空盒
parent
d15e3baa69
commit
f3559d133d
|
@ -72,7 +72,7 @@
|
|||
<PreprocessorDefinitions>FRAMELESSHELPER_WIDGETS_STATIC;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<AdditionalDependencies>%(AdditionalDependencies)</AdditionalDependencies>
|
||||
<AdditionalDependencies>opengl32.lib;%(AdditionalDependencies)</AdditionalDependencies>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)' == 'Debug|x64'" Label="Configuration">
|
||||
|
@ -154,6 +154,8 @@
|
|||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="..\data.json" />
|
||||
<None Include="res\Shaders\cubemap.frag" />
|
||||
<None Include="res\Shaders\cubemap.vert" />
|
||||
<None Include="res\Shaders\depth_init.comp" />
|
||||
<None Include="res\Shaders\depth_mipmap.comp" />
|
||||
<None Include="res\Shaders\element.comp" />
|
||||
|
@ -170,6 +172,8 @@
|
|||
<None Include="res\Shaders\shader.frag" />
|
||||
<None Include="res\Shaders\shader.vert" />
|
||||
<None Include="res\Shaders\shadow_mapping.comp" />
|
||||
<None Include="res\Shaders\skybox.frag" />
|
||||
<None Include="res\Shaders\skybox.vert" />
|
||||
<None Include="res\Shaders\ssgi.comp" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
|
|
|
@ -299,6 +299,18 @@
|
|||
<None Include="res\Shaders\ssgi.comp">
|
||||
<Filter>Resource Files\Shaders</Filter>
|
||||
</None>
|
||||
<None Include="res\Shaders\cubemap.vert">
|
||||
<Filter>Resource Files\Shaders</Filter>
|
||||
</None>
|
||||
<None Include="res\Shaders\cubemap.frag">
|
||||
<Filter>Resource Files\Shaders</Filter>
|
||||
</None>
|
||||
<None Include="res\Shaders\skybox.vert">
|
||||
<Filter>Resource Files\Shaders</Filter>
|
||||
</None>
|
||||
<None Include="res\Shaders\skybox.frag">
|
||||
<Filter>Resource Files\Shaders</Filter>
|
||||
</None>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<QtUic Include="EditorWidget.ui">
|
||||
|
|
|
@ -24,6 +24,10 @@
|
|||
<file>darkstyle.qss</file>
|
||||
<file>lightstyle.qss</file>
|
||||
<file>Shaders/element.comp</file>
|
||||
<file>Shaders/cubemap.frag</file>
|
||||
<file>Shaders/cubemap.vert</file>
|
||||
<file>Shaders/skybox.frag</file>
|
||||
<file>Shaders/skybox.vert</file>
|
||||
</qresource>
|
||||
<qresource prefix="/qt/etc">
|
||||
<file>qt.conf</file>
|
||||
|
|
|
@ -0,0 +1,22 @@
|
|||
#version 450 core
|
||||
out vec4 FragColor;
|
||||
in vec3 WorldPos;
|
||||
|
||||
uniform sampler2D equirectangularMap;
|
||||
|
||||
const vec2 invAtan = vec2(0.1591, 0.3183);
|
||||
vec2 SampleSphericalMap(vec3 v)
|
||||
{
|
||||
vec2 uv = vec2(atan(v.z, v.x), asin(v.y));
|
||||
uv *= invAtan;
|
||||
uv += 0.5;
|
||||
return uv;
|
||||
}
|
||||
|
||||
void main()
|
||||
{
|
||||
vec2 uv = SampleSphericalMap(normalize(WorldPos));
|
||||
vec3 color = texture(equirectangularMap, uv).rgb;
|
||||
|
||||
FragColor = vec4(color, 1.0);
|
||||
}
|
|
@ -0,0 +1,13 @@
|
|||
#version 450 core
|
||||
layout (location = 0) in vec3 aPos;
|
||||
|
||||
out vec3 WorldPos;
|
||||
|
||||
uniform mat4 projection;
|
||||
uniform mat4 view;
|
||||
|
||||
void main()
|
||||
{
|
||||
WorldPos = aPos;
|
||||
gl_Position = projection * view * vec4(WorldPos, 1.0);
|
||||
}
|
|
@ -70,90 +70,19 @@ void main()
|
|||
//FragColor = vec4(vec3(depth*10000),1);
|
||||
//FragColor = vec4(vec3(textureSize(gShadowMap, 0)-vec3(1)),1);
|
||||
//FragColor = vec4(texture(gRadiance, TexCoords).rgb, 1);
|
||||
vec3 albedo = pow(texture(gBaseColor, TexCoords).rgb, vec3(2.2));
|
||||
vec3 color = albedo * texture(gIndirectLight, TexCoords).rgb + texture(gDirectLight, TexCoords).rgb;
|
||||
|
||||
//vec3 albedo = pow(texture(gBaseColor, TexCoords).rgb, vec3(2.2));
|
||||
//vec3 color = albedo * texture(gIndirectLight, TexCoords).rgb + texture(gDirectLight, TexCoords).rgb;
|
||||
vec4 rgbm = texture(gBaseColor, TexCoords);
|
||||
if(rgbm.a==0)
|
||||
{
|
||||
//FragColor = vec4(1,0,0,1);
|
||||
//return;
|
||||
discard;
|
||||
}
|
||||
vec3 color = 8 * rgbm.rgb * rgbm.a;
|
||||
color = color / (color + vec3(1.0));
|
||||
color = pow(color, vec3(1.0/2.2));
|
||||
FragColor = vec4(color, 1.0);
|
||||
return;
|
||||
|
||||
|
||||
|
||||
float metallic = texture(gMetallicRoughness, TexCoords).r;
|
||||
float roughness = texture(gMetallicRoughness, TexCoords).g;
|
||||
|
||||
|
||||
vec3 N = texture(gNormal, TexCoords).xyz;
|
||||
vec3 WorldPos = texture(gPosition, TexCoords).xyz;
|
||||
|
||||
if(N==vec3(0))
|
||||
{
|
||||
vec3 color = mainLightRadiance;
|
||||
|
||||
color = color / (color + vec3(1.0));
|
||||
color = pow(color, vec3(1.0/2.2));
|
||||
|
||||
FragColor = vec4(color, 1.0);
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
vec3 V = normalize(camPos - WorldPos);
|
||||
|
||||
vec3 F0 = vec3(0.04);
|
||||
F0 = mix(F0, albedo, metallic);
|
||||
|
||||
// reflectance equation
|
||||
vec3 Lo = vec3(0.0);
|
||||
|
||||
|
||||
// calculate per-light radiance
|
||||
vec3 L = normalize(mainLightDirection);
|
||||
vec3 H = normalize(V + L);
|
||||
//float distance = length(lightPositions[i] - WorldPos);
|
||||
//float attenuation = 1.0 / (distance * distance);
|
||||
vec3 radiance = mainLightRadiance ;//* attenuation;
|
||||
|
||||
// cook-torrance brdf
|
||||
float NDF = DistributionGGX(N, H, roughness);
|
||||
float G = GeometrySmith(N, V, L, roughness);
|
||||
vec3 F = fresnelSchlick(clamp(dot(H, V),0.,1.), F0);
|
||||
//F = clamp(F,vec3(0),vec3(1));
|
||||
|
||||
vec3 kS = F;
|
||||
vec3 kD = vec3(1.0) - kS;
|
||||
kD *= 1.0 - metallic;
|
||||
|
||||
vec3 nominator = NDF * G * F;
|
||||
float denominator = 4.0 * max(dot(N, V), 0.0) * max(dot(N, L), 0.0) + 0.001;
|
||||
vec3 specular = nominator / denominator;
|
||||
|
||||
// add to outgoing radiance Lo
|
||||
float NdotL = max(dot(N, L), 0.0);
|
||||
Lo += (kD * albedo / PI + specular) * radiance * NdotL;
|
||||
|
||||
vec3 ambient = vec3(0.03) * albedo;
|
||||
|
||||
|
||||
|
||||
//vec4 FragPosLightSpace = lightSpaceMatrix * vec4(WorldPos, 1.0);
|
||||
//float bias = 0.08 * max(0.05 * (1.0 - dot(N, L)), 0.005);
|
||||
//int debugLayer;
|
||||
//float shadow = ShadowCalculation(WorldPos, N, debugLayer);
|
||||
|
||||
//vec3 color = ambient + Lo;
|
||||
//vec3 color = indirect*1;
|
||||
float directLight = texture(gDirectLight, TexCoords).r;
|
||||
color = ambient + directLight * Lo;
|
||||
//color*=mix(mix(vec3(1,0,0), vec3(0,1,0), float(debugLayer)/shadowCascadeCount/0.5),
|
||||
//mix(vec3(0,1,0), vec3(0,0,1), float(debugLayer)/(shadowCascadeCount)/0.5-1), float(debugLayer)/(shadowCascadeCount));
|
||||
//vec3 color = (1.0 - shadow) * Lo;
|
||||
//vec3 color = (1.0 - shadow) * Lo + indirect*10;
|
||||
color = color / (color + vec3(1.0));
|
||||
color = pow(color, vec3(1.0/2.2));
|
||||
|
||||
FragColor = vec4(color, 1.0);
|
||||
//FragColor = vec4(vec3(shadow), 1);
|
||||
//FragColor = vec4(texture(gShadowNormal, TexCoords).rgb, 1.0);
|
||||
|
||||
}
|
|
@ -2,7 +2,8 @@
|
|||
|
||||
layout (local_size_x = 8, local_size_y = 8) in;
|
||||
|
||||
uniform sampler2D gBaseColor;
|
||||
layout(rgba8, binding = 0) uniform image2D gBaseColor;
|
||||
//uniform sampler2D gBaseColor;
|
||||
uniform sampler2D gNormal;
|
||||
uniform sampler2D gPosition;
|
||||
uniform sampler2D gMetallicRoughness;
|
||||
|
@ -132,11 +133,26 @@ float ShadowCalculation(vec3 fragPosWorldSpace, vec3 normal, out int layer)
|
|||
return shadow;
|
||||
}
|
||||
|
||||
vec4 encodeRGBM(vec3 color)
|
||||
{
|
||||
if(dot(color,color)==0)
|
||||
return vec4(0,0,0,1);
|
||||
vec4 rgbm;
|
||||
float range = 8;
|
||||
color /= range;
|
||||
rgbm.a = clamp(max(max(color.r, color.g), max(color.b, 1e-6)), 0.0, 1.0);
|
||||
rgbm.a = ceil(rgbm.a * 255.0) / 255.0;
|
||||
rgbm.rgb = color / rgbm.a;
|
||||
return rgbm;
|
||||
}
|
||||
|
||||
void main()
|
||||
{
|
||||
ivec2 pixelLocation = ivec2(gl_GlobalInvocationID.xy);
|
||||
|
||||
vec3 albedo = pow(texelFetch(gBaseColor, pixelLocation, 0).rgb, vec3(2.2));
|
||||
|
||||
//vec3 albedo = pow(texelFetch(gBaseColor, pixelLocation, 0).rgb, vec3(2.2));
|
||||
vec3 albedo = pow(imageLoad(gBaseColor, pixelLocation).rgb, vec3(2.2));
|
||||
float metallic = texelFetch(gMetallicRoughness, pixelLocation, 0).r;
|
||||
float roughness = texelFetch(gMetallicRoughness, pixelLocation, 0).g;
|
||||
|
||||
|
@ -145,12 +161,9 @@ void main()
|
|||
|
||||
if(normal==vec3(0))
|
||||
{
|
||||
vec3 color = mainLightRadiance;
|
||||
|
||||
//color = color / (color + vec3(1.0));
|
||||
//color = pow(color, vec3(1.0/2.2));
|
||||
|
||||
imageStore(gDirectLight, pixelLocation, vec4(color, 1.0));
|
||||
//vec3 color = mainLightRadiance;
|
||||
//imageStore(gBaseColor, pixelLocation, vec4(color, 1.0));
|
||||
imageStore(gBaseColor, pixelLocation, vec4(0));
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -187,5 +200,6 @@ void main()
|
|||
int debugLayer;
|
||||
float shadow = ShadowCalculation(worldPos, normal, debugLayer);
|
||||
|
||||
imageStore(gDirectLight, pixelLocation, vec4((1-shadow)*Lo, 1));
|
||||
vec3 color = (1-shadow)*Lo + albedo*0.03;
|
||||
imageStore(gBaseColor, pixelLocation, encodeRGBM(color));
|
||||
}
|
|
@ -0,0 +1,16 @@
|
|||
#version 450 core
|
||||
out vec4 FragColor;
|
||||
in vec3 WorldPos;
|
||||
|
||||
uniform samplerCube environmentMap;
|
||||
|
||||
void main()
|
||||
{
|
||||
vec3 envColor = texture(environmentMap, WorldPos).rgb;
|
||||
|
||||
// HDR tonemap and gamma correct
|
||||
envColor = envColor / (envColor + vec3(1.0));
|
||||
envColor = pow(envColor, vec3(1.0/2.2));
|
||||
|
||||
FragColor = vec4(envColor, 1.0);
|
||||
}
|
|
@ -0,0 +1,17 @@
|
|||
#version 450 core
|
||||
layout (location = 0) in vec3 aPos;
|
||||
|
||||
uniform mat4 projection;
|
||||
uniform mat4 view;
|
||||
|
||||
out vec3 WorldPos;
|
||||
|
||||
void main()
|
||||
{
|
||||
WorldPos = aPos;
|
||||
|
||||
mat4 rotView = mat4(mat3(view));
|
||||
vec4 clipPos = projection * rotView * vec4(WorldPos, 1.0);
|
||||
|
||||
gl_Position = clipPos.xyww;
|
||||
}
|
|
@ -6,6 +6,10 @@
|
|||
#include <QScreen>
|
||||
#include <QGuiApplication>
|
||||
#include <random>
|
||||
#include <glm/gtc/matrix_transform.hpp>
|
||||
#define STB_IMAGE_IMPLEMENTATION
|
||||
#include <stb_image.h>
|
||||
|
||||
using namespace Renderer;
|
||||
//QVector3D lightPositions[] = { 2000 * QVector3D(0.2, 4, 1).normalized(), QVector3D(100,100,100) ,QVector3D(-100,100,100) ,QVector3D(100,100,-100) };
|
||||
QVector3D lightColors[] = { 20 * QVector3D(0.7529,0.7450,0.6784).normalized(), QVector3D(0,0,0) ,QVector3D(0,0,0) ,QVector3D(0,0,0) };
|
||||
|
@ -89,13 +93,180 @@ void RendererGLWidget::setMainLightYaw(float yaw)
|
|||
sunYaw = yaw;
|
||||
}
|
||||
QOpenGLTexture randomMap(QOpenGLTexture::Target2D);
|
||||
|
||||
void renderCube(QOpenGLFunctions_4_5_Compatibility* glFunc)
|
||||
{
|
||||
static GLuint cubeVAO = 0, cubeVBO = 0;
|
||||
// initialize (if necessary)
|
||||
if (cubeVAO == 0)
|
||||
{
|
||||
float vertices[] = {
|
||||
// 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, 1.0f, 1.0f, // top-right
|
||||
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, 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, 1.0f, // top-left
|
||||
// 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, 1.0f, 0.0f, // bottom-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, 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, 0.0f, // bottom-left
|
||||
// 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, 1.0f, // top-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, 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, 1.0f, 0.0f, // top-right
|
||||
// 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, 0.0f, 1.0f, // bottom-right
|
||||
1.0f, 1.0f, -1.0f, 1.0f, 0.0f, 0.0f, 1.0f, 1.0f, // top-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, 0.0f, 0.0f, // bottom-left
|
||||
// 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, 1.0f, 1.0f, // top-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, 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, 1.0f, // top-right
|
||||
// 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, 1.0f, 0.0f, // bottom-right
|
||||
1.0f, 1.0f, -1.0f, 0.0f, 1.0f, 0.0f, 1.0f, 1.0f, // top-right
|
||||
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, 0.0f, 1.0f, // top-left
|
||||
-1.0f, 1.0f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f // bottom-left
|
||||
};
|
||||
glFunc->glGenVertexArrays(1, &cubeVAO);
|
||||
glFunc->glGenBuffers(1, &cubeVBO);
|
||||
// fill buffer
|
||||
glFunc->glBindBuffer(GL_ARRAY_BUFFER, cubeVBO);
|
||||
glFunc->glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);
|
||||
// link vertex attributes
|
||||
glFunc->glBindVertexArray(cubeVAO);
|
||||
glFunc->glEnableVertexAttribArray(0);
|
||||
glFunc->glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 8 * sizeof(float), (void*)0);
|
||||
glFunc->glEnableVertexAttribArray(1);
|
||||
glFunc->glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 8 * sizeof(float), (void*)(3 * sizeof(float)));
|
||||
glFunc->glEnableVertexAttribArray(2);
|
||||
glFunc->glVertexAttribPointer(2, 2, GL_FLOAT, GL_FALSE, 8 * sizeof(float), (void*)(6 * sizeof(float)));
|
||||
glFunc->glBindBuffer(GL_ARRAY_BUFFER, 0);
|
||||
glFunc->glBindVertexArray(0);
|
||||
}
|
||||
// render Cube
|
||||
glFunc->glBindVertexArray(cubeVAO);
|
||||
glFunc->glDrawArrays(GL_TRIANGLES, 0, 36);
|
||||
glFunc->glBindVertexArray(0);
|
||||
}
|
||||
|
||||
GLuint generateCubemap(QOpenGLFunctions_4_5_Compatibility* glFunc)
|
||||
{
|
||||
QOpenGLShaderProgram shader;
|
||||
if (!shader.addShaderFromSourceFile(QOpenGLShader::Vertex, ":/Shaders/cubemap.vert"))
|
||||
qDebug() << "ERROR:" << shader.log();
|
||||
if (!shader.addShaderFromSourceFile(QOpenGLShader::Fragment, ":/Shaders/cubemap.frag"))
|
||||
qDebug() << "ERROR:" << shader.log();
|
||||
if (!shader.link())
|
||||
qDebug() << "ERROR:" << shader.log();
|
||||
// pbr: setup framebuffer
|
||||
// ----------------------
|
||||
unsigned int captureFBO;
|
||||
unsigned int captureRBO;
|
||||
glFunc->glGenFramebuffers(1, &captureFBO);
|
||||
glFunc->glGenRenderbuffers(1, &captureRBO);
|
||||
|
||||
glFunc->glBindFramebuffer(GL_FRAMEBUFFER, captureFBO);
|
||||
glFunc->glBindRenderbuffer(GL_RENDERBUFFER, captureRBO);
|
||||
glFunc->glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT24, 1024, 1024);
|
||||
glFunc->glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, captureRBO);
|
||||
|
||||
// pbr: load the HDR environment map
|
||||
// ---------------------------------
|
||||
stbi_set_flip_vertically_on_load(true);
|
||||
int width, height, nrComponents;
|
||||
float* data = stbi_loadf("HDRI/clarens_midday_4k.hdr", &width, &height, &nrComponents, 0);
|
||||
unsigned int hdrTexture;
|
||||
if (data)
|
||||
{
|
||||
glGenTextures(1, &hdrTexture);
|
||||
glBindTexture(GL_TEXTURE_2D, hdrTexture);
|
||||
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB16F, width, height, 0, GL_RGB, GL_FLOAT, data);
|
||||
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
|
||||
|
||||
stbi_image_free(data);
|
||||
}
|
||||
else
|
||||
std::cout << "Failed to load HDR image." << std::endl;
|
||||
|
||||
// pbr: setup cubemap to render to and attach to framebuffer
|
||||
// ---------------------------------------------------------
|
||||
unsigned int envCubemap;
|
||||
glFunc->glGenTextures(1, &envCubemap);
|
||||
glFunc->glBindTexture(GL_TEXTURE_CUBE_MAP, envCubemap);
|
||||
for (unsigned int i = 0; i < 6; ++i)
|
||||
{
|
||||
glFunc->glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, 0, GL_RGB16F, 512, 512, 0, GL_RGB, GL_FLOAT, nullptr);
|
||||
}
|
||||
glFunc->glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
|
||||
glFunc->glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
|
||||
glFunc->glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_EDGE);
|
||||
glFunc->glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
|
||||
glFunc->glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
|
||||
|
||||
// pbr: set up projection and view matrices for capturing data onto the 6 cubemap face directions
|
||||
// ----------------------------------------------------------------------------------------------
|
||||
QMatrix4x4 captureProjection;
|
||||
captureProjection.perspective(90.0f, 1.0f, 0.1f, 10.0f);
|
||||
|
||||
QMatrix4x4 captureViews[6];
|
||||
captureViews[0].lookAt(QVector3D(0.0f, 0.0f, 0.0f), QVector3D( 1.0f, 0.0f, 0.0f), QVector3D(0.0f, -1.0f, 0.0f));
|
||||
captureViews[1].lookAt(QVector3D(0.0f, 0.0f, 0.0f), QVector3D(-1.0f, 0.0f, 0.0f), QVector3D(0.0f, -1.0f, 0.0f));
|
||||
captureViews[2].lookAt(QVector3D(0.0f, 0.0f, 0.0f), QVector3D( 0.0f, 1.0f, 0.0f), QVector3D(0.0f, 0.0f, 1.0f));
|
||||
captureViews[3].lookAt(QVector3D(0.0f, 0.0f, 0.0f), QVector3D( 0.0f, -1.0f, 0.0f), QVector3D(0.0f, 0.0f, -1.0f));
|
||||
captureViews[4].lookAt(QVector3D(0.0f, 0.0f, 0.0f), QVector3D( 0.0f, 0.0f, 1.0f), QVector3D(0.0f, -1.0f, 0.0f));
|
||||
captureViews[5].lookAt(QVector3D(0.0f, 0.0f, 0.0f), QVector3D( 0.0f, 0.0f, -1.0f), QVector3D(0.0f, -1.0f, 0.0f));
|
||||
|
||||
// pbr: convert HDR equirectangular environment map to cubemap equivalent
|
||||
// ----------------------------------------------------------------------
|
||||
shader.bind();
|
||||
shader.setUniformValue("equirectangularMap", 0);
|
||||
shader.setUniformValue("projection", captureProjection);
|
||||
glFunc->glActiveTexture(GL_TEXTURE0);
|
||||
glFunc->glBindTexture(GL_TEXTURE_2D, hdrTexture);
|
||||
|
||||
glFunc->glViewport(0, 0, 512, 512); // don't forget to configure the viewport to the capture dimensions.
|
||||
glFunc->glBindFramebuffer(GL_FRAMEBUFFER, captureFBO);
|
||||
for (unsigned int i = 0; i < 6; ++i)
|
||||
{
|
||||
shader.setUniformValue("view", captureViews[i]);
|
||||
glFunc->glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_CUBE_MAP_POSITIVE_X + i, envCubemap, 0);
|
||||
glFunc->glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
|
||||
|
||||
renderCube(glFunc);
|
||||
}
|
||||
glFunc->glBindFramebuffer(GL_FRAMEBUFFER, 0);
|
||||
return envCubemap;
|
||||
}
|
||||
|
||||
|
||||
void RendererGLWidget::initializeGL()
|
||||
{
|
||||
initializeOpenGLFunctions();
|
||||
qDebug() << "GL_VERSION" << (char*)glGetString(GL_VERSION);
|
||||
|
||||
glEnable(GL_DEPTH_TEST);
|
||||
glEnable(GL_CULL_FACE);
|
||||
glDepthFunc(GL_LEQUAL);
|
||||
glClearColor(0, 0, 0, 1);
|
||||
|
||||
shadowProgramPtr = new QOpenGLShaderProgram;
|
||||
|
@ -162,6 +333,13 @@ void RendererGLWidget::initializeGL()
|
|||
if (!finalProgramPtr->link())
|
||||
qDebug() << "ERROR:" << finalProgramPtr->log();
|
||||
|
||||
skyBoxProgramPtr = new QOpenGLShaderProgram;
|
||||
if (!skyBoxProgramPtr->addShaderFromSourceFile(QOpenGLShader::Vertex, ":/Shaders/skybox.vert"))
|
||||
qDebug() << "ERROR:" << skyBoxProgramPtr->log();
|
||||
if (!skyBoxProgramPtr->addShaderFromSourceFile(QOpenGLShader::Fragment, ":/Shaders/skybox.frag"))
|
||||
qDebug() << "ERROR:" << skyBoxProgramPtr->log();
|
||||
if (!skyBoxProgramPtr->link())
|
||||
qDebug() << "ERROR:" << skyBoxProgramPtr->log();
|
||||
|
||||
shadowProgramPtr->bind();
|
||||
glGenBuffers(1, &lightSpaceMatricesUBO);
|
||||
|
@ -177,7 +355,7 @@ void RendererGLWidget::initializeGL()
|
|||
depthInitProgramPtr->release();
|
||||
|
||||
shadowMappingProgramPtr->bind();
|
||||
shadowMappingProgramPtr->setUniformValue("gBaseColor", 0);
|
||||
//shadowMappingProgramPtr->setUniformValue("gBaseColor", 0);
|
||||
shadowMappingProgramPtr->setUniformValue("gNormal", 1);
|
||||
shadowMappingProgramPtr->setUniformValue("gPosition", 2);
|
||||
shadowMappingProgramPtr->setUniformValue("gMetallicRoughness", 3);
|
||||
|
@ -229,6 +407,11 @@ void RendererGLWidget::initializeGL()
|
|||
paintingHelper = new PaintingHelper(QOpenGLContext::currentContext()->versionFunctions<QOpenGLFunctions_4_5_Compatibility>());
|
||||
model = new Model(context(), modelProgramPtr, paintingProgramPtr, shadowProgramPtr, paintingHelper);
|
||||
|
||||
skyBoxProgramPtr->bind();
|
||||
skyBoxProgramPtr->setUniformValue("environmentMap", 0);
|
||||
skyBoxProgramPtr->release();
|
||||
skyCubemap = generateCubemap(QOpenGLContext::currentContext()->versionFunctions<QOpenGLFunctions_4_5_Compatibility>());
|
||||
|
||||
|
||||
quadVAO.create();
|
||||
QOpenGLVertexArrayObject::Binder vaoBinder(&quadVAO);
|
||||
|
@ -259,6 +442,7 @@ void RendererGLWidget::initializeGL()
|
|||
|
||||
void RendererGLWidget::paintGL()
|
||||
{
|
||||
glEnable(GL_CULL_FACE);
|
||||
|
||||
light.lightDirection.setX(cos(qDegreesToRadians(sunPitch)) * cos(qDegreesToRadians(sunYaw)));
|
||||
light.lightDirection.setY(sin(qDegreesToRadians(sunPitch)));
|
||||
|
@ -266,13 +450,13 @@ void RendererGLWidget::paintGL()
|
|||
light.lightDirection.normalize();
|
||||
|
||||
const std::vector<QMatrix4x4> lightMatrices = light.getLightSpaceMatrices();
|
||||
//qDebug() << lightMatrices;
|
||||
glBindBuffer(GL_UNIFORM_BUFFER, lightSpaceMatricesUBO);
|
||||
for (size_t i = 0; i < lightMatrices.size(); i++)
|
||||
{
|
||||
glBufferSubData(GL_UNIFORM_BUFFER, i * 16 * sizeof(GLfloat), 16 * sizeof(GLfloat), lightMatrices[i].data());
|
||||
}
|
||||
glBindBuffer(GL_UNIFORM_BUFFER, 0);
|
||||
|
||||
{
|
||||
glBindFramebuffer(GL_FRAMEBUFFER, shadowFboHandle);
|
||||
glViewport(0, 0, shadowMapResolution, shadowMapResolution);
|
||||
|
@ -303,7 +487,6 @@ void RendererGLWidget::paintGL()
|
|||
if (model != nullptr)
|
||||
model->draw();
|
||||
|
||||
|
||||
fboPtr->release();
|
||||
}
|
||||
|
||||
|
@ -350,8 +533,8 @@ void RendererGLWidget::paintGL()
|
|||
shadowMappingProgramPtr->setUniformValue("camPos", camera.Position);
|
||||
shadowMappingProgramPtr->setUniformValue("mainLightDirection", light.lightDirection);
|
||||
shadowMappingProgramPtr->setUniformValue("mainLightRadiance", lightColors[0]);
|
||||
glActiveTexture(GL_TEXTURE0);
|
||||
glBindTexture(GL_TEXTURE_2D, gbuffers[0]);
|
||||
/*glActiveTexture(GL_TEXTURE0);
|
||||
glBindTexture(GL_TEXTURE_2D, gbuffers[0]);*/
|
||||
glActiveTexture(GL_TEXTURE1);
|
||||
glBindTexture(GL_TEXTURE_2D, gbuffers[1]);
|
||||
glActiveTexture(GL_TEXTURE2);
|
||||
|
@ -360,11 +543,12 @@ void RendererGLWidget::paintGL()
|
|||
glBindTexture(GL_TEXTURE_2D, gbuffers[3]);
|
||||
glActiveTexture(GL_TEXTURE4);
|
||||
glBindTexture(GL_TEXTURE_2D_ARRAY, shadowGbuffer);
|
||||
glBindImageTexture(0, gbuffers[0], 0, GL_FALSE, 0, GL_READ_WRITE, GL_RGBA8);
|
||||
glBindImageTexture(1, gbuffers[8], 0, GL_FALSE, 0, GL_READ_WRITE, GL_RGBA16F);
|
||||
glDispatchCompute(ceil(frameWidth / 8.), ceil(frameHeight / 8.), 1);
|
||||
shadowMappingProgramPtr->release();
|
||||
|
||||
ssgiProgramPtr->bind();
|
||||
/*ssgiProgramPtr->bind();
|
||||
ssgiProgramPtr->setUniformValue("camPos", camera.Position);
|
||||
ssgiProgramPtr->setUniformValue("cameraMatrix", projection * view);
|
||||
ssgiProgramPtr->setUniformValue("projectionMatrix", projection);
|
||||
|
@ -386,11 +570,11 @@ void RendererGLWidget::paintGL()
|
|||
glBindTexture(GL_TEXTURE_2D, gbuffers[8]);
|
||||
glBindImageTexture(1, gbuffers[9], 0, GL_FALSE, 0, GL_READ_WRITE, GL_RGBA16F);
|
||||
glDispatchCompute(ceil(frameWidth / 8.), ceil(frameHeight / 8.), 1);
|
||||
ssgiProgramPtr->release();
|
||||
ssgiProgramPtr->release();*/
|
||||
|
||||
glViewport(0, 0, frameWidth, frameHeight);
|
||||
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
|
||||
QOpenGLVertexArrayObject::Binder vaoBinder(&quadVAO);
|
||||
//QOpenGLVertexArrayObject::Binder vaoBinder(&quadVAO);
|
||||
finalProgramPtr->bind();
|
||||
/*finalProgramPtr->setUniformValue("camPos", camera.Position);
|
||||
finalProgramPtr->setUniformValue("mainLightDirection", light.lightDirection);
|
||||
|
@ -410,10 +594,21 @@ void RendererGLWidget::paintGL()
|
|||
//glActiveTexture(GL_TEXTURE4);
|
||||
//glBindTexture(GL_TEXTURE_2D, gbuffers[7]);
|
||||
//glActiveTexture(GL_TEXTURE5);
|
||||
//glBindTexture(GL_TEXTURE_2D, gbuffers[8]);
|
||||
//glBindTexture(GL_TEXTURE_2D, gbuffers[8]);
|
||||
quadVAO.bind();
|
||||
glDrawArrays(GL_TRIANGLE_STRIP, 0, 4);
|
||||
quadVAO.release();
|
||||
finalProgramPtr->release();
|
||||
|
||||
skyBoxProgramPtr->bind();
|
||||
glDisable(GL_CULL_FACE);
|
||||
skyBoxProgramPtr->setUniformValue("view", view);
|
||||
skyBoxProgramPtr->setUniformValue("projection", projection);
|
||||
glActiveTexture(GL_TEXTURE0);
|
||||
glBindTexture(GL_TEXTURE_CUBE_MAP, skyCubemap);
|
||||
renderCube(QOpenGLContext::currentContext()->versionFunctions<QOpenGLFunctions_4_5_Compatibility>());
|
||||
skyBoxProgramPtr->release();
|
||||
|
||||
GLuint paintingCompDuration;
|
||||
glGetQueryObjectuiv(paintingCompQuery, GL_QUERY_RESULT, &paintingCompDuration);
|
||||
|
||||
|
@ -427,7 +622,7 @@ void RendererGLWidget::paintGL()
|
|||
if (accTime > 1.)
|
||||
{
|
||||
std::cout << std::format("{:20}\r", "");
|
||||
std::cout << std::format("FPS: {:.2f} Painting: {}ms Pos: {},{},{}\r", frameCnt / accTime, paintingCompDuration/1e6, camera.Position.x(), camera.Position.y(), camera.Position.z());
|
||||
std::cout << std::format("FPS: {:.2f} Painting: {}ms Pos: {},{},{}\r", frameCnt / accTime, paintingCompDuration / 1e6, camera.Position.x(), camera.Position.y(), camera.Position.z());
|
||||
//std::cout << "FPS: " << frameCnt / accTime << " " << camera.Position.x() << " " << camera.Position.y() << " " << camera.Position.z() << "\r";
|
||||
accTime = 0;
|
||||
frameCnt = 0;
|
||||
|
|
|
@ -57,11 +57,13 @@ namespace Renderer
|
|||
QOpenGLShaderProgram* shadowMappingProgramPtr = nullptr;
|
||||
QOpenGLShaderProgram* ssgiProgramPtr = nullptr;
|
||||
QOpenGLShaderProgram* finalProgramPtr = nullptr;
|
||||
QOpenGLShaderProgram* skyBoxProgramPtr = nullptr;
|
||||
QOpenGLFramebufferObject* fboPtr = nullptr;
|
||||
GLuint gbuffers[10];
|
||||
GLuint shadowFboHandle = 0;
|
||||
GLuint shadowGbuffer;
|
||||
GLuint lightSpaceMatricesUBO;
|
||||
GLuint skyCubemap;
|
||||
QOpenGLBuffer quadVBO;
|
||||
QOpenGLVertexArrayObject quadVAO;
|
||||
Model* model = nullptr;
|
||||
|
|
Loading…
Reference in New Issue