Add an abstract Renderer::setViewport method and implemented it for Renderer9.
TRAC #22116
Signed-off-by: Shannon Woods
Signed-off-by: Daniel Koch
git-svn-id: https://angleproject.googlecode.com/svn/branches/dx11proto@1453 736b8ea6-26fd-11df-bfd4-992fa37f6226
diff --git a/src/libGLESv2/renderer/Renderer.h b/src/libGLESv2/renderer/Renderer.h
index 0fc21b2..4c7b8b7 100644
--- a/src/libGLESv2/renderer/Renderer.h
+++ b/src/libGLESv2/renderer/Renderer.h
@@ -37,6 +37,11 @@
class Display;
}
+namespace gl
+{
+class ProgramBinary;
+}
+
namespace rx
{
class TextureStorage2D;
@@ -81,6 +86,9 @@
virtual void setScissorRectangle(const gl::Rectangle& scissor, unsigned int renderTargetWidth,
unsigned int renderTargetHeight) = 0;
+ virtual bool setViewport(const gl::Rectangle& viewport, float zNear, float zFar,
+ unsigned int renderTargetWidth, unsigned int renderTargetHeight,
+ gl::ProgramBinary *currentProgram, bool forceSetUniforms) = 0;
virtual void applyRenderTarget(gl::Framebuffer *frameBuffer) = 0;
diff --git a/src/libGLESv2/renderer/Renderer11.cpp b/src/libGLESv2/renderer/Renderer11.cpp
index 8c3e679..bbdb731 100644
--- a/src/libGLESv2/renderer/Renderer11.cpp
+++ b/src/libGLESv2/renderer/Renderer11.cpp
@@ -374,6 +374,15 @@
mForceSetScissor = false;
}
+bool Renderer11::setViewport(const gl::Rectangle& viewport, float zNear, float zFar,
+ unsigned int renderTargetWidth, unsigned int renderTargetHeight,
+ gl::ProgramBinary *currentProgram, bool forceSetUniforms)
+{
+ // TODO
+ UNIMPLEMENTED();
+ return true;
+}
+
void Renderer11::applyRenderTarget(gl::Framebuffer *frameBuffer)
{
// TODO
diff --git a/src/libGLESv2/renderer/Renderer11.h b/src/libGLESv2/renderer/Renderer11.h
index ed6aa0e..12c6344 100644
--- a/src/libGLESv2/renderer/Renderer11.h
+++ b/src/libGLESv2/renderer/Renderer11.h
@@ -57,6 +57,9 @@
virtual void setScissorRectangle(const gl::Rectangle& scissor, unsigned int renderTargetWidth,
unsigned int renderTargetHeight);
+ virtual bool setViewport(const gl::Rectangle& viewport, float zNear, float zFar,
+ unsigned int renderTargetWidth, unsigned int renderTargetHeight,
+ gl::ProgramBinary *currentProgram, bool forceSetUniforms);
virtual void applyRenderTarget(gl::Framebuffer *frameBuffer);
diff --git a/src/libGLESv2/renderer/Renderer9.cpp b/src/libGLESv2/renderer/Renderer9.cpp
index c496af0..908c3e8 100644
--- a/src/libGLESv2/renderer/Renderer9.cpp
+++ b/src/libGLESv2/renderer/Renderer9.cpp
@@ -11,6 +11,8 @@
#include "libGLESv2/utilities.h"
#include "libGLESv2/mathutil.h"
#include "libGLESv2/Framebuffer.h"
+#include "libGLESv2/Program.h"
+#include "libGLESv2/ProgramBinary.h"
#include "libGLESv2/renderer/Renderer9.h"
#include "libGLESv2/renderer/renderer9_utils.h"
#include "libGLESv2/renderer/SwapChain9.h"
@@ -86,6 +88,7 @@
mForceSetRasterState = true;
mForceSetBlendState = true;
mForceSetScissor = true;
+ mForceSetViewport = true;
}
Renderer9::~Renderer9()
@@ -869,9 +872,67 @@
mForceSetScissor = false;
}
+bool Renderer9::setViewport(const gl::Rectangle& viewport, float zNear, float zFar,
+ unsigned int renderTargetWidth, unsigned int renderTargetHeight,
+ gl::ProgramBinary *currentProgram, bool forceSetUniforms)
+{
+ bool viewportChanged = mForceSetViewport || memcmp(&viewport, &mCurViewport, sizeof(gl::Rectangle)) != 0 ||
+ zNear != mCurNear || zFar != mCurFar;
+
+ D3DVIEWPORT9 dxViewport;
+ dxViewport.X = gl::clamp(viewport.x, 0, static_cast<int>(renderTargetWidth));
+ dxViewport.Y = gl::clamp(viewport.y, 0, static_cast<int>(renderTargetHeight));
+ dxViewport.Width = gl::clamp(viewport.width, 0, static_cast<int>(renderTargetWidth) - static_cast<int>(dxViewport.X));
+ dxViewport.Height = gl::clamp(viewport.height, 0, static_cast<int>(renderTargetHeight) - static_cast<int>(dxViewport.Y));
+ dxViewport.MinZ = zNear;
+ dxViewport.MaxZ = zFar;
+
+ if (dxViewport.Width <= 0 || dxViewport.Height <= 0)
+ {
+ return false; // Nothing to render
+ }
+
+ if (viewportChanged)
+ {
+ mDevice->SetViewport(&dxViewport);
+
+ mCurViewport = viewport;
+ mCurNear = zNear;
+ mCurFar = zFar;
+ }
+
+ if (currentProgram && (viewportChanged || forceSetUniforms))
+ {
+ GLint halfPixelSize = currentProgram->getDxHalfPixelSizeLocation();
+ GLfloat xy[2] = { 1.0f / dxViewport.Width, -1.0f / dxViewport.Height };
+ currentProgram->setUniform2fv(halfPixelSize, 1, xy);
+
+ // These values are used for computing gl_FragCoord in Program::linkVaryings().
+ GLint coord = currentProgram->getDxCoordLocation();
+ GLfloat whxy[4] = { viewport.width * 0.5f,
+ viewport.height * 0.5f,
+ viewport.x + (viewport.width * 0.5f),
+ viewport.y + (viewport.height * 0.5f) };
+ currentProgram->setUniform4fv(coord, 1, whxy);
+
+ GLint depth = currentProgram->getDxDepthLocation();
+ GLfloat dz[2] = { (zFar - zNear) * 0.5f, (zNear + zFar) * 0.5f };
+ currentProgram->setUniform2fv(depth, 1, dz);
+
+ GLint depthRange = currentProgram->getDxDepthRangeLocation();
+ GLfloat nearFarDiff[3] = { zNear, zFar, zFar - zNear };
+ currentProgram->setUniform3fv(depthRange, 1, nearFarDiff);
+ }
+
+ mForceSetViewport = false;
+ return true;
+}
+
void Renderer9::applyRenderTarget(gl::Framebuffer *frameBuffer)
{
+ // TODO: only set these when the rendertarget actually changes
mForceSetScissor = true;
+ mForceSetViewport = true;
// TODO
}
diff --git a/src/libGLESv2/renderer/Renderer9.h b/src/libGLESv2/renderer/Renderer9.h
index 1770727..520c4a9 100644
--- a/src/libGLESv2/renderer/Renderer9.h
+++ b/src/libGLESv2/renderer/Renderer9.h
@@ -65,8 +65,6 @@
// state setup
void applyShaders();
void applyConstants();
- void applyRenderTargets();
- void applyState();
#endif
virtual void setSamplerState(gl::SamplerType type, int index, const gl::SamplerState &sampler);
virtual void setTexture(gl::SamplerType type, int index, gl::Texture *texture);
@@ -79,6 +77,9 @@
virtual void setScissorRectangle(const gl::Rectangle& scissor, unsigned int renderTargetWidth,
unsigned int renderTargetHeight);
+ virtual bool setViewport(const gl::Rectangle& viewport, float zNear, float zFar,
+ unsigned int renderTargetWidth, unsigned int renderTargetHeight,
+ gl::ProgramBinary *currentProgram, bool forceSetUniforms);
virtual void applyRenderTarget(gl::Framebuffer *frameBuffer);
@@ -205,6 +206,11 @@
unsigned int mCurRenderTargetWidth;
unsigned int mCurRenderTargetHeight;
+ bool mForceSetViewport;
+ gl::Rectangle mCurViewport;
+ float mCurNear;
+ float mCurFar;
+
bool mForceSetBlendState;
gl::BlendState mCurBlendState;
gl::Color mCurBlendColor;