- change swrender mapping to use two buffers/textures and glTexSubImage2D for uploads

This commit is contained in:
Magnus Norddahl 2018-06-18 21:15:52 +02:00 committed by Christoph Oelckers
parent 42bb9b7e59
commit 01bda6348e
3 changed files with 27 additions and 19 deletions

View file

@ -192,7 +192,8 @@ unsigned int FHardwareTexture::CreateTexture(unsigned char * buffer, int w, int
}
*/
TranslatedTexture * glTex=GetTexID(translation);
if (glTex->glTexID==0) glGenTextures(1,&glTex->glTexID);
bool firstCall = glTex->glTexID == 0;
if (firstCall) glGenTextures(1,&glTex->glTexID);
if (texunit != 0) glActiveTexture(GL_TEXTURE0+texunit);
glBindTexture(GL_TEXTURE_2D, glTex->glTexID);
FGLDebug::LabelObject(GL_TEXTURE, glTex->glTexID, name);
@ -256,6 +257,9 @@ unsigned int FHardwareTexture::CreateTexture(unsigned char * buffer, int w, int
sourcetype = GL_BGRA;
}
if (!firstCall && glBufferID > 0)
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, rw, rh, sourcetype, GL_UNSIGNED_BYTE, buffer);
else
glTexImage2D(GL_TEXTURE_2D, 0, texformat, rw, rh, 0, sourcetype, GL_UNSIGNED_BYTE, buffer);
if (deletebuffer && buffer) free(buffer);

View file

@ -86,38 +86,40 @@ public:
SWSceneDrawer::SWSceneDrawer()
{
PaletteTexture = new FSWPaletteTexture;
PaletteTexture.reset(new FSWPaletteTexture);
}
SWSceneDrawer::~SWSceneDrawer()
{
if (PaletteTexture != nullptr) delete PaletteTexture;
if (FBTexture != nullptr) delete FBTexture;
}
sector_t *SWSceneDrawer::RenderView(player_t *player)
{
// Avoid using the pixel buffer from the last frame
FBTextureIndex = (FBTextureIndex + 1) % 2;
auto &fbtex = FBTexture[FBTextureIndex];
DCanvas buffer(screen->GetWidth(), screen->GetHeight(), V_IsTrueColor());
if (FBTexture == nullptr || FBTexture->SystemTexture[0] == nullptr ||
FBTexture->GetWidth() != screen->GetWidth() ||
FBTexture->GetHeight() != screen->GetHeight() ||
(V_IsTrueColor() ? 1:0) != FBTexture->WidthBits)
if (fbtex == nullptr || fbtex->SystemTexture[0] == nullptr ||
fbtex->GetWidth() != screen->GetWidth() ||
fbtex->GetHeight() != screen->GetHeight() ||
(V_IsTrueColor() ? 1:0) != fbtex->WidthBits)
{
// This manually constructs its own material here.
if (FBTexture != nullptr) delete FBTexture;
FBTexture = new FSWSceneTexture(screen->GetWidth(), screen->GetHeight(), V_IsTrueColor());
FBTexture->SystemTexture[0]->AllocateBuffer(screen->GetWidth(), screen->GetHeight(), V_IsTrueColor() ? 4 : 1);
auto mat = FMaterial::ValidateTexture(FBTexture, false);
mat->AddTextureLayer(PaletteTexture);
fbtex.reset();
fbtex.reset(new FSWSceneTexture(screen->GetWidth(), screen->GetHeight(), V_IsTrueColor()));
fbtex->SystemTexture[0]->AllocateBuffer(screen->GetWidth(), screen->GetHeight(), V_IsTrueColor() ? 4 : 1);
auto mat = FMaterial::ValidateTexture(fbtex.get(), false);
mat->AddTextureLayer(PaletteTexture.get());
}
auto buf = FBTexture->SystemTexture[0]->MapBuffer();
auto buf = fbtex->SystemTexture[0]->MapBuffer();
if (!buf) I_FatalError("Unable to map buffer for software rendering");
buffer.SetBuffer(screen->GetWidth(), screen->GetHeight(), screen->GetWidth(), buf);
SWRenderer->RenderView(player, &buffer);
FBTexture->SystemTexture[0]->CreateTexture(nullptr, screen->GetWidth(), screen->GetHeight(), 0, false, 0, "swbuffer");
fbtex->SystemTexture[0]->CreateTexture(nullptr, screen->GetWidth(), screen->GetHeight(), 0, false, 0, "swbuffer");
auto map = swrenderer::CameraLight::Instance()->ShaderColormap();
screen->DrawTexture(FBTexture, 0, 0, DTA_SpecialColormap, map, TAG_DONE);
screen->DrawTexture(fbtex.get(), 0, 0, DTA_SpecialColormap, map, TAG_DONE);
SWRenderer->DrawRemainingPlayerSprites();
return r_viewpoint.sector;
}

View file

@ -6,13 +6,15 @@
#include "hwrenderer/scene/hw_clipper.h"
#include "r_utility.h"
#include "c_cvars.h"
#include <memory>
class FSWSceneTexture;
class SWSceneDrawer
{
FTexture *PaletteTexture = nullptr;
FSWSceneTexture *FBTexture = nullptr;
std::unique_ptr<FTexture> PaletteTexture;
std::unique_ptr<FSWSceneTexture> FBTexture[2];
int FBTextureIndex = 0;
bool FBIsTruecolor = false;
public: