love
parent
bc14d16db2
commit
002f5c2ae8
|
@ -24,6 +24,7 @@
|
||||||
#include <blt/gfx/gl_includes.h>
|
#include <blt/gfx/gl_includes.h>
|
||||||
#include <variant>
|
#include <variant>
|
||||||
#include <array>
|
#include <array>
|
||||||
|
#include <blt/std/hashmap.h>
|
||||||
|
|
||||||
namespace blt::gfx
|
namespace blt::gfx
|
||||||
{
|
{
|
||||||
|
@ -40,16 +41,18 @@ namespace blt::gfx
|
||||||
{
|
{
|
||||||
GLuint bufferID_ = 0;
|
GLuint bufferID_ = 0;
|
||||||
GLsizeiptr size_ = 0;
|
GLsizeiptr size_ = 0;
|
||||||
|
GLint buffer_type;
|
||||||
|
GLint memory_type;
|
||||||
|
|
||||||
void create();
|
void create(GLint type);
|
||||||
|
|
||||||
void bind(GLint buffer_type = GL_ARRAY_BUFFER) const;
|
void bind() const;
|
||||||
|
|
||||||
void allocate(GLsizeiptr size, GLint buffer_type = GL_ARRAY_BUFFER, GLint memory_type = GL_STATIC_DRAW, void* data = nullptr);
|
void allocate(GLsizeiptr size, GLint memory_type = GL_STATIC_DRAW, void* data = nullptr);
|
||||||
|
|
||||||
static void sub_update(GLsizeiptr offset, GLsizeiptr size, void* data, GLint buffer_type = GL_ARRAY_BUFFER);
|
void sub_update(GLsizeiptr offset, GLsizeiptr size, void* data);
|
||||||
|
|
||||||
void update(GLsizeiptr size, void* data, GLint buffer_type = GL_ARRAY_BUFFER, GLint memory_type = GL_STATIC_DRAW);
|
void update(GLsizeiptr size, void* data);
|
||||||
|
|
||||||
void destroy();
|
void destroy();
|
||||||
};
|
};
|
||||||
|
@ -68,6 +71,7 @@ namespace blt::gfx
|
||||||
size_t max = 0;
|
size_t max = 0;
|
||||||
|
|
||||||
void swap();
|
void swap();
|
||||||
|
|
||||||
public:
|
public:
|
||||||
static_dynamic_array();
|
static_dynamic_array();
|
||||||
|
|
||||||
|
@ -79,18 +83,10 @@ namespace blt::gfx
|
||||||
|
|
||||||
static_dynamic_array& operator=(static_dynamic_array&& move) noexcept = default;
|
static_dynamic_array& operator=(static_dynamic_array&& move) noexcept = default;
|
||||||
|
|
||||||
vbo_t& operator[](size_t index)
|
vbo_t& operator[](size_t index);
|
||||||
{
|
|
||||||
if (index >= size_)
|
|
||||||
swap();
|
|
||||||
max = std::max(index, max);
|
|
||||||
if (std::holds_alternative<vbo_t*>(data_))
|
|
||||||
return std::get<vbo_t*>(data_)[index];
|
|
||||||
else
|
|
||||||
return std::get<array_t>(data_)[index];
|
|
||||||
}
|
|
||||||
|
|
||||||
[[nodiscard]] size_t used() const noexcept {
|
[[nodiscard]] inline size_t used() const noexcept
|
||||||
|
{
|
||||||
return max;
|
return max;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -107,12 +103,47 @@ namespace blt::gfx
|
||||||
class basic_vertex_array
|
class basic_vertex_array
|
||||||
{
|
{
|
||||||
private:
|
private:
|
||||||
|
|
||||||
|
|
||||||
GLuint vaoID;
|
GLuint vaoID;
|
||||||
static_dynamic_array VBOs;
|
static_dynamic_array VBOs;
|
||||||
|
HASHSET<GLuint> used_attributes;
|
||||||
|
vbo_t element;
|
||||||
public:
|
public:
|
||||||
basic_vertex_array();
|
basic_vertex_array();
|
||||||
|
|
||||||
|
basic_vertex_array(const basic_vertex_array&) = delete;
|
||||||
|
|
||||||
|
basic_vertex_array(basic_vertex_array&&) = delete;
|
||||||
|
|
||||||
|
basic_vertex_array& operator=(const basic_vertex_array&) = delete;
|
||||||
|
|
||||||
|
basic_vertex_array& operator=(basic_vertex_array&&) = delete;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This function takes ownership of the underlying VBO (GPU side). It will be freed when the basic vertex array is deleted
|
||||||
|
* @param vbo vbo to bind to this attribute
|
||||||
|
* @param attribute_number attribute number to bind to
|
||||||
|
* @param coordinate_size size of the data (number of
|
||||||
|
* @param type type of data
|
||||||
|
* @param stride how many bytes this data takes (for the entire per-vertex data structure) 0 will assume packed data
|
||||||
|
* @param offset offset into the data structure to where the data is stored
|
||||||
|
*/
|
||||||
|
void bindVBO(const vbo_t& vbo, int attribute_number, int coordinate_size, GLenum type, int stride, long offset);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns a non-owning reference to a vbo allowing for updating the VBO
|
||||||
|
* The VBO is considered invalid if its ID is 0
|
||||||
|
*/
|
||||||
|
inline vbo_t& operator[](size_t index)
|
||||||
|
{
|
||||||
|
return VBOs[index];
|
||||||
|
}
|
||||||
|
|
||||||
|
inline void bind()
|
||||||
|
{
|
||||||
|
glBindVertexArray(vaoID);
|
||||||
|
}
|
||||||
|
|
||||||
|
~basic_vertex_array();
|
||||||
};
|
};
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -1 +1 @@
|
||||||
Subproject commit b135e5b915e0efaae2f8d9dc30d4752726b74bb4
|
Subproject commit 5ae17f4a86a021fb914f0c17b116dc511e5f3f93
|
|
@ -45,14 +45,26 @@ namespace blt::gfx
|
||||||
std::memset(ptr.data(), 0, DATA_SIZE);
|
std::memset(ptr.data(), 0, DATA_SIZE);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
vbo_t& static_dynamic_array::operator[](size_t index)
|
||||||
|
{
|
||||||
|
if (index >= size_)
|
||||||
|
swap();
|
||||||
|
max = std::max(index, max);
|
||||||
|
if (std::holds_alternative<vbo_t*>(data_))
|
||||||
|
return std::get<vbo_t*>(data_)[index];
|
||||||
|
else
|
||||||
|
return std::get<array_t>(data_)[index];
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* -----------------------------------
|
* -----------------------------------
|
||||||
* vbo_t
|
* vbo_t
|
||||||
* -----------------------------------
|
* -----------------------------------
|
||||||
*/
|
*/
|
||||||
void vbo_t::create()
|
void vbo_t::create(GLint type)
|
||||||
{
|
{
|
||||||
glGenBuffers(1, &bufferID_);
|
glGenBuffers(1, &bufferID_);
|
||||||
|
buffer_type = type;
|
||||||
}
|
}
|
||||||
|
|
||||||
void vbo_t::destroy()
|
void vbo_t::destroy()
|
||||||
|
@ -60,27 +72,28 @@ namespace blt::gfx
|
||||||
glDeleteBuffers(1, &bufferID_);
|
glDeleteBuffers(1, &bufferID_);
|
||||||
}
|
}
|
||||||
|
|
||||||
void vbo_t::allocate(GLsizeiptr size, GLint buffer_type, GLint memory_type, void* data)
|
void vbo_t::allocate(GLsizeiptr size, GLint mem_type, void* data)
|
||||||
{
|
{
|
||||||
size_ = size;
|
size_ = size;
|
||||||
glBufferData(buffer_type, size, data, memory_type);
|
glBufferData(buffer_type, size, data, mem_type);
|
||||||
|
memory_type = mem_type;
|
||||||
}
|
}
|
||||||
|
|
||||||
void vbo_t::update(GLsizeiptr size, void* data, GLint buffer_type, GLint memory_type)
|
void vbo_t::update(GLsizeiptr size, void* data)
|
||||||
{
|
{
|
||||||
if (size <= size_)
|
if (size <= size_)
|
||||||
sub_update(0, size, data, buffer_type);
|
sub_update(0, size, data);
|
||||||
else
|
else
|
||||||
allocate(size, buffer_type, memory_type, data);
|
allocate(size, memory_type, data);
|
||||||
size_ = size;
|
size_ = size;
|
||||||
}
|
}
|
||||||
|
|
||||||
void vbo_t::sub_update(GLsizeiptr offset, GLsizeiptr size, void* data, GLint buffer_type)
|
void vbo_t::sub_update(GLsizeiptr offset, GLsizeiptr size, void* data)
|
||||||
{
|
{
|
||||||
glBufferSubData(buffer_type, offset, size, data);
|
glBufferSubData(buffer_type, offset, size, data);
|
||||||
}
|
}
|
||||||
|
|
||||||
void vbo_t::bind(GLint buffer_type) const
|
void vbo_t::bind() const
|
||||||
{
|
{
|
||||||
glBindBuffer(buffer_type, bufferID_);
|
glBindBuffer(buffer_type, bufferID_);
|
||||||
}
|
}
|
||||||
|
@ -95,4 +108,28 @@ namespace blt::gfx
|
||||||
{
|
{
|
||||||
glGenVertexArrays(1, &vaoID);
|
glGenVertexArrays(1, &vaoID);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
basic_vertex_array::~basic_vertex_array()
|
||||||
|
{
|
||||||
|
// free all VBOs
|
||||||
|
for (size_t i = 0; i < VBOs.used(); i++)
|
||||||
|
if (VBOs[i].bufferID_)
|
||||||
|
VBOs[i].destroy();
|
||||||
|
// then free the vertex array
|
||||||
|
glDeleteVertexArrays(1, &vaoID);
|
||||||
|
}
|
||||||
|
|
||||||
|
void basic_vertex_array::bindVBO(const vbo_t& vbo, int attribute_number, int coordinate_size, GLenum type, int stride, long offset)
|
||||||
|
{
|
||||||
|
used_attributes.insert(attribute_number);
|
||||||
|
bind();
|
||||||
|
vbo.bind();
|
||||||
|
|
||||||
|
glVertexAttribPointer(
|
||||||
|
attribute_number, coordinate_size, type, GL_FALSE, stride < 0 ? 0 : stride, (void*) offset
|
||||||
|
);
|
||||||
|
glEnableVertexAttribArray(attribute_number);
|
||||||
|
|
||||||
|
VBOs[attribute_number] = vbo;
|
||||||
|
}
|
||||||
}
|
}
|
Loading…
Reference in New Issue