Home | History | Annotate | Download | only in functional
      1 /*-------------------------------------------------------------------------
      2  * drawElements Quality Program OpenGL ES 3.0 Module
      3  * -------------------------------------------------
      4  *
      5  * Copyright 2014 The Android Open Source Project
      6  *
      7  * Licensed under the Apache License, Version 2.0 (the "License");
      8  * you may not use this file except in compliance with the License.
      9  * You may obtain a copy of the License at
     10  *
     11  *      http://www.apache.org/licenses/LICENSE-2.0
     12  *
     13  * Unless required by applicable law or agreed to in writing, software
     14  * distributed under the License is distributed on an "AS IS" BASIS,
     15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     16  * See the License for the specific language governing permissions and
     17  * limitations under the License.
     18  *
     19  *//*!
     20  * \file
     21  * \brief FBO depthbuffer tests.
     22  *//*--------------------------------------------------------------------*/
     23 
     24 #include "es3fFboDepthbufferTests.hpp"
     25 #include "es3fFboTestCase.hpp"
     26 #include "es3fFboTestUtil.hpp"
     27 #include "gluTextureUtil.hpp"
     28 #include "tcuTextureUtil.hpp"
     29 #include "sglrContextUtil.hpp"
     30 #include "glwEnums.hpp"
     31 
     32 namespace deqp
     33 {
     34 namespace gles3
     35 {
     36 namespace Functional
     37 {
     38 
     39 using std::string;
     40 using tcu::Vec2;
     41 using tcu::Vec3;
     42 using tcu::Vec4;
     43 using tcu::IVec2;
     44 using tcu::IVec3;
     45 using tcu::IVec4;
     46 using tcu::UVec4;
     47 using namespace FboTestUtil;
     48 
     49 class BasicFboDepthCase : public FboTestCase
     50 {
     51 public:
     52 	BasicFboDepthCase (Context& context, const char* name, const char* desc, deUint32 format, int width, int height)
     53 		: FboTestCase	(context, name, desc)
     54 		, m_format		(format)
     55 		, m_width		(width)
     56 		, m_height		(height)
     57 	{
     58 	}
     59 
     60 protected:
     61 	void preCheck (void)
     62 	{
     63 		checkFormatSupport(m_format);
     64 	}
     65 
     66 	void render (tcu::Surface& dst)
     67 	{
     68 		const deUint32	colorFormat		= GL_RGBA8;
     69 		deUint32		fbo				= 0;
     70 		deUint32		colorRbo		= 0;
     71 		deUint32		depthRbo		= 0;
     72 		GradientShader	gradShader		(glu::TYPE_FLOAT_VEC4);
     73 		Texture2DShader	texShader		(DataTypes() << glu::TYPE_SAMPLER_2D, glu::TYPE_FLOAT_VEC4);
     74 		deUint32		gradShaderID	= getCurrentContext()->createProgram(&gradShader);
     75 		deUint32		texShaderID		= getCurrentContext()->createProgram(&texShader);
     76 		float			clearDepth		= 1.0f;
     77 
     78 		// Setup shaders
     79 		gradShader.setGradient(*getCurrentContext(), gradShaderID, tcu::Vec4(0.0f), tcu::Vec4(1.0f));
     80 		texShader.setUniforms (*getCurrentContext(), texShaderID);
     81 
     82 		// Setup FBO
     83 
     84 		glGenFramebuffers(1, &fbo);
     85 		glGenRenderbuffers(1, &colorRbo);
     86 		glGenRenderbuffers(1, &depthRbo);
     87 
     88 		glBindRenderbuffer(GL_RENDERBUFFER, colorRbo);
     89 		glRenderbufferStorage(GL_RENDERBUFFER, colorFormat, m_width, m_height);
     90 
     91 		glBindRenderbuffer(GL_RENDERBUFFER, depthRbo);
     92 		glRenderbufferStorage(GL_RENDERBUFFER, m_format, m_width, m_height);
     93 
     94 		glBindFramebuffer(GL_FRAMEBUFFER, fbo);
     95 		glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER, colorRbo);
     96 		glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, depthRbo);
     97 		checkError();
     98 		checkFramebufferStatus(GL_FRAMEBUFFER);
     99 
    100 		glViewport(0, 0, m_width, m_height);
    101 
    102 		// Clear depth to 1
    103 		glClearBufferfv(GL_DEPTH, 0, &clearDepth);
    104 
    105 		// Render gradient with depth = [-1..1]
    106 		glEnable(GL_DEPTH_TEST);
    107 		sglr::drawQuad(*getCurrentContext(), gradShaderID, Vec3(-1.0f, -1.0f, -1.0f), Vec3(1.0f, 1.0f, 1.0f));
    108 
    109 		// Render grid pattern with depth = 0
    110 		{
    111 			const deUint32		format		= GL_RGBA;
    112 			const deUint32		dataType	= GL_UNSIGNED_BYTE;
    113 			const int			texW		= 128;
    114 			const int			texH		= 128;
    115 			deUint32			gridTex		= 0;
    116 			tcu::TextureLevel	data		(glu::mapGLTransferFormat(format, dataType), texW, texH, 1);
    117 
    118 			tcu::fillWithGrid(data.getAccess(), 8, Vec4(0.2f, 0.7f, 0.1f, 1.0f), Vec4(0.7f, 0.1f, 0.5f, 0.8f));
    119 
    120 			glGenTextures(1, &gridTex);
    121 			glBindTexture(GL_TEXTURE_2D, gridTex);
    122 			glTexParameteri(GL_TEXTURE_2D,	GL_TEXTURE_WRAP_S,		GL_CLAMP_TO_EDGE);
    123 			glTexParameteri(GL_TEXTURE_2D,	GL_TEXTURE_WRAP_T,		GL_CLAMP_TO_EDGE);
    124 			glTexParameteri(GL_TEXTURE_2D,	GL_TEXTURE_MIN_FILTER,	GL_LINEAR);
    125 			glTexParameteri(GL_TEXTURE_2D,	GL_TEXTURE_MAG_FILTER,	GL_LINEAR);
    126 			glTexImage2D(GL_TEXTURE_2D, 0, format, texW, texH, 0, format, dataType, data.getAccess().getDataPtr());
    127 
    128 			sglr::drawQuad(*getCurrentContext(), texShaderID, Vec3(-1.0f, -1.0f, 0.0f), Vec3(1.0f, 1.0f, 0.0f));
    129 		}
    130 
    131 		// Read results.
    132 		readPixels(dst, 0, 0, m_width, m_height, glu::mapGLInternalFormat(colorFormat), Vec4(1.0f), Vec4(0.0f));
    133 	}
    134 
    135 private:
    136 	deUint32		m_format;
    137 	int				m_width;
    138 	int				m_height;
    139 };
    140 
    141 class DepthWriteClampCase : public FboTestCase
    142 {
    143 public:
    144 	DepthWriteClampCase (Context& context, const char* name, const char* desc, deUint32 format, int width, int height)
    145 		: FboTestCase	(context, name, desc)
    146 		, m_format		(format)
    147 		, m_width		(width)
    148 		, m_height		(height)
    149 	{
    150 	}
    151 
    152 protected:
    153 	void preCheck (void)
    154 	{
    155 		checkFormatSupport(m_format);
    156 	}
    157 
    158 	void render (tcu::Surface& dst)
    159 	{
    160 		const deUint32			colorFormat			= GL_RGBA8;
    161 		deUint32				fbo					= 0;
    162 		deUint32				colorRbo			= 0;
    163 		deUint32				depthTexture		= 0;
    164 		glu::TransferFormat		transferFmt			= glu::getTransferFormat(glu::mapGLInternalFormat(m_format));
    165 
    166 		DepthGradientShader		depthGradShader		(glu::TYPE_FLOAT_VEC4);
    167 		const deUint32			depthGradShaderID	= getCurrentContext()->createProgram(&depthGradShader);
    168 		const float				clearDepth			= 1.0f;
    169 		const tcu::Vec4			red					(1.0, 0.0, 0.0, 1.0);
    170 		const tcu::Vec4			green				(0.0, 1.0, 0.0, 1.0);
    171 
    172 		// Setup FBO
    173 
    174 		glGenFramebuffers(1, &fbo);
    175 		glGenRenderbuffers(1, &colorRbo);
    176 		glGenTextures(1, &depthTexture);
    177 
    178 		glBindRenderbuffer(GL_RENDERBUFFER, colorRbo);
    179 		glRenderbufferStorage(GL_RENDERBUFFER, colorFormat, m_width, m_height);
    180 
    181 		glBindTexture(GL_TEXTURE_2D, depthTexture);
    182 		glTexImage2D(GL_TEXTURE_2D, 0, m_format, m_width, m_height, 0, transferFmt.format, transferFmt.dataType, DE_NULL);
    183 		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
    184 		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
    185 
    186 		glBindFramebuffer(GL_FRAMEBUFFER, fbo);
    187 		glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER, colorRbo);
    188 		glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, depthTexture, 0);
    189 		checkError();
    190 		checkFramebufferStatus(GL_FRAMEBUFFER);
    191 
    192 		glViewport(0, 0, m_width, m_height);
    193 
    194 		// Clear depth to 1
    195 		glClearBufferfv(GL_DEPTH, 0, &clearDepth);
    196 
    197 		// Test that invalid values are not written to the depth buffer
    198 
    199 		// Render green quad, depth gradient = [-1..2]
    200 		glEnable(GL_DEPTH_TEST);
    201 		glDepthFunc(GL_ALWAYS);
    202 
    203 		depthGradShader.setUniforms(*getCurrentContext(), depthGradShaderID, -1.0f, 2.0f, green);
    204 		sglr::drawQuad(*getCurrentContext(), depthGradShaderID, Vec3(-1.0f, -1.0f, -1.0f), Vec3(1.0f, 1.0f, 1.0f));
    205 		glDepthMask(GL_FALSE);
    206 
    207 		// Test if any fragment has greater depth than 1; there should be none
    208 		glDepthFunc(GL_LESS); // (1 < depth) ?
    209 		depthGradShader.setUniforms(*getCurrentContext(), depthGradShaderID, 1.0f, 1.0f, red);
    210 		sglr::drawQuad(*getCurrentContext(), depthGradShaderID, Vec3(-1.0f, -1.0f, -1.0f), Vec3(1.0f, 1.0f, 1.0f));
    211 
    212 		// Test if any fragment has smaller depth than 0; there should be none
    213 		glDepthFunc(GL_GREATER); // (0 > depth) ?
    214 		depthGradShader.setUniforms(*getCurrentContext(), depthGradShaderID, 0.0f, 0.0f, red);
    215 		sglr::drawQuad(*getCurrentContext(), depthGradShaderID, Vec3(-1.0f, -1.0f, -1.0f), Vec3(1.0f, 1.0f, 1.0f));
    216 
    217 		// Read results.
    218 		readPixels(dst, 0, 0, m_width, m_height, glu::mapGLInternalFormat(colorFormat), Vec4(1.0f), Vec4(0.0f));
    219 	}
    220 
    221 private:
    222 	const deUint32		m_format;
    223 	const int			m_width;
    224 	const int			m_height;
    225 };
    226 
    227 class DepthTestClampCase : public FboTestCase
    228 {
    229 public:
    230 	DepthTestClampCase (Context& context, const char* name, const char* desc, deUint32 format, int width, int height)
    231 		: FboTestCase	(context, name, desc)
    232 		, m_format		(format)
    233 		, m_width		(width)
    234 		, m_height		(height)
    235 	{
    236 	}
    237 
    238 protected:
    239 	void preCheck (void)
    240 	{
    241 		checkFormatSupport(m_format);
    242 	}
    243 
    244 	void render (tcu::Surface& dst)
    245 	{
    246 		const deUint32			colorFormat			= GL_RGBA8;
    247 		deUint32				fbo					= 0;
    248 		deUint32				colorRbo			= 0;
    249 		deUint32				depthTexture		= 0;
    250 		glu::TransferFormat		transferFmt			= glu::getTransferFormat(glu::mapGLInternalFormat(m_format));
    251 
    252 		DepthGradientShader		depthGradShader		(glu::TYPE_FLOAT_VEC4);
    253 		const deUint32			depthGradShaderID	= getCurrentContext()->createProgram(&depthGradShader);
    254 		const float				clearDepth			= 1.0f;
    255 		const tcu::Vec4			yellow				(1.0, 1.0, 0.0, 1.0);
    256 		const tcu::Vec4			green				(0.0, 1.0, 0.0, 1.0);
    257 
    258 		// Setup FBO
    259 
    260 		glGenFramebuffers(1, &fbo);
    261 		glGenRenderbuffers(1, &colorRbo);
    262 		glGenTextures(1, &depthTexture);
    263 
    264 		glBindRenderbuffer(GL_RENDERBUFFER, colorRbo);
    265 		glRenderbufferStorage(GL_RENDERBUFFER, colorFormat, m_width, m_height);
    266 
    267 		glBindTexture(GL_TEXTURE_2D, depthTexture);
    268 		glTexImage2D(GL_TEXTURE_2D, 0, m_format, m_width, m_height, 0, transferFmt.format, transferFmt.dataType, DE_NULL);
    269 		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
    270 		glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
    271 
    272 		glBindFramebuffer(GL_FRAMEBUFFER, fbo);
    273 		glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER, colorRbo);
    274 		glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, depthTexture, 0);
    275 		checkError();
    276 		checkFramebufferStatus(GL_FRAMEBUFFER);
    277 
    278 		glViewport(0, 0, m_width, m_height);
    279 
    280 		// Clear depth to 1
    281 		glClearBufferfv(GL_DEPTH, 0, &clearDepth);
    282 
    283 		// Test values used in depth test are clamped
    284 
    285 		// Render green quad, depth gradient = [-1..2]
    286 		glEnable(GL_DEPTH_TEST);
    287 		glDepthFunc(GL_ALWAYS);
    288 
    289 		depthGradShader.setUniforms(*getCurrentContext(), depthGradShaderID, -1.0f, 2.0f, green);
    290 		sglr::drawQuad(*getCurrentContext(), depthGradShaderID, Vec3(-1.0f, -1.0f, -1.0f), Vec3(1.0f, 1.0f, 1.0f));
    291 
    292 		// Render yellow quad, depth gradient = [-0.5..3]. Gradients have equal values only outside [0, 1] range due to clamping
    293 		glDepthFunc(GL_EQUAL);
    294 		depthGradShader.setUniforms(*getCurrentContext(), depthGradShaderID, -0.5f, 3.0f, yellow);
    295 		sglr::drawQuad(*getCurrentContext(), depthGradShaderID, Vec3(-1.0f, -1.0f, -1.0f), Vec3(1.0f, 1.0f, 1.0f));
    296 
    297 		// Read results.
    298 		readPixels(dst, 0, 0, m_width, m_height, glu::mapGLInternalFormat(colorFormat), Vec4(1.0f), Vec4(0.0f));
    299 	}
    300 
    301 private:
    302 	const deUint32		m_format;
    303 	const int			m_width;
    304 	const int			m_height;
    305 };
    306 
    307 FboDepthTests::FboDepthTests (Context& context)
    308 	: TestCaseGroup(context, "depth", "Depth tests")
    309 {
    310 }
    311 
    312 FboDepthTests::~FboDepthTests (void)
    313 {
    314 }
    315 
    316 void FboDepthTests::init (void)
    317 {
    318 	static const deUint32 depthFormats[] =
    319 	{
    320 		GL_DEPTH_COMPONENT32F,
    321 		GL_DEPTH_COMPONENT24,
    322 		GL_DEPTH_COMPONENT16,
    323 		GL_DEPTH32F_STENCIL8,
    324 		GL_DEPTH24_STENCIL8
    325 	};
    326 
    327 	// .basic
    328 	{
    329 		tcu::TestCaseGroup* basicGroup = new tcu::TestCaseGroup(m_testCtx, "basic", "Basic depth tests");
    330 		addChild(basicGroup);
    331 
    332 		for (int fmtNdx = 0; fmtNdx < DE_LENGTH_OF_ARRAY(depthFormats); fmtNdx++)
    333 			basicGroup->addChild(new BasicFboDepthCase(m_context, getFormatName(depthFormats[fmtNdx]), "", depthFormats[fmtNdx], 119, 127));
    334 	}
    335 
    336 	// .depth_write_clamp
    337 	{
    338 		tcu::TestCaseGroup* depthClampGroup = new tcu::TestCaseGroup(m_testCtx, "depth_write_clamp", "Depth write clamping tests");
    339 		addChild(depthClampGroup);
    340 
    341 		for (int fmtNdx = 0; fmtNdx < DE_LENGTH_OF_ARRAY(depthFormats); fmtNdx++)
    342 			depthClampGroup->addChild(new DepthWriteClampCase(m_context, getFormatName(depthFormats[fmtNdx]), "", depthFormats[fmtNdx], 119, 127));
    343 	}
    344 
    345 	// .depth_test_clamp
    346 	{
    347 		tcu::TestCaseGroup* depthClampGroup = new tcu::TestCaseGroup(m_testCtx, "depth_test_clamp", "Depth test value clamping tests");
    348 		addChild(depthClampGroup);
    349 
    350 		for (int fmtNdx = 0; fmtNdx < DE_LENGTH_OF_ARRAY(depthFormats); fmtNdx++)
    351 			depthClampGroup->addChild(new DepthTestClampCase(m_context, getFormatName(depthFormats[fmtNdx]), "", depthFormats[fmtNdx], 119, 127));
    352 	}
    353 }
    354 
    355 } // Functional
    356 } // gles3
    357 } // deqp
    358