blob: a99416e527909407b521ad296f78eddf29cccdc8 [file] [log] [blame]
Geoff Lang95663912015-04-02 15:54:45 -04001#include "ANGLETest.h"
2
3// Use this to select which configurations (e.g. which renderer, which GLES major version) these tests should be run against.
Geoff Lang8a6f19d2015-04-02 15:57:55 -04004ANGLE_TYPED_TEST_CASE(FramebufferRenderMipmapTest, ES2_D3D9, ES2_D3D11, ES3_D3D11, ES2_OPENGL, ES3_OPENGL);
Geoff Lang95663912015-04-02 15:54:45 -04005
6template<typename T>
7class FramebufferRenderMipmapTest : public ANGLETest
8{
9protected:
10 FramebufferRenderMipmapTest() : ANGLETest(T::GetGlesMajorVersion(), T::GetPlatform())
11 {
12 setWindowWidth(256);
13 setWindowHeight(256);
14 setConfigRedBits(8);
15 setConfigGreenBits(8);
16 setConfigBlueBits(8);
17 setConfigAlphaBits(8);
18 }
19
20 virtual void SetUp()
21 {
22 ANGLETest::SetUp();
23
24 const std::string vsSource = SHADER_SOURCE
25 (
26 attribute highp vec4 position;
27 void main(void)
28 {
29 gl_Position = position;
30 }
31 );
32
33 const std::string fsSource = SHADER_SOURCE
34 (
35 uniform highp vec4 color;
36 void main(void)
37 {
38 gl_FragColor = color;
39 }
40 );
41
42 mProgram = CompileProgram(vsSource, fsSource);
43 if (mProgram == 0)
44 {
45 FAIL() << "shader compilation failed.";
46 }
47
48 mColorLocation = glGetUniformLocation(mProgram, "color");
49
50 glUseProgram(mProgram);
51
52 glClearColor(0, 0, 0, 0);
53 glClearDepthf(0.0);
54 glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
55
56 glEnable(GL_BLEND);
57 glDisable(GL_DEPTH_TEST);
58
59 ASSERT_GL_NO_ERROR();
60 }
61
62 virtual void TearDown()
63 {
64 glDeleteProgram(mProgram);
65
66 ANGLETest::TearDown();
67 }
68
69 GLuint mProgram;
70 GLint mColorLocation;
71};
72
73// Validate that if we are in ES3 or GL_OES_fbo_render_mipmap exists, there are no validation errors
74// when using a non-zero level in glFramebufferTexture2D.
75TYPED_TEST(FramebufferRenderMipmapTest, Validation)
76{
77 bool renderToMipmapSupported = extensionEnabled("GL_OES_fbo_render_mipmap") || getClientVersion() > 2;
78
79 GLuint tex = 0;
80 glGenTextures(1, &tex);
81 glBindTexture(GL_TEXTURE_2D, tex);
82
83 const size_t levels = 5;
84 for (size_t i = 0; i < levels; i++)
85 {
86 size_t size = 1 << ((levels - 1) - i);
87 glTexImage2D(GL_TEXTURE_2D, i, GL_RGBA, size, size, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL);
88 }
89
90 EXPECT_GL_NO_ERROR();
91
92 GLuint fbo = 0;
93 glGenFramebuffers(1, &fbo);
94 glBindFramebuffer(GL_FRAMEBUFFER, fbo);
95 EXPECT_GL_NO_ERROR();
96
97 for (size_t i = 0; i < levels; i++)
98 {
99 glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, tex, i);
100
101 if (i > 0 && !renderToMipmapSupported)
102 {
103 EXPECT_GL_ERROR(GL_INVALID_VALUE);
104 }
105 else
106 {
107 EXPECT_GL_NO_ERROR();
108 EXPECT_EQ(glCheckFramebufferStatus(GL_FRAMEBUFFER), GLenum(GL_FRAMEBUFFER_COMPLETE));
109 }
110 }
111
112 glDeleteFramebuffers(1, &fbo);
113 glDeleteTextures(1, &tex);
114}
115
116// Render to various levels of a texture and check that they have the correct color data via ReadPixels
117TYPED_TEST(FramebufferRenderMipmapTest, RenderToMipmap)
118{
119 bool renderToMipmapSupported = extensionEnabled("GL_OES_fbo_render_mipmap") || getClientVersion() > 2;
120 if (!renderToMipmapSupported)
121 {
122 std::cout << "Test skipped because GL_OES_fbo_render_mipmap or ES3 is not available." << std::endl;
123 return;
124 }
125
126 const GLfloat levelColors[] =
127 {
128 1.0f, 0.0f, 0.0f, 1.0f,
129 0.0f, 1.0f, 0.0f, 1.0f,
130 0.0f, 0.0f, 1.0f, 1.0f,
131 1.0f, 1.0f, 0.0f, 1.0f,
132 1.0f, 0.0f, 1.0f, 1.0f,
133 0.0f, 1.0f, 1.0f, 1.0f,
134 };
135 const size_t testLevels = ArraySize(levelColors) / 4;
136
137 GLuint tex = 0;
138 glGenTextures(1, &tex);
139 glBindTexture(GL_TEXTURE_2D, tex);
140
141 for (size_t i = 0; i < testLevels; i++)
142 {
143 size_t size = 1 << ((testLevels - 1) - i);
144 glTexImage2D(GL_TEXTURE_2D, i, GL_RGBA, size, size, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL);
145 }
146
147 EXPECT_GL_NO_ERROR();
148
149 GLuint fbo = 0;
150 glGenFramebuffers(1, &fbo);
151 glBindFramebuffer(GL_FRAMEBUFFER, fbo);
152 EXPECT_GL_NO_ERROR();
153
154 // Render to the levels of the texture with different colors
155 for (size_t i = 0; i < testLevels; i++)
156 {
157 glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, tex, i);
158 EXPECT_GL_NO_ERROR();
159
160 glUseProgram(mProgram);
161 glUniform4fv(mColorLocation, 1, levelColors + (i * 4));
162
163 drawQuad(mProgram, "position", 0.5f);
164 EXPECT_GL_NO_ERROR();
165 }
166
167 // Test that the levels of the texture are correct
168 for (size_t i = 0; i < testLevels; i++)
169 {
170 glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, tex, i);
171 EXPECT_GL_NO_ERROR();
172
173 const GLfloat *color = levelColors + (i * 4);
174 EXPECT_PIXEL_EQ(0, 0, color[0] * 255, color[1] * 255, color[2] * 255, color[3] * 255);
175 }
176
177 glDeleteFramebuffers(1, &fbo);
178 glDeleteTextures(1, &tex);
179
180 EXPECT_GL_NO_ERROR();
181}