mirror of https://github.com/bjornbytes/lovr.git
Model;
This commit is contained in:
parent
9d6b6dddb4
commit
fb6c1c28ed
|
@ -133,6 +133,22 @@ void lovrBufferSetVertex(Buffer* buffer, int index, void* data) {
|
|||
}
|
||||
}
|
||||
|
||||
void lovrBufferSetVertices(Buffer* buffer, float* vertices, int count) {
|
||||
memcpy(buffer->data, vertices, buffer->stride * count);
|
||||
|
||||
glBindVertexArray(buffer->vao);
|
||||
glBindBuffer(GL_ARRAY_BUFFER, buffer->vbo);
|
||||
glBufferData(GL_ARRAY_BUFFER, buffer->size * buffer->stride, buffer->data, buffer->usage);
|
||||
|
||||
int i;
|
||||
BufferAttribute attribute;
|
||||
size_t offset = 0;
|
||||
vec_foreach(&buffer->format, attribute, i) {
|
||||
glVertexAttribPointer(i, attribute.size, attribute.type, GL_FALSE, buffer->stride, (void*) offset);
|
||||
offset += attribute.size + sizeof(attribute.type);
|
||||
}
|
||||
}
|
||||
|
||||
unsigned int* lovrBufferGetVertexMap(Buffer* buffer, int* count) {
|
||||
*count = buffer->map.length;
|
||||
return buffer->map.data;
|
||||
|
|
|
@ -58,6 +58,7 @@ int lovrBufferGetVertexSize(Buffer* buffer);
|
|||
void* lovrBufferGetScratchVertex(Buffer* buffer);
|
||||
void lovrBufferGetVertex(Buffer* buffer, int index, void* dest);
|
||||
void lovrBufferSetVertex(Buffer* buffer, int index, void* vertex);
|
||||
void lovrBufferSetVertices(Buffer* buffer, float* vertices, int count);
|
||||
unsigned int* lovrBufferGetVertexMap(Buffer* buffer, int* count);
|
||||
void lovrBufferSetVertexMap(Buffer* buffer, unsigned int* map, int count);
|
||||
char lovrBufferIsRangeEnabled(Buffer* buffer);
|
||||
|
|
|
@ -7,7 +7,6 @@
|
|||
#include <assimp/cimport.h>
|
||||
#include <assimp/scene.h>
|
||||
#include <assimp/postprocess.h>
|
||||
#include "../model/model.h"
|
||||
|
||||
static GraphicsState state;
|
||||
|
||||
|
|
|
@ -6,7 +6,6 @@
|
|||
|
||||
#ifndef LOVR_GRAPHICS_TYPES
|
||||
#define LOVR_GRAPHICS_TYPES
|
||||
typedef vec_t(mat4) vec_mat4_t;
|
||||
|
||||
#define LOVR_COLOR(r, g, b, a) ((a << 0) | (b << 8) | (g << 16) | (r << 24))
|
||||
#define LOVR_COLOR_R(c) (c >> 24 & 0xff)
|
||||
|
|
|
@ -1,9 +1,76 @@
|
|||
#include "model.h"
|
||||
#include <stdlib.h>
|
||||
|
||||
static void visitNode(ModelData* modelData, ModelNode* node, mat4 transform, vec_float_t* vertices, vec_uint_t* indices) {
|
||||
mat4 newTransform;
|
||||
|
||||
if (!transform) {
|
||||
newTransform = mat4_init();
|
||||
} else {
|
||||
newTransform = mat4_copy(transform);
|
||||
}
|
||||
|
||||
mat4_multiply(newTransform, node->transform);
|
||||
|
||||
int indexOffset = vertices->length / 3;
|
||||
|
||||
// Meshes
|
||||
for (int m = 0; m < node->meshes.length; m++) {
|
||||
ModelMesh* mesh = modelData->meshes.data[node->meshes.data[m]];
|
||||
|
||||
// Transformed vertices
|
||||
for (int v = 0; v < mesh->vertices.length; v++) {
|
||||
ModelVertex vertex = mesh->vertices.data[v];
|
||||
|
||||
float v[4] = {
|
||||
vertex.x,
|
||||
vertex.y,
|
||||
vertex.z,
|
||||
1.f
|
||||
};
|
||||
|
||||
mat4_multiplyVector(newTransform, v);
|
||||
vec_pusharr(vertices, v, 3);
|
||||
}
|
||||
|
||||
// Face vertex indices
|
||||
for (int f = 0; f < mesh->faces.length; f++) {
|
||||
ModelFace face = mesh->faces.data[f];
|
||||
|
||||
for (int v = 0; v < face.indices.length; v++) {
|
||||
vec_push(indices, face.indices.data[v] + indexOffset);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (int c = 0; c < node->children.length; c++) {
|
||||
visitNode(modelData, node->children.data[c], newTransform, vertices, indices);
|
||||
}
|
||||
}
|
||||
|
||||
Model* lovrModelCreate(const char* filename) {
|
||||
Model* model = malloc(sizeof(model));
|
||||
model->modelData = lovrModelDataCreate(filename);
|
||||
|
||||
vec_float_t vertices;
|
||||
vec_init(&vertices);
|
||||
|
||||
vec_uint_t indices;
|
||||
vec_init(&indices);
|
||||
|
||||
visitNode(model->modelData, model->modelData->root, NULL, &vertices, &indices);
|
||||
|
||||
BufferFormat format;
|
||||
BufferAttribute position = { .name = "position", .type = BUFFER_FLOAT, .size = 3 };
|
||||
vec_init(&format);
|
||||
vec_push(&format, position);
|
||||
|
||||
model->buffer = lovrBufferCreate(vertices.length / 3, &format, BUFFER_TRIANGLES, BUFFER_STATIC);
|
||||
lovrBufferSetVertices(model->buffer, vertices.data, vertices.length / 3);
|
||||
lovrBufferSetVertexMap(model->buffer, indices.data, indices.length);
|
||||
|
||||
vec_deinit(&vertices);
|
||||
vec_deinit(&indices);
|
||||
return model;
|
||||
}
|
||||
|
||||
|
@ -11,3 +78,7 @@ void lovrModelDestroy(Model* model) {
|
|||
lovrModelDataDestroy(model->modelData);
|
||||
free(model);
|
||||
}
|
||||
|
||||
void lovrModelDraw(Model* model) {
|
||||
lovrBufferDraw(model->buffer);
|
||||
}
|
||||
|
|
|
@ -1,11 +1,15 @@
|
|||
#include "buffer.h"
|
||||
#include "../model/modelData.h"
|
||||
#include "../glfw.h"
|
||||
|
||||
#ifndef LOVR_MODEL_TYPES
|
||||
#define LOVR_MODEL_TYPES
|
||||
typedef struct {
|
||||
ModelData* modelData;
|
||||
Buffer* buffer;
|
||||
} Model;
|
||||
#endif
|
||||
|
||||
Model* lovrModelCreate(const char* filename);
|
||||
void lovrModelDestroy(Model* model);
|
||||
void lovrModelDraw(Model* model);
|
||||
|
|
|
@ -20,5 +20,12 @@ int luax_destroymodel(lua_State* L) {
|
|||
}
|
||||
|
||||
const luaL_Reg lovrModel[] = {
|
||||
{ "draw", l_lovrModelDraw },
|
||||
{ NULL, NULL }
|
||||
};
|
||||
|
||||
int l_lovrModelDraw(lua_State* L) {
|
||||
Model* model = luax_checkmodel(L, 1);
|
||||
lovrModelDraw(model);
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -7,3 +7,5 @@ void luax_pushmodel(lua_State* L, Model* model);
|
|||
Model* luax_checkmodel(lua_State* L, int index);
|
||||
int luax_destroymodel(lua_State* L);
|
||||
extern const luaL_Reg lovrModel[];
|
||||
|
||||
int l_lovrModelDraw(lua_State* L);
|
||||
|
|
11
src/matrix.c
11
src/matrix.c
|
@ -185,6 +185,17 @@ mat4 mat4_multiply(mat4 a, mat4 b) {
|
|||
return a;
|
||||
}
|
||||
|
||||
void mat4_multiplyVector(mat4 m, float* v) {
|
||||
float v0 = v[0];
|
||||
float v1 = v[1];
|
||||
float v2 = v[2];
|
||||
float v3 = v[3];
|
||||
v[0] = v0 * m[0] + v1 * m[4] + v2 * m[8] + v3 * m[12];
|
||||
v[1] = v0 * m[1] + v1 * m[5] + v2 * m[9] + v3 * m[13];
|
||||
v[2] = v0 * m[2] + v1 * m[6] + v2 * m[10] + v3 * m[14];
|
||||
v[3] = v0 * m[3] + v1 * m[7] + v2 * m[11] + v3 * m[15];
|
||||
}
|
||||
|
||||
// Modified from gl-matrix.c
|
||||
mat4 mat4_invert(mat4 m) {
|
||||
float a00 = m[0], a01 = m[1], a02 = m[2], a03 = m[3],
|
||||
|
|
|
@ -1,4 +1,10 @@
|
|||
#include "vendor/vec/vec.h"
|
||||
|
||||
#ifndef LOVR_MATRIX_TYPES
|
||||
#define LOVR_MATRIX_TYPES
|
||||
typedef float* mat4;
|
||||
typedef vec_t(mat4) vec_mat4_t;
|
||||
#endif
|
||||
|
||||
mat4 mat4_init();
|
||||
void mat4_deinit(mat4 matrix);
|
||||
|
@ -15,4 +21,5 @@ mat4 mat4_translate(mat4 matrix, float x, float y, float z);
|
|||
mat4 mat4_rotate(mat4 matrix, float w, float x, float y, float z);
|
||||
mat4 mat4_scale(mat4 matrix, float x, float y, float z);
|
||||
mat4 mat4_multiply(mat4 a, mat4 b);
|
||||
void mat4_multiplyVector(mat4 m, float* v);
|
||||
mat4 mat4_invert(mat4 matrix);
|
||||
|
|
|
@ -1 +0,0 @@
|
|||
// This page intentionally left blank
|
|
@ -1 +0,0 @@
|
|||
// This page intentionally left blank
|
|
@ -3,7 +3,6 @@
|
|||
#include <assimp/scene.h>
|
||||
#include <assimp/cimport.h>
|
||||
#include <assimp/postprocess.h>
|
||||
#include <stdio.h>
|
||||
|
||||
static void assimpNodeTraversal(ModelNode* node, struct aiNode* assimpNode) {
|
||||
|
||||
|
@ -27,18 +26,25 @@ static void assimpNodeTraversal(ModelNode* node, struct aiNode* assimpNode) {
|
|||
|
||||
ModelData* lovrModelDataCreate(const char* filename) {
|
||||
ModelData* modelData = malloc(sizeof(ModelData));
|
||||
const struct aiScene* scene = aiImportFile(filename, aiProcessPreset_TargetRealtime_MaxQuality);
|
||||
const struct aiScene* scene = aiImportFile(filename, aiProcessPreset_TargetRealtime_MaxQuality | aiProcess_OptimizeGraph);
|
||||
|
||||
// Meshes
|
||||
vec_init(&modelData->meshes);
|
||||
for (int m = 0; m < scene->mNumMeshes; m++) {
|
||||
struct aiMesh* assimpMesh = scene->mMeshes[m];
|
||||
ModelMesh* mesh = malloc(sizeof(ModelMesh));
|
||||
vec_push(&modelData->meshes, mesh);
|
||||
|
||||
// Faces
|
||||
vec_init(&mesh->faces);
|
||||
for (int f = 0; f < assimpMesh->mNumFaces; f++) {
|
||||
struct aiFace assimpFace = assimpMesh->mFaces[f];
|
||||
|
||||
// Skip lines and points, polygons are triangulated
|
||||
if (assimpFace.mNumIndices != 3) {
|
||||
continue;
|
||||
}
|
||||
|
||||
ModelFace face;
|
||||
vec_init(&face.indices);
|
||||
|
||||
|
@ -57,6 +63,8 @@ ModelData* lovrModelDataCreate(const char* filename) {
|
|||
vertex.x = assimpMesh->mVertices[v].x;
|
||||
vertex.y = assimpMesh->mVertices[v].y;
|
||||
vertex.z = assimpMesh->mVertices[v].z;
|
||||
|
||||
vec_push(&mesh->vertices, vertex);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue