/*
- * Copyright (C) 2021-2022 Mt.ZERO Software, Harry Godden - All Rights Reserved
+ * Copyright (C) 2021-2023 Mt.ZERO Software, Harry Godden - All Rights Reserved
*/
#ifndef MODEL_H
#define MODEL_H
-#include "common.h"
+#include "skaterift.h"
-#define MDL_VERSION_NR 100
+#define MDL_VERSION_MIN 101
+#define MDL_VERSION_NR 102
enum mdl_shader
{
k_shader_standard_vertex_blend = 3,
k_shader_water = 4,
k_shader_invisible = 5,
- k_shader_boundary = 6
+ k_shader_boundary = 6,
+ k_shader_fxglow = 7
};
enum mdl_surface_prop
k_material_flag_grow_grass = 0x00000004,
k_material_flag_grindable = 0x00000008,
k_material_flag_invisible = 0x00000010,
- k_material_flag_boundary = 0x00000020
+ k_material_flag_boundary = 0x00000020,
+ k_material_flag_preview_visibile = 0x00000040
};
#pragma pack(push,1)
typedef struct mdl_array mdl_array;
typedef struct mdl_header mdl_header;
+typedef struct glmesh glmesh;
+struct glmesh
+{
+ GLuint vao, vbo, ebo;
+ u32 indice_count;
+ u32 loaded;
+};
+
struct mdl_transform
{
v3f co, s;
mdl_array index;
};
-struct mdl_context
-{
+struct mdl_context{
FILE *file;
mdl_header info;
- struct mdl_array_ptr
- {
+ struct mdl_array_ptr{
void *data;
u32 count, stride;
}
/* mesh buffers */
verts,
indices;
-
u32 pack_base_offset;
-
- /* pack data */
- //pack;
+
+ /* runtime */
+ glmesh mesh;
};
u32 size = arr->item_size*arr->item_count;
return vg_align8(size);
}
- else
- return 0;
+ else return 0;
}
VG_STATIC const char *mdl_pstr( mdl_context *mdl, u32 pstr );
fseek( mdl->file, mdl->pack_base_offset+info->pack_offset, SEEK_SET );
u64 l = fread( dst, info->pack_size, 1, mdl->file );
- if( l != 1 )
- mdl_load_fatal_corrupt( mdl );
+ if( l != 1 ) mdl_load_fatal_corrupt( mdl );
}
/* TODO: Rename these */
-VG_STATIC
-void mdl_load_array_file_buffer( mdl_context *mdl, mdl_array *arr,
- void *buffer )
+VG_STATIC void mdl_load_array_file_buffer( mdl_context *mdl, mdl_array *arr,
+ void *buffer )
{
if( arr->item_count ){
fseek( mdl->file, arr->file_offset, SEEK_SET );
u64 l = fread( buffer, arr->item_size*arr->item_count, 1, mdl->file );
- if( l != 1 )
- mdl_load_fatal_corrupt( mdl );
+ if( l != 1 ) mdl_load_fatal_corrupt( mdl );
}
}
if( l != 1 )
mdl_load_fatal_corrupt( mdl );
- if( mdl->info.version != MDL_VERSION_NR ){
+ if( mdl->info.version < MDL_VERSION_MIN ){
vg_warn( "For model: %s\n", path );
- vg_warn( " version: %u (current: %u)\n", mdl->info.version,
- MDL_VERSION_NR );
+ vg_warn( " version: %u (min: %u, current: %u)\n",
+ mdl->info.version, MDL_VERSION_MIN, MDL_VERSION_NR );
vg_fatal_error( "Legacy model version incompatable" );
}
VG_STATIC const char *mdl_pstr( mdl_context *mdl, u32 pstr )
{
- return mdl_arritm( &mdl->strings, pstr );
+ return ((char *)mdl_arritm( &mdl->strings, pstr )) + 4;
+}
+
+
+VG_STATIC int
+mdl_pstreq( mdl_context *mdl, u32 pstr, const char *str, u32 djb2 )
+{
+ u32 hash = *((u32 *)mdl_arritm( &mdl->strings, pstr ));
+ if( hash == djb2 ){
+ if( !strcmp( str, mdl_pstr( mdl, pstr ))) return 1;
+ else return 0;
+ }
+ else return 0;
}
+#define MDL_CONST_PSTREQ( MDL, Q, CONSTSTR )\
+ mdl_pstreq( MDL, Q, CONSTSTR, vg_strdjb2( CONSTSTR ) )
+
/*
* Simple mesh interface for OpenGL
* ----------------------------------------------------------------------------
*/
-typedef struct glmesh glmesh;
-struct glmesh
-{
- GLuint vao, vbo, ebo;
- u32 indice_count;
- u32 loaded;
-};
-
VG_STATIC void mesh_upload( glmesh *mesh,
mdl_vert *verts, u32 vert_count,
u32 *indices, u32 indice_count )
VG_STATIC void async_mdl_load_glmesh( void *payload, u32 size )
{
struct payload_glmesh_load *job = payload;
-
mesh_upload( job->mesh, job->verts, job->vertex_count,
job->indices, job->indice_count );
}
+/* TODO: Find out if this needs deprecating in favour of the new full loader */
VG_STATIC void mdl_async_load_glmesh( mdl_context *mdl, glmesh *mesh )
{
mdl_array *arr_vertices = mdl_find_array( mdl, "mdl_vert" );
vg_fatal_error( "no vertex/indice data\n" );
}
}
+
+/* uploads the glmesh, and textures. everything is saved into the mdl_context */
+VG_STATIC void mdl_async_full_load_std( mdl_context *mdl ){
+ mdl_async_load_glmesh( mdl, &mdl->mesh );
+
+ for( u32 i=0; i<mdl_arrcount( &mdl->textures ); i ++ ){
+ vg_linear_clear( vg_mem.scratch );
+ mdl_texture *tex = mdl_arritm( &mdl->textures, i );
+
+ void *data = vg_linear_alloc( vg_mem.scratch, tex->file.pack_size );
+ mdl_fread_pack_file( mdl, &tex->file, data );
+
+ vg_tex2d_load_qoi_async( data, tex->file.pack_size,
+ VG_TEX2D_CLAMP|VG_TEX2D_NEAREST, &tex->glname );
+ }
+}
#endif