1
0
mirror of https://github.com/blawar/GLideN64.git synced 2024-07-04 10:03:36 +00:00

Rewrite N64 Depth Compare

This commit is contained in:
Logan McNaughton 2018-04-10 10:00:44 -06:00 committed by Sergey Lipskiy
parent c57eaf5285
commit 2e227cef53
8 changed files with 70 additions and 76 deletions

View File

@ -81,7 +81,6 @@ namespace graphics {
struct InitTextureParams {
ObjectHandle handle;
ImageUnitParam ImageUnit;
TextureUnitParam textureUnitIndex{0};
u32 msaaLevel = 0;
u32 width = 0;
@ -98,7 +97,6 @@ namespace graphics {
struct UpdateTextureDataParams {
ObjectHandle handle;
ImageUnitParam ImageUnit;
TextureUnitParam textureUnitIndex{0};
u32 x = 0;
u32 y = 0;

View File

@ -229,8 +229,10 @@ public:
std::stringstream ss;
ss << "#version " << Utils::to_string(_glinfo.majorVersion) << Utils::to_string(_glinfo.minorVersion) << "0 es " << std::endl;
ss << "# define IN in" << std::endl << "# define OUT out" << std::endl;
if (_glinfo.noPerspective)
ss << "noperspective OUT highp float vZCoord;" << std::endl << "uniform lowp int uClampMode;" << std::endl;
if (_glinfo.noPerspective) {
ss << "#extension GL_NV_shader_noperspective_interpolation : enable" << std::endl
<< "noperspective OUT highp float vZCoord;" << std::endl << "uniform lowp int uClampMode;" << std::endl;
}
m_part = ss.str();
}
else {
@ -455,6 +457,13 @@ public:
} else if (_glinfo.isGLESX) {
std::stringstream ss;
ss << "#version " << Utils::to_string(_glinfo.majorVersion) << Utils::to_string(_glinfo.minorVersion) << "0 es " << std::endl;
if (_glinfo.noPerspective)
ss << "#extension GL_NV_shader_noperspective_interpolation : enable" << std::endl;
if (config.frameBufferEmulation.N64DepthCompare != 0) {
if (_glinfo.fragment_interlockNV)
ss << "#extension GL_NV_fragment_shader_interlock : enable" << std::endl
<< "layout(pixel_interlock_ordered) in;" << std::endl;
}
ss << "# define IN in" << std::endl
<< "# define OUT out" << std::endl
<< "# define texture2D texture" << std::endl;
@ -462,9 +471,19 @@ public:
} else {
std::stringstream ss;
ss << "#version " << Utils::to_string(_glinfo.majorVersion) << Utils::to_string(_glinfo.minorVersion) << "0 core " << std::endl;
if (_glinfo.imageTextures && _glinfo.majorVersion * 10 + _glinfo.minorVersion < 42) {
ss << "#extension GL_ARB_shader_image_load_store : enable" << std::endl
<< "#extension GL_ARB_shading_language_420pack : enable" << std::endl;
if (config.frameBufferEmulation.N64DepthCompare != 0) {
if (_glinfo.majorVersion * 10 + _glinfo.minorVersion < 42) {
ss << "#extension GL_ARB_shader_image_load_store : enable" << std::endl
<< "#extension GL_ARB_shading_language_420pack : enable" << std::endl;
}
if (_glinfo.fragment_interlock)
ss << "#extension GL_ARB_fragment_shader_interlock : enable" << std::endl
<< "layout(pixel_interlock_ordered) in;" << std::endl;
else if (_glinfo.fragment_interlockNV)
ss << "#extension GL_NV_fragment_shader_interlock : enable" << std::endl
<< "layout(pixel_interlock_ordered) in;" << std::endl;
else if (_glinfo.fragment_ordering)
ss << "#extension GL_INTEL_fragment_shader_ordering : enable" << std::endl;
}
ss << "# define IN in" << std::endl
<< "# define OUT out" << std::endl
@ -938,8 +957,8 @@ public:
if (config.frameBufferEmulation.N64DepthCompare != 0) {
m_part +=
"layout(binding = 2, r32f) highp uniform coherent image2D uDepthImageZ; \n"
"layout(binding = 3, r32f) highp uniform coherent image2D uDepthImageDeltaZ;\n"
"layout(binding = 2, r32f) highp uniform restrict image2D uDepthImageZ; \n"
"layout(binding = 3, r32f) highp uniform restrict image2D uDepthImageDeltaZ;\n"
"bool depth_compare(highp float curZ);\n"
"bool depth_render(highp float Z, highp float curZ);\n";
;
@ -1312,10 +1331,27 @@ public:
ShaderFragmentCallN64Depth(const opengl::GLInfo & _glinfo)
{
if (config.frameBufferEmulation.N64DepthCompare != 0) {
m_part =
" if (uRenderTarget != 0) { if (!depth_render(fragColor.r, fragDepth)) discard; } \n"
" else if (!depth_compare(fragDepth)) discard; \n"
;
m_part = " bool should_discard = false; \n";
if (_glinfo.fragment_interlock)
m_part += " beginInvocationInterlockARB(); \n";
else if (_glinfo.fragment_interlockNV)
m_part += " beginInvocationInterlockNV(); \n";
else if (_glinfo.fragment_ordering)
m_part += " beginFragmentShaderOrderingINTEL(); \n";
m_part +=
" if (uRenderTarget != 0) { if (!depth_render(fragColor.r, fragDepth)) should_discard = true; } \n"
" else if (!depth_compare(fragDepth)) should_discard = true; \n"
;
if (_glinfo.fragment_interlock)
m_part += " endInvocationInterlockARB(); \n";
else if (_glinfo.fragment_interlockNV)
m_part += " endInvocationInterlockNV(); \n";
m_part += " if (should_discard) discard; \n";
}
}
};
@ -1919,14 +1955,11 @@ public:
" imageStore(uDepthImageZ, coord, depthOutZ); \n"
" imageStore(uDepthImageDeltaZ, coord, depthOutDeltaZ);\n"
" } \n"
" memoryBarrierImage(); \n"
" if (uEnableDepthCompare != 0) \n"
" return bRes; \n"
" return true; \n"
"} \n"
;
if (!_glinfo.isGLESX && _glinfo.imageTextures && _glinfo.majorVersion * 10 + _glinfo.minorVersion < 43)
m_part = "#extension GL_ARB_compute_shader : enable \n" + m_part;
}
}
};
@ -1950,12 +1983,9 @@ public:
" highp vec4 depthOutDeltaZ = vec4(0.0, 1.0, 1.0, 1.0);\n"
" imageStore(uDepthImageZ,coord, depthOutZ); \n"
" imageStore(uDepthImageDeltaZ,coord, depthOutDeltaZ); \n"
" memoryBarrierImage(); \n"
" return true; \n"
"} \n"
;
if (!_glinfo.isGLESX && _glinfo.imageTextures && _glinfo.majorVersion * 10 + _glinfo.minorVersion < 43)
m_part = "#extension GL_ARB_compute_shader : enable \n" + m_part;
}
}
};

