Quicky hacky solution for blur timings. Not scalable, needs future refactoring

This commit is contained in:
Ethan Adams 2025-02-26 14:33:26 -05:00
parent 46838f2743
commit e2c5462c38
8 changed files with 101 additions and 57 deletions

View file

@ -5,14 +5,16 @@ layout (std140) uniform uPostProcess {
int dt; int dt;
vec3 colorMod; vec3 colorMod;
float blurIntensity; float blurIntensity;
float blurDuration;
float shakeIntensity; float shakeIntensity;
float shakeTime; float shakeDuration;
int effects; int effects;
vec3 colorMod_hud; vec3 colorMod_hud;
float blurIntensity_hud; float blurIntensity_hud;
float blurDuration_hud;
float shakeIntensity_hud; float shakeIntensity_hud;
float shakeTime_hud; float shakeDuration_hud;
int effects_hud; int effects_hud;
}; };
out vec4 FragColor; out vec4 FragColor;
@ -31,7 +33,9 @@ void main()
{ {
if (worldOrHud == false) if (worldOrHud == false)
{ {
/* if ((effects & 1) != 0) // BLUR
{
vec4 result = vec4(0.0);
vec2 offsets[9] = vec2[]( vec2 offsets[9] = vec2[](
vec2(-offset, offset), // top-left vec2(-offset, offset), // top-left
vec2( 0.0f, offset), // top-center vec2( 0.0f, offset), // top-center
@ -43,24 +47,20 @@ void main()
vec2( 0.0f, -offset), // bottom-center vec2( 0.0f, -offset), // bottom-center
vec2( offset, -offset) // bottom-right vec2( offset, -offset) // bottom-right
); );
vec2 tex_offset = 1.0 / vec2(800.0, 600.0); // gets size of single texel
vec4 result = vec4(0.0);
vec4 sampleTex[9]; vec4 sampleTex[9];
for (int i = 0; i < 9; i++) for (int i = 0; i < 9; i++)
{ {
sampleTex[i] = vec4(texture(screenTexture, texCoord.st + offsets[i])); sampleTex[i] = vec4(texture(screenTexture, texCoord.st + offsets[i]));
} }
for (int i = 0; i < 9; i++) for (int i = 0; i < 9; i++)
result += sampleTex[i] * edge_kernel[i]; result += sampleTex[i] * blur_kernel[i];
*/
//FragColor = mix(vec4(result), vec4(0.4, 0.0, 0.7, 1.0), 0.2);
if ((effects & (1 << 1)) != 0)
{
//FragColor = mix(texture(screenTexture, texCoord), vec4(1.0, 0.8, 0.0, 1.0), 0.3 - (1.0 / shakeTime) * shakeIntensity); //FragColor = mix(texture(screenTexture, texCoord), vec4(1.0, 0.8, 0.0, 1.0), 0.3 - (1.0 / shakeTime) * shakeIntensity);
FragColor = texture(screenTexture, texCoord); //FragColor = vec4(1.0 / blurDuration, 1.0, 0.0, 1.0);
FragColor = vec4(result);
} }
else else
{ {
//FragColor = vec4(1.0, 0.0, 1.0 / blurDuration, 1.0);
FragColor = texture(screenTexture, texCoord); FragColor = texture(screenTexture, texCoord);
} }
} }

View file

@ -7,14 +7,16 @@ layout (std140) uniform uPostProcess {
int dt; int dt;
vec3 colorMod; vec3 colorMod;
float blurIntensity; float blurIntensity;
float blurDuration;
float shakeIntensity; float shakeIntensity;
float shakeTime; float shakeDuration;
int effects; int effects;
vec3 colorMod_hud; vec3 colorMod_hud;
float blurIntensity_hud; float blurIntensity_hud;
float blurDuration_hud;
float shakeIntensity_hud; float shakeIntensity_hud;
float shakeTime_hud; float shakeDuration_hud;
int effects_hud; int effects_hud;
}; };
@ -48,8 +50,8 @@ void main()
//SHAKE //SHAKE
if ((effects_hud & (1 << 1)) != 0) if ((effects_hud & (1 << 1)) != 0)
{ {
gl_Position.x += cos(shakeTime_hud - 90) * 0.01; gl_Position.x += cos(dt - 90) * shakeIntensity_hud;
gl_Position.y += cos(shakeTime_hud - 80) * 0.01; gl_Position.y += cos(dt - 80) * shakeIntensity_hud;
} }
} }
} }

View file

@ -4,10 +4,12 @@
#include <SDL_Timer.h> #include <SDL_Timer.h>
#include <glad/glad.h> #include <glad/glad.h>
#include <glm/glm.hpp> #include <glm/glm.hpp>
#include <limits>
#include <memory> #include <memory>
#include <utility/resourcemanager.h> #include <utility/resourcemanager.h>
#include <graphics/shader.h> #include <graphics/shader.h>
#include <utility/logger.h> #include <utility/logger.h>
#include <util.h>
class Postprocessor class Postprocessor
{ {
@ -22,7 +24,8 @@ public:
GREYSCALE = 1 << 4 GREYSCALE = 1 << 4
}; };
void ApplyEffect(EFFECT effect, float intensity=0.f, float effectDuration=0.f, glm::vec3 colorModifer=glm::vec3(0.0f));
void ApplyEffect(EFFECT effect, float intensity=0.f, float effectDuration=UTIL::INF_TIME, glm::vec3 colorModifer=glm::vec3(0.0f));
void RemoveEffects(EFFECT effect); void RemoveEffects(EFFECT effect);
void RemoveAllEffects(); void RemoveAllEffects();
@ -49,17 +52,20 @@ private:
alignas(4) int dt; alignas(4) int dt;
alignas(16) glm::vec3 colorMod; alignas(16) glm::vec3 colorMod;
alignas(4) float blurIntensity; alignas(4) float blurIntensity;
alignas(4) float blurDuration;
alignas(4) float shakeIntensity; alignas(4) float shakeIntensity;
alignas(4) float shakeTime; alignas(4) float shakeDuration;
alignas(4) int curEffects; alignas(4) int curEffects;
// hud // hud
alignas(16) glm::vec3 colorMod_hud; alignas(16) glm::vec3 colorMod_hud;
alignas(4) float blurIntensity_hud; alignas(4) float blurIntensity_hud;
alignas(4) float blurDuration_hud;
alignas(4) float shakeIntensity_hud; alignas(4) float shakeIntensity_hud;
alignas(4) float shakeTime_hud; alignas(4) float shakeDuration_hud;
alignas(4) int curEffects_hud; alignas(4) int curEffects_hud;
}postProcessData; }postProcessData;
void tickEffectTime(bool worldOrHud);
unsigned int lastTime; unsigned int lastTime;
Shader* postProcessShader; Shader* postProcessShader;
}; };

View file

@ -6,6 +6,8 @@
namespace UTIL namespace UTIL
{ {
constexpr float INF_TIME = -99.6875f;
void flip_surface(SDL_Surface* surface); void flip_surface(SDL_Surface* surface);
class RandomGenerator class RandomGenerator

View file

@ -103,6 +103,14 @@ public:
float duration; float duration;
}; };
class ScreenBlurEvent : public Event {
public:
ScreenBlurEvent(float intensity, float duration) : intensity(intensity), duration(duration) {}
std::string getType() const override { return "OnScreenBlur"; }
float intensity;
float duration;
};
class EventManager { class EventManager {
public: public:
using EventCallback = std::function<void(std::shared_ptr<Event>)>; using EventCallback = std::function<void(std::shared_ptr<Event>)>;

View file

@ -100,6 +100,7 @@ void GameActor::fireWeapon()const {
if (sceneContext->getPlayerID() == entityid) { if (sceneContext->getPlayerID() == entityid) {
if (auto gEvent = sceneContext->getGlobalEventManager().lock()) { if (auto gEvent = sceneContext->getGlobalEventManager().lock()) {
gEvent->notify(std::make_shared<ScreenShakeEvent>(0.01f, 0.8f)); gEvent->notify(std::make_shared<ScreenShakeEvent>(0.01f, 0.8f));
gEvent->notify(std::make_shared<ScreenBlurEvent>(1.f, 0.8f));
} }
} }
} }

View file

@ -1,5 +1,6 @@
#include "graphics/postprocess.h" #include "graphics/postprocess.h"
#include <graphics/quad.h> #include <graphics/quad.h>
#include <util.h>
Postprocessor::Postprocessor(const std::shared_ptr<ResourceManager>& resourceManager) Postprocessor::Postprocessor(const std::shared_ptr<ResourceManager>& resourceManager)
{ {
@ -40,9 +41,10 @@ void Postprocessor::ApplyEffect(EFFECT effect, float intensity, float effectDura
postProcessData.curEffects |= effect; postProcessData.curEffects |= effect;
if ((effect & EFFECT::BLUR) != 0) { if ((effect & EFFECT::BLUR) != 0) {
postProcessData.blurIntensity = intensity; postProcessData.blurIntensity = intensity;
postProcessData.blurDuration = effectDuration;
} else if ((effect & EFFECT::SHAKE) != 0) { } else if ((effect & EFFECT::SHAKE) != 0) {
postProcessData.shakeIntensity = intensity; postProcessData.shakeIntensity = intensity;
postProcessData.shakeTime = effectDuration; postProcessData.shakeDuration = effectDuration;
} }
if ((effect & EFFECT::COLORMOD) != 0) { if ((effect & EFFECT::COLORMOD) != 0) {
postProcessData.colorMod = colorModifer; postProcessData.colorMod = colorModifer;
@ -67,18 +69,8 @@ void Postprocessor::applyPostProcess(bool worldOrHud)
postProcessData.curTime = curTime; postProcessData.curTime = curTime;
postProcessData.dt = curTime - lastTime; postProcessData.dt = curTime - lastTime;
auto subtractTime = [](float remaining, unsigned int dt){ tickEffectTime(worldOrHud);
if ((remaining - 1.0f / static_cast<float>(dt)) <= 0.0f) LOG(DEBUG, "Blur duration: {}", postProcessData.blurDuration);
return 0.0f;
return remaining - (1.0f / static_cast<float>(dt));
};
if (!worldOrHud)
postProcessData.shakeTime = subtractTime(postProcessData.shakeTime, postProcessData.dt);
else
postProcessData.shakeTime_hud = subtractTime(postProcessData.shakeTime_hud, postProcessData.dt);
if (postProcessData.shakeTime <= 0.0f) {
RemoveEffects(SHAKE);
}
postProcessShader->use(); postProcessShader->use();
postProcessShader->setBool("worldOrHud", worldOrHud); postProcessShader->setBool("worldOrHud", worldOrHud);
@ -86,17 +78,43 @@ void Postprocessor::applyPostProcess(bool worldOrHud)
glBufferSubData(GL_UNIFORM_BUFFER, 0, sizeof(PostProcessData_t), &postProcessData); glBufferSubData(GL_UNIFORM_BUFFER, 0, sizeof(PostProcessData_t), &postProcessData);
/*
PostProcessData_t* pp_data = (PostProcessData_t*)glMapBuffer(
GL_UNIFORM_BUFFER,
GL_MAP_WRITE_BIT | GL_MAP_INVALIDATE_RANGE_BIT | GL_MAP_UNSYNCHRONIZED_BIT);
if (pp_data) {
std::memcpy(pp_data, &postProcessData, sizeof(PostProcessData_t));
glUnmapBuffer(GL_UNIFORM_BUFFER);
}
*/
glBindBuffer(GL_UNIFORM_BUFFER, 0); glBindBuffer(GL_UNIFORM_BUFFER, 0);
lastTime = curTime; lastTime = curTime;
} }
void Postprocessor::tickEffectTime(bool worldOrHud)
{
auto subtractTime = [](float remaining, float dt){
if (remaining == UTIL::INF_TIME) {
return remaining;
}
else if ((remaining - 1.0f / dt) <= 0.0f)
return 0.0f;
return remaining - (1.0f / dt);
};
auto checkToRemove = [](float timeLeft) {
return timeLeft != UTIL::INF_TIME && timeLeft <= 0.f; // checking if the duration is not INF_TIME and is leq than 0.0f
};
// !!! FIX THIS, IT WORKS BUT NOT A SCALABLE SOLUTION !!!
float dt = static_cast<float>(postProcessData.dt);
if (worldOrHud) {
postProcessData.blurDuration_hud = subtractTime(postProcessData.blurDuration_hud, dt);
postProcessData.shakeDuration_hud = subtractTime(postProcessData.shakeDuration_hud, dt);
if (checkToRemove(postProcessData.blurDuration_hud)) {
//RemoveEffects(BLUR);
}
if (checkToRemove(postProcessData.shakeDuration_hud)) {
//RemoveEffects(SHAKE);
}
} else {
postProcessData.blurDuration = subtractTime(postProcessData.blurDuration, dt);
postProcessData.shakeDuration = subtractTime(postProcessData.shakeDuration, dt);
if (checkToRemove(postProcessData.blurDuration)) {
RemoveEffects(BLUR);
}
if (checkToRemove(postProcessData.shakeDuration)) {
RemoveEffects(SHAKE);
}
}
}

View file

@ -29,6 +29,13 @@ void Renderer::hookEventManager(std::weak_ptr<EventManager> eventManager)
shakeEvent->duration shakeEvent->duration
); );
}); });
e->subscribe("OnScreenBlur", [this](std::shared_ptr<Event> event) {
auto blurEvent = std::dynamic_pointer_cast<ScreenBlurEvent>(event);
postProcessor->ApplyEffect(Postprocessor::BLUR,
blurEvent->intensity,
blurEvent->duration
);
});
} }
} }