Home | History | Annotate | Download | only in functional
      1 /*-------------------------------------------------------------------------
      2  * drawElements Quality Program OpenGL ES 2.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 Light amount test.
     22  *//*--------------------------------------------------------------------*/
     23 
     24 #include "es2fLightAmountTest.hpp"
     25 #include "tcuStringTemplate.hpp"
     26 #include "gluDefs.hpp"
     27 #include "gluShaderProgram.hpp"
     28 #include "tcuTestLog.hpp"
     29 #include "deStringUtil.hpp"
     30 #include "deInt32.h"
     31 #include "deRandom.h"
     32 
     33 #include <stdio.h>
     34 #include <vector>
     35 
     36 #include "glw.h"
     37 
     38 using namespace std;
     39 
     40 namespace deqp
     41 {
     42 namespace gles2
     43 {
     44 namespace Functional
     45 {
     46 
     47 const char* s_noLightsVertexShader =
     48 	"uniform mat4 u_modelviewMatrix;\n"
     49 	"uniform mat4 u_modelviewProjectionMatrix;\n"
     50 	"uniform mat3 u_normalMatrix;\n"
     51 	"\n"
     52 	"attribute vec4 a_position;\n"
     53 	"attribute vec3 a_normal;\n"
     54 	"\n"
     55 	"varying vec3 v_color;\n"
     56 	"\n"
     57 	"void main()\n"
     58 	"{\n"
     59 	"	v_color = vec3(0.0);\n"
     60 	"	gl_Position = u_modelviewProjectionMatrix * a_position;\n"
     61 	"}\n"
     62 ;
     63 
     64 const char* s_vertexShaderTemplate =
     65 	"struct Light\n"
     66 	"{\n"
     67 	"	vec3	position;\n"
     68 	"	vec3	diffuse;\n"
     69 	"	vec3	specular;\n"
     70 	"	vec3	attenuation;\n"
     71 	"};\n"
     72 	"uniform Light u_lights[${NUM_DIR_LIGHTS} + ${NUM_OMNI_LIGHTS}];\n"
     73 	"uniform mat4 u_modelviewMatrix;\n"
     74 	"uniform mat4 u_modelviewProjectionMatrix;\n"
     75 	"uniform mat3 u_normalMatrix;\n"
     76 	"\n"
     77 	"attribute vec4 a_position;\n"
     78 	"attribute vec3 a_normal;\n"
     79 	"\n"
     80 	"varying vec3 v_color;\n"
     81 	"\n"
     82 	"float computeAttenuation(vec3 dirToLight, vec3 attenuation)\n"
     83 	"{\n"
     84 	"	float dist = length(dirToLight);\n"
     85 	"	return 1.0 / (attenuation.x + attenuation.y*dist + attenuation.z*dist*dist);\n"
     86 	"}\n"
     87 	"\n"
     88 	"vec3 computeDirLight(int ndx, vec3 position, vec3 normal)\n"
     89 	"{\n"
     90 	"	Light light = u_lights[ndx];\n"
     91 	"	float cosAngle = dot(light.position, normal);\n"
     92 	"	return cosAngle * light.diffuse;\n"
     93 	"}\n"
     94 	"\n"
     95 	"vec3 computeOmniLight(int ndx, vec3 position, vec3 normal)\n"
     96 	"{\n"
     97 	"	Light light = u_lights[ndx];\n"
     98 	"	vec3 dirToLight = light.position - position;\n"
     99 	"	float cosAngle = dot(normalize(dirToLight), normal);\n"
    100 	"	float atten = computeAttenuation(dirToLight, light.attenuation);\n"
    101 	"	return atten * cosAngle * light.diffuse;\n"
    102 	"}\n"
    103 	"\n"
    104 	"void main()\n"
    105 	"{\n"
    106 	"	vec3 lightSpacePos = vec3(u_modelviewMatrix * a_position);\n"
    107 	"	vec3 lightNormal = normalize(u_normalMatrix * a_normal);\n"
    108 	"	vec3 color = vec3(0.0);\n"
    109 	"	for (int i = 0; i < ${NUM_DIR_LIGHTS}; i++)\n"
    110 	"		color += computeDirLight(i, lightSpacePos, lightNormal);\n"
    111 	"	for (int i = 0; i < ${NUM_OMNI_LIGHTS}; i++)\n"
    112 	"		color += computeOmniLight(${NUM_DIR_LIGHTS}+i, lightSpacePos, lightNormal);\n"
    113 	"	v_color = color;\n"
    114 	"	gl_Position = u_modelviewProjectionMatrix * a_position;\n"
    115 	"}\n"
    116 ;
    117 
    118 const char* s_fragmentShaderTemplate =
    119 	"varying highp vec3 v_color;\n"
    120 	"\n"
    121 	"void main()\n"
    122 	"{\n"
    123 	"	gl_FragColor = vec4(v_color, 1.0);\n"
    124 	"}\n"
    125 	;
    126 
    127 class LightAmountCase : public TestCase
    128 {
    129 public:
    130 	LightAmountCase(Context&  context, const char* name, int numDirectionalLights, int numOmniLights, int numSpotLights)
    131 		: TestCase(context, name, name)
    132 		, m_numDirectionalLights	(numDirectionalLights)
    133 		, m_numOmniLights			(numOmniLights)
    134 		, m_numSpotLights			(numSpotLights)
    135 	{
    136 	}
    137 
    138 	virtual IterateResult	iterate		(void);
    139 
    140 private:
    141 	int				m_numDirectionalLights;
    142 	int				m_numOmniLights;
    143 	int				m_numSpotLights;
    144 };
    145 
    146 TestCase::IterateResult LightAmountCase::iterate (void)
    147 {
    148 	GLU_CHECK_MSG("LightAmountTest::iterate() begin");
    149 
    150 	string vertexShaderSource;
    151 	string fragmentShaderSource;
    152 
    153 	// Fill in shader template parameters.
    154 	{
    155 		bool hasAnyLights = ((m_numDirectionalLights + m_numOmniLights + m_numSpotLights) != 0);
    156 
    157 		tcu::StringTemplate vertexTemplate(hasAnyLights ? s_vertexShaderTemplate : s_noLightsVertexShader);
    158 		tcu::StringTemplate fragmentTemplate(s_fragmentShaderTemplate);
    159 
    160 		map<string, string> params;
    161 		params.insert(pair<string, string>("NUM_DIR_LIGHTS", de::toString(m_numDirectionalLights)));
    162 		params.insert(pair<string, string>("NUM_OMNI_LIGHTS", de::toString(m_numOmniLights)));
    163 		params.insert(pair<string, string>("NUM_SPOT_LIGHTS", de::toString(m_numSpotLights)));
    164 
    165 		vertexShaderSource		= vertexTemplate.specialize(params);
    166 		fragmentShaderSource	= fragmentTemplate.specialize(params);
    167 	}
    168 
    169 	// Create shader and program objects.
    170 	glu::ShaderProgram program(m_context.getRenderContext(), glu::makeVtxFragSources(vertexShaderSource, fragmentShaderSource));
    171 	m_testCtx.getLog() << program;
    172 
    173 	// Draw something? Check results?
    174 	glUseProgram(program.getProgram());
    175 
    176 	bool testOk = program.isOk();
    177 
    178 	GLU_CHECK_MSG("LightAmountTest::iterate() end");
    179 
    180 	m_testCtx.setTestResult(testOk ? QP_TEST_RESULT_PASS : QP_TEST_RESULT_FAIL, testOk ? "Pass" : "Fail");
    181 	return TestCase::STOP;
    182 }
    183 
    184 //
    185 
    186 LightAmountTest::LightAmountTest (Context& context) : TestCaseGroup(context, "light_amount", "Light Amount Stress Tests")
    187 {
    188 }
    189 
    190 LightAmountTest::~LightAmountTest (void)
    191 {
    192 }
    193 
    194 void LightAmountTest::init (void)
    195 {
    196 	//										name				dir,	omni,	spot
    197 	addChild(new LightAmountCase(m_context, "none",				0,		0,		0	));
    198 	addChild(new LightAmountCase(m_context, "1dir",				1,		0,		0	));
    199 	addChild(new LightAmountCase(m_context, "2dir",				2,		0,		0	));
    200 	addChild(new LightAmountCase(m_context, "4dir",				4,		0,		0	));
    201 	addChild(new LightAmountCase(m_context, "6dir",				6,		0,		0	));
    202 	addChild(new LightAmountCase(m_context, "8dir",				8,		0,		0	));
    203 	addChild(new LightAmountCase(m_context, "10dir",			10,		0,		0	));
    204 	addChild(new LightAmountCase(m_context, "12dir",			12,		0,		0	));
    205 	addChild(new LightAmountCase(m_context, "14dir",			14,		0,		0	));
    206 	addChild(new LightAmountCase(m_context, "16dir",			16,		0,		0	));
    207 	addChild(new LightAmountCase(m_context, "1omni",			0,		1,		0	));
    208 	addChild(new LightAmountCase(m_context, "2omni",			0,		2,		0	));
    209 	addChild(new LightAmountCase(m_context, "4omni",			0,		4,		0	));
    210 	addChild(new LightAmountCase(m_context, "6omni",			0,		6,		0	));
    211 	addChild(new LightAmountCase(m_context, "8omni",			0,		8,		0	));
    212 	addChild(new LightAmountCase(m_context, "10omni",			0,		10,		0	));
    213 	addChild(new LightAmountCase(m_context, "12omni",			0,		12,		0	));
    214 	addChild(new LightAmountCase(m_context, "14omni",			0,		14,		0	));
    215 	addChild(new LightAmountCase(m_context, "16omni",			0,		16,		0	));
    216 //	addChild(new LightAmountCase(m_context, "1spot",			0,		0,		1	));
    217 //	addChild(new LightAmountCase(m_context, "2spot",			0,		0,		2	));
    218 //	addChild(new LightAmountCase(m_context, "4spot",			0,		0,		4	));
    219 //	addChild(new LightAmountCase(m_context, "6spot",			0,		0,		6	));
    220 //	addChild(new LightAmountCase(m_context, "8spot",			0,		0,		8	));
    221 //	addChild(new LightAmountCase(m_context, "1dir_1omni",		1,		1,		0	));
    222 //	addChild(new LightAmountCase(m_context, "2dir_2omni",		2,		2,		0	));
    223 //	addChild(new LightAmountCase(m_context, "4dir_4omni",		4,		4,		0	));
    224 //	addChild(new LightAmountCase(m_context, "1dir_1spot",		1,		0,		1	));
    225 //	addChild(new LightAmountCase(m_context, "2dir_2spot",		2,		0,		2	));
    226 //	addChild(new LightAmountCase(m_context, "4dir_4spot",		4,		0,		4	));
    227 //	addChild(new LightAmountCase(m_context, "1omni_1spot",		0,		1,		1	));
    228 //	addChild(new LightAmountCase(m_context, "2omni_2spot",		0,		2,		2	));
    229 //	addChild(new LightAmountCase(m_context, "4omni_4spot",		0,		4,		4	));
    230 //	addChild(new LightAmountCase(m_context, "1dir_1omni_1spot",	1,		1,		1	));
    231 //	addChild(new LightAmountCase(m_context, "2dir_2omni_2spot",	2,		2,		2	));
    232 //	addChild(new LightAmountCase(m_context, "4dir_2omni_2spot",	4,		2,		2	));
    233 //	addChild(new LightAmountCase(m_context, "2dir_4omni_2spot",	2,		4,		2	));
    234 //	addChild(new LightAmountCase(m_context, "2dir_2omni_4spot",	2,		2,		4	));
    235 //	addChild(new LightAmountCase(m_context, "4dir_4omni_4spot",	4,		4,		4	));
    236 }
    237 
    238 } // Functional
    239 } // gles2
    240 } // deqp
    241