diff options
-rw-r--r-- | cwd/assets/altcraft/scripts/ui.lua | 1 | ||||
-rw-r--r-- | cwd/assets/altcraft/shaders/frag/fwd_entity.fs | 11 | ||||
-rw-r--r-- | cwd/assets/altcraft/shaders/frag/fwd_face.fs | 38 | ||||
-rw-r--r-- | cwd/assets/altcraft/shaders/frag/fwd_sky.fs | 65 | ||||
-rw-r--r-- | cwd/assets/altcraft/ui/options.rml | 6 | ||||
-rw-r--r-- | src/Render.cpp | 83 | ||||
-rw-r--r-- | src/Render.hpp | 3 | ||||
-rw-r--r-- | src/RendererWorld.cpp | 15 | ||||
-rw-r--r-- | src/RendererWorld.hpp | 4 |
9 files changed, 193 insertions, 33 deletions
diff --git a/cwd/assets/altcraft/scripts/ui.lua b/cwd/assets/altcraft/scripts/ui.lua index 938088f..bc04626 100644 --- a/cwd/assets/altcraft/scripts/ui.lua +++ b/cwd/assets/altcraft/scripts/ui.lua @@ -1,5 +1,6 @@ local options = { gamma = 2.2, + deffered = false, flight = false, mouseSensetivity = 0.1, renderDistance = 2, diff --git a/cwd/assets/altcraft/shaders/frag/fwd_entity.fs b/cwd/assets/altcraft/shaders/frag/fwd_entity.fs new file mode 100644 index 0000000..094aaf2 --- /dev/null +++ b/cwd/assets/altcraft/shaders/frag/fwd_entity.fs @@ -0,0 +1,11 @@ +#version 330 core + +in vec4 entityWorldPos; + +out vec4 fragColor; + +uniform vec3 entityColor; + +void main() { + fragColor = vec4(entityColor, 1.0f); +} diff --git a/cwd/assets/altcraft/shaders/frag/fwd_face.fs b/cwd/assets/altcraft/shaders/frag/fwd_face.fs new file mode 100644 index 0000000..deb8341 --- /dev/null +++ b/cwd/assets/altcraft/shaders/frag/fwd_face.fs @@ -0,0 +1,38 @@ +#version 330 core + +in vec4 faceWorldPos; +in vec3 faceTextureUv; +in vec3 faceAddColor; +in vec3 faceNormal; +in vec2 faceLight; + +out vec4 fragColor; + +uniform sampler2DArray textureAtlas; + +layout (std140) uniform Globals { + mat4 projView; + mat4 proj; + mat4 view; + uvec2 viewportSize; + vec4 ssaoKernels[64]; + float globalTime; + float dayTime; + float gamma; +}; + +void main() { + vec4 col = texture(textureAtlas, faceTextureUv); + if (col.a < 0.3f) + discard; + + float localLight = faceLight.r / 15.0f; + float skyLight = faceLight.g / 15.0f; + float lightLevel = clamp(localLight + skyLight * dayTime, 0.01f, 1.0f); + lightLevel = pow(lightLevel, 3); + lightLevel = clamp(lightLevel, 0.005f, 1.0f); + + fragColor = vec4(col.rgb * faceAddColor.rgb * lightLevel, 1.0f); + + fragColor.rgb = pow(fragColor.rgb, vec3(1.0f / gamma)); +} diff --git a/cwd/assets/altcraft/shaders/frag/fwd_sky.fs b/cwd/assets/altcraft/shaders/frag/fwd_sky.fs new file mode 100644 index 0000000..b6185fd --- /dev/null +++ b/cwd/assets/altcraft/shaders/frag/fwd_sky.fs @@ -0,0 +1,65 @@ +#version 330 core + +in vec3 facePos; + +out vec4 fragColor; + +layout (std140) uniform Globals { + mat4 projView; + mat4 proj; + mat4 view; + uvec2 viewportSize; + vec4 ssaoKernels[64]; + float globalTime; + float dayTime; + float gamma; +}; + +uniform sampler2DArray textureAtlas; +uniform vec4 sunTexture; +uniform float sunTextureLayer; +uniform vec4 moonTexture; +uniform float moonTextureLayer; + +const vec4 DaySkyColor = vec4(0.21, 0.4, 1, 1); + +const vec3 SunPos = vec3(0, 0.1, 0.5); + +const vec3 MoonPos = vec3(0, 0.1, -0.5); + +const vec4 NightSkyColor = vec4(0.0, 0.0008, 0.002, 1.0); + +vec3 TransformTextureCoord(vec4 TextureAtlasCoords, vec2 UvCoords, float Layer) { + float x = TextureAtlasCoords.x; + float y = TextureAtlasCoords.y; + float w = TextureAtlasCoords.z; + float h = TextureAtlasCoords.w; + vec2 A = vec2(x, 1 - y - h); + vec2 B = vec2(x + w, 1 - y); + vec2 transformed = A + UvCoords * (B - A); + return vec3(transformed.x, transformed.y, Layer); +} + +vec4 Sun() { + vec3 sunDelta = (facePos - SunPos) * 3.0f; + float distanceToSun = length(sunDelta); + vec4 sunColor = texture(textureAtlas, TransformTextureCoord(sunTexture, (vec2(sunDelta.xy) + 0.5f), sunTextureLayer)); + vec4 sun = mix(vec4(0, 0, 0, 1), sunColor, clamp(1 - distanceToSun * 2.0f, 0, 1)); + return sun; +} + +vec4 Moon() { + vec3 moonDelta = (facePos - MoonPos) * 4.5f; + float distanceToMoon = length(moonDelta); + vec4 moonColor = texture(textureAtlas, TransformTextureCoord(moonTexture, (vec2(moonDelta.xy) + 0.5f), moonTextureLayer)); + vec4 moon = mix(vec4(0, 0, 0, 1),moonColor, clamp(1 - distanceToMoon * 2.0f, 0, 1)); + return moon; +} + +void main() { + fragColor = vec4(mix(NightSkyColor, DaySkyColor, dayTime).rgb, 1.0f); + fragColor += vec4(Sun().rgb, 1.0f); + fragColor += vec4(Moon().rgb, 1.0f); + + fragColor.rgb = pow(fragColor.rgb, vec3(1.0f / gamma)); +} diff --git a/cwd/assets/altcraft/ui/options.rml b/cwd/assets/altcraft/ui/options.rml index 9aa4624..ea7c39e 100644 --- a/cwd/assets/altcraft/ui/options.rml +++ b/cwd/assets/altcraft/ui/options.rml @@ -14,6 +14,12 @@ </div> <div class="option"> + <label>Deffered shading</label> + <input type="checkbox" id="deffered" /> + <span id="deffered-val"></span> + </div> + + <div class="option"> <label>Flight</label> <input type="checkbox" id="flight" /> <span id="flight-val"></span> diff --git a/src/Render.cpp b/src/Render.cpp index 1e85437..35ee695 100644 --- a/src/Render.cpp +++ b/src/Render.cpp @@ -140,28 +140,53 @@ void Render::PrepareToRendering() { float resolutionScale = Settings::ReadDouble("resolutionScale", 1.0f); size_t scaledW = width * resolutionScale, scaledH = height * resolutionScale; - gbuffer = std::make_unique<Gbuffer>(scaledW, scaledH, scaledW, scaledH, Settings::ReadBool("ssao", false)); - gbuffer->SetRenderBuff(renderBuff); - auto gal = Gal::GetImplementation(); gal->GetDefaultFramebuffer()->SetViewport(0, 0, width, height); - gal->GetGlobalShaderParameters()->Get<GlobalShaderParameters>()->gamma = Settings::ReadDouble("gamma", 2.2); - std::mt19937 rng(std::chrono::steady_clock::now().time_since_epoch().count()); - std::uniform_real_distribution<float> dis(-1.0f, 1.0f); - auto& ssaoKernels = gal->GetGlobalShaderParameters()->Get<GlobalShaderParameters>()->ssaoKernels; - for (auto& vec : ssaoKernels) { - vec.x = dis(rng); - vec.y = dis(rng); - vec.z = (dis(rng) + 1.0f) / 2.0f; - vec.w = 0.0f; - vec = glm::normalize(vec); - } - for (size_t i = 0; i < sizeof(ssaoKernels) / sizeof(*ssaoKernels); i++) { - float scale = i / 64.0f; - scale = glm::mix(0.1f, 1.0f, scale * scale); - ssaoKernels[i] *= scale; + gbuffer.reset(); + fbTarget.reset(); + fbTextureColor.reset(); + fbTextureDepthStencil.reset(); + + bool useDeffered = Settings::ReadBool("deffered", false); + + if (useDeffered) { + gbuffer = std::make_unique<Gbuffer>(scaledW, scaledH, scaledW, scaledH, Settings::ReadBool("ssao", false)); + gbuffer->SetRenderBuff(renderBuff); + + std::mt19937 rng(std::chrono::steady_clock::now().time_since_epoch().count()); + std::uniform_real_distribution<float> dis(-1.0f, 1.0f); + auto& ssaoKernels = gal->GetGlobalShaderParameters()->Get<GlobalShaderParameters>()->ssaoKernels; + for (auto& vec : ssaoKernels) { + vec.x = dis(rng); + vec.y = dis(rng); + vec.z = (dis(rng) + 1.0f) / 2.0f; + vec.w = 0.0f; + vec = glm::normalize(vec); + } + for (size_t i = 0; i < sizeof(ssaoKernels) / sizeof(*ssaoKernels); i++) { + float scale = i / 64.0f; + scale = glm::mix(0.1f, 1.0f, scale * scale); + ssaoKernels[i] *= scale; + } + } else { + auto fbTextureColorConf = gal->CreateTexture2DConfig(scaledW, scaledH, Gal::Format::R8G8B8); + fbTextureColorConf->SetMinFilter(Gal::Filtering::Bilinear); + fbTextureColorConf->SetMaxFilter(Gal::Filtering::Bilinear); + fbTextureColor = gal->BuildTexture(fbTextureColorConf); + + auto fbTextureDepthStencilConf = gal->CreateTexture2DConfig(scaledW, scaledH, Gal::Format::D24S8); + fbTextureDepthStencilConf->SetMinFilter(Gal::Filtering::Bilinear); + fbTextureDepthStencilConf->SetMaxFilter(Gal::Filtering::Bilinear); + fbTextureDepthStencil = gal->BuildTexture(fbTextureDepthStencilConf); + + auto fbTargetConf = gal->CreateFramebufferConfig(); + fbTargetConf->SetTexture(0, fbTextureColor); + fbTargetConf->SetDepthStencil(fbTextureDepthStencil); + + fbTarget = gal->BuildFramebuffer(fbTargetConf); + fbTarget->SetViewport(0, 0, scaledW, scaledH); } std::string vertexSource, pixelSource; @@ -189,19 +214,19 @@ void Render::PrepareToRendering() { fbPPC->SetTarget(gal->GetDefaultFramebuffer()); fbPPC->SetVertexShader(gal->LoadVertexShader(vertexSource)); fbPPC->SetPixelShader(gal->LoadPixelShader(pixelSource)); - fbPPC->AddStaticTexture("inputTexture", gbuffer->GetFinalTexture()); + fbPPC->AddStaticTexture("inputTexture", useDeffered ? gbuffer->GetFinalTexture() : fbTextureColor); auto fbColorBB = fbPPC->BindVertexBuffer({ {"pos", Gal::Type::Vec2}, {"uvPos", Gal::Type::Vec2} }); - + fbPipeline = gal->BuildPipeline(fbPPC); fbPipelineInstance = fbPipeline->CreateInstance({ {fbColorBB, fbBuffer} }); if (world) - world->PrepareRender(gbuffer->GetGeometryTarget()); + world->PrepareRender(useDeffered ? gbuffer->GetGeometryTarget() : fbTarget, useDeffered); } void Render::UpdateKeyboard() { @@ -226,7 +251,10 @@ void Render::RenderFrame() { OPTICK_EVENT(); Gal::GetImplementation()->GetDefaultFramebuffer()->Clear(); - gbuffer->Clear(); + if (gbuffer) + gbuffer->Clear(); + if (fbTarget) + fbTarget->Clear(); if (isWireframe) Gal::GetImplementation()->SetWireframe(true); @@ -236,7 +264,8 @@ void Render::RenderFrame() { if (isWireframe) Gal::GetImplementation()->SetWireframe(false); - gbuffer->Render(); + if (gbuffer) + gbuffer->Render(); fbPipeline->Activate(); fbPipelineInstance->Activate(); @@ -368,7 +397,8 @@ void Render::HandleEvents() { if (renderBuff > gbuffer->GetMaxRenderBuffers()) renderBuff = 0; } - gbuffer->SetRenderBuff(renderBuff); + if (gbuffer) + gbuffer->SetRenderBuff(renderBuff); break; } @@ -512,7 +542,10 @@ void Render::InitEvents() { listener.RegisterHandler("PlayerConnected", [this](const Event&) { stateString = "Loading terrain..."; - world = std::make_unique<RendererWorld>(gbuffer->GetGeometryTarget()); + world = std::make_unique<RendererWorld>( + Settings::ReadBool("deffered", false) ? gbuffer->GetGeometryTarget() : fbTarget, + Settings::ReadBool("deffered", false) + ); world->MaxRenderingDistance = Settings::ReadDouble("renderDistance", 2.0f); PUSH_EVENT("UpdateSectionsRender", 0); }); diff --git a/src/Render.hpp b/src/Render.hpp index 8bdcd63..944a4cb 100644 --- a/src/Render.hpp +++ b/src/Render.hpp @@ -39,6 +39,9 @@ class Render { std::shared_ptr<Gal::Pipeline> fbPipeline; std::shared_ptr<Gal::PipelineInstance> fbPipelineInstance; std::shared_ptr<Gal::Buffer> fbBuffer; + std::shared_ptr<Gal::Framebuffer> fbTarget; + std::shared_ptr<Gal::Texture> fbTextureColor; + std::shared_ptr<Gal::Texture> fbTextureDepthStencil; std::unique_ptr<Gbuffer> gbuffer; EventListener listener; std::string stateString; diff --git a/src/RendererWorld.cpp b/src/RendererWorld.cpp index 2108ba6..b5120c2 100644 --- a/src/RendererWorld.cpp +++ b/src/RendererWorld.cpp @@ -152,7 +152,7 @@ void RendererWorld::UpdateAllSections(VectorF playerPos) { } } -RendererWorld::RendererWorld(std::shared_ptr<Gal::Framebuffer> target) { +RendererWorld::RendererWorld(std::shared_ptr<Gal::Framebuffer> target, bool defferedShading) { OPTICK_EVENT(); MaxRenderingDistance = 2; numOfWorkers = _max(1, (signed int) std::thread::hardware_concurrency() - 2); @@ -161,7 +161,7 @@ RendererWorld::RendererWorld(std::shared_ptr<Gal::Framebuffer> target) { globalTimeStart = std::chrono::high_resolution_clock::now(); - PrepareRender(target); + PrepareRender(target, defferedShading); listener->RegisterHandler("DeleteSectionRender", [this](const Event& eventData) { OPTICK_EVENT("EV_DeleteSectionRender"); @@ -407,13 +407,14 @@ void RendererWorld::Render(float screenRatio) { DebugInfo::renderFaces = renderedFaces; } -void RendererWorld::PrepareRender(std::shared_ptr<Gal::Framebuffer> target) { +void RendererWorld::PrepareRender(std::shared_ptr<Gal::Framebuffer> target, bool defferedShading) { std::string sectionVertexSource, sectionPixelSource; { auto vertAsset = AssetManager::GetAssetByAssetName("/altcraft/shaders/vert/face"); sectionVertexSource = std::string((char*)vertAsset->data.data(), (char*)vertAsset->data.data() + vertAsset->data.size()); - auto pixelAsset = AssetManager::GetAssetByAssetName("/altcraft/shaders/frag/face"); + auto pixelAsset = defferedShading ? AssetManager::GetAssetByAssetName("/altcraft/shaders/frag/face") : + AssetManager::GetAssetByAssetName("/altcraft/shaders/frag/fwd_face"); sectionPixelSource = std::string((char*)pixelAsset->data.data(), (char*)pixelAsset->data.data() + pixelAsset->data.size()); } @@ -422,7 +423,8 @@ void RendererWorld::PrepareRender(std::shared_ptr<Gal::Framebuffer> target) { auto vertAsset = AssetManager::GetAssetByAssetName("/altcraft/shaders/vert/entity"); entitiesVertexSource = std::string((char*)vertAsset->data.data(), (char*)vertAsset->data.data() + vertAsset->data.size()); - auto pixelAsset = AssetManager::GetAssetByAssetName("/altcraft/shaders/frag/entity"); + auto pixelAsset = defferedShading ? AssetManager::GetAssetByAssetName("/altcraft/shaders/frag/entity") : + AssetManager::GetAssetByAssetName("/altcraft/shaders/frag/fwd_entity"); entitiesPixelSource = std::string((char*)pixelAsset->data.data(), (char*)pixelAsset->data.data() + pixelAsset->data.size()); } @@ -431,7 +433,8 @@ void RendererWorld::PrepareRender(std::shared_ptr<Gal::Framebuffer> target) { auto vertAsset = AssetManager::GetAssetByAssetName("/altcraft/shaders/vert/sky"); skyVertexSource = std::string((char*)vertAsset->data.data(), (char*)vertAsset->data.data() + vertAsset->data.size()); - auto pixelAsset = AssetManager::GetAssetByAssetName("/altcraft/shaders/frag/sky"); + auto pixelAsset = defferedShading ? AssetManager::GetAssetByAssetName("/altcraft/shaders/frag/sky") : + AssetManager::GetAssetByAssetName("/altcraft/shaders/frag/fwd_sky"); skyPixelSource = std::string((char*)pixelAsset->data.data(), (char*)pixelAsset->data.data() + pixelAsset->data.size()); } diff --git a/src/RendererWorld.hpp b/src/RendererWorld.hpp index a6fca06..184323d 100644 --- a/src/RendererWorld.hpp +++ b/src/RendererWorld.hpp @@ -55,11 +55,11 @@ class RendererWorld { std::shared_ptr<Gal::PipelineInstance> skyPipelineInstance; std::shared_ptr<Gal::Buffer> skyBuffer; public: - RendererWorld(std::shared_ptr<Gal::Framebuffer> target); + RendererWorld(std::shared_ptr<Gal::Framebuffer> target, bool defferedShading); ~RendererWorld(); void Render(float screenRatio); - void PrepareRender(std::shared_ptr<Gal::Framebuffer> target); + void PrepareRender(std::shared_ptr<Gal::Framebuffer> target, bool defferedShading); double MaxRenderingDistance; |