mirror of
https://github.com/ZDoom/gzdoom.git
synced 2024-11-23 04:22:34 +00:00
- moved viewport code to DFrameBuffer.
This commit is contained in:
parent
f17f8c9359
commit
c2a7a4bf30
16 changed files with 244 additions and 207 deletions
|
@ -60,7 +60,7 @@ void FShadowMap::Update()
|
||||||
glViewport(0, 0, gl_shadowmap_quality, 1024);
|
glViewport(0, 0, gl_shadowmap_quality, 1024);
|
||||||
GLRenderer->RenderScreenQuad();
|
GLRenderer->RenderScreenQuad();
|
||||||
|
|
||||||
const auto &viewport = GLRenderer->mScreenViewport;
|
const auto &viewport = screen->mScreenViewport;
|
||||||
glViewport(viewport.left, viewport.top, viewport.width, viewport.height);
|
glViewport(viewport.left, viewport.top, viewport.width, viewport.height);
|
||||||
|
|
||||||
glBindBufferBase(GL_SHADER_STORAGE_BUFFER, 4, 0);
|
glBindBufferBase(GL_SHADER_STORAGE_BUFFER, 4, 0);
|
||||||
|
|
|
@ -187,6 +187,9 @@ void FGLRenderer::AmbientOccludeScene()
|
||||||
|
|
||||||
float blurSharpness = 1.0f / blurAmount;
|
float blurSharpness = 1.0f / blurAmount;
|
||||||
|
|
||||||
|
const auto &mSceneViewport = screen->mSceneViewport;
|
||||||
|
const auto &mScreenViewport = screen->mScreenViewport;
|
||||||
|
|
||||||
float sceneScaleX = mSceneViewport.width / (float)mScreenViewport.width;
|
float sceneScaleX = mSceneViewport.width / (float)mScreenViewport.width;
|
||||||
float sceneScaleY = mSceneViewport.height / (float)mScreenViewport.height;
|
float sceneScaleY = mSceneViewport.height / (float)mScreenViewport.height;
|
||||||
float sceneOffsetX = mSceneViewport.left / (float)mScreenViewport.width;
|
float sceneOffsetX = mSceneViewport.left / (float)mScreenViewport.width;
|
||||||
|
@ -254,7 +257,7 @@ void FGLRenderer::AmbientOccludeScene()
|
||||||
|
|
||||||
// Add SSAO back to scene texture:
|
// Add SSAO back to scene texture:
|
||||||
mBuffers->BindSceneFB(false);
|
mBuffers->BindSceneFB(false);
|
||||||
glViewport(mSceneViewport.left, mSceneViewport.top, mSceneViewport.width, mSceneViewport.height);
|
glViewport(screen->mSceneViewport.left, screen->mSceneViewport.top, screen->mSceneViewport.width, screen->mSceneViewport.height);
|
||||||
glEnable(GL_BLEND);
|
glEnable(GL_BLEND);
|
||||||
glBlendEquation(GL_FUNC_ADD);
|
glBlendEquation(GL_FUNC_ADD);
|
||||||
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
|
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
|
||||||
|
@ -292,6 +295,9 @@ void FGLRenderer::UpdateCameraExposure()
|
||||||
FGLPostProcessState savedState;
|
FGLPostProcessState savedState;
|
||||||
savedState.SaveTextureBindings(2);
|
savedState.SaveTextureBindings(2);
|
||||||
|
|
||||||
|
const auto &mSceneViewport = screen->mSceneViewport;
|
||||||
|
const auto &mScreenViewport = screen->mScreenViewport;
|
||||||
|
|
||||||
// Extract light level from scene texture:
|
// Extract light level from scene texture:
|
||||||
auto &level0 = mBuffers->ExposureLevels[0];
|
auto &level0 = mBuffers->ExposureLevels[0];
|
||||||
level0.Framebuffer.Bind();
|
level0.Framebuffer.Bind();
|
||||||
|
@ -365,6 +371,9 @@ void FGLRenderer::BloomScene(int fixedcm)
|
||||||
|
|
||||||
auto &level0 = mBuffers->BloomLevels[0];
|
auto &level0 = mBuffers->BloomLevels[0];
|
||||||
|
|
||||||
|
const auto &mSceneViewport = screen->mSceneViewport;
|
||||||
|
const auto &mScreenViewport = screen->mScreenViewport;
|
||||||
|
|
||||||
// Extract blooming pixels from scene texture:
|
// Extract blooming pixels from scene texture:
|
||||||
level0.VFramebuffer.Bind();
|
level0.VFramebuffer.Bind();
|
||||||
glViewport(0, 0, level0.Width, level0.Height);
|
glViewport(0, 0, level0.Width, level0.Height);
|
||||||
|
@ -450,7 +459,7 @@ void FGLRenderer::BlurScene(float gameinfobluramount)
|
||||||
int numLevels = 3; // Must be 4 or less (since FGLRenderBuffers::NumBloomLevels is 4 and we are using its buffers).
|
int numLevels = 3; // Must be 4 or less (since FGLRenderBuffers::NumBloomLevels is 4 and we are using its buffers).
|
||||||
assert(numLevels <= FGLRenderBuffers::NumBloomLevels);
|
assert(numLevels <= FGLRenderBuffers::NumBloomLevels);
|
||||||
|
|
||||||
const auto &viewport = mScreenViewport; // The area we want to blur. Could also be mSceneViewport if only the scene area is to be blured
|
const auto &viewport = screen->mScreenViewport; // The area we want to blur. Could also be mSceneViewport if only the scene area is to be blured
|
||||||
|
|
||||||
const auto &level0 = mBuffers->BloomLevels[0];
|
const auto &level0 = mBuffers->BloomLevels[0];
|
||||||
|
|
||||||
|
@ -490,7 +499,7 @@ void FGLRenderer::BlurScene(float gameinfobluramount)
|
||||||
// Copy blur back to scene texture:
|
// Copy blur back to scene texture:
|
||||||
mBuffers->BlitLinear(level0.VFramebuffer, mBuffers->GetCurrentFB(), 0, 0, level0.Width, level0.Height, viewport.left, viewport.top, viewport.width, viewport.height);
|
mBuffers->BlitLinear(level0.VFramebuffer, mBuffers->GetCurrentFB(), 0, 0, level0.Width, level0.Height, viewport.left, viewport.top, viewport.width, viewport.height);
|
||||||
|
|
||||||
glViewport(mScreenViewport.left, mScreenViewport.top, mScreenViewport.width, mScreenViewport.height);
|
glViewport(viewport.left, viewport.top, viewport.width, viewport.height);
|
||||||
|
|
||||||
FGLDebug::PopGroup();
|
FGLDebug::PopGroup();
|
||||||
}
|
}
|
||||||
|
@ -639,7 +648,7 @@ void FGLRenderer::LensDistortScene()
|
||||||
0.0f
|
0.0f
|
||||||
};
|
};
|
||||||
|
|
||||||
float aspect = mSceneViewport.width / (float)mSceneViewport.height;
|
float aspect = screen->mSceneViewport.width / (float)screen->mSceneViewport.height;
|
||||||
|
|
||||||
// Scale factor to keep sampling within the input texture
|
// Scale factor to keep sampling within the input texture
|
||||||
float r2 = aspect * aspect * 0.25 + 0.25f;
|
float r2 = aspect * aspect * 0.25 + 0.25f;
|
||||||
|
@ -715,6 +724,8 @@ void FGLRenderer::ApplyFXAA()
|
||||||
void FGLRenderer::Flush()
|
void FGLRenderer::Flush()
|
||||||
{
|
{
|
||||||
const s3d::Stereo3DMode& stereo3dMode = s3d::Stereo3DMode::getCurrentMode();
|
const s3d::Stereo3DMode& stereo3dMode = s3d::Stereo3DMode::getCurrentMode();
|
||||||
|
const auto &mSceneViewport = screen->mSceneViewport;
|
||||||
|
const auto &mScreenViewport = screen->mScreenViewport;
|
||||||
|
|
||||||
if (stereo3dMode.IsMono() || !FGLRenderBuffers::IsEnabled())
|
if (stereo3dMode.IsMono() || !FGLRenderBuffers::IsEnabled())
|
||||||
{
|
{
|
||||||
|
@ -747,7 +758,7 @@ void FGLRenderer::Flush()
|
||||||
//
|
//
|
||||||
//-----------------------------------------------------------------------------
|
//-----------------------------------------------------------------------------
|
||||||
|
|
||||||
void FGLRenderer::CopyToBackbuffer(const GL_IRECT *bounds, bool applyGamma)
|
void FGLRenderer::CopyToBackbuffer(const IntRect *bounds, bool applyGamma)
|
||||||
{
|
{
|
||||||
screen->Draw2D(); // draw all pending 2D stuff before copying the buffer
|
screen->Draw2D(); // draw all pending 2D stuff before copying the buffer
|
||||||
screen->Clear2D();
|
screen->Clear2D();
|
||||||
|
@ -760,7 +771,7 @@ void FGLRenderer::CopyToBackbuffer(const GL_IRECT *bounds, bool applyGamma)
|
||||||
FGLPostProcessState savedState;
|
FGLPostProcessState savedState;
|
||||||
mBuffers->BindOutputFB();
|
mBuffers->BindOutputFB();
|
||||||
|
|
||||||
GL_IRECT box;
|
IntRect box;
|
||||||
if (bounds)
|
if (bounds)
|
||||||
{
|
{
|
||||||
box = *bounds;
|
box = *bounds;
|
||||||
|
@ -768,7 +779,7 @@ void FGLRenderer::CopyToBackbuffer(const GL_IRECT *bounds, bool applyGamma)
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
ClearBorders();
|
ClearBorders();
|
||||||
box = mOutputLetterbox;
|
box = screen->mOutputLetterbox;
|
||||||
}
|
}
|
||||||
|
|
||||||
mBuffers->BindCurrentTexture(0);
|
mBuffers->BindCurrentTexture(0);
|
||||||
|
@ -782,7 +793,7 @@ void FGLRenderer::CopyToBackbuffer(const GL_IRECT *bounds, bool applyGamma)
|
||||||
FGLDebug::PopGroup();
|
FGLDebug::PopGroup();
|
||||||
}
|
}
|
||||||
|
|
||||||
void FGLRenderer::DrawPresentTexture(const GL_IRECT &box, bool applyGamma)
|
void FGLRenderer::DrawPresentTexture(const IntRect &box, bool applyGamma)
|
||||||
{
|
{
|
||||||
glViewport(box.left, box.top, box.width, box.height);
|
glViewport(box.left, box.top, box.width, box.height);
|
||||||
|
|
||||||
|
@ -815,7 +826,7 @@ void FGLRenderer::DrawPresentTexture(const GL_IRECT &box, bool applyGamma)
|
||||||
mPresentShader->Saturation.Set(clamp<float>(vid_saturation, -15.0f, 15.f));
|
mPresentShader->Saturation.Set(clamp<float>(vid_saturation, -15.0f, 15.f));
|
||||||
mPresentShader->GrayFormula.Set(static_cast<int>(gl_satformula));
|
mPresentShader->GrayFormula.Set(static_cast<int>(gl_satformula));
|
||||||
}
|
}
|
||||||
mPresentShader->Scale.Set(mScreenViewport.width / (float)mBuffers->GetWidth(), mScreenViewport.height / (float)mBuffers->GetHeight());
|
mPresentShader->Scale.Set(screen->mScreenViewport.width / (float)mBuffers->GetWidth(), screen->mScreenViewport.height / (float)mBuffers->GetHeight());
|
||||||
RenderScreenQuad();
|
RenderScreenQuad();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -827,7 +838,7 @@ void FGLRenderer::DrawPresentTexture(const GL_IRECT &box, bool applyGamma)
|
||||||
|
|
||||||
void FGLRenderer::ClearBorders()
|
void FGLRenderer::ClearBorders()
|
||||||
{
|
{
|
||||||
const auto &box = mOutputLetterbox;
|
const auto &box = screen->mOutputLetterbox;
|
||||||
|
|
||||||
int clientWidth = framebuffer->GetClientWidth();
|
int clientWidth = framebuffer->GetClientWidth();
|
||||||
int clientHeight = framebuffer->GetClientHeight();
|
int clientHeight = framebuffer->GetClientHeight();
|
||||||
|
|
|
@ -67,7 +67,6 @@
|
||||||
EXTERN_CVAR(Int, screenblocks)
|
EXTERN_CVAR(Int, screenblocks)
|
||||||
EXTERN_CVAR(Bool, cl_capfps)
|
EXTERN_CVAR(Bool, cl_capfps)
|
||||||
|
|
||||||
CVAR(Bool, gl_scale_viewport, true, CVAR_ARCHIVE);
|
|
||||||
extern bool NoInterpolateView;
|
extern bool NoInterpolateView;
|
||||||
|
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
|
@ -225,117 +224,6 @@ FGLRenderer::~FGLRenderer()
|
||||||
delete mFXAALumaShader;
|
delete mFXAALumaShader;
|
||||||
}
|
}
|
||||||
|
|
||||||
//==========================================================================
|
|
||||||
//
|
|
||||||
// Calculates the viewport values needed for 2D and 3D operations
|
|
||||||
//
|
|
||||||
//==========================================================================
|
|
||||||
|
|
||||||
void FGLRenderer::SetOutputViewport(GL_IRECT *bounds)
|
|
||||||
{
|
|
||||||
if (bounds)
|
|
||||||
{
|
|
||||||
mSceneViewport = *bounds;
|
|
||||||
mScreenViewport = *bounds;
|
|
||||||
mOutputLetterbox = *bounds;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Special handling so the view with a visible status bar displays properly
|
|
||||||
int height, width;
|
|
||||||
if (screenblocks >= 10)
|
|
||||||
{
|
|
||||||
height = framebuffer->GetHeight();
|
|
||||||
width = framebuffer->GetWidth();
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
height = (screenblocks*framebuffer->GetHeight() / 10) & ~7;
|
|
||||||
width = (screenblocks*framebuffer->GetWidth() / 10);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Back buffer letterbox for the final output
|
|
||||||
int clientWidth = framebuffer->GetClientWidth();
|
|
||||||
int clientHeight = framebuffer->GetClientHeight();
|
|
||||||
if (clientWidth == 0 || clientHeight == 0)
|
|
||||||
{
|
|
||||||
// When window is minimized there may not be any client area.
|
|
||||||
// Pretend to the rest of the render code that we just have a very small window.
|
|
||||||
clientWidth = 160;
|
|
||||||
clientHeight = 120;
|
|
||||||
}
|
|
||||||
int screenWidth = framebuffer->GetWidth();
|
|
||||||
int screenHeight = framebuffer->GetHeight();
|
|
||||||
float scaleX, scaleY;
|
|
||||||
if (ViewportIsScaled43())
|
|
||||||
{
|
|
||||||
scaleX = MIN(clientWidth / (float)screenWidth, clientHeight / (screenHeight * 1.2f));
|
|
||||||
scaleY = scaleX * 1.2f;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
scaleX = MIN(clientWidth / (float)screenWidth, clientHeight / (float)screenHeight);
|
|
||||||
scaleY = scaleX;
|
|
||||||
}
|
|
||||||
mOutputLetterbox.width = (int)round(screenWidth * scaleX);
|
|
||||||
mOutputLetterbox.height = (int)round(screenHeight * scaleY);
|
|
||||||
mOutputLetterbox.left = (clientWidth - mOutputLetterbox.width) / 2;
|
|
||||||
mOutputLetterbox.top = (clientHeight - mOutputLetterbox.height) / 2;
|
|
||||||
|
|
||||||
// The entire renderable area, including the 2D HUD
|
|
||||||
mScreenViewport.left = 0;
|
|
||||||
mScreenViewport.top = 0;
|
|
||||||
mScreenViewport.width = screenWidth;
|
|
||||||
mScreenViewport.height = screenHeight;
|
|
||||||
|
|
||||||
// Viewport for the 3D scene
|
|
||||||
mSceneViewport.left = viewwindowx;
|
|
||||||
mSceneViewport.top = screenHeight - (height + viewwindowy - ((height - viewheight) / 2));
|
|
||||||
mSceneViewport.width = viewwidth;
|
|
||||||
mSceneViewport.height = height;
|
|
||||||
|
|
||||||
// Scale viewports to fit letterbox
|
|
||||||
bool notScaled = ((mScreenViewport.width == ViewportScaledWidth(mScreenViewport.width, mScreenViewport.height)) &&
|
|
||||||
(mScreenViewport.width == ViewportScaledHeight(mScreenViewport.width, mScreenViewport.height)) &&
|
|
||||||
!ViewportIsScaled43());
|
|
||||||
if ((gl_scale_viewport && !framebuffer->IsFullscreen() && notScaled) || !FGLRenderBuffers::IsEnabled())
|
|
||||||
{
|
|
||||||
mScreenViewport.width = mOutputLetterbox.width;
|
|
||||||
mScreenViewport.height = mOutputLetterbox.height;
|
|
||||||
mSceneViewport.left = (int)round(mSceneViewport.left * scaleX);
|
|
||||||
mSceneViewport.top = (int)round(mSceneViewport.top * scaleY);
|
|
||||||
mSceneViewport.width = (int)round(mSceneViewport.width * scaleX);
|
|
||||||
mSceneViewport.height = (int)round(mSceneViewport.height * scaleY);
|
|
||||||
|
|
||||||
// Without render buffers we have to render directly to the letterbox
|
|
||||||
if (!FGLRenderBuffers::IsEnabled())
|
|
||||||
{
|
|
||||||
mScreenViewport.left += mOutputLetterbox.left;
|
|
||||||
mScreenViewport.top += mOutputLetterbox.top;
|
|
||||||
mSceneViewport.left += mOutputLetterbox.left;
|
|
||||||
mSceneViewport.top += mOutputLetterbox.top;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
s3d::Stereo3DMode::getCurrentMode().AdjustViewports();
|
|
||||||
}
|
|
||||||
|
|
||||||
//===========================================================================
|
|
||||||
//
|
|
||||||
// Calculates the OpenGL window coordinates for a zdoom screen position
|
|
||||||
//
|
|
||||||
//===========================================================================
|
|
||||||
|
|
||||||
int FGLRenderer::ScreenToWindowX(int x)
|
|
||||||
{
|
|
||||||
return mScreenViewport.left + (int)round(x * mScreenViewport.width / (float)framebuffer->GetWidth());
|
|
||||||
}
|
|
||||||
|
|
||||||
int FGLRenderer::ScreenToWindowY(int y)
|
|
||||||
{
|
|
||||||
return mScreenViewport.top + mScreenViewport.height - (int)round(y * mScreenViewport.height / (float)framebuffer->GetHeight());
|
|
||||||
}
|
|
||||||
|
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
//
|
//
|
||||||
//
|
//
|
||||||
|
@ -482,7 +370,7 @@ void FGLRenderer::RenderTextureView(FCanvasTexture *tex, AActor *Viewpoint, doub
|
||||||
gltex->BindToFrameBuffer();
|
gltex->BindToFrameBuffer();
|
||||||
}
|
}
|
||||||
|
|
||||||
GL_IRECT bounds;
|
IntRect bounds;
|
||||||
bounds.left = bounds.top = 0;
|
bounds.left = bounds.top = 0;
|
||||||
bounds.width = FHardwareTexture::GetTexDimension(gltex->GetWidth());
|
bounds.width = FHardwareTexture::GetTexDimension(gltex->GetWidth());
|
||||||
bounds.height = FHardwareTexture::GetTexDimension(gltex->GetHeight());
|
bounds.height = FHardwareTexture::GetTexDimension(gltex->GetHeight());
|
||||||
|
@ -516,7 +404,7 @@ void FGLRenderer::WriteSavePic(player_t *player, FileWriter *file, int width, in
|
||||||
|
|
||||||
void FGLRenderer::BeginFrame()
|
void FGLRenderer::BeginFrame()
|
||||||
{
|
{
|
||||||
buffersActive = GLRenderer->mBuffers->Setup(GLRenderer->mScreenViewport.width, GLRenderer->mScreenViewport.height, GLRenderer->mSceneViewport.width, GLRenderer->mSceneViewport.height);
|
buffersActive = GLRenderer->mBuffers->Setup(screen->mScreenViewport.width, screen->mScreenViewport.height, screen->mSceneViewport.width, screen->mSceneViewport.height);
|
||||||
}
|
}
|
||||||
|
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
|
@ -579,6 +467,7 @@ void FGLRenderer::Draw2D(F2DDrawer *drawer)
|
||||||
{
|
{
|
||||||
mBuffers->BindCurrentFB();
|
mBuffers->BindCurrentFB();
|
||||||
}
|
}
|
||||||
|
const auto &mScreenViewport = screen->mScreenViewport;
|
||||||
glViewport(mScreenViewport.left, mScreenViewport.top, mScreenViewport.width, mScreenViewport.height);
|
glViewport(mScreenViewport.left, mScreenViewport.top, mScreenViewport.width, mScreenViewport.height);
|
||||||
|
|
||||||
gl_RenderState.mViewMatrix.loadIdentity();
|
gl_RenderState.mViewMatrix.loadIdentity();
|
||||||
|
@ -641,10 +530,10 @@ void FGLRenderer::Draw2D(F2DDrawer *drawer)
|
||||||
glEnable(GL_SCISSOR_TEST);
|
glEnable(GL_SCISSOR_TEST);
|
||||||
// scissor test doesn't use the current viewport for the coordinates, so use real screen coordinates
|
// scissor test doesn't use the current viewport for the coordinates, so use real screen coordinates
|
||||||
// Note that the origin here is the lower left corner!
|
// Note that the origin here is the lower left corner!
|
||||||
auto sciX = ScreenToWindowX(cmd.mScissor[0]);
|
auto sciX = screen->ScreenToWindowX(cmd.mScissor[0]);
|
||||||
auto sciY = ScreenToWindowY(cmd.mScissor[3]);
|
auto sciY = screen->ScreenToWindowY(cmd.mScissor[3]);
|
||||||
auto sciW = ScreenToWindowX(cmd.mScissor[2]) - sciX;
|
auto sciW = screen->ScreenToWindowX(cmd.mScissor[2]) - sciX;
|
||||||
auto sciH = ScreenToWindowY(cmd.mScissor[1]) - sciY;
|
auto sciH = screen->ScreenToWindowY(cmd.mScissor[1]) - sciY;
|
||||||
glScissor(sciX, sciY, sciW, sciH);
|
glScissor(sciX, sciY, sciW, sciH);
|
||||||
}
|
}
|
||||||
else glDisable(GL_SCISSOR_TEST);
|
else glDisable(GL_SCISSOR_TEST);
|
||||||
|
|
|
@ -51,19 +51,6 @@ class FCustomPostProcessShaders;
|
||||||
class GLSceneDrawer;
|
class GLSceneDrawer;
|
||||||
class SWSceneDrawer;
|
class SWSceneDrawer;
|
||||||
|
|
||||||
struct GL_IRECT
|
|
||||||
{
|
|
||||||
int left,top;
|
|
||||||
int width,height;
|
|
||||||
|
|
||||||
|
|
||||||
void Offset(int xofs,int yofs)
|
|
||||||
{
|
|
||||||
left+=xofs;
|
|
||||||
top+=yofs;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
enum
|
enum
|
||||||
{
|
{
|
||||||
DM_MAINVIEW,
|
DM_MAINVIEW,
|
||||||
|
@ -147,9 +134,6 @@ public:
|
||||||
SWSceneDrawer *swdrawer = nullptr;
|
SWSceneDrawer *swdrawer = nullptr;
|
||||||
LegacyShaderContainer *legacyShaders = nullptr;
|
LegacyShaderContainer *legacyShaders = nullptr;
|
||||||
|
|
||||||
GL_IRECT mScreenViewport;
|
|
||||||
GL_IRECT mSceneViewport;
|
|
||||||
GL_IRECT mOutputLetterbox;
|
|
||||||
bool mDrawingScene2D = false;
|
bool mDrawingScene2D = false;
|
||||||
bool buffersActive = false;
|
bool buffersActive = false;
|
||||||
|
|
||||||
|
@ -160,10 +144,6 @@ public:
|
||||||
FGLRenderer(OpenGLFrameBuffer *fb);
|
FGLRenderer(OpenGLFrameBuffer *fb);
|
||||||
~FGLRenderer() ;
|
~FGLRenderer() ;
|
||||||
|
|
||||||
void SetOutputViewport(GL_IRECT *bounds);
|
|
||||||
int ScreenToWindowX(int x);
|
|
||||||
int ScreenToWindowY(int y);
|
|
||||||
|
|
||||||
void Initialize(int width, int height);
|
void Initialize(int width, int height);
|
||||||
|
|
||||||
void ClearBorders();
|
void ClearBorders();
|
||||||
|
@ -184,8 +164,8 @@ public:
|
||||||
void LensDistortScene();
|
void LensDistortScene();
|
||||||
void ApplyFXAA();
|
void ApplyFXAA();
|
||||||
void BlurScene(float gameinfobluramount);
|
void BlurScene(float gameinfobluramount);
|
||||||
void CopyToBackbuffer(const GL_IRECT *bounds, bool applyGamma);
|
void CopyToBackbuffer(const IntRect *bounds, bool applyGamma);
|
||||||
void DrawPresentTexture(const GL_IRECT &box, bool applyGamma);
|
void DrawPresentTexture(const IntRect &box, bool applyGamma);
|
||||||
void Flush();
|
void Flush();
|
||||||
void Draw2D(F2DDrawer *data);
|
void Draw2D(F2DDrawer *data);
|
||||||
void RenderTextureView(FCanvasTexture *tex, AActor *Viewpoint, double FOV);
|
void RenderTextureView(FCanvasTexture *tex, AActor *Viewpoint, double FOV);
|
||||||
|
|
|
@ -123,7 +123,7 @@ void GLSceneDrawer::SetViewArea()
|
||||||
|
|
||||||
void GLSceneDrawer::Reset3DViewport()
|
void GLSceneDrawer::Reset3DViewport()
|
||||||
{
|
{
|
||||||
glViewport(GLRenderer->mScreenViewport.left, GLRenderer->mScreenViewport.top, GLRenderer->mScreenViewport.width, GLRenderer->mScreenViewport.height);
|
glViewport(screen->mScreenViewport.left, screen->mScreenViewport.top, screen->mScreenViewport.width, screen->mScreenViewport.height);
|
||||||
}
|
}
|
||||||
|
|
||||||
//-----------------------------------------------------------------------------
|
//-----------------------------------------------------------------------------
|
||||||
|
@ -150,7 +150,7 @@ void GLSceneDrawer::Set3DViewport(bool mainview)
|
||||||
glClearColor(GLRenderer->mSceneClearColor[0], GLRenderer->mSceneClearColor[1], GLRenderer->mSceneClearColor[2], 1.0f);
|
glClearColor(GLRenderer->mSceneClearColor[0], GLRenderer->mSceneClearColor[1], GLRenderer->mSceneClearColor[2], 1.0f);
|
||||||
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT);
|
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT);
|
||||||
|
|
||||||
const auto &bounds = GLRenderer->mSceneViewport;
|
const auto &bounds = screen->mSceneViewport;
|
||||||
glViewport(bounds.left, bounds.top, bounds.width, bounds.height);
|
glViewport(bounds.left, bounds.top, bounds.width, bounds.height);
|
||||||
glScissor(bounds.left, bounds.top, bounds.width, bounds.height);
|
glScissor(bounds.left, bounds.top, bounds.width, bounds.height);
|
||||||
|
|
||||||
|
@ -637,7 +637,7 @@ void GLSceneDrawer::SetFixedColormap (player_t *player)
|
||||||
//
|
//
|
||||||
//-----------------------------------------------------------------------------
|
//-----------------------------------------------------------------------------
|
||||||
|
|
||||||
sector_t * GLSceneDrawer::RenderViewpoint (AActor * camera, GL_IRECT * bounds, float fov, float ratio, float fovratio, bool mainview, bool toscreen)
|
sector_t * GLSceneDrawer::RenderViewpoint (AActor * camera, IntRect * bounds, float fov, float ratio, float fovratio, bool mainview, bool toscreen)
|
||||||
{
|
{
|
||||||
sector_t * lviewsector;
|
sector_t * lviewsector;
|
||||||
GLRenderer->mSceneClearColor[0] = 0.0f;
|
GLRenderer->mSceneClearColor[0] = 0.0f;
|
||||||
|
@ -680,7 +680,7 @@ sector_t * GLSceneDrawer::RenderViewpoint (AActor * camera, GL_IRECT * bounds, f
|
||||||
SetFixedColormap(camera->player); // reiterate color map for each eye, so night vision goggles work in both eyes
|
SetFixedColormap(camera->player); // reiterate color map for each eye, so night vision goggles work in both eyes
|
||||||
const s3d::EyePose * eye = stereo3dMode.getEyePose(eye_ix);
|
const s3d::EyePose * eye = stereo3dMode.getEyePose(eye_ix);
|
||||||
eye->SetUp();
|
eye->SetUp();
|
||||||
GLRenderer->SetOutputViewport(bounds);
|
screen->SetOutputViewport(bounds);
|
||||||
Set3DViewport(mainview);
|
Set3DViewport(mainview);
|
||||||
GLRenderer->mDrawingScene2D = true;
|
GLRenderer->mDrawingScene2D = true;
|
||||||
GLRenderer->mCurrentFoV = fov;
|
GLRenderer->mCurrentFoV = fov;
|
||||||
|
@ -704,12 +704,12 @@ sector_t * GLSceneDrawer::RenderViewpoint (AActor * camera, GL_IRECT * bounds, f
|
||||||
|
|
||||||
// This should be done after postprocessing, not before.
|
// This should be done after postprocessing, not before.
|
||||||
GLRenderer->mBuffers->BindCurrentFB();
|
GLRenderer->mBuffers->BindCurrentFB();
|
||||||
glViewport(GLRenderer->mScreenViewport.left, GLRenderer->mScreenViewport.top, GLRenderer->mScreenViewport.width, GLRenderer->mScreenViewport.height);
|
glViewport(screen->mScreenViewport.left, screen->mScreenViewport.top, screen->mScreenViewport.width, screen->mScreenViewport.height);
|
||||||
|
|
||||||
if (!toscreen)
|
if (!toscreen)
|
||||||
{
|
{
|
||||||
gl_RenderState.mViewMatrix.loadIdentity();
|
gl_RenderState.mViewMatrix.loadIdentity();
|
||||||
gl_RenderState.mProjectionMatrix.ortho(GLRenderer->mScreenViewport.left, GLRenderer->mScreenViewport.width, GLRenderer->mScreenViewport.height, GLRenderer->mScreenViewport.top, -1.0f, 1.0f);
|
gl_RenderState.mProjectionMatrix.ortho(screen->mScreenViewport.left, screen->mScreenViewport.width, screen->mScreenViewport.height, screen->mScreenViewport.top, -1.0f, 1.0f);
|
||||||
gl_RenderState.ApplyMatrices();
|
gl_RenderState.ApplyMatrices();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -733,7 +733,7 @@ sector_t * GLSceneDrawer::RenderViewpoint (AActor * camera, GL_IRECT * bounds, f
|
||||||
|
|
||||||
void GLSceneDrawer::WriteSavePic (player_t *player, FileWriter *file, int width, int height)
|
void GLSceneDrawer::WriteSavePic (player_t *player, FileWriter *file, int width, int height)
|
||||||
{
|
{
|
||||||
GL_IRECT bounds;
|
IntRect bounds;
|
||||||
|
|
||||||
P_FindParticleSubsectors(); // make sure that all recently spawned particles have a valid subsector.
|
P_FindParticleSubsectors(); // make sure that all recently spawned particles have a valid subsector.
|
||||||
bounds.left=0;
|
bounds.left=0;
|
||||||
|
|
|
@ -63,7 +63,7 @@ public:
|
||||||
void EndDrawScene(sector_t * viewsector);
|
void EndDrawScene(sector_t * viewsector);
|
||||||
void DrawEndScene2D(sector_t * viewsector);
|
void DrawEndScene2D(sector_t * viewsector);
|
||||||
|
|
||||||
sector_t *RenderViewpoint(AActor * camera, GL_IRECT * bounds, float fov, float ratio, float fovratio, bool mainview, bool toscreen);
|
sector_t *RenderViewpoint(AActor * camera, IntRect * bounds, float fov, float ratio, float fovratio, bool mainview, bool toscreen);
|
||||||
sector_t *RenderView(player_t *player);
|
sector_t *RenderView(player_t *player);
|
||||||
void WriteSavePic(player_t *player, FileWriter *file, int width, int height);
|
void WriteSavePic(player_t *player, FileWriter *file, int width, int height);
|
||||||
|
|
||||||
|
|
|
@ -45,12 +45,12 @@ void MaskAnaglyph::Present() const
|
||||||
gl_RenderState.SetColorMask(leftEye.GetColorMask().r, leftEye.GetColorMask().g, leftEye.GetColorMask().b, true);
|
gl_RenderState.SetColorMask(leftEye.GetColorMask().r, leftEye.GetColorMask().g, leftEye.GetColorMask().b, true);
|
||||||
gl_RenderState.ApplyColorMask();
|
gl_RenderState.ApplyColorMask();
|
||||||
GLRenderer->mBuffers->BindEyeTexture(0, 0);
|
GLRenderer->mBuffers->BindEyeTexture(0, 0);
|
||||||
GLRenderer->DrawPresentTexture(GLRenderer->mOutputLetterbox, true);
|
GLRenderer->DrawPresentTexture(screen->mOutputLetterbox, true);
|
||||||
|
|
||||||
gl_RenderState.SetColorMask(rightEye.GetColorMask().r, rightEye.GetColorMask().g, rightEye.GetColorMask().b, true);
|
gl_RenderState.SetColorMask(rightEye.GetColorMask().r, rightEye.GetColorMask().g, rightEye.GetColorMask().b, true);
|
||||||
gl_RenderState.ApplyColorMask();
|
gl_RenderState.ApplyColorMask();
|
||||||
GLRenderer->mBuffers->BindEyeTexture(1, 0);
|
GLRenderer->mBuffers->BindEyeTexture(1, 0);
|
||||||
GLRenderer->DrawPresentTexture(GLRenderer->mOutputLetterbox, true);
|
GLRenderer->DrawPresentTexture(screen->mOutputLetterbox, true);
|
||||||
|
|
||||||
gl_RenderState.ResetColorMask();
|
gl_RenderState.ResetColorMask();
|
||||||
gl_RenderState.ApplyColorMask();
|
gl_RenderState.ApplyColorMask();
|
||||||
|
|
|
@ -92,7 +92,7 @@ static void prepareInterleavedPresent(FPresentStereoShaderBase& shader)
|
||||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
|
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
|
||||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
|
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
|
||||||
|
|
||||||
const GL_IRECT& box = GLRenderer->mOutputLetterbox;
|
const IntRect& box = screen->mOutputLetterbox;
|
||||||
glViewport(box.left, box.top, box.width, box.height);
|
glViewport(box.left, box.top, box.width, box.height);
|
||||||
|
|
||||||
shader.Bind();
|
shader.Bind();
|
||||||
|
@ -115,8 +115,8 @@ static void prepareInterleavedPresent(FPresentStereoShaderBase& shader)
|
||||||
shader.GrayFormula.Set(static_cast<int>(gl_satformula));
|
shader.GrayFormula.Set(static_cast<int>(gl_satformula));
|
||||||
}
|
}
|
||||||
shader.Scale.Set(
|
shader.Scale.Set(
|
||||||
GLRenderer->mScreenViewport.width / (float)GLRenderer->mBuffers->GetWidth(),
|
screen->mScreenViewport.width / (float)GLRenderer->mBuffers->GetWidth(),
|
||||||
GLRenderer->mScreenViewport.height / (float)GLRenderer->mBuffers->GetHeight());
|
screen->mScreenViewport.height / (float)GLRenderer->mBuffers->GetHeight());
|
||||||
}
|
}
|
||||||
|
|
||||||
// fixme: I don't know how to get absolute window position on Mac and Linux
|
// fixme: I don't know how to get absolute window position on Mac and Linux
|
||||||
|
@ -150,7 +150,7 @@ void CheckerInterleaved3D::Present() const
|
||||||
GLRenderer->mPresent3dCheckerShader->WindowPositionParity.Set(
|
GLRenderer->mPresent3dCheckerShader->WindowPositionParity.Set(
|
||||||
(windowVOffset
|
(windowVOffset
|
||||||
+ windowHOffset
|
+ windowHOffset
|
||||||
+ GLRenderer->mOutputLetterbox.height + 1 // +1 because of origin at bottom
|
+ screen->mOutputLetterbox.height + 1 // +1 because of origin at bottom
|
||||||
) % 2 // because we want the top pixel offset, but gl_FragCoord.y is the bottom pixel offset
|
) % 2 // because we want the top pixel offset, but gl_FragCoord.y is the bottom pixel offset
|
||||||
);
|
);
|
||||||
|
|
||||||
|
@ -162,15 +162,15 @@ void s3d::CheckerInterleaved3D::AdjustViewports() const
|
||||||
// decrease the total pixel count by 2, but keep the same aspect ratio
|
// decrease the total pixel count by 2, but keep the same aspect ratio
|
||||||
const float sqrt2 = 1.41421356237f;
|
const float sqrt2 = 1.41421356237f;
|
||||||
// Change size of renderbuffer, and align to screen
|
// Change size of renderbuffer, and align to screen
|
||||||
GLRenderer->mSceneViewport.height /= sqrt2;
|
screen->mSceneViewport.height /= sqrt2;
|
||||||
GLRenderer->mSceneViewport.top /= sqrt2;
|
screen->mSceneViewport.top /= sqrt2;
|
||||||
GLRenderer->mSceneViewport.width /= sqrt2;
|
screen->mSceneViewport.width /= sqrt2;
|
||||||
GLRenderer->mSceneViewport.left /= sqrt2;
|
screen->mSceneViewport.left /= sqrt2;
|
||||||
|
|
||||||
GLRenderer->mScreenViewport.height /= sqrt2;
|
screen->mScreenViewport.height /= sqrt2;
|
||||||
GLRenderer->mScreenViewport.top /= sqrt2;
|
screen->mScreenViewport.top /= sqrt2;
|
||||||
GLRenderer->mScreenViewport.width /= sqrt2;
|
screen->mScreenViewport.width /= sqrt2;
|
||||||
GLRenderer->mScreenViewport.left /= sqrt2;
|
screen->mScreenViewport.left /= sqrt2;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ColumnInterleaved3D::Present() const
|
void ColumnInterleaved3D::Present() const
|
||||||
|
@ -214,7 +214,7 @@ void RowInterleaved3D::Present() const
|
||||||
|
|
||||||
GLRenderer->mPresent3dRowShader->WindowPositionParity.Set(
|
GLRenderer->mPresent3dRowShader->WindowPositionParity.Set(
|
||||||
(windowVOffset
|
(windowVOffset
|
||||||
+ GLRenderer->mOutputLetterbox.height + 1 // +1 because of origin at bottom
|
+ screen->mOutputLetterbox.height + 1 // +1 because of origin at bottom
|
||||||
) % 2
|
) % 2
|
||||||
);
|
);
|
||||||
|
|
||||||
|
|
|
@ -80,12 +80,12 @@ void QuadStereo::Present() const
|
||||||
glDrawBuffer(GL_BACK_LEFT);
|
glDrawBuffer(GL_BACK_LEFT);
|
||||||
GLRenderer->ClearBorders();
|
GLRenderer->ClearBorders();
|
||||||
GLRenderer->mBuffers->BindEyeTexture(0, 0);
|
GLRenderer->mBuffers->BindEyeTexture(0, 0);
|
||||||
GLRenderer->DrawPresentTexture(GLRenderer->mOutputLetterbox, true);
|
GLRenderer->DrawPresentTexture(screen->mOutputLetterbox, true);
|
||||||
|
|
||||||
glDrawBuffer(GL_BACK_RIGHT);
|
glDrawBuffer(GL_BACK_RIGHT);
|
||||||
GLRenderer->ClearBorders();
|
GLRenderer->ClearBorders();
|
||||||
GLRenderer->mBuffers->BindEyeTexture(1, 0);
|
GLRenderer->mBuffers->BindEyeTexture(1, 0);
|
||||||
GLRenderer->DrawPresentTexture(GLRenderer->mOutputLetterbox, true);
|
GLRenderer->DrawPresentTexture(screen->mOutputLetterbox, true);
|
||||||
|
|
||||||
glDrawBuffer(GL_BACK);
|
glDrawBuffer(GL_BACK);
|
||||||
}
|
}
|
||||||
|
@ -94,7 +94,7 @@ void QuadStereo::Present() const
|
||||||
GLRenderer->mBuffers->BindOutputFB();
|
GLRenderer->mBuffers->BindOutputFB();
|
||||||
GLRenderer->ClearBorders();
|
GLRenderer->ClearBorders();
|
||||||
GLRenderer->mBuffers->BindEyeTexture(0, 0);
|
GLRenderer->mBuffers->BindEyeTexture(0, 0);
|
||||||
GLRenderer->DrawPresentTexture(GLRenderer->mOutputLetterbox, true);
|
GLRenderer->DrawPresentTexture(screen->mOutputLetterbox, true);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -44,11 +44,11 @@ void SideBySideBase::Present() const
|
||||||
GLRenderer->ClearBorders();
|
GLRenderer->ClearBorders();
|
||||||
|
|
||||||
// Compute screen regions to use for left and right eye views
|
// Compute screen regions to use for left and right eye views
|
||||||
int leftWidth = GLRenderer->mOutputLetterbox.width / 2;
|
int leftWidth = screen->mOutputLetterbox.width / 2;
|
||||||
int rightWidth = GLRenderer->mOutputLetterbox.width - leftWidth;
|
int rightWidth = screen->mOutputLetterbox.width - leftWidth;
|
||||||
GL_IRECT leftHalfScreen = GLRenderer->mOutputLetterbox;
|
IntRect leftHalfScreen = screen->mOutputLetterbox;
|
||||||
leftHalfScreen.width = leftWidth;
|
leftHalfScreen.width = leftWidth;
|
||||||
GL_IRECT rightHalfScreen = GLRenderer->mOutputLetterbox;
|
IntRect rightHalfScreen = screen->mOutputLetterbox;
|
||||||
rightHalfScreen.width = rightWidth;
|
rightHalfScreen.width = rightWidth;
|
||||||
rightHalfScreen.left += leftWidth;
|
rightHalfScreen.left += leftWidth;
|
||||||
|
|
||||||
|
@ -63,10 +63,10 @@ void SideBySideBase::Present() const
|
||||||
void SideBySideBase::AdjustViewports() const
|
void SideBySideBase::AdjustViewports() const
|
||||||
{
|
{
|
||||||
// Change size of renderbuffer, and align to screen
|
// Change size of renderbuffer, and align to screen
|
||||||
GLRenderer->mSceneViewport.width /= 2;
|
screen->mSceneViewport.width /= 2;
|
||||||
GLRenderer->mSceneViewport.left /= 2;
|
screen->mSceneViewport.left /= 2;
|
||||||
GLRenderer->mScreenViewport.width /= 2;
|
screen->mScreenViewport.width /= 2;
|
||||||
GLRenderer->mScreenViewport.left /= 2;
|
screen->mScreenViewport.left /= 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* static */
|
/* static */
|
||||||
|
@ -101,8 +101,8 @@ SideBySideFull::SideBySideFull(double ipdMeters)
|
||||||
void SideBySideFull::AdjustPlayerSprites() const /* override */
|
void SideBySideFull::AdjustPlayerSprites() const /* override */
|
||||||
{
|
{
|
||||||
// Show weapon at double width, so it would appear normal width after rescaling
|
// Show weapon at double width, so it would appear normal width after rescaling
|
||||||
int w = GLRenderer->mScreenViewport.width;
|
int w = screen->mScreenViewport.width;
|
||||||
int h = GLRenderer->mScreenViewport.height;
|
int h = screen->mScreenViewport.height;
|
||||||
gl_RenderState.mProjectionMatrix.ortho(w/2, w + w/2, h, 0, -1.0f, 1.0f);
|
gl_RenderState.mProjectionMatrix.ortho(w/2, w + w/2, h, 0, -1.0f, 1.0f);
|
||||||
gl_RenderState.ApplyMatrices();
|
gl_RenderState.ApplyMatrices();
|
||||||
}
|
}
|
||||||
|
@ -120,12 +120,12 @@ void TopBottom3D::Present() const
|
||||||
GLRenderer->ClearBorders();
|
GLRenderer->ClearBorders();
|
||||||
|
|
||||||
// Compute screen regions to use for left and right eye views
|
// Compute screen regions to use for left and right eye views
|
||||||
int topHeight = GLRenderer->mOutputLetterbox.height / 2;
|
int topHeight = screen->mOutputLetterbox.height / 2;
|
||||||
int bottomHeight = GLRenderer->mOutputLetterbox.height - topHeight;
|
int bottomHeight = screen->mOutputLetterbox.height - topHeight;
|
||||||
GL_IRECT topHalfScreen = GLRenderer->mOutputLetterbox;
|
IntRect topHalfScreen = screen->mOutputLetterbox;
|
||||||
topHalfScreen.height = topHeight;
|
topHalfScreen.height = topHeight;
|
||||||
topHalfScreen.top = topHeight;
|
topHalfScreen.top = topHeight;
|
||||||
GL_IRECT bottomHalfScreen = GLRenderer->mOutputLetterbox;
|
IntRect bottomHalfScreen = screen->mOutputLetterbox;
|
||||||
bottomHalfScreen.height = bottomHeight;
|
bottomHalfScreen.height = bottomHeight;
|
||||||
bottomHalfScreen.top = 0;
|
bottomHalfScreen.top = 0;
|
||||||
|
|
||||||
|
@ -140,10 +140,10 @@ void TopBottom3D::Present() const
|
||||||
void TopBottom3D::AdjustViewports() const
|
void TopBottom3D::AdjustViewports() const
|
||||||
{
|
{
|
||||||
// Change size of renderbuffer, and align to screen
|
// Change size of renderbuffer, and align to screen
|
||||||
GLRenderer->mSceneViewport.height /= 2;
|
screen->mSceneViewport.height /= 2;
|
||||||
GLRenderer->mSceneViewport.top /= 2;
|
screen->mSceneViewport.top /= 2;
|
||||||
GLRenderer->mScreenViewport.height /= 2;
|
screen->mScreenViewport.height /= 2;
|
||||||
GLRenderer->mScreenViewport.top /= 2;
|
screen->mScreenViewport.top /= 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
} /* namespace s3d */
|
} /* namespace s3d */
|
||||||
|
|
|
@ -93,7 +93,7 @@ void LeftEyeView::Present() const
|
||||||
GLRenderer->mBuffers->BindOutputFB();
|
GLRenderer->mBuffers->BindOutputFB();
|
||||||
GLRenderer->ClearBorders();
|
GLRenderer->ClearBorders();
|
||||||
GLRenderer->mBuffers->BindEyeTexture(0, 0);
|
GLRenderer->mBuffers->BindEyeTexture(0, 0);
|
||||||
GLRenderer->DrawPresentTexture(GLRenderer->mOutputLetterbox, true);
|
GLRenderer->DrawPresentTexture(screen->mOutputLetterbox, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* static */
|
/* static */
|
||||||
|
@ -109,7 +109,7 @@ void RightEyeView::Present() const
|
||||||
GLRenderer->mBuffers->BindOutputFB();
|
GLRenderer->mBuffers->BindOutputFB();
|
||||||
GLRenderer->ClearBorders();
|
GLRenderer->ClearBorders();
|
||||||
GLRenderer->mBuffers->BindEyeTexture(0, 0);
|
GLRenderer->mBuffers->BindEyeTexture(0, 0);
|
||||||
GLRenderer->DrawPresentTexture(GLRenderer->mOutputLetterbox, true);
|
GLRenderer->DrawPresentTexture(screen->mOutputLetterbox, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -39,6 +39,7 @@
|
||||||
#include "hwrenderer/utility/hw_clock.h"
|
#include "hwrenderer/utility/hw_clock.h"
|
||||||
#include "gl/data/gl_vertexbuffer.h"
|
#include "gl/data/gl_vertexbuffer.h"
|
||||||
#include "gl/models/gl_models.h"
|
#include "gl/models/gl_models.h"
|
||||||
|
#include "gl/stereo3d/gl_stereo3d.h"
|
||||||
#include "gl_debug.h"
|
#include "gl_debug.h"
|
||||||
#include "r_videoscale.h"
|
#include "r_videoscale.h"
|
||||||
|
|
||||||
|
@ -137,7 +138,7 @@ void OpenGLFrameBuffer::InitializeState()
|
||||||
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
|
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
|
||||||
|
|
||||||
GLRenderer->Initialize(GetWidth(), GetHeight());
|
GLRenderer->Initialize(GetWidth(), GetHeight());
|
||||||
GLRenderer->SetOutputViewport(nullptr);
|
SetOutputViewport(nullptr);
|
||||||
}
|
}
|
||||||
|
|
||||||
//==========================================================================
|
//==========================================================================
|
||||||
|
@ -167,7 +168,7 @@ void OpenGLFrameBuffer::Update()
|
||||||
GLRenderer->mVBO->OutputResized(Width, Height);
|
GLRenderer->mVBO->OutputResized(Width, Height);
|
||||||
}
|
}
|
||||||
|
|
||||||
GLRenderer->SetOutputViewport(nullptr);
|
SetOutputViewport(nullptr);
|
||||||
}
|
}
|
||||||
|
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
|
@ -379,6 +380,17 @@ void OpenGLFrameBuffer::ResetFixedColormap()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool OpenGLFrameBuffer::RenderBuffersEnabled()
|
||||||
|
{
|
||||||
|
return FGLRenderBuffers::IsEnabled();
|
||||||
|
}
|
||||||
|
|
||||||
|
void OpenGLFrameBuffer::SetOutputViewport(IntRect *bounds)
|
||||||
|
{
|
||||||
|
Super::SetOutputViewport(bounds);
|
||||||
|
s3d::Stereo3DMode::getCurrentMode().AdjustViewports();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void OpenGLFrameBuffer::UpdatePalette()
|
void OpenGLFrameBuffer::UpdatePalette()
|
||||||
{
|
{
|
||||||
|
@ -446,7 +458,7 @@ void OpenGLFrameBuffer::BeginFrame()
|
||||||
|
|
||||||
void OpenGLFrameBuffer::GetScreenshotBuffer(const uint8_t *&buffer, int &pitch, ESSType &color_type, float &gamma)
|
void OpenGLFrameBuffer::GetScreenshotBuffer(const uint8_t *&buffer, int &pitch, ESSType &color_type, float &gamma)
|
||||||
{
|
{
|
||||||
const auto &viewport = GLRenderer->mOutputLetterbox;
|
const auto &viewport = mOutputLetterbox;
|
||||||
|
|
||||||
// Grab what is in the back buffer.
|
// Grab what is in the back buffer.
|
||||||
// We cannot rely on SCREENWIDTH/HEIGHT here because the output may have been scaled.
|
// We cannot rely on SCREENWIDTH/HEIGHT here because the output may have been scaled.
|
||||||
|
@ -513,10 +525,10 @@ void OpenGLFrameBuffer::GameRestart()
|
||||||
|
|
||||||
void OpenGLFrameBuffer::ScaleCoordsFromWindow(int16_t &x, int16_t &y)
|
void OpenGLFrameBuffer::ScaleCoordsFromWindow(int16_t &x, int16_t &y)
|
||||||
{
|
{
|
||||||
int letterboxX = GLRenderer->mOutputLetterbox.left;
|
int letterboxX = mOutputLetterbox.left;
|
||||||
int letterboxY = GLRenderer->mOutputLetterbox.top;
|
int letterboxY = mOutputLetterbox.top;
|
||||||
int letterboxWidth = GLRenderer->mOutputLetterbox.width;
|
int letterboxWidth = mOutputLetterbox.width;
|
||||||
int letterboxHeight = GLRenderer->mOutputLetterbox.height;
|
int letterboxHeight = mOutputLetterbox.height;
|
||||||
|
|
||||||
// Subtract the LB video mode letterboxing
|
// Subtract the LB video mode letterboxing
|
||||||
if (IsFullscreen())
|
if (IsFullscreen())
|
||||||
|
|
|
@ -46,6 +46,8 @@ public:
|
||||||
void TextureFilterChanged() override;
|
void TextureFilterChanged() override;
|
||||||
void ResetFixedColormap() override;
|
void ResetFixedColormap() override;
|
||||||
void BeginFrame() override;
|
void BeginFrame() override;
|
||||||
|
bool RenderBuffersEnabled() override;
|
||||||
|
void SetOutputViewport(IntRect *bounds) override;
|
||||||
|
|
||||||
// Retrieves a buffer containing image data for a screenshot.
|
// Retrieves a buffer containing image data for a screenshot.
|
||||||
// Hint: Pitch can be negative for upside-down images, in which case buffer
|
// Hint: Pitch can be negative for upside-down images, in which case buffer
|
||||||
|
|
|
@ -115,7 +115,7 @@ bool OpenGLFrameBuffer::WipeStartScreen(int type)
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
const auto &viewport = GLRenderer->mScreenViewport;
|
const auto &viewport = screen->mScreenViewport;
|
||||||
wipestartscreen = new FHardwareTexture(true);
|
wipestartscreen = new FHardwareTexture(true);
|
||||||
wipestartscreen->CreateTexture(NULL, viewport.width, viewport.height, 0, false, 0, "WipeStartScreen");
|
wipestartscreen->CreateTexture(NULL, viewport.width, viewport.height, 0, false, 0, "WipeStartScreen");
|
||||||
GLRenderer->mSamplerManager->Bind(0, CLAMP_NOFILTER, -1);
|
GLRenderer->mSamplerManager->Bind(0, CLAMP_NOFILTER, -1);
|
||||||
|
@ -163,7 +163,7 @@ bool OpenGLFrameBuffer::WipeStartScreen(int type)
|
||||||
void OpenGLFrameBuffer::WipeEndScreen()
|
void OpenGLFrameBuffer::WipeEndScreen()
|
||||||
{
|
{
|
||||||
GLRenderer->Flush();
|
GLRenderer->Flush();
|
||||||
const auto &viewport = GLRenderer->mScreenViewport;
|
const auto &viewport = screen->mScreenViewport;
|
||||||
wipeendscreen = new FHardwareTexture(true);
|
wipeendscreen = new FHardwareTexture(true);
|
||||||
wipeendscreen->CreateTexture(NULL, viewport.width, viewport.height, 0, false, 0, "WipeEndScreen");
|
wipeendscreen->CreateTexture(NULL, viewport.width, viewport.height, 0, false, 0, "WipeEndScreen");
|
||||||
GLRenderer->mSamplerManager->Bind(0, CLAMP_NOFILTER, -1);
|
GLRenderer->mSamplerManager->Bind(0, CLAMP_NOFILTER, -1);
|
||||||
|
@ -206,7 +206,7 @@ bool OpenGLFrameBuffer::WipeDo(int ticks)
|
||||||
if (FGLRenderBuffers::IsEnabled())
|
if (FGLRenderBuffers::IsEnabled())
|
||||||
{
|
{
|
||||||
GLRenderer->mBuffers->BindCurrentFB();
|
GLRenderer->mBuffers->BindCurrentFB();
|
||||||
const auto &bounds = GLRenderer->mScreenViewport;
|
const auto &bounds = screen->mScreenViewport;
|
||||||
glViewport(bounds.left, bounds.top, bounds.width, bounds.height);
|
glViewport(bounds.left, bounds.top, bounds.width, bounds.height);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
115
src/v_video.cpp
115
src/v_video.cpp
|
@ -75,6 +75,8 @@
|
||||||
EXTERN_CVAR(Bool, cl_capfps)
|
EXTERN_CVAR(Bool, cl_capfps)
|
||||||
EXTERN_CVAR(Float, vid_brightness)
|
EXTERN_CVAR(Float, vid_brightness)
|
||||||
EXTERN_CVAR(Float, vid_contrast)
|
EXTERN_CVAR(Float, vid_contrast)
|
||||||
|
CVAR(Bool, gl_scale_viewport, true, CVAR_ARCHIVE);
|
||||||
|
EXTERN_CVAR(Int, screenblocks)
|
||||||
|
|
||||||
CUSTOM_CVAR(Int, vid_maxfps, 200, CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
CUSTOM_CVAR(Int, vid_maxfps, 200, CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
||||||
{
|
{
|
||||||
|
@ -134,6 +136,8 @@ public:
|
||||||
bool SetFlash(PalEntry rgb, int amount) { DBGBREAK; return false; }
|
bool SetFlash(PalEntry rgb, int amount) { DBGBREAK; return false; }
|
||||||
void GetFlash(PalEntry &rgb, int &amount) { DBGBREAK; }
|
void GetFlash(PalEntry &rgb, int &amount) { DBGBREAK; }
|
||||||
bool IsFullscreen() { DBGBREAK; return 0; }
|
bool IsFullscreen() { DBGBREAK; return 0; }
|
||||||
|
int GetClientWidth() { DBGBREAK; return 0; }
|
||||||
|
int GetClientHeight() { DBGBREAK; return 0; }
|
||||||
|
|
||||||
float Gamma;
|
float Gamma;
|
||||||
};
|
};
|
||||||
|
@ -967,6 +971,117 @@ void DFrameBuffer::WriteSavePic(player_t *player, FileWriter *file, int width, i
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//==========================================================================
|
||||||
|
//
|
||||||
|
// Calculates the viewport values needed for 2D and 3D operations
|
||||||
|
//
|
||||||
|
//==========================================================================
|
||||||
|
|
||||||
|
void DFrameBuffer::SetOutputViewport(IntRect *bounds)
|
||||||
|
{
|
||||||
|
if (bounds)
|
||||||
|
{
|
||||||
|
mSceneViewport = *bounds;
|
||||||
|
mScreenViewport = *bounds;
|
||||||
|
mOutputLetterbox = *bounds;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Special handling so the view with a visible status bar displays properly
|
||||||
|
int height, width;
|
||||||
|
if (screenblocks >= 10)
|
||||||
|
{
|
||||||
|
height = GetHeight();
|
||||||
|
width = GetWidth();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
height = (screenblocks*GetHeight() / 10) & ~7;
|
||||||
|
width = (screenblocks*GetWidth() / 10);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Back buffer letterbox for the final output
|
||||||
|
int clientWidth = GetClientWidth();
|
||||||
|
int clientHeight = GetClientHeight();
|
||||||
|
if (clientWidth == 0 || clientHeight == 0)
|
||||||
|
{
|
||||||
|
// When window is minimized there may not be any client area.
|
||||||
|
// Pretend to the rest of the render code that we just have a very small window.
|
||||||
|
clientWidth = 160;
|
||||||
|
clientHeight = 120;
|
||||||
|
}
|
||||||
|
int screenWidth = GetWidth();
|
||||||
|
int screenHeight = GetHeight();
|
||||||
|
float scaleX, scaleY;
|
||||||
|
if (ViewportIsScaled43())
|
||||||
|
{
|
||||||
|
scaleX = MIN(clientWidth / (float)screenWidth, clientHeight / (screenHeight * 1.2f));
|
||||||
|
scaleY = scaleX * 1.2f;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
scaleX = MIN(clientWidth / (float)screenWidth, clientHeight / (float)screenHeight);
|
||||||
|
scaleY = scaleX;
|
||||||
|
}
|
||||||
|
mOutputLetterbox.width = (int)round(screenWidth * scaleX);
|
||||||
|
mOutputLetterbox.height = (int)round(screenHeight * scaleY);
|
||||||
|
mOutputLetterbox.left = (clientWidth - mOutputLetterbox.width) / 2;
|
||||||
|
mOutputLetterbox.top = (clientHeight - mOutputLetterbox.height) / 2;
|
||||||
|
|
||||||
|
// The entire renderable area, including the 2D HUD
|
||||||
|
mScreenViewport.left = 0;
|
||||||
|
mScreenViewport.top = 0;
|
||||||
|
mScreenViewport.width = screenWidth;
|
||||||
|
mScreenViewport.height = screenHeight;
|
||||||
|
|
||||||
|
// Viewport for the 3D scene
|
||||||
|
mSceneViewport.left = viewwindowx;
|
||||||
|
mSceneViewport.top = screenHeight - (height + viewwindowy - ((height - viewheight) / 2));
|
||||||
|
mSceneViewport.width = viewwidth;
|
||||||
|
mSceneViewport.height = height;
|
||||||
|
|
||||||
|
// Scale viewports to fit letterbox
|
||||||
|
bool notScaled = ((mScreenViewport.width == ViewportScaledWidth(mScreenViewport.width, mScreenViewport.height)) &&
|
||||||
|
(mScreenViewport.width == ViewportScaledHeight(mScreenViewport.width, mScreenViewport.height)) &&
|
||||||
|
!ViewportIsScaled43());
|
||||||
|
if ((gl_scale_viewport && !IsFullscreen() && notScaled) || !RenderBuffersEnabled())
|
||||||
|
{
|
||||||
|
mScreenViewport.width = mOutputLetterbox.width;
|
||||||
|
mScreenViewport.height = mOutputLetterbox.height;
|
||||||
|
mSceneViewport.left = (int)round(mSceneViewport.left * scaleX);
|
||||||
|
mSceneViewport.top = (int)round(mSceneViewport.top * scaleY);
|
||||||
|
mSceneViewport.width = (int)round(mSceneViewport.width * scaleX);
|
||||||
|
mSceneViewport.height = (int)round(mSceneViewport.height * scaleY);
|
||||||
|
|
||||||
|
// Without render buffers we have to render directly to the letterbox
|
||||||
|
if (!RenderBuffersEnabled())
|
||||||
|
{
|
||||||
|
mScreenViewport.left += mOutputLetterbox.left;
|
||||||
|
mScreenViewport.top += mOutputLetterbox.top;
|
||||||
|
mSceneViewport.left += mOutputLetterbox.left;
|
||||||
|
mSceneViewport.top += mOutputLetterbox.top;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//===========================================================================
|
||||||
|
//
|
||||||
|
// Calculates the OpenGL window coordinates for a zdoom screen position
|
||||||
|
//
|
||||||
|
//===========================================================================
|
||||||
|
|
||||||
|
int DFrameBuffer::ScreenToWindowX(int x)
|
||||||
|
{
|
||||||
|
return mScreenViewport.left + (int)round(x * mScreenViewport.width / (float)GetWidth());
|
||||||
|
}
|
||||||
|
|
||||||
|
int DFrameBuffer::ScreenToWindowY(int y)
|
||||||
|
{
|
||||||
|
return mScreenViewport.top + mScreenViewport.height - (int)round(y * mScreenViewport.height / (float)GetHeight());
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
CCMD(clean)
|
CCMD(clean)
|
||||||
{
|
{
|
||||||
Printf ("CleanXfac: %d\nCleanYfac: %d\n", CleanXfac, CleanYfac);
|
Printf ("CleanXfac: %d\nCleanYfac: %d\n", CleanXfac, CleanYfac);
|
||||||
|
|
|
@ -63,6 +63,21 @@ enum EHWCaps
|
||||||
RFL_NO_SHADERS = 256
|
RFL_NO_SHADERS = 256
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct IntRect
|
||||||
|
{
|
||||||
|
int left, top;
|
||||||
|
int width, height;
|
||||||
|
|
||||||
|
|
||||||
|
void Offset(int xofs, int yofs)
|
||||||
|
{
|
||||||
|
left += xofs;
|
||||||
|
top += yofs;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
extern int CleanWidth, CleanHeight, CleanXfac, CleanYfac;
|
extern int CleanWidth, CleanHeight, CleanXfac, CleanYfac;
|
||||||
|
@ -332,6 +347,10 @@ public:
|
||||||
int hwcaps = 0;
|
int hwcaps = 0;
|
||||||
int instack[2] = { 0,0 }; // this is globally maintained state for portal recursion avoidance.
|
int instack[2] = { 0,0 }; // this is globally maintained state for portal recursion avoidance.
|
||||||
|
|
||||||
|
IntRect mScreenViewport;
|
||||||
|
IntRect mSceneViewport;
|
||||||
|
IntRect mOutputLetterbox;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
DFrameBuffer (int width, int height, bool bgra);
|
DFrameBuffer (int width, int height, bool bgra);
|
||||||
virtual ~DFrameBuffer() {}
|
virtual ~DFrameBuffer() {}
|
||||||
|
@ -385,6 +404,11 @@ public:
|
||||||
virtual void ResetFixedColormap() {}
|
virtual void ResetFixedColormap() {}
|
||||||
virtual void BeginFrame() {}
|
virtual void BeginFrame() {}
|
||||||
|
|
||||||
|
virtual int GetClientWidth() = 0;
|
||||||
|
virtual int GetClientHeight() = 0;
|
||||||
|
virtual bool RenderBuffersEnabled() { return false; };
|
||||||
|
|
||||||
|
|
||||||
// Begin 2D drawing operations.
|
// Begin 2D drawing operations.
|
||||||
// Returns true if hardware-accelerated 2D has been entered, false if not.
|
// Returns true if hardware-accelerated 2D has been entered, false if not.
|
||||||
void Begin2D(bool copy3d) { isIn2D = true; }
|
void Begin2D(bool copy3d) { isIn2D = true; }
|
||||||
|
@ -472,6 +496,10 @@ public:
|
||||||
// Calculate gamma table
|
// Calculate gamma table
|
||||||
void CalcGamma(float gamma, uint8_t gammalookup[256]);
|
void CalcGamma(float gamma, uint8_t gammalookup[256]);
|
||||||
|
|
||||||
|
virtual void SetOutputViewport(IntRect *bounds);
|
||||||
|
int ScreenToWindowX(int x);
|
||||||
|
int ScreenToWindowY(int y);
|
||||||
|
|
||||||
|
|
||||||
// Retrieves a buffer containing image data for a screenshot.
|
// Retrieves a buffer containing image data for a screenshot.
|
||||||
// Hint: Pitch can be negative for upside-down images, in which case buffer
|
// Hint: Pitch can be negative for upside-down images, in which case buffer
|
||||||
|
|
Loading…
Reference in a new issue