View File

@ -203,20 +203,8 @@ void BufferedDrawer::drawTriangles(const graphics::Context::DrawTriangleParamete
return;
}
if (config.frameBufferEmulation.N64DepthCompare == 0) {
glDrawRangeElementsBaseVertex(GLenum(_params.mode), 0, _params.verticesCount - 1, _params.elementsCount, GL_UNSIGNED_SHORT,
(u16*)nullptr + m_trisBuffers.ebo.pos - _params.elementsCount, m_trisBuffers.vbo.pos - _params.verticesCount);
return;
}
// Draw polygons one by one
const GLint eboStartPos = m_trisBuffers.ebo.pos - _params.elementsCount;
const GLint vboStartPos = m_trisBuffers.vbo.pos - _params.verticesCount;
for (GLuint i = 0; i < _params.elementsCount; i += 3) {
glMemoryBarrier(GL_SHADER_IMAGE_ACCESS_BARRIER_BIT);
glDrawRangeElementsBaseVertex(GLenum(_params.mode), 0, _params.verticesCount - 1, 3, GL_UNSIGNED_SHORT,
(u16*)nullptr + eboStartPos + i, vboStartPos);
}
glDrawRangeElementsBaseVertex(GLenum(_params.mode), 0, _params.verticesCount - 1, _params.elementsCount, GL_UNSIGNED_SHORT,
(u16*)nullptr + m_trisBuffers.ebo.pos - _params.elementsCount, m_trisBuffers.vbo.pos - _params.verticesCount);
}
void BufferedDrawer::drawLine(f32 _width, SPVertex * _vertices)

