Share data between VertexArray and Impl.
Using the same design as for the Framebuffer::Data helper, we can
use a struct to share between the object and the Impl. This also
gives the Impl access to the maxEnabledAttrib, and saves some
duplicated storage.
BUG=angleproject:1040
TEST=WebGL CTS, end2end_tests, unittests
Change-Id: I55c91e8a5f3dcae302cab441182320aafd5375ef
Reviewed-on: https://chromium-review.googlesource.com/283930
Tested-by: Jamie Madill <jmadill@chromium.org>
Reviewed-by: Corentin Wallez <cwallez@chromium.org>
Reviewed-by: Geoff Lang <geofflang@chromium.org>
diff --git a/src/libANGLE/renderer/gl/VertexArrayGL.cpp b/src/libANGLE/renderer/gl/VertexArrayGL.cpp
index ba5521c..c7b6ace 100644
--- a/src/libANGLE/renderer/gl/VertexArrayGL.cpp
+++ b/src/libANGLE/renderer/gl/VertexArrayGL.cpp
@@ -21,15 +21,12 @@
namespace rx
{
-VertexArrayGL::VertexArrayGL(const FunctionsGL *functions, StateManagerGL *stateManager)
- : VertexArrayImpl(),
+VertexArrayGL::VertexArrayGL(const gl::VertexArray::Data &data, const FunctionsGL *functions, StateManagerGL *stateManager)
+ : VertexArrayImpl(data),
mFunctions(functions),
mStateManager(stateManager),
mVertexArrayID(0),
- mElementArrayBuffer(),
- mAttributes(),
mAppliedElementArrayBuffer(0),
- mAppliedAttributes(),
mStreamingElementArrayBufferSize(0),
mStreamingElementArrayBuffer(0),
mStreamingArrayBufferSize(0),
@@ -42,7 +39,6 @@
// Set the cached vertex attribute array size
GLint maxVertexAttribs;
mFunctions->getIntegerv(GL_MAX_VERTEX_ATTRIBS, &maxVertexAttribs);
- mAttributes.resize(maxVertexAttribs);
mAppliedAttributes.resize(maxVertexAttribs);
}
@@ -59,22 +55,14 @@
mStreamingArrayBufferSize = 0;
mStreamingArrayBuffer = 0;
- mElementArrayBuffer.set(nullptr);
- for (size_t idx = 0; idx < mAttributes.size(); idx++)
- {
- mAttributes[idx].buffer.set(NULL);
- }
-
for (size_t idx = 0; idx < mAppliedAttributes.size(); idx++)
{
- mAppliedAttributes[idx].buffer.set(NULL);
+ mAppliedAttributes[idx].buffer.set(nullptr);
}
}
void VertexArrayGL::setElementArrayBuffer(const gl::Buffer *buffer)
{
- mElementArrayBuffer.set(buffer);
-
// If the buffer is being unbound/deleted, reset the currently applied buffer ID
// so that even if a new buffer is generated with the same ID, it will be re-bound.
if (buffer == nullptr && mAppliedElementArrayBuffer != mStreamingElementArrayBuffer)
@@ -85,17 +73,14 @@
void VertexArrayGL::setAttribute(size_t idx, const gl::VertexAttribute &attr)
{
- mAttributes[idx] = attr;
}
void VertexArrayGL::setAttributeDivisor(size_t idx, GLuint divisor)
{
- mAttributes[idx].divisor = divisor;
}
void VertexArrayGL::enableAttribute(size_t idx, bool enabledState)
{
- mAttributes[idx].enabled = enabledState;
}
gl::Error VertexArrayGL::syncDrawArraysState(GLint first, GLsizei count) const
@@ -158,9 +143,10 @@
bool VertexArrayGL::doAttributesNeedStreaming() const
{
// TODO: if GLES, nothing needs to be streamed
- for (size_t idx = 0; idx < mAttributes.size(); idx++)
+ const auto &attribs = mData.getVertexAttributes();
+ for (size_t idx = 0; idx < attribs.size(); idx++)
{
- if (mAttributes[idx].enabled && mAttributes[idx].buffer.get() == nullptr)
+ if (attribs[idx].enabled && attribs[idx].buffer.get() == nullptr)
{
return true;
}
@@ -175,13 +161,16 @@
*outStreamingDataSize = 0;
*outMaxAttributeDataSize = 0;
- for (size_t idx = 0; idx < mAttributes.size(); idx++)
+ const auto &attribs = mData.getVertexAttributes();
+ for (size_t idx = 0; idx < attribs.size(); idx++)
{
+ const auto &attrib = attribs[idx];
+
// Always sync the enabled and divisor state, they are required for both streaming and buffered
// attributes
- if (mAppliedAttributes[idx].enabled != mAttributes[idx].enabled)
+ if (mAppliedAttributes[idx].enabled != attrib.enabled)
{
- if (mAttributes[idx].enabled)
+ if (attrib.enabled)
{
mFunctions->enableVertexAttribArray(idx);
}
@@ -189,15 +178,15 @@
{
mFunctions->disableVertexAttribArray(idx);
}
- mAppliedAttributes[idx].enabled = mAttributes[idx].enabled;
+ mAppliedAttributes[idx].enabled = attrib.enabled;
}
- if (mAppliedAttributes[idx].divisor != mAttributes[idx].divisor)
+ if (mAppliedAttributes[idx].divisor != attrib.divisor)
{
- mFunctions->vertexAttribDivisor(idx, mAttributes[idx].divisor);
- mAppliedAttributes[idx].divisor = mAttributes[idx].divisor;
+ mFunctions->vertexAttribDivisor(idx, attrib.divisor);
+ mAppliedAttributes[idx].divisor = attrib.divisor;
}
- if (mAttributes[idx].enabled && mAttributes[idx].buffer.get() == nullptr)
+ if (attribs[idx].enabled && attrib.buffer.get() == nullptr)
{
ASSERT(attributesNeedStreaming);
@@ -206,16 +195,16 @@
// If streaming is going to be required, compute the size of the required buffer
// and how much slack space at the beginning of the buffer will be required by determining
// the attribute with the largest data size.
- size_t typeSize = ComputeVertexAttributeTypeSize(mAttributes[idx]);
+ size_t typeSize = ComputeVertexAttributeTypeSize(attrib);
*outStreamingDataSize += typeSize * streamedVertexCount;
*outMaxAttributeDataSize = std::max(*outMaxAttributeDataSize, typeSize);
}
else
{
// Sync the attribute with no translation
- if (mAppliedAttributes[idx] != mAttributes[idx])
+ if (mAppliedAttributes[idx] != attrib)
{
- const gl::Buffer *arrayBuffer = mAttributes[idx].buffer.get();
+ const gl::Buffer *arrayBuffer = attrib.buffer.get();
if (arrayBuffer != nullptr)
{
const BufferGL *arrayBufferGL = GetImplAs<BufferGL>(arrayBuffer);
@@ -226,19 +215,19 @@
mStateManager->bindBuffer(GL_ARRAY_BUFFER, 0);
}
- if (mAttributes[idx].pureInteger)
+ if (attrib.pureInteger)
{
- mFunctions->vertexAttribIPointer(idx, mAttributes[idx].size, mAttributes[idx].type,
- mAttributes[idx].stride, mAttributes[idx].pointer);
+ mFunctions->vertexAttribIPointer(idx, attrib.size, attrib.type,
+ attrib.stride, attrib.pointer);
}
else
{
- mFunctions->vertexAttribPointer(idx, mAttributes[idx].size, mAttributes[idx].type,
- mAttributes[idx].normalized, mAttributes[idx].stride,
- mAttributes[idx].pointer);
+ mFunctions->vertexAttribPointer(idx, attrib.size, attrib.type,
+ attrib.normalized, attrib.stride,
+ attrib.pointer);
}
- mAppliedAttributes[idx] = mAttributes[idx];
+ mAppliedAttributes[idx] = attrib;
}
}
}
@@ -251,10 +240,12 @@
{
ASSERT(outIndices);
+ gl::Buffer *elementArrayBuffer = mData.getElementArrayBuffer().get();
+
// Need to check the range of indices if attributes need to be streamed
- if (mElementArrayBuffer.get() != nullptr)
+ if (elementArrayBuffer != nullptr)
{
- const BufferGL *bufferGL = GetImplAs<BufferGL>(mElementArrayBuffer.get());
+ const BufferGL *bufferGL = GetImplAs<BufferGL>(elementArrayBuffer);
GLuint elementArrayBufferID = bufferGL->getBufferID();
if (elementArrayBufferID != mAppliedElementArrayBuffer)
{
@@ -266,7 +257,7 @@
if (attributesNeedStreaming)
{
ptrdiff_t elementArrayBufferOffset = reinterpret_cast<ptrdiff_t>(indices);
- gl::Error error = mElementArrayBuffer->getIndexRange(type, static_cast<size_t>(elementArrayBufferOffset), count, outIndexRange);
+ gl::Error error = mData.getElementArrayBuffer()->getIndexRange(type, static_cast<size_t>(elementArrayBufferOffset), count, outIndexRange);
if (error.isError())
{
return error;
@@ -351,14 +342,17 @@
const size_t streamedVertexCount = indexRange.end - indexRange.start + 1;
- for (size_t idx = 0; idx < mAttributes.size(); idx++)
+ const auto &attribs = mData.getVertexAttributes();
+ for (size_t idx = 0; idx < attribs.size(); idx++)
{
- if (mAttributes[idx].enabled && mAttributes[idx].buffer.get() == nullptr)
- {
- const size_t sourceStride = ComputeVertexAttributeStride(mAttributes[idx]);
- const size_t destStride = ComputeVertexAttributeTypeSize(mAttributes[idx]);
+ const auto &attrib = attribs[idx];
- const uint8_t *inputPointer = reinterpret_cast<const uint8_t*>(mAttributes[idx].pointer);
+ if (attrib.enabled && attrib.buffer.get() == nullptr)
+ {
+ const size_t sourceStride = ComputeVertexAttributeStride(attrib);
+ const size_t destStride = ComputeVertexAttributeTypeSize(attrib);
+
+ const uint8_t *inputPointer = reinterpret_cast<const uint8_t*>(attrib.pointer);
// Pack the data when copying it, user could have supplied a very large stride that would
// cause the buffer to be much larger than needed.
@@ -383,8 +377,8 @@
// Compute where the 0-index vertex would be.
const size_t vertexStartOffset = curBufferOffset - (indexRange.start * destStride);
- mFunctions->vertexAttribPointer(idx, mAttributes[idx].size, mAttributes[idx].type,
- mAttributes[idx].normalized, destStride,
+ mFunctions->vertexAttribPointer(idx, attrib.size, attrib.type,
+ attrib.normalized, destStride,
reinterpret_cast<const GLvoid*>(vertexStartOffset));
curBufferOffset += destStride * streamedVertexCount;