| // |
| // Copyright 2015 The ANGLE Project Authors. All rights reserved. |
| // Use of this source code is governed by a BSD-style license that can be |
| // found in the LICENSE file. |
| // |
| |
| // IndexBufferOffsetTest.cpp: Test glDrawElements with an offset and an index buffer |
| |
| #include "system_utils.h" |
| #include "test_utils/ANGLETest.h" |
| |
| using namespace angle; |
| |
| class IndexBufferOffsetTest : public ANGLETest |
| { |
| protected: |
| IndexBufferOffsetTest() |
| { |
| setWindowWidth(128); |
| setWindowHeight(128); |
| setConfigRedBits(8); |
| setConfigGreenBits(8); |
| setConfigBlueBits(8); |
| setConfigAlphaBits(8); |
| } |
| |
| void SetUp() override |
| { |
| ANGLETest::SetUp(); |
| |
| const std::string vertexShaderSource = |
| SHADER_SOURCE(precision highp float; attribute vec2 position; |
| |
| void main() { gl_Position = vec4(position, 0.0, 1.0); }); |
| |
| const std::string fragmentShaderSource = |
| SHADER_SOURCE(precision highp float; uniform vec4 color; |
| |
| void main() { gl_FragColor = color; }); |
| |
| mProgram = CompileProgram(vertexShaderSource, fragmentShaderSource); |
| ASSERT_NE(0u, mProgram); |
| |
| mColorUniformLocation = glGetUniformLocation(mProgram, "color"); |
| mPositionAttributeLocation = glGetAttribLocation(mProgram, "position"); |
| |
| const GLfloat vertices[] = {-1.0f, -1.0f, -1.0f, 1.0f, 1.0f, -1.0f, 1.0f, 1.0f}; |
| glGenBuffers(1, &mVertexBuffer); |
| glBindBuffer(GL_ARRAY_BUFFER, mVertexBuffer); |
| glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), &vertices[0], GL_STATIC_DRAW); |
| |
| glGenBuffers(1, &mIndexBuffer); |
| glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, mIndexBuffer); |
| } |
| |
| void TearDown() override |
| { |
| glDeleteBuffers(1, &mVertexBuffer); |
| glDeleteBuffers(1, &mIndexBuffer); |
| glDeleteProgram(mProgram); |
| ANGLETest::TearDown(); |
| } |
| |
| void runTest(GLenum type, int typeWidth, void *indexData) |
| { |
| glClearColor(0.0f, 0.0f, 0.0f, 1.0f); |
| glClear(GL_COLOR_BUFFER_BIT); |
| |
| GLuint nullIndexData[] = {0, 0, 0, 0, 0, 0}; |
| |
| size_t indexDataWidth = 6 * typeWidth; |
| |
| glBufferData(GL_ELEMENT_ARRAY_BUFFER, 3 * indexDataWidth, nullptr, GL_DYNAMIC_DRAW); |
| glBufferSubData(GL_ELEMENT_ARRAY_BUFFER, 0, indexDataWidth, nullIndexData); |
| glBufferSubData(GL_ELEMENT_ARRAY_BUFFER, indexDataWidth, indexDataWidth, indexData); |
| glBufferSubData(GL_ELEMENT_ARRAY_BUFFER, 2 * indexDataWidth, indexDataWidth, nullIndexData); |
| |
| glUseProgram(mProgram); |
| |
| glBindBuffer(GL_ARRAY_BUFFER, mVertexBuffer); |
| glVertexAttribPointer(mPositionAttributeLocation, 2, GL_FLOAT, GL_FALSE, 0, 0); |
| glEnableVertexAttribArray(mPositionAttributeLocation); |
| |
| glUniform4f(mColorUniformLocation, 1.0f, 0.0f, 0.0f, 1.0f); |
| |
| for (int i = 0; i < 16; i++) |
| { |
| glDrawElements(GL_TRIANGLES, 6, type, reinterpret_cast<void *>(indexDataWidth)); |
| EXPECT_PIXEL_EQ(64, 64, 255, 0, 0, 255); |
| } |
| |
| glBufferSubData(GL_ELEMENT_ARRAY_BUFFER, indexDataWidth, indexDataWidth, nullIndexData); |
| glBufferSubData(GL_ELEMENT_ARRAY_BUFFER, 2 * indexDataWidth, indexDataWidth, indexData); |
| |
| glUniform4f(mColorUniformLocation, 0.0f, 1.0f, 0.0f, 1.0f); |
| glDrawElements(GL_TRIANGLES, 6, type, reinterpret_cast<void *>(indexDataWidth * 2)); |
| EXPECT_PIXEL_EQ(64, 64, 0, 255, 0, 255); |
| |
| EXPECT_GL_NO_ERROR(); |
| swapBuffers(); |
| } |
| |
| GLuint mProgram; |
| GLint mColorUniformLocation; |
| GLint mPositionAttributeLocation; |
| GLuint mVertexBuffer; |
| GLuint mIndexBuffer; |
| }; |
| |
| // Test using an offset for an UInt8 index buffer |
| TEST_P(IndexBufferOffsetTest, UInt8Index) |
| { |
| GLubyte indexData[] = {0, 1, 2, 1, 2, 3}; |
| runTest(GL_UNSIGNED_BYTE, 1, indexData); |
| } |
| |
| // Test using an offset for an UInt16 index buffer |
| TEST_P(IndexBufferOffsetTest, UInt16Index) |
| { |
| GLushort indexData[] = {0, 1, 2, 1, 2, 3}; |
| runTest(GL_UNSIGNED_SHORT, 2, indexData); |
| } |
| |
| // Test using an offset for an UInt32 index buffer |
| TEST_P(IndexBufferOffsetTest, UInt32Index) |
| { |
| if (getClientMajorVersion() < 3 && !extensionEnabled("GL_OES_element_index_uint")) |
| { |
| std::cout << "Test skipped because ES3 or GL_OES_element_index_uint is not available." |
| << std::endl; |
| return; |
| } |
| |
| GLuint indexData[] = {0, 1, 2, 1, 2, 3}; |
| runTest(GL_UNSIGNED_INT, 4, indexData); |
| } |
| |
| ANGLE_INSTANTIATE_TEST(IndexBufferOffsetTest, |
| ES2_D3D9(), |
| ES2_D3D11(), |
| ES3_D3D11(), |
| ES2_OPENGL(), |
| ES3_OPENGL(), |
| ES2_OPENGLES(), |
| ES3_OPENGLES()); |