LibGame v0.4.0
The LG Game Engine - Copyright (C) 2024-2026 ETMSoftware
Loading...
Searching...
No Matches
lg_mesh.h
1/*
2 * LibGame - Copyright (C) Emmanuel Thomas-Maurin 2011-2026
3 * All rights reserved
4 */
5
6#ifndef LG_MESH_H
7#define LG_MESH_H
8
9#define LG_MESH_NAME_MAX_LEN (512 - 1)
10#define LG_MESH_FULLPATH_MAX_LEN (512 - 1)
11#define MAT_NAME_MAX_LEN (64 - 1)
12#define TEX_FILENAME_MAX_LEN (512 - 1) /* = LG_TEX_PATH_MAX_LEN */
13
14#define N_NEWMTL_USEMTL_TAGS_MAX 4096
15
16#define BINARY_MESH_EXT "bmesh"
17
18#define LG_FLOAT_EPSILON (1e-6) /* 1e-6 or 1e-8 ? */
19#define MAX_U32BIT_VALUE 4294967296
20
21#define CHECK_PATH(_z_) INFO_OUT("DEBUG: [%s %d]: %s() -> %s\n", basename2(__FILE__), __LINE__, __func__, _z_)
22
23#define LG_MESH_IS_RH 1
24#define LG_MESH_IS_LH 2
25
26/*
27 * If GL ES version < 3.0, need GL_OES_element_index_uint extension for UNSIGNED_INT (uint32_t) IBO indices
28 */
29
30/* Mesh original format, ie from OBJ/FBX file or whatever */
31typedef enum {
32 LG_MESH_OBJ,
33 LG_MESH_FBX,
34 LG_MESH_TERRAIN,
35 LG_MESH_OTHER
36} lg_mesh_type;
37
38/* Actually name and texture - misleading */
39typedef struct {
40 char name[MAT_NAME_MAX_LEN + 1];
41 LG_Texture *texture;
42 char tex_full_path[TEX_FILENAME_MAX_LEN + 1]; /* Full path to image file */
44
45/* Axis-aligned bounding box */
46typedef union {
47 struct {
48 float min_x;
49 float max_x;
50 float min_y;
51 float max_y;
52 float min_z;
53 float max_z;
54 };
55 #if 0
56 /* LG_BBox_v2 ? */
57 struct {
58 vec3_t center;
59 float extents;
60 };
61 /* LG_BBox_v3 ? */
62 struct {
63 vec3_t min;
64 vec3_t max;
65 };
66 #endif
67} LG_BBox;
68
69/*
70 * === Triangle mesh ===
71 *
72 * We want the same type sizes in binary files on all suppored platforms
73 * (ie Linux and Android so far) to avoid portability issues, so we now
74 * use fixed-size types (uint32_t, int32_t, ...) a lot for vertices structs
75 * and buffer objects.
76 *
77 * In OBJ file:
78 * - 'mtllib' -> obj_file.mtl
79 * - 'usemtl' -> material name
80 *
81 * In MTL file:
82 * - 'newmtl' -> material name
83 * - 'map_K*' -> texture path
84 */
85typedef struct {
86 int32_t type; /* lg_mesh_type = mesh original format, ie from OBJ/FBX file or whatever */
87 char full_path[LG_MESH_FULLPATH_MAX_LEN + 1]; /* Full path of MESH file (OBJ/FBX/BMESH) */
88 zboolean skinned;
89 /* Generated VBO and IBO */
90 union {
91 Vertex_uv_n *vbo_data; /* VBO (with interleaved vertex data) - sizeof(Vertex_uv_n) = 24 */
92 Vertex_uvn_iw *vbo_data_iw; /* VBO (with interleaved vertex data) - sizeof(Vertex_uvn_iw) = 36 */
93 //Vertex_rgba_n *vbo_data_rgba_n; /* -> TO ASSIGN COLORS TO ELEVATIONS - sizeof(Vertex_rgba_n) = 24 */
94 };
95 uint32_t *ibo_data; /* IBO (indices start at 0) - sizeof(uint32_t) = 4 */
96 uint32_t vbo_size; /* previously size_t */
97 uint32_t ibo_size; /* previously size_t */
98 /* Read from OBJ file */
99 int32_t n_v; /* Num of coords vertices */
100 int32_t n_vt; /* Num of texture coords */
101 int32_t n_vn; /* Num of normals */
102 int32_t n_f; /* Num of faces */
103 char mtl_file[LG_MESH_FULLPATH_MAX_LEN + 1]; /* The MTL file path */
104 int32_t n_usemtl; /* Num of 'usemtl' tags in OBJ file */
105 /* Read from MTL file */
106 int32_t n_mat; /* Num of 'newmtl'/'map_K' tags (materials with referenced textures) in MTL file */
107 LG_Material materials[N_NEWMTL_USEMTL_TAGS_MAX]; /* Material's 'lib' (LG_Material = name and texture) */
108 uint32_t i_mat_in_vbo[N_NEWMTL_USEMTL_TAGS_MAX]; /* Material face indice in VBO, referenced by 'usemtl' tags */
109 uint32_t i_mat_in_lib[N_NEWMTL_USEMTL_TAGS_MAX]; /* Texture indice in materials[N_NEWMTL_USEMTL_TAGS_MAX] */
110 LG_BBox bbox;
111 LG_Cuboid b_cuboid; /* Bounding cuboid */
112 Lines3D_VB b_cuboid_l3d_vb; /* Lines3D_VB from bounding box cuboid */
113 zboolean xyz_normalized;
114 double normalize_k;
115 zboolean horiz_centered; /* Horizontally centered -> x, z*/
116 zboolean vert_centered; /* Vertically centered -> y */
117 zboolean vert_bottom; /* Vertically at bottom -> y - set mesh origin at bottom, override do_vert_center */
118} LG_Mesh;
119
120/* Mesh loading flags */
121typedef struct {
122 zboolean save_to_assets; /* Save to assets as BMESH, otherwise to cache - on Android, should always be set to FALSE as you can't write to assets */
123 zboolean invert_z; /* Invert z spatial coord - should be set to TRUE if mesh uses RH coords sys, FALSE if mesh uses LH coords sys */
124 zboolean normalize_xyz;
125 zboolean horiz_center;
126 zboolean vert_center; /* Center mesh vertically, if vert_bottom is not set */
127 zboolean vert_bottom; /* Set mesh origin vertically at bottom, override vert_center */
129
130/* Helper #define's */
131#define SAVE_TO_ASSETS TRUE
132#define INVERT_Z TRUE
133#define NORMALIZE_XYZ TRUE
134#define HORIZ_CENTER TRUE
135#define VERT_CENTER TRUE
136#define VERT_BOTTOM TRUE
137
138/*
139 * BINARY MESH (.bmesh) file format
140 * ================================
141 * - Header = Serializable_LG_Mesh
142 * -> header_size = lg_align_up_to_next_4_bytes_boundary((void *)sizeof(Serializable_LG_Mesh))
143 * - VBO data block - aligned to 4 bytes boundaries
144 * -> starting at header_size
145 * - IBO data block - aligned to 4 bytes boundaries
146 * -> starting at header_size + lg_align_up_to_next_4_bytes_boundary((void *)(uint64_t)mesh->vbo_size)
147 */
148
149/*
150 * === Structs for serialization ===
151 * We convert pointers to two uint32_t values:
152 * Vertex_uv_n *vbo_data
153 * ->
154 * uint32_t vbo_data_big;
155 * uint32_t vbo_data_little;
156 *
157 */
158
159typedef struct {
160 char name[MAT_NAME_MAX_LEN + 1];
161 uint32_t texture_big; /* Pointer value as 2 uint32_t */
162 uint32_t texture_little;
163 char tex_full_path[TEX_FILENAME_MAX_LEN + 1];
165
166typedef struct {
167 int32_t type;
168 char full_path[LG_MESH_FULLPATH_MAX_LEN + 1];
169 zboolean skinned;
170 uint32_t vbo_data_big; /* Pointer value as 2 uint32_t */
171 uint32_t vbo_data_little;
172 uint32_t ibo_data_big; /* Pointer value as 2 uint32_t */
173 uint32_t ibo_data_little;
174 uint32_t vbo_size;
175 uint32_t ibo_size;
176 int32_t n_v;
177 int32_t n_vt;
178 int32_t n_vn;
179 int32_t n_f;
180 char mtl_file[LG_MESH_FULLPATH_MAX_LEN + 1];
181 int32_t n_usemtl;
182 int32_t n_mat;
183 Serializable_LG_Material materials[N_NEWMTL_USEMTL_TAGS_MAX];
184 uint32_t i_mat_in_vbo[N_NEWMTL_USEMTL_TAGS_MAX];
185 uint32_t i_mat_in_lib[N_NEWMTL_USEMTL_TAGS_MAX];
186 LG_BBox bbox;
187 LG_Cuboid b_cuboid;
188 Lines3D_VB b_cuboid_l3d_vb;
189 zboolean xyz_normalized;
190 double normalize_k;
191 zboolean horiz_centered;
192 zboolean vert_centered;
193 zboolean vert_bottom;
195
197
198LG_Mesh *lg_mesh_new_from_obj(const char *, zboolean, zboolean, zboolean, zboolean, zboolean);
199
200LG_Mesh *lg_mesh_new_from_obj_relpath(const char *, zboolean, zboolean, zboolean, zboolean, zboolean);
201
202LG_Mesh *lg_mesh_new_from_fbx(const char *, zboolean, zboolean, zboolean, zboolean, zboolean);
203
204LG_Mesh *lg_mesh_new_from_fbx_relpath(const char *, zboolean, zboolean, zboolean, zboolean, zboolean);
205
206void lg_mesh_free(LG_Mesh *);
207
208void lg_mesh_free_v2(LG_Mesh **);
209
210int lg_bmesh_save_to_file(const char *, LG_Mesh *);
211
212int lg_bmesh_load_from_file(const char *, LG_Mesh **);
213
215
217
219
221
223
224LG_LoadMesh_Flags lg_loadmesh_flags(zboolean, zboolean, zboolean, zboolean, zboolean, zboolean);
225
226void lg_mesh_info(LG_Mesh *, int);
227
228char *lg_replace_file_extension(const char *, const char *);
229
230#endif /* LG_MESH_H */
void lg_mesh_info(LG_Mesh *mesh, int show_first_n)
Definition lg_mesh.c:638
LG_Mesh * lg_mesh_new_from_fbx(const char *full_path, zboolean invert_z, zboolean normalize_xyz, zboolean horiz_center, zboolean vert_center, zboolean vert_bottom)
Definition lg_mesh.c:234
int lg_mesh_reload_mats(LG_Mesh *mesh)
Definition lg_mesh.c:464
void lg_mesh_free_v2(LG_Mesh **mesh)
Definition lg_mesh.c:291
LG_Mesh * lg_mesh_new_from_obj_relpath(const char *relative_path, zboolean invert_z, zboolean normalize_xyz, zboolean horiz_center, zboolean vert_center, zboolean vert_bottom)
Definition lg_mesh.c:208
LG_Mesh * lg_mesh_new_from_fbx_relpath(const char *relative_path, zboolean invert_z, zboolean normalize_xyz, zboolean horiz_center, zboolean vert_center, zboolean vert_bottom)
Definition lg_mesh.c:250
LG_LoadMesh_Flags lg_loadmesh_flags(zboolean save_to_assets, zboolean invert_z, zboolean normalize_xyz, zboolean horiz_center, zboolean vert_center, zboolean vert_bottom)
Definition lg_mesh.c:621
int lg_bmesh_load_from_file(const char *full_path, LG_Mesh **mesh)
Definition lg_mesh.c:375
void lg_serialize_LG_Material_64_to_32(Serializable_LG_Material *s_mat, LG_Material *mat)
Definition lg_mesh.c:486
void lg_unserialize_LG_Material_32_to_64(LG_Material *mat, Serializable_LG_Material *s_mat)
Definition lg_mesh.c:500
void lg_unserialize_LG_Mesh_32_to_64(LG_Mesh *mesh, Serializable_LG_Mesh *s_mesh)
Definition lg_mesh.c:561
void lg_serialize_LG_Mesh_64_to_32(Serializable_LG_Mesh *s_mesh, LG_Mesh *mesh)
Definition lg_mesh.c:513
LG_Mesh * lg_mesh_new_from_obj(const char *full_path, zboolean invert_z, zboolean normalize_xyz, zboolean horiz_center, zboolean vert_center, zboolean vert_bottom)
Definition lg_mesh.c:182
int lg_bmesh_save_to_file(const char *full_path, LG_Mesh *mesh)
Definition lg_mesh.c:316
void lg_mesh_free(LG_Mesh *mesh)
Definition lg_mesh.c:260
char * lg_replace_file_extension(const char *path, const char *new_ext)
Definition lg_mesh.c:743
LG_Mesh * lg_mesh_load(const char *full_path, LG_LoadMesh_Flags flags)
Definition lg_mesh.c:104
Definition lg_3d_primitives.h:67
Definition lg_mesh.h:121
Definition lg_mesh.h:39
Definition lg_mesh.h:85
Definition lg_textures.h:45
Definition lg_3d_primitives.h:53
Definition lg_mesh.h:159
Definition lg_mesh.h:166
Definition lg_vertex.h:46
Definition lg_vertex.h:62
Definition math_3d.h:123
Definition lg_mesh.h:46