fixed m4x3 mul, rendering works
[csRadar.git] / vmf.h
diff --git a/vmf.h b/vmf.h
index cdec7dd94ec2550dfe228fcd1ff02bd2bbd5a81c..4793e0bda61af53b28c06a4bc521193369c9bc0a 100644 (file)
--- a/vmf.h
+++ b/vmf.h
@@ -1,4 +1,7 @@
 #define SOLID_MAX_SIDES 512
+#define VMF_FLAG_IS_PROP 0x1
+#define VMF_FLAG_IS_INSTANCE 0x2
+#define VMF_FLAG_BRUSH_ENT 0x4
 
 typedef struct vmf_solid vmf_solid;
 typedef struct vmf_vert vmf_vert;
@@ -67,6 +70,8 @@ struct vmf_map
                u32     hash;
                
                vdf_node *root;
+               
+               m4x3f transform;
        }
        *cache;
        
@@ -75,6 +80,12 @@ struct vmf_map
 
 // IMPLEMENTATION
 
+void solidgen_ctx_reset( vmf_solid *ctx )
+{
+       csr_sb_clear( ctx->verts );
+       csr_sb_clear( ctx->indices );
+}
+
 void solidgen_ctx_init( vmf_solid *ctx )
 {
        const u32 init_size = 128;
@@ -573,12 +584,17 @@ u32 vmf_get_mdl( vmf_map *map, const char *mdl )
        return 0;
 }
 
+int vmf_class_is_prop( vdf_node *ent )
+{
+       return !strncmp( kv_get( ent, "classname", "" ), "prop_", 5 );
+}
+
 void vmf_populate_models( vdf_node *vmf, vmf_map *map )
 {
        vdf_foreach( vmf, "entity", ent )
        {
                // Use any class name with prop_
-               if( !strncmp( kv_get( ent, "classname", "" ), "prop_", 5 ))
+               if( vmf_class_is_prop( ent ) )
                {
                        // Check if it exists
                        const char *model_path = kv_get( ent, "model", "" );
@@ -598,7 +614,8 @@ void vmf_populate_models( vdf_node *vmf, vmf_map *map )
                        }
                        
                        // Assign prop-ID for later use
-                       ent->user = mdl_id;
+                       ent->user = VMF_FLAG_IS_PROP;
+                       ent->user1 = mdl_id;
                }
        }
 }
@@ -621,7 +638,7 @@ void vmf_load_models( vmf_map *map )
                vmf_populate_models( map->cache[i].root, map );
        }
        
-       printf( "Indexed (%u) models\n", csr_sb_count( map->models ) );
+       printf( "Indexed (%u) models\n", csr_sb_count( map->models )-1 );
        
        u32 num_success = 0;
        
@@ -629,20 +646,22 @@ void vmf_load_models( vmf_map *map )
        // TODO: Make nice loading bar
        for( int i = 1; i < csr_sb_count( map->models ); i ++ )
        {
-               printf( "Load model (%d)\n", i );
-               
                struct vmf_model *mdl = &map->models[i];
                
                if( mdl_from_find_files( mdl->str, &mdl->mdl ) )
                {
                        num_success ++;
                }
+               else
+               {
+                       fprintf( stderr, "Failed to load model: %s\n", mdl->str );
+               }
        }
        
-       printf( "Done (%u of %u loaded)\n", num_success, csr_sb_count( map->models ) );
+       printf( "Done (%u of %u loaded)\n", num_success, csr_sb_count( map->models )-1 );
 }
 
-void vmf_init_subvmf( vmf_map *map, const char *subvmf );
+u32 vmf_init_subvmf( vmf_map *map, const char *subvmf );
 
 void vmf_load_all_instances( vmf_map *map, vdf_node *vmf )
 {
@@ -654,32 +673,39 @@ void vmf_load_all_instances( vmf_map *map, vdf_node *vmf )
                        const char *path = kv_get( ent, "file", "" );
                        if( strcmp( path, "" ) )
                        {
-                               vmf_init_subvmf( map, path );
+                               if( (ent->user1 = vmf_init_subvmf( map, path )))
+                               {
+                                       ent->user1 --;
+                                       ent->user = VMF_FLAG_IS_INSTANCE;
+                               }
                        }
                }
        }
 }
 
-void vmf_init_subvmf( vmf_map *map, const char *subvmf )
+// TODO: Merge this into above function.. doesnt need to be seperated
+u32 vmf_init_subvmf( vmf_map *map, const char *subvmf )
 {
-       printf( "Loading subvmf: %s\n", subvmf );
-       
+       u32 id;
        u32 hash = djb2( (const unsigned char *)subvmf );
        
        // Check if present
-       for( int i = 0; i < csr_sb_count( map->cache ); i ++ )
+       for( u32 i = 0; i < csr_sb_count( map->cache ); i ++ )
        {
                if( hash == map->cache[i].hash )
                {
                        if( !strcmp( map->cache[i].name, subvmf ) )
                        {
-                               return;
+                               return i+1;
                        }
                }
        }
        
+       printf( "Loading subvmf: %s\n", subvmf );
+       
+       id = csr_sb_count( map->cache );
        map->cache = csr_sb_reserve( map->cache, 1, sizeof( struct vmf_instance ));
-       struct vmf_instance *inst = &map->cache[ csr_sb_count( map->cache ) ];
+       struct vmf_instance *inst = &map->cache[ id ];
        
        if( (inst->root = vdf_open_file( subvmf )) )
        {
@@ -691,12 +717,13 @@ void vmf_init_subvmf( vmf_map *map, const char *subvmf )
                
                // Recursive load other instances
                vmf_load_all_instances( map, inst->root );
+               
+               return id+1;
        }
        else
        {
-               // TODO: Don't die here?
                fprintf( stderr, "Failed to load instance file\n" );
-               exit(0);
+               return 0;
        }
 }
 
@@ -781,3 +808,26 @@ void solidgen_to_obj( vmf_solid *ctx, const char *path )
                fprintf( stderr, "Could not open %s for writing\n", path );
        }
 }
+
+void vmf_entity_transform( vdf_node *ent, m4x3f mat )
+{
+       v3f angles = {0.f,0.f,0.f};
+       v3f offset = {0.f,0.f,0.f};
+       float scale;
+       
+       // Parse
+       scale = kv_get_float( ent, "uniformscale", 1.f );
+       kv_float_array( ent, "angles", 3, angles );
+       kv_float_array( ent, "origin", 3, offset );
+       
+       // Translation
+       m4x3_translate( mat, offset );
+       
+       // Make rotation ( Pitch yaw roll // YZX. Source->OpenGL ordering a lil messed up )
+       m4x3_rotate_z( mat, csr_rad( angles[1] ) );
+       m4x3_rotate_y( mat, csr_rad( angles[0] ) );
+       m4x3_rotate_x( mat, csr_rad( angles[2] ) );
+       
+       // Scale
+       m4x3_scale( mat, scale );
+}