c5dc63699a
mesh_gpu_upload sube positions+normals interleaved (stride 6 floats, location 0=a_pos, location 1=a_normal) + EBO uint32. mesh_gpu_destroy libera todo. GL_STATIC_DRAW (mesh inmutable post-upload). issue 0029
70 lines
2.2 KiB
C++
70 lines
2.2 KiB
C++
#include "gfx/mesh_gpu.h"
|
|
|
|
#include <vector>
|
|
|
|
namespace fn::gfx {
|
|
|
|
MeshGpu mesh_gpu_upload(const Mesh& mesh) {
|
|
MeshGpu g{};
|
|
if (mesh.positions.empty() || mesh.indices.empty()) return g;
|
|
if (mesh.normals.size() != mesh.positions.size()) return g;
|
|
|
|
const size_t nverts = mesh.positions.size() / 3;
|
|
|
|
// Interleave pos.xyz + normal.xyz, stride 6 floats.
|
|
std::vector<float> interleaved;
|
|
interleaved.resize(nverts * 6);
|
|
for (size_t i = 0; i < nverts; ++i) {
|
|
interleaved[i*6 + 0] = mesh.positions[i*3 + 0];
|
|
interleaved[i*6 + 1] = mesh.positions[i*3 + 1];
|
|
interleaved[i*6 + 2] = mesh.positions[i*3 + 2];
|
|
interleaved[i*6 + 3] = mesh.normals[i*3 + 0];
|
|
interleaved[i*6 + 4] = mesh.normals[i*3 + 1];
|
|
interleaved[i*6 + 5] = mesh.normals[i*3 + 2];
|
|
}
|
|
|
|
glGenVertexArrays(1, &g.vao);
|
|
glGenBuffers(1, &g.vbo);
|
|
glGenBuffers(1, &g.ebo);
|
|
|
|
glBindVertexArray(g.vao);
|
|
|
|
glBindBuffer(GL_ARRAY_BUFFER, g.vbo);
|
|
glBufferData(GL_ARRAY_BUFFER,
|
|
(GLsizeiptr)(interleaved.size() * sizeof(float)),
|
|
interleaved.data(),
|
|
GL_STATIC_DRAW);
|
|
|
|
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, g.ebo);
|
|
glBufferData(GL_ELEMENT_ARRAY_BUFFER,
|
|
(GLsizeiptr)(mesh.indices.size() * sizeof(uint32_t)),
|
|
mesh.indices.data(),
|
|
GL_STATIC_DRAW);
|
|
|
|
// location 0 = a_pos (vec3)
|
|
glEnableVertexAttribArray(0);
|
|
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE,
|
|
(GLsizei)(6 * sizeof(float)),
|
|
(const void*)0);
|
|
// location 1 = a_normal (vec3)
|
|
glEnableVertexAttribArray(1);
|
|
glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE,
|
|
(GLsizei)(6 * sizeof(float)),
|
|
(const void*)(3 * sizeof(float)));
|
|
|
|
glBindBuffer(GL_ARRAY_BUFFER, 0);
|
|
glBindVertexArray(0);
|
|
|
|
g.index_count = (int)mesh.indices.size();
|
|
return g;
|
|
}
|
|
|
|
void mesh_gpu_destroy(MeshGpu& g) {
|
|
if (g.ebo) { glDeleteBuffers(1, &g.ebo); g.ebo = 0; }
|
|
if (g.vbo) { glDeleteBuffers(1, &g.vbo); g.vbo = 0; }
|
|
if (g.vao) { glDeleteVertexArrays(1, &g.vao); g.vao = 0; }
|
|
g.index_count = 0;
|
|
}
|
|
|
|
} // namespace fn::gfx
|