View File

@ -54,10 +54,18 @@ void GLInfo::init() {
Utils::isExtensionSupported(*this, "GL_ARB_compute_shader"))) && IS_GL_FUNCTION_VALID(glBindImageTexture);
msaa = true;
}
if (!imageTextures && config.frameBufferEmulation.N64DepthCompare != 0) {
config.frameBufferEmulation.N64DepthCompare = 0;
LOG(LOG_WARNING, "N64 depth compare will not work without Image Textures support provided in OpenGL >= 4.3 or GLES >= 3.1\n");
fragment_interlock = Utils::isExtensionSupported(*this, "GL_ARB_fragment_shader_interlock");
fragment_interlockNV = Utils::isExtensionSupported(*this, "GL_NV_fragment_shader_interlock") && !fragment_interlock;
fragment_ordering = Utils::isExtensionSupported(*this, "GL_INTEL_fragment_shader_ordering") && !fragment_interlock && !fragment_interlockNV;
if (config.frameBufferEmulation.N64DepthCompare != 0) {
if (!(imageTextures && (fragment_interlock || fragment_interlockNV || fragment_ordering))) {
config.frameBufferEmulation.N64DepthCompare = 0;
LOG(LOG_WARNING, "Your GPU does not support the extensions needed for N64 Depth Compare.\n");
}
}
if (isGLES2)
config.generalEmulation.enableFragmentDepthWrite = 0;

View File

@ -28,6 +28,9 @@ struct GLInfo {
bool fetch_depth = false;
bool texture_barrier = false;
bool texture_barrierNV = false;
bool fragment_interlock = false;
bool fragment_interlockNV = false;
bool fragment_ordering = false;
Renderer renderer = Renderer::Other;
void init();

View File

@ -98,9 +98,8 @@ namespace opengl {
#endif
}
Init2DTexStorage(CachedBindTexture* _bind, bool _imageTextures)
: m_bind(_bind)
, m_imageTextures(_imageTextures) {}
Init2DTexStorage(CachedBindTexture* _bind)
: m_bind(_bind) {}
void init2DTexture(const graphics::Context::InitTextureParams & _params) override
{
@ -125,10 +124,6 @@ namespace opengl {
GLenum(_params.dataType),
_params.data);
}
if (_params.ImageUnit.isValid() && m_imageTextures)
glBindImageTexture(GLuint(_params.ImageUnit), GLuint(_params.handle),
0, GL_FALSE, GL_FALSE, GL_READ_ONLY, GLuint(_params.internalFormat));
}
else {
m_bind->bind(_params.textureUnitIndex, graphics::textureTarget::TEXTURE_2D_MULTISAMPLE, _params.handle);
@ -152,7 +147,6 @@ namespace opengl {
private:
CachedBindTexture* m_bind;
bool m_imageTextures;
graphics::ObjectHandle m_handle;
};
@ -189,11 +183,6 @@ namespace opengl {
GLenum(_params.dataType),
_params.data);
}
if (_params.ImageUnit.isValid()) {
glBindImageTexture(GLuint(_params.ImageUnit), GLuint(_params.handle),
0, GL_FALSE, GL_FALSE, GL_READ_ONLY, GLuint(_params.internalFormat));
}
}
else {
glTexStorage2DMultisample(GLuint(_params.handle),
@ -220,9 +209,8 @@ namespace opengl {
class Update2DTexSubImage : public Update2DTexture
{
public:
Update2DTexSubImage(CachedBindTexture* _bind, bool _imageTextures)
: m_bind(_bind)
, m_imageTextures(_imageTextures) {}
Update2DTexSubImage(CachedBindTexture* _bind)
: m_bind(_bind) {}
void update2DTexture(const graphics::Context::UpdateTextureDataParams & _params) override
{
@ -237,15 +225,10 @@ namespace opengl {
GLuint(_params.format),
GLenum(_params.dataType),
_params.data);
if (_params.ImageUnit.isValid() && _params.internalFormat.isValid() && m_imageTextures)
glBindImageTexture(GLuint(_params.ImageUnit), GLuint(_params.handle),
0, GL_FALSE, GL_FALSE, GL_READ_ONLY, GLuint(_params.internalFormat));
}
private:
CachedBindTexture* m_bind;
bool m_imageTextures;
};
class Update2DTextureSubImage : public Update2DTexture
@ -270,11 +253,6 @@ namespace opengl {
GLuint(_params.format),
GLenum(_params.dataType),
_params.data);
if (_params.ImageUnit.isValid() && _params.internalFormat.isValid()) {
glBindImageTexture(GLuint(_params.ImageUnit), GLuint(_params.handle),
0, GL_FALSE, GL_FALSE, GL_READ_ONLY, GLuint(_params.internalFormat));
}
}
};
@ -399,7 +377,7 @@ namespace opengl {
return new Init2DTextureStorage;
if (Init2DTexStorage::Check(m_glInfo))
return new Init2DTexStorage(m_cachedFunctions.getCachedBindTexture(), m_glInfo.imageTextures);
return new Init2DTexStorage(m_cachedFunctions.getCachedBindTexture());
return new Init2DTexImage(m_cachedFunctions.getCachedBindTexture());
}
@ -409,7 +387,7 @@ namespace opengl {
if (Update2DTextureSubImage::Check(m_glInfo))
return new Update2DTextureSubImage;
return new Update2DTexSubImage(m_cachedFunctions.getCachedBindTexture(), m_glInfo.imageTextures);
return new Update2DTexSubImage(m_cachedFunctions.getCachedBindTexture());
}
Set2DTextureParameters * TextureManipulationObjectFactory::getSet2DTextureParameters() const

View File

@ -81,16 +81,7 @@ void UnbufferedDrawer::drawTriangles(const graphics::Context::DrawTriangleParame
return;
}
if (config.frameBufferEmulation.N64DepthCompare == 0) {
glDrawElements(GLenum(_params.mode), _params.elementsCount, GL_UNSIGNED_SHORT, _params.elements);
return;
}
// Draw polygons one by one
for (GLuint i = 0; i < _params.elementsCount; i += 3) {
glMemoryBarrier(GL_SHADER_IMAGE_ACCESS_BARRIER_BIT);
glDrawElements(GLenum(_params.mode), 3, GL_UNSIGNED_SHORT, (u16*)_params.elements + i);
}
glDrawElements(GLenum(_params.mode), _params.elementsCount, GL_UNSIGNED_SHORT, _params.elements);
}
void UnbufferedDrawer::drawRects(const graphics::Context::DrawRectParameters & _params)

View File

@ -74,8 +74,6 @@ namespace graphics {
}
namespace textureImageUnits {
extern ImageUnitParam Zlut;
extern ImageUnitParam Tlut;
extern ImageUnitParam DepthZ;
extern ImageUnitParam DepthDeltaZ;
}