From 52869ac0e949b1b4be27dd0b0801b2184d24acb4 Mon Sep 17 00:00:00 2001 From: Justin Marshall Date: Sat, 11 Jul 2020 22:24:19 -0700 Subject: [PATCH] Initial light rendering code, doesn't render correct in all situations yet. --- code/redalert/light.cpp | 33 ++++++++++++++++++++++++++++++--- code/redalert/light.h | 4 ++++ code/redalert/mapedit.cpp | 2 +- code/redalert/newblit.cpp | 36 +++++++++++++++++++++++++++++++++--- code/redalert/newblit.h | 11 ++++++++++- 5 files changed, 78 insertions(+), 8 deletions(-) diff --git a/code/redalert/light.cpp b/code/redalert/light.cpp index 42fd4ea..a9a9ae8 100644 --- a/code/redalert/light.cpp +++ b/code/redalert/light.cpp @@ -30,9 +30,29 @@ LightManager::LightManager() { void LightManager::Init(void) { lightEditorIcon = Image_LoadImage("ui/edwin/lightbulb.png"); pointLightAttenImage0 = Image_LoadImage("ui/lights/light_point_atten.png"); + + hdrLightBufferTexture = Image_CreateBlankImage("hdrRenderTexture", ScreenWidth, ScreenHeight); + hdrRenderTexture = new RenderTexture(hdrLightBufferTexture, NULL); + hdrRenderTexture->InitRenderTexture(); } void LightManager::RenderLights(void) { + if(Debug_Map) { + for (int i = 0; i < MAX_WORLD_LIGHTS; i++) { + if (!lights[i].active) { + continue; + } + + if (!lights[i].isPending) { + int screenx, screeny; + lights[i].GetRenderPosition(screenx, screeny); + GL_RenderImage(lightEditorIcon, screenx, screeny, 30, 30); + } + } + } + + GL_SetRenderTexture(hdrRenderTexture); + for (int i = 0; i < MAX_WORLD_LIGHTS; i++) { if (!lights[i].active) { continue; @@ -41,9 +61,16 @@ void LightManager::RenderLights(void) { if (!lights[i].isPending) { int screenx, screeny; lights[i].GetRenderPosition(screenx, screeny); - GL_RenderImage(lightEditorIcon, screenx, screeny, 30, 30); + int halfRadius = lights[i].radius / 2; + GL_RenderImage(pointLightAttenImage0, screenx - halfRadius, ScreenHeight - (screeny + halfRadius), lights[i].radius, lights[i].radius); } } + + GL_SetRenderTexture(NULL); + + GL_EnableBlend(GL_BLEND_MULT); + GL_RenderImage(hdrLightBufferTexture, 0, 0, ScreenWidth, ScreenHeight); + GL_EnableBlend(GL_BLEND_NONE); } void LightManager::FreeAllLights(void) { @@ -76,12 +103,12 @@ Light_t *LightManager::PlaceLight(char *name, int x, int y, float r, float g, fl else { strcpy(light->name, name); } + light->position = XYP_Coord(x, y); light->color.x = r; light->color.y = g; light->color.z = b; light->radius = radius; - light->type = type; - light->PlaceLight(x, y); + light->type = type; return light; } diff --git a/code/redalert/light.h b/code/redalert/light.h index e8361b3..93030ce 100644 --- a/code/redalert/light.h +++ b/code/redalert/light.h @@ -5,6 +5,7 @@ #include "vectormath.h" class CCINIClass; +class RenderTexture; struct Image_t; #define MAX_WORLD_LIGHTS 6556 @@ -55,6 +56,9 @@ private: int numLights; Image_t* lightEditorIcon; Image_t* pointLightAttenImage0; + + Image_t* hdrLightBufferTexture; + RenderTexture* hdrRenderTexture; }; extern LightManager lightManager; \ No newline at end of file diff --git a/code/redalert/mapedit.cpp b/code/redalert/mapedit.cpp index 048b488..539337f 100644 --- a/code/redalert/mapedit.cpp +++ b/code/redalert/mapedit.cpp @@ -1682,7 +1682,7 @@ void MapEditClass::Main_Menu(void) break; case 8: - GrabbedLight = lightManager.PlaceLight(NULL, 0, 0, 1.0f, 1.0f, 1.0f, 100, LIGHT_POINT); + GrabbedLight = lightManager.PlaceLight(NULL, 0, 0, 1.0f, 1.0f, 1.0f, 75, LIGHT_POINT); GrabbedLight->isPending = true; break; diff --git a/code/redalert/newblit.cpp b/code/redalert/newblit.cpp index c48170f..8dd2628 100644 --- a/code/redalert/newblit.cpp +++ b/code/redalert/newblit.cpp @@ -4,6 +4,7 @@ #include #include "FUNCTION.H" #include "Image.h" +#include "gl/glew.h" extern byte backbuffer_palette[768]; extern uint8_t g_ColorXlat[16]; @@ -11,9 +12,38 @@ extern uint8_t g_ColorXlat[16]; bool forceForgegroundRender = false; int32_t g_currentColor; -//void GL_SetRenderTarget(void *renderTarget) { -// //ImGui::GetBackgroundDrawList()->AddCallback() -//} +static void GL_SetRenderTextureCallback(const ImDrawList* parent_list, const ImDrawCmd* cmd) { + RenderTexture* renderTexture = (RenderTexture*)cmd->UserCallbackData; + if(renderTexture == NULL) { + RenderTexture::BindNull(); + } + else { + renderTexture->MakeCurrent(); + glClearColor(0.5, 0.5, 0.5, 1.0); + glClear(GL_COLOR_BUFFER_BIT); + } +} + +static void GL_EnableBlendCallback(const ImDrawList* parent_list, const ImDrawCmd* cmd) { + GLBlendType blendType = (GLBlendType)(int64_t)cmd->UserCallbackData; + glEnable(GL_BLEND); + if(blendType == GL_BLEND_NONE) { + glBlendEquation(GL_FUNC_ADD); + glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); + } + else { + glBlendEquation(GL_ADD); + glBlendFunc(GL_DST_COLOR, GL_SRC_COLOR); + } +} + +void GL_EnableBlend(GLBlendType blendType) { + ImGui::GetBackgroundDrawList()->AddCallback(GL_EnableBlendCallback, (void *)blendType); +} + +void GL_SetRenderTexture(RenderTexture *renderTexture) { + ImGui::GetBackgroundDrawList()->AddCallback(GL_SetRenderTextureCallback, renderTexture); +} void GL_ForceForegroundRender(bool force) { forceForgegroundRender = force; diff --git a/code/redalert/newblit.h b/code/redalert/newblit.h index d53899a..c7b4723 100644 --- a/code/redalert/newblit.h +++ b/code/redalert/newblit.h @@ -2,6 +2,13 @@ // struct Image_t; +class RenderTexture; + +enum GLBlendType { + GL_BLEND_NONE = 0, + GL_BLEND_MULT +}; + void GL_RenderImage(Image_t* image, int x, int y, int width, int height, int colorRemap = 0, int shapeId = 0); void GL_RenderForeGroundImage(Image_t* image, int x, int y, int width, int height, int colorRemap = 0, int shapeId = 0); void GL_DrawText(int color, int x, int y, char* text); @@ -12,4 +19,6 @@ void GL_ResetClipRect(void); void GL_SetClipRect(int x, int y, int width, int height); void GL_ForceForegroundRender(bool force); void GL_DrawForegroundText(int color, int x, int y, char* text); -void GL_SetColor(float r, float g, float b); \ No newline at end of file +void GL_SetColor(float r, float g, float b); +void GL_SetRenderTexture(RenderTexture* renderTexture); +void GL_EnableBlend(GLBlendType blendType); \ No newline at end of file