summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/cglm_bindings.c17
-rw-r--r--src/cglm_bindings.h12
-rw-r--r--src/honey.c14
-rw-r--r--src/mesh/mesh.c126
-rw-r--r--src/mesh/mesh.h8
5 files changed, 165 insertions, 12 deletions
diff --git a/src/cglm_bindings.c b/src/cglm_bindings.c
index 95c9d81..f8f6c8a 100644
--- a/src/cglm_bindings.c
+++ b/src/cglm_bindings.c
@@ -61,6 +61,7 @@ void honey_setup_cglm(lua_State* L)
honey_lua_element camera_elements[] = {
{ "perspective", HONEY_FUNCTION, { .function = honey_cglm_perspective } },
{ "orthographic", HONEY_FUNCTION, { .function = honey_cglm_orthographic } },
+ { "look", HONEY_FUNCTION, { .function = honey_cglm_look } },
};
honey_lua_element cglm_elements[] = {
@@ -73,7 +74,7 @@ void honey_setup_cglm(lua_State* L)
{ "mat3", HONEY_TABLE, { .table = { 8, mat3_elements } } },
{ "mat4", HONEY_TABLE, { .table = { 10, mat4_elements } } },
{ "affine", HONEY_TABLE, { .table = { 3, affine_elements } } },
- { "camera", HONEY_TABLE, { .table = { 2, camera_elements } } },
+ { "camera", HONEY_TABLE, { .table = { 3, camera_elements } } },
};
honey_lua_create_table(L, cglm_elements, 9);
@@ -769,3 +770,17 @@ int honey_cglm_orthographic(lua_State* L)
glm_ortho_aabb(box, matrix);
return 0;
}
+
+/* ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ */
+
+int honey_cglm_look(lua_State* L)
+{
+ float *position, *direction, *up, *dest;
+ honey_lua_parse_arguments(L, 4,
+ HONEY_USERDATA, &position,
+ HONEY_USERDATA, &direction,
+ HONEY_USERDATA, &up,
+ HONEY_USERDATA, &dest);
+ glm_look(position, direction, up, dest);
+ return 0;
+}
diff --git a/src/cglm_bindings.h b/src/cglm_bindings.h
index 09a29c3..ba7714e 100644
--- a/src/cglm_bindings.h
+++ b/src/cglm_bindings.h
@@ -508,4 +508,16 @@ int honey_cglm_perspective(lua_State* L);
*/
int honey_cglm_orthographic(lua_State* L);
+/** @brief Compute the view matrix.
+ *
+ * @param[in] position The camera's vec3 position.
+ * @param[in] direction The vec3 direction the camera is facing.
+ * @param[in] up The camera's vec3 up vector.
+ * @param[out] dest The view matrix destination.
+ *
+ * @returns Nothing.
+ */
+int honey_cglm_look(lua_State* L);
+
+
#endif
diff --git a/src/honey.c b/src/honey.c
index 17b0648..c63ab2f 100644
--- a/src/honey.c
+++ b/src/honey.c
@@ -97,16 +97,9 @@ bool honey_run(lua_State* L, honey_options opts) {
honey_window_information* info = lua_touserdata(L, -1);
honey_window window = info->window;
- char* script;
- honey_result res = honey_format_string(&script,
- "%s/main.lua",
- opts.script_directory);
- if (res != HONEY_OK) {
- fprintf(stderr, "[honey] FATAL: could not allocate space for script filename!");
- return false;
- }
+ chdir(opts.script_directory);
- if (luaL_loadfile(L, script) == 0) {
+ if (luaL_loadfile(L, "main.lua") == 0) {
if (!honey_lua_pcall(L, 0, 1) == 0) {
const char* error = lua_tostring(L, -1);
fprintf(stderr, "[honey] ERROR: %s\n", error);
@@ -116,8 +109,7 @@ bool honey_run(lua_State* L, honey_options opts) {
else {
fprintf(stderr,
- "[honey] ERROR: failed to load %s: %s!\n",
- script,
+ "[honey] ERROR: failed to load main.lua: %s!\n",
lua_tostring(L, -1));
return false;
}
diff --git a/src/mesh/mesh.c b/src/mesh/mesh.c
index 9c045ec..ab3e92c 100644
--- a/src/mesh/mesh.c
+++ b/src/mesh/mesh.c
@@ -22,6 +22,7 @@ static int honey_mesh_lua_delete(lua_State* L)
void honey_setup_mesh(lua_State* L)
{
honey_lua_element mesh_elements[] = {
+ { "load", HONEY_FUNCTION, { .function = honey_mesh_load } },
{ "draw", HONEY_FUNCTION, { .function = honey_mesh_lua_draw } },
{ "delete", HONEY_FUNCTION, { .function = honey_mesh_lua_delete } },
};
@@ -31,6 +32,131 @@ void honey_setup_mesh(lua_State* L)
/* ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ */
+static honey_mesh assimp_to_honey_mesh(struct aiMesh* mesh,
+ struct aiScene* scene)
+{
+ unsigned int vertex_step = 6;
+ bool mesh_has_uvs = false;
+ unsigned int n_vertices = mesh->mNumVertices;
+
+ if (mesh->mTextureCoords[0]) {
+ mesh_has_uvs = true;
+ vertex_step = 8;
+ }
+
+ float* vertices = malloc(sizeof(float) * vertex_step * n_vertices);
+ for (int i=0; i<n_vertices; i++) {
+ int j = i*vertex_step;
+ /* positions */
+ vertices[j+0] = mesh->mVertices[i].x;
+ vertices[j+1] = mesh->mVertices[i].y;
+ vertices[j+2] = mesh->mVertices[i].z;
+
+ /* normals */
+ vertices[j+3] = mesh->mNormals[i].x;
+ vertices[j+4] = mesh->mNormals[i].y;
+ vertices[j+5] = mesh->mNormals[i].z;
+
+ /* uvs? */
+ if (mesh_has_uvs) {
+ vertices[j+6] = mesh->mTextureCoords[0][i].x;
+ vertices[j+7] = mesh->mTextureCoords[0][i].y;
+ }
+ }
+
+ unsigned int n_indices = mesh->mNumFaces*3;
+ unsigned int* indices = malloc(sizeof(unsigned int) * n_indices);
+ for (int i=0; i<mesh->mNumFaces; i++) {
+ int j = 3*i;
+ struct aiFace face = mesh->mFaces[i];
+ indices[j+0] = face.mIndices[0];
+ indices[j+1] = face.mIndices[1];
+ indices[j+2] = face.mIndices[2];
+ }
+
+ honey_mesh result;
+
+ if (mesh_has_uvs) {
+ unsigned int n_attributes = 3;
+ unsigned int attribute_sizes[] = { 3, 3, 2 };
+ honey_mesh_new(&result,
+ vertices, n_vertices,
+ n_attributes, attribute_sizes,
+ indices, n_indices);
+ }
+ else {
+ unsigned int n_attributes = 2;
+ unsigned int attribute_sizes[] = { 3, 3 };
+ honey_mesh_new(&result,
+ vertices, n_vertices,
+ n_attributes, attribute_sizes,
+ indices, n_indices);
+ }
+
+ free(vertices);
+ free(indices);
+
+ return result;
+}
+
+/* ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ */
+
+static void process_nodes_recursively(lua_State* L,
+ struct aiScene* scene,
+ struct aiNode* node,
+ int* n_meshes)
+{
+ for (int i=0; i<node->mNumMeshes; i++) {
+ honey_mesh* mesh = lua_newuserdata(L, sizeof(honey_mesh));
+ struct aiMesh* assimp_mesh = scene->mMeshes[node->mMeshes[i]];
+ *mesh = assimp_to_honey_mesh(assimp_mesh, scene);
+ lua_rawseti(L, -2, *n_meshes);
+ *n_meshes++;
+ }
+
+ for (int i=0; i<node->mNumChildren; i++) {
+ process_nodes_recursively(L, scene, node->mChildren[i], n_meshes);
+ }
+}
+
+/* ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ */
+
+int honey_mesh_load(lua_State* L)
+{
+ char* filename;
+ honey_lua_parse_arguments(L, 1, HONEY_STRING, &filename);
+
+ int n_meshes = 1;
+
+ struct aiScene* scene = aiImportFile(filename,
+ aiProcess_Triangulate |
+ aiProcess_FlipUVs);
+ if (scene == NULL) {
+ char* error;
+ honey_format_string(&error, "could not open file '%s'", filename);
+ lua_pushstring(L, error);
+ free(error);
+ lua_error(L);
+ }
+
+ if (scene->mFlags & AI_SCENE_FLAGS_INCOMPLETE ||
+ scene->mRootNode == NULL) {
+ char* error;
+ honey_format_string(&error, "could not read mesh(es) in '%s'", filename);
+ lua_pushstring(L, error);
+ free(error);
+ lua_error(L);
+ }
+
+ lua_createtable(L, 0, 0);
+
+ process_nodes_recursively(L, scene, scene->mRootNode, n_meshes);
+
+ return 1;
+}
+
+/* ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ */
+
honey_result honey_mesh_new(honey_mesh* mesh,
float* vertices,
unsigned int n_vertices,
diff --git a/src/mesh/mesh.h b/src/mesh/mesh.h
index 81bcc94..0f9c1a3 100644
--- a/src/mesh/mesh.h
+++ b/src/mesh/mesh.h
@@ -16,6 +16,14 @@ typedef struct {
/** @brief Lua bindings for mesh drawing and deletion functions. */
void honey_setup_mesh(lua_State* L);
+/** @brief Load all meshes from a file.
+ *
+ * @param[in] filename The name of the file to load from.
+ *
+ * @returns A table containing all of the meshes.
+ */
+int honey_mesh_load(lua_State* L);
+
/** @brief Create a new mesh from vertex and index arrays.
*
* Note that this function creates copies of the vertex and index arrays,