6#include <boost/container_hash/hash.hpp>
156 return "vertexcoord";
173 template<
typename... Args>
192 boost::hash_combine(seed,
static_cast<size_t>(
m_type));
193 boost::hash_combine(seed,
static_cast<size_t>(
m_format));
195 boost::hash_combine(seed, boost::hash<const char*>()(
m_semantic));
226 template<
typename First,
typename... Rest>
227 constexpr void processArgs(First&& first, Rest&&... rest)
noexcept {
240 template<
typename... Elements>
266 return static_cast<int>(i);
275 return static_cast<int>(i);
283 return (index >= 0) ? &
m_elements[index] :
nullptr;
288 return (index >= 0) ? &
m_elements[index] :
nullptr;
327 template<
typename... Args>
366 return static_cast<int>(i);
375 return static_cast<int>(i);
383 return (index >= 0) ? &
m_elements[index] :
nullptr;
388 return (index >= 0) ? &
m_elements[index] :
nullptr;
418 for (
int i = posIndex; i > 0; --i) {
439 template<
typename... Rest>
445 template<
typename... Rest>
463 const auto* element =
m_layout.getElementByType(type);
465 size_t offset =
m_layout.getElementOffsetByType(type);
466 return *
reinterpret_cast<T*
>(
m_data + offset);
474 const auto* element =
m_layout.getElementBySemantic(semantic);
476 size_t offset =
m_layout.getElementOffsetBySemantic(semantic);
477 return *
reinterpret_cast<T*
>(
m_data + offset);
485 const auto* element =
m_layout.getElementByType(type);
487 size_t offset =
m_layout.getElementOffsetByType(type);
488 *
reinterpret_cast<T*
>(
m_data + offset) = value;
493 if (elementIndex <
m_layout.getElementCount()) {
494 size_t offset =
m_layout.getElementOffset(elementIndex);
495 *
reinterpret_cast<T*
>(
m_data + offset) = value;
501 const auto* element =
m_layout.getElementBySemantic(semantic);
503 size_t offset =
m_layout.getElementOffsetBySemantic(semantic);
504 *
reinterpret_cast<T*
>(
m_data + offset) = value;
535 const auto* element =
m_layout.getElementByType(type);
537 size_t offset =
m_layout.getElementOffsetByType(type);
538 return *
reinterpret_cast<const T*
>(
m_data + offset);
540 static const T dummy{};
546 const auto* element =
m_layout.getElementBySemantic(semantic);
548 size_t offset =
m_layout.getElementOffsetBySemantic(semantic);
549 return *
reinterpret_cast<const T*
>(
m_data + offset);
551 static const T dummy{};
625 assert(!
m_data.empty() &&
"Vertex buffer is empty");
630 assert(!
m_data.empty() &&
"Vertex buffer is empty");
635 assert(!
m_data.empty() &&
"Vertex buffer is empty");
640 assert(!
m_data.empty() &&
"Vertex buffer is empty");
644 template<
typename... Args>
646 static_assert(
sizeof...(args) > 0,
"At least one attribute must be provided");
649 Vertex vertex = (*this)[index];
658 if (elementIndex <
m_layout.getElementCount()) {
659 vertex.
setAttribute(elementIndex, std::forward<T>(value));
663 template<
typename T,
typename... Rest>
665 if (elementIndex <
m_layout.getElementCount()) {
666 vertex.
setAttribute(elementIndex, std::forward<T>(first));
667 setAttributes(vertex, elementIndex + 1, std::forward<Rest>(rest)...);
const VertexLayout & getLayout() const noexcept
const T & getAttribute(const char *semantic) const noexcept
const VertexLayout & m_layout
const uint8_t * getData() const noexcept
ConstVertex(const Vertex &vertex) noexcept
const T & getAttribute(VtxType type) const noexcept
constexpr const VertexElement * getElementByType(VtxType type) const noexcept
constexpr void addElements(const VertexElement &element, Rest &&... rest) noexcept
constexpr size_t getElementCount() const noexcept
size_t getHash() const noexcept
constexpr size_t getElementOffsetBySemantic(const char *semantic) const noexcept
constexpr const VertexElement & getElement(size_t index) const noexcept
constexpr size_t getElementOffset(size_t index) const noexcept
constexpr void addElements(const VertexLayout &layout, Rest &&... rest) noexcept
VertexElement m_elements[MaxElements]
constexpr void ensurePositionFirst() noexcept
constexpr void addElement(const VertexElement &element) noexcept
static constexpr size_t MaxElements
constexpr void addElements() noexcept
constexpr const VertexElement * getElementBySemantic(const char *semantic) const noexcept
constexpr int getElementIndexBySemantic(const char *semantic) const noexcept
constexpr size_t getElementOffsetByType(VtxType type) const noexcept
constexpr PixelLayout(Args &&... args) noexcept
constexpr int getElementIndexByType(VtxType type) const noexcept
constexpr void addElements(const PixelLayout &layout) noexcept
constexpr void addElements(const VertexLayout &layout) noexcept
constexpr size_t getStride() const noexcept
VertexBuffer(const VertexLayout &layout) noexcept
void emplaceBack(Args &&... args)
void reserve(size_t vertexCount)
size_t getStride() const noexcept
ConstVertex front() const noexcept
const void * getData() const noexcept
void setAttributes(Vertex &vertex, size_t elementIndex, T &&first, Rest &&... rest)
size_t getDataSize() const noexcept
std::vector< uint8_t > m_data
void setAttributes(Vertex &vertex, size_t elementIndex, T &&value)
size_t getVertexCount() const noexcept
ConstVertex back() const noexcept
Vertex operator[](size_t index) noexcept
const VertexLayout & getLayout() const noexcept
void resize(size_t vertexCount)
constexpr void processArgs(First &&first, Rest &&... rest) noexcept
constexpr VtxType getType() const noexcept
size_t getHash() const noexcept
constexpr void processArgs(VtxType type) noexcept
constexpr Format getFormat() const noexcept
constexpr void processArgs(Format format) noexcept
constexpr void processArgs(ModelVertexAttribute attr) noexcept
constexpr VertexElement() noexcept
constexpr size_t getSize() const noexcept
constexpr const char * getSemantic() const noexcept
constexpr ModelVertexAttribute getModelAttribute() const noexcept
constexpr void processArgs(const char *semantic) noexcept
constexpr VertexElement(Args &&... args) noexcept
ModelVertexAttribute m_modelAttribute
constexpr void processArgs() noexcept
void setAttribute(const char *semantic, const T &value) noexcept
void setAttribute(size_t elementIndex, const T &value) noexcept
uint8_t * getData() noexcept
void setAttribute(VtxType type, const T &value) noexcept
const VertexLayout & getLayout() const noexcept
Vertex(uint8_t *data, const VertexLayout &layout) noexcept
friend class VertexBuffer
T & getAttribute(const char *semantic) noexcept
T & getAttribute(VtxType type) noexcept
const uint8_t * getData() const noexcept
const VertexLayout & m_layout
constexpr const VertexElement * getElementByType(VtxType type) const noexcept
VertexElement m_elements[MaxElements]
constexpr size_t getElementOffset(size_t index) const noexcept
constexpr size_t getStride() const noexcept
constexpr int getElementIndexByType(VtxType type) const noexcept
constexpr size_t getElementOffsetBySemantic(const char *semantic) const noexcept
constexpr size_t getElementOffsetByType(VtxType type) const noexcept
constexpr int getElementIndexBySemantic(const char *semantic) const noexcept
size_t getHash() const noexcept
static constexpr size_t MaxElements
constexpr void addElement(const VertexElement &element) noexcept
constexpr size_t getElementCount() const noexcept
constexpr const VertexElement & getElement(size_t index) const noexcept
constexpr const VertexElement * getElementBySemantic(const char *semantic) const noexcept
constexpr VertexLayout(const Elements &... elements) noexcept
constexpr const char * GetDefaultSemantic(VtxType type) noexcept
constexpr bool StringEquals(const char *a, const char *b) noexcept
constexpr bool isPositionType(VtxType type) noexcept
constexpr ModelVertexAttribute GetDefaultModelAttribute(VtxType type) noexcept
constexpr Format GetDefaultFormat(VtxType type) noexcept
constexpr size_t FormatSize(Format format) noexcept