Commit c1e0268a by Luc Ferron Committed by Commit Bot

Vulkan: drawArrays followed by drawElements bugfix

Also add a test in StateChangeTest.cpp to validate the behavior. Bug: angleproject:2458 Change-Id: I58848772c0b4f71aaa3ee187778e49fa08e6800d Reviewed-on: https://chromium-review.googlesource.com/1007320Reviewed-by: 's avatarJamie Madill <jmadill@chromium.org> Reviewed-by: 's avatarLuc Ferron <lucferron@chromium.org> Commit-Queue: Luc Ferron <lucferron@chromium.org>
parent a56467e0
......@@ -464,7 +464,11 @@ gl::Error VertexArrayVk::onDraw(const gl::Context *context,
updateArrayBufferReadDependencies(drawNode, activeAttribs,
renderer->getCurrentQueueSerial());
}
mVertexBuffersDirty = false;
// This forces the binding to happen if we follow a drawElement call from a drawArrays call.
mIndexBufferDirty = true;
}
return gl::NoError();
......
......@@ -15,6 +15,18 @@ using namespace angle;
namespace
{
constexpr char kBasicVertexShader[] =
R"(attribute vec3 position;
void main()
{
gl_Position = vec4(position, 1);
})";
constexpr char kGreenFragmentShader[] =
R"(void main()
{
gl_FragColor = vec4(0, 1, 0, 1);
})";
class StateChangeTest : public ANGLETest
{
......@@ -1008,6 +1020,61 @@ void SimpleStateChangeTest::simpleDrawWithColor(const GLColor &color)
simpleDrawWithBuffer(&colorBuffer);
}
// Test that we can do a drawElements call successfully after making a drawArrays call in the same
// frame.
TEST_P(SimpleStateChangeTest, DrawArraysThenDrawElement)
{
ANGLE_GL_PROGRAM(program, kBasicVertexShader, kGreenFragmentShader);
glUseProgram(program);
// We expect to draw a triangle with the first 3 points to the left, then another triangle with
// the last 3 vertices using a drawElements call.
auto vertices = std::vector<Vector3>{{-1.0f, -1.0f, 0.0f},
{-1.0f, 1.0f, 0.0f},
{0.0f, 0.0f, 0.0f},
{1.0f, 1.0f, 0.0f},
{1.0f, -1.0f, 0.0f}};
// If we use these indices to draw we'll be using the last 2 vertex only to draw.
auto indices = std::vector<GLushort>{2, 3, 4};
GLint positionLocation = glGetAttribLocation(program, "position");
ASSERT_NE(-1, positionLocation);
GLBuffer vertexBuffer;
glBindBuffer(GL_ARRAY_BUFFER, vertexBuffer);
glBufferData(GL_ARRAY_BUFFER, sizeof(vertices[0]) * vertices.size(), vertices.data(),
GL_STATIC_DRAW);
GLBuffer indexBuffer;
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, indexBuffer);
glBufferData(GL_ELEMENT_ARRAY_BUFFER, indices.size() * sizeof(GLushort), &indices[0],
GL_STATIC_DRAW);
glVertexAttribPointer(positionLocation, 3, GL_FLOAT, GL_FALSE, 0, nullptr);
glEnableVertexAttribArray(positionLocation);
for (int i = 0; i < 10; i++)
{
glClear(GL_COLOR_BUFFER_BIT);
glDrawArrays(GL_TRIANGLES, 0, 3); // triangle to the left
glDrawElements(GL_TRIANGLES, 3, GL_UNSIGNED_SHORT, nullptr); // triangle to the right
swapBuffers();
}
glDisableVertexAttribArray(positionLocation);
ASSERT_GL_NO_ERROR();
int quarterWidth = getWindowWidth() / 4;
int halfHeight = getWindowHeight() / 2;
// Validate triangle to the left
EXPECT_PIXEL_COLOR_EQ(quarterWidth, halfHeight, GLColor::green);
// Validate triangle to the right
EXPECT_PIXEL_COLOR_EQ((quarterWidth * 3), halfHeight, GLColor::green);
}
// Handles deleting a Buffer when it's being used.
TEST_P(SimpleStateChangeTest, DeleteBufferInUse)
{
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment