8 typedef struct scene scene
;
32 GLuint tex_dual_noise
;
35 static void scene_init( scene
*pscene
)
38 pscene
->indices
= NULL
;
39 pscene
->vertex_count
= 0;
40 pscene
->indice_count
= 0;
41 pscene
->shadower_count
= 0;
42 pscene
->shadower_cap
= 0;
43 pscene
->submesh
.indice_start
= 0;
44 pscene
->submesh
.indice_count
= 0;
46 v3_fill( pscene
->bbx
[0], 999999.9f
);
47 v3_fill( pscene
->bbx
[1], -999999.9f
);
50 static int noise_ready
= 0;
55 u8
*buf
= malloc( 256*256*2 );
57 for( int i
=0; i
<256*256; i
++ )
63 for( int y
=0; y
<256; y
++ )
65 for( int x
=0; x
<256; x
++ )
67 u8
*pr
= &buf
[(y
*256+x
)*2],
68 *pg
= &buf
[(((y
+17)&0xff)*256+((x
+37)&0xff))*2+1];
73 /* TODO: This texture should be delted somewhere */
74 glGenTextures( 1, &tex_dual_noise
);
75 glBindTexture( GL_TEXTURE_2D
, tex_dual_noise
);
76 glTexImage2D( GL_TEXTURE_2D
, 0, GL_RG
, 256, 256, 0, GL_RG
,
77 GL_UNSIGNED_BYTE
, buf
);
87 static void *buffer_reserve( void *buffer
, u32 count
, u32
*cap
, u32 amount
,
90 if( count
+amount
> *cap
)
92 *cap
= VG_MAX( (*cap
)*2, (*cap
)+amount
);
94 return realloc( buffer
, (*cap
) * emsize
);
100 static void *buffer_fix( void *buffer
, u32 count
, u32
*cap
, size_t emsize
)
103 return realloc( buffer
, (*cap
) * emsize
);
107 * Append a model into the scene with a given transform
109 static void scene_add_submesh( scene
*pscene
, mdl_header
*mdl
,
110 mdl_submesh
*sm
, m4x3f transform
)
112 pscene
->verts
= buffer_reserve( pscene
->verts
, pscene
->vertex_count
,
113 &pscene
->vertex_cap
, sm
->vertex_count
, sizeof(mdl_vert
) );
114 pscene
->indices
= buffer_reserve( pscene
->indices
, pscene
->indice_count
,
115 &pscene
->indice_cap
, sm
->indice_count
, sizeof(u32
) );
118 m3x3_copy( transform
, normal_matrix
);
119 v3_normalize( normal_matrix
[0] );
120 v3_normalize( normal_matrix
[1] );
121 v3_normalize( normal_matrix
[2] );
123 /* Transform and place vertices */
124 mdl_vert
*src_verts
= mdl_submesh_vertices( mdl
, sm
);
125 u32
*src_indices
= mdl_submesh_indices( mdl
, sm
);
128 box_copy( sm
->bbx
, bbxnew
);
129 m4x3_transform_aabb( transform
, bbxnew
);
130 box_concat( pscene
->bbx
, bbxnew
);
132 for( u32 i
=0; i
<sm
->vertex_count
; i
++ )
134 mdl_vert
*pvert
= &pscene
->verts
[ pscene
->vertex_count
+i
],
135 *src
= &src_verts
[ i
];
137 m4x3_mulv( transform
, src
->co
, pvert
->co
);
138 m3x3_mulv( normal_matrix
, src
->norm
, pvert
->norm
);
140 pvert
->colour
[0] = src
->colour
[0];
141 pvert
->colour
[1] = src
->colour
[1];
142 pvert
->colour
[2] = src
->colour
[2];
143 pvert
->colour
[3] = src
->colour
[3];
144 v2_copy( src
->uv
, pvert
->uv
);
147 for( u32 i
=0; i
<sm
->indice_count
; i
++ )
149 u32
*pidx
= &pscene
->indices
[ pscene
->indice_count
+i
];
150 *pidx
= src_indices
[i
] + pscene
->vertex_count
;
153 pscene
->vertex_count
+= sm
->vertex_count
;
154 pscene
->indice_count
+= sm
->indice_count
;
158 * One by one adders for simplified access (mostly procedural stuff)
160 static void scene_push_tri( scene
*pscene
, u32 tri
[3] )
162 pscene
->indices
= buffer_reserve( pscene
->indices
, pscene
->indice_count
,
163 &pscene
->indice_cap
, 3, sizeof(u32
) );
165 u32
*dst
= &pscene
->indices
[pscene
->indice_count
];
170 pscene
->indice_count
+= 3;
173 static void scene_push_vert( scene
*pscene
, mdl_vert
*v
)
175 pscene
->verts
= buffer_reserve( pscene
->verts
, pscene
->vertex_count
,
176 &pscene
->vertex_cap
, 1, sizeof(mdl_vert
) );
178 pscene
->verts
[pscene
->vertex_count
++] = *v
;
181 static void scene_copy_slice( scene
*pscene
, mdl_submesh
*sm
)
183 sm
->indice_start
= pscene
->submesh
.indice_start
;
184 sm
->indice_count
= pscene
->indice_count
- sm
->indice_start
;
186 sm
->vertex_start
= pscene
->submesh
.vertex_start
;
187 sm
->vertex_count
= pscene
->vertex_count
- sm
->vertex_start
;
189 pscene
->submesh
.indice_start
= pscene
->indice_count
;
190 pscene
->submesh
.vertex_start
= pscene
->vertex_count
;
193 static void scene_fix( scene
*pscene
)
195 buffer_fix( pscene
->verts
, pscene
->vertex_count
,
196 &pscene
->vertex_cap
, sizeof( mdl_vert
));
198 buffer_fix( pscene
->indices
, pscene
->indice_count
,
199 &pscene
->indice_cap
, sizeof( mdl_vert
));
202 static void scene_upload( scene
*pscene
)
204 mesh_upload( &pscene
->mesh
,
205 pscene
->verts
, pscene
->vertex_count
,
206 pscene
->indices
, pscene
->indice_count
);
208 vg_info( "Scene upload\n" );
209 vg_info( " indices:%u\n", pscene
->indice_count
);
210 vg_info( " verts:%u\n", pscene
->vertex_count
);
213 static void scene_bind( scene
*pscene
)
215 mesh_bind( &pscene
->mesh
);
218 static void scene_draw( scene
*pscene
)
220 mesh_drawn( 0, pscene
->indice_count
);
223 static void scene_free_offline_buffers( scene
*pscene
)
225 free( pscene
->verts
);
226 free( pscene
->indices
);
229 static void scene_free( scene
*pscene
)
231 scene_free_offline_buffers( pscene
);
235 static void scene_register(void)
243 static void scene_bh_expand_bound( void *user
, boxf bound
, u32 item_index
)
246 mdl_vert
*pa
= &s
->verts
[ s
->indices
[item_index
*3+0] ],
247 *pb
= &s
->verts
[ s
->indices
[item_index
*3+1] ],
248 *pc
= &s
->verts
[ s
->indices
[item_index
*3+2] ];
250 box_addpt( bound
, pa
->co
);
251 box_addpt( bound
, pb
->co
);
252 box_addpt( bound
, pc
->co
);
255 static float scene_bh_centroid( void *user
, u32 item_index
, int axis
)
258 mdl_vert
*pa
= &s
->verts
[ s
->indices
[item_index
*3+0] ],
259 *pb
= &s
->verts
[ s
->indices
[item_index
*3+1] ],
260 *pc
= &s
->verts
[ s
->indices
[item_index
*3+2] ];
262 return (pa
->co
[axis
] + pb
->co
[axis
] + pc
->co
[axis
]) * (1.0f
/3.0f
);
265 static void scene_bh_swap( void *user
, u32 ia
, u32 ib
)
269 u32
*ti
= &s
->indices
[ia
*3];
270 u32
*tj
= &s
->indices
[ib
*3];
286 static void scene_bh_debug( void *user
, u32 item_index
)
289 u32 idx
= item_index
*3;
290 mdl_vert
*pa
= &s
->verts
[ s
->indices
[ idx
+0 ] ],
291 *pb
= &s
->verts
[ s
->indices
[ idx
+1 ] ],
292 *pc
= &s
->verts
[ s
->indices
[ idx
+2 ] ];
294 vg_line( pa
->co
, pb
->co
, 0xff0000ff );
295 vg_line( pb
->co
, pc
->co
, 0xff0000ff );
296 vg_line( pc
->co
, pa
->co
, 0xff0000ff );
299 static int scene_bh_ray( void *user
, u32 index
, v3f co
, v3f dir
, ray_hit
*hit
)
304 u32
*tri
= &s
->indices
[ index
*3 ];
306 for( int i
=0; i
<3; i
++ )
307 v3_copy( s
->verts
[tri
[i
]].co
, positions
[i
] );
310 if(ray_tri( positions
, co
, dir
, &t
))
323 static bh_system bh_system_scene
=
325 .expand_bound
= scene_bh_expand_bound
,
326 .item_centroid
= scene_bh_centroid
,
327 .item_swap
= scene_bh_swap
,
328 .item_debug
= scene_bh_debug
,
329 .cast_ray
= scene_bh_ray
333 * An extra step is added onto the end to calculate the hit normal
335 static int scene_raycast( scene
*s
, v3f co
, v3f dir
, ray_hit
*hit
)
337 int count
= bh_ray( &s
->bhtris
, 0, co
, dir
, hit
);
343 float *pa
= s
->verts
[hit
->tri
[0]].co
,
344 *pb
= s
->verts
[hit
->tri
[1]].co
,
345 *pc
= s
->verts
[hit
->tri
[2]].co
;
347 v3_sub( pa
, pb
, v0
);
348 v3_sub( pc
, pb
, v1
);
349 v3_cross( v1
, v0
, hit
->normal
);
350 v3_normalize( hit
->normal
);
351 v3_muladds( co
, dir
, hit
->dist
, hit
->pos
);
357 static void scene_bh_create( scene
*s
)
359 u32 triangle_count
= s
->indice_count
/ 3;
360 bh_create( &s
->bhtris
, &bh_system_scene
, s
, triangle_count
);