1 #include "precompiled.h"
3 // Copyright (c) 2002-2012 The ANGLE Project Authors. All rights reserved.
4 // Use of this source code is governed by a BSD-style license that can be
5 // found in the LICENSE file.
8 // VertexBuffer.cpp: Defines the abstract VertexBuffer class and VertexBufferInterface
9 // class with derivations, classes that perform graphics API agnostic vertex buffer operations.
11 #include "libGLESv2/renderer/VertexBuffer.h"
12 #include "libGLESv2/renderer/Renderer.h"
13 #include "libGLESv2/Context.h"
18 unsigned int VertexBuffer::mNextSerial = 1;
20 VertexBuffer::VertexBuffer()
25 VertexBuffer::~VertexBuffer()
29 void VertexBuffer::updateSerial()
31 mSerial = mNextSerial++;
34 unsigned int VertexBuffer::getSerial() const
39 VertexBufferInterface::VertexBufferInterface(rx::Renderer *renderer, bool dynamic) : mRenderer(renderer)
45 mVertexBuffer = renderer->createVertexBuffer();
48 VertexBufferInterface::~VertexBufferInterface()
53 unsigned int VertexBufferInterface::getSerial() const
55 return mVertexBuffer->getSerial();
58 unsigned int VertexBufferInterface::getBufferSize() const
60 return mVertexBuffer->getBufferSize();
63 bool VertexBufferInterface::setBufferSize(unsigned int size)
65 if (mVertexBuffer->getBufferSize() == 0)
67 return mVertexBuffer->initialize(size, mDynamic);
71 return mVertexBuffer->setBufferSize(size);
75 unsigned int VertexBufferInterface::getWritePosition() const
77 return mWritePosition;
80 void VertexBufferInterface::setWritePosition(unsigned int writePosition)
82 mWritePosition = writePosition;
85 bool VertexBufferInterface::discard()
87 return mVertexBuffer->discard();
90 bool VertexBufferInterface::storeVertexAttributes(const gl::VertexAttribute &attrib, GLint start, GLsizei count, GLsizei instances,
91 unsigned int *outStreamOffset)
93 unsigned int spaceRequired;
94 if (!mVertexBuffer->getSpaceRequired(attrib, count, instances, &spaceRequired))
99 if (mWritePosition + spaceRequired < mWritePosition)
104 if (!reserveSpace(mReservedSpace))
110 if (!mVertexBuffer->storeVertexAttributes(attrib, start, count, instances, mWritePosition))
117 *outStreamOffset = mWritePosition;
120 mWritePosition += spaceRequired;
125 bool VertexBufferInterface::storeRawData(const void* data, unsigned int size, unsigned int *outStreamOffset)
127 if (mWritePosition + size < mWritePosition)
132 if (!reserveSpace(mReservedSpace))
138 if (!mVertexBuffer->storeRawData(data, size, mWritePosition))
145 *outStreamOffset = mWritePosition;
148 mWritePosition += size;
153 bool VertexBufferInterface::reserveVertexSpace(const gl::VertexAttribute &attribute, GLsizei count, GLsizei instances)
155 unsigned int requiredSpace;
156 if (!mVertexBuffer->getSpaceRequired(attribute, count, instances, &requiredSpace))
161 // Protect against integer overflow
162 if (mReservedSpace + requiredSpace < mReservedSpace)
167 mReservedSpace += requiredSpace;
171 bool VertexBufferInterface::reserveRawDataSpace(unsigned int size)
173 // Protect against integer overflow
174 if (mReservedSpace + size < mReservedSpace)
179 mReservedSpace += size;
183 VertexBuffer* VertexBufferInterface::getVertexBuffer() const
185 return mVertexBuffer;
189 StreamingVertexBufferInterface::StreamingVertexBufferInterface(rx::Renderer *renderer, std::size_t initialSize) : VertexBufferInterface(renderer, true)
191 setBufferSize(initialSize);
194 StreamingVertexBufferInterface::~StreamingVertexBufferInterface()
198 bool StreamingVertexBufferInterface::reserveSpace(unsigned int size)
201 unsigned int curBufferSize = getBufferSize();
202 if (size > curBufferSize)
204 result = setBufferSize(std::max(size, 3 * curBufferSize / 2));
207 else if (getWritePosition() + size > curBufferSize)
219 StaticVertexBufferInterface::StaticVertexBufferInterface(rx::Renderer *renderer) : VertexBufferInterface(renderer, false)
223 StaticVertexBufferInterface::~StaticVertexBufferInterface()
227 bool StaticVertexBufferInterface::lookupAttribute(const gl::VertexAttribute &attribute, unsigned int *outStreamOffset)
229 for (unsigned int element = 0; element < mCache.size(); element++)
231 if (mCache[element].type == attribute.mType &&
232 mCache[element].size == attribute.mSize &&
233 mCache[element].stride == attribute.stride() &&
234 mCache[element].normalized == attribute.mNormalized)
236 if (mCache[element].attributeOffset == attribute.mOffset % attribute.stride())
240 *outStreamOffset = mCache[element].streamOffset;
250 bool StaticVertexBufferInterface::reserveSpace(unsigned int size)
252 unsigned int curSize = getBufferSize();
258 else if (curSize >= size)
264 UNREACHABLE(); // Static vertex buffers can't be resized
269 bool StaticVertexBufferInterface::storeVertexAttributes(const gl::VertexAttribute &attrib, GLint start, GLsizei count, GLsizei instances,
270 unsigned int *outStreamOffset)
272 unsigned int streamOffset;
273 if (VertexBufferInterface::storeVertexAttributes(attrib, start, count, instances, &streamOffset))
275 int attributeOffset = attrib.mOffset % attrib.stride();
276 VertexElement element = { attrib.mType, attrib.mSize, attrib.stride(), attrib.mNormalized, attributeOffset, streamOffset };
277 mCache.push_back(element);
281 *outStreamOffset = streamOffset;