X-Git-Url: https://harrygodden.com/git/?a=blobdiff_plain;f=world_render.c;h=1d2256b4f6ddf88d7cefc696b68ece318e23e585;hb=1a7f4a35e88698bdb45c90f646f1645589d5511c;hp=37b095c7bd8939816e4d30115e06dc1018baab68;hpb=22f62f001f21d1b91fefd9fc495c122d9ddf205a;p=carveJwlIkooP6JGAAIwe30JlM.git diff --git a/world_render.c b/world_render.c index 37b095c..1d2256b 100644 --- a/world_render.c +++ b/world_render.c @@ -12,20 +12,18 @@ #include "respawn.h" static int ccmd_set_time( int argc, const char *argv[] ){ - if( argc == 1 ){ - world_instance *world = world_current_instance(); + world_instance *world = world_current_instance(); + if( argc == 1 ) world->time = atof( argv[0] ); - } - else { - vg_error( "Usage set_time <0-1.0>\n" ); - } + else + vg_error( "Usage set_time <0-1.0> (current time: %f)\n", world->time ); return 0; } static void async_world_render_init( void *payload, u32 size ) { vg_info( "Allocate uniform buffers\n" ); - for( int i=0; i<4; i++ ){ + for( int i=0; iubo_bind_point = i; @@ -39,7 +37,7 @@ static void async_world_render_init( void *payload, u32 size ) } vg_info( "Allocate frame buffers\n" ); - for( int i=0; i<4; i++ ){ + for( int i=0; iheightmap; @@ -86,6 +84,7 @@ static void world_render_init(void) shader_scene_depth_register(); shader_scene_position_register(); shader_model_sky_register(); + shader_model_sky_space_register(); vg_info( "Loading world resources\n" ); vg_linear_clear( vg_mem.scratch ); @@ -104,24 +103,21 @@ static void world_render_init(void) vg_async_call( async_world_render_init, NULL, 0 ); } -static void world_link_lighting_ub( world_instance *world, GLuint shader ) -{ +static void world_link_lighting_ub( world_instance *world, GLuint shader ){ GLuint idx = glGetUniformBlockIndex( shader, "ub_world_lighting" ); glUniformBlockBinding( shader, idx, world->ubo_bind_point ); } static void world_bind_position_texture( world_instance *world, GLuint shader, GLuint location, - int slot ) -{ + int slot ){ render_fb_bind_texture( &world->heightmap, 0, slot ); glUniform1i( location, slot ); } static void world_bind_light_array( world_instance *world, GLuint shader, GLuint location, - int slot ) -{ + int slot ){ glActiveTexture( GL_TEXTURE0 + slot ); glBindTexture( GL_TEXTURE_BUFFER, world->tex_light_entities ); glUniform1i( location, slot ); @@ -129,8 +125,7 @@ static void world_bind_light_array( world_instance *world, static void world_bind_light_index( world_instance *world, GLuint shader, GLuint location, - int slot ) -{ + int slot ){ glActiveTexture( GL_TEXTURE0 + slot ); glBindTexture( GL_TEXTURE_3D, world->tex_light_cubes ); glUniform1i( location, slot ); @@ -142,8 +137,7 @@ static void render_world_depth( world_instance *world, camera *cam ); * Rendering */ -static void bind_terrain_noise(void) -{ +static void bind_terrain_noise(void){ glActiveTexture( GL_TEXTURE0 ); glBindTexture( GL_TEXTURE_2D, world_render.tex_terrain_noise ); } @@ -157,8 +151,48 @@ struct world_pass{ struct world_surface *mat ); void (*fn_set_mdl)( m4x3f mdl ); void (*fn_set_uPvmPrev)( m4x4f pvm ); + void (*fn_set_uNormalMtx)( m3x3f mnorm ); }; +/* FIXME: we gotta do something about this crap, maybe batch lists. something.. + * anything but this. */ +static +void world_render_props( world_instance *world, u32 material_id, + struct world_pass *pass ){ + if( !mdl_arrcount( &world->ent_prop ) ) return; + + /* HACK: use the first material for every prop entity */ + ent_prop *first = mdl_arritm( &world->ent_prop, 0 ); + if( !first->submesh_count ) return; + + mdl_submesh *sm = mdl_arritm( &world->meta.submeshs, first->submesh_start ); + if( sm->material_id != material_id ) return; + + struct world_surface *mat = &world->surfaces[ material_id ]; + pass->fn_bind_textures( world, mat ); + + for( u32 j=0; jent_prop ); j++ ){ + ent_prop *prop = mdl_arritm( &world->ent_prop, j ); + if( prop->flags & 0x1 ) continue; + + for( u32 k=0; ksubmesh_count; k++ ){ + sm = mdl_arritm( &world->meta.submeshs, prop->submesh_start+k ); + + m4x3f mmdl; + mdl_transform_m4x3( &prop->transform, mmdl ); + + m4x4f m4mdl; + m4x3_expand( mmdl, m4mdl ); + m4x4_mul( pass->cam->mtx_prev.pv, m4mdl, m4mdl ); + + pass->fn_set_mdl( mmdl ); + pass->fn_set_uPvmPrev( m4mdl ); + + mdl_draw_submesh( sm ); + } + } +} + static void world_render_traffic( world_instance *world, u32 material_id, struct world_pass *pass ){ @@ -210,6 +244,7 @@ void world_render_pass( world_instance *world, struct world_pass *pass ){ } else{ world_render_traffic( world, i, pass ); + world_render_props( world, i, pass ); sm = &mat->sm_no_collide; } @@ -268,8 +303,7 @@ static void bindpoint_diffuse1_and_cubemap10( world_instance *world, shader_scene_cubemapped_uColour( mat->info.colour ); } -static void render_world_vb( world_instance *world, camera *cam ) -{ +static void render_world_vb( world_instance *world, camera *cam ){ shader_scene_vertex_blend_use(); shader_scene_vertex_blend_uTexGarbage(0); shader_scene_vertex_blend_uTexGradients(1); @@ -529,30 +563,7 @@ void world_render_challenges( world_instance *world, struct world_pass *pass, } /* render texts */ - shader_scene_font_use(); - shader_scene_font_uTexGarbage(0); - shader_scene_font_uTexMain(1); - - shader_scene_font_uPv( skaterift.cam.mtx.pv ); - shader_scene_font_uTime( vg.time ); - - /* TODO: Code dupe... */ - world_link_lighting_ub( world, _shader_scene_font.id ); - world_bind_position_texture( world, _shader_scene_font.id, - _uniform_scene_font_g_world_depth, 2 ); - world_bind_light_array( world, _shader_scene_font.id, - _uniform_scene_font_uLightsArray, 3 ); - world_bind_light_index( world, _shader_scene_font.id, - _uniform_scene_font_uLightsIndex, 4 ); - - bind_terrain_noise(); - shader_scene_font_uCamera( skaterift.cam.transform[3] ); - - //shader_scene_font_uColour( (v4f){1.0f,1.0f,1.0f,1.0f} ); - glActiveTexture( GL_TEXTURE1 ); - glBindTexture( GL_TEXTURE_2D, gui.font.texture ); - - mesh_bind( &gui.font.mesh ); + font3d_bind( &gui.font, k_font_shader_world, 0, world, &skaterift.cam ); char buf[32]; u32 count = 0; @@ -568,7 +579,7 @@ void world_render_challenges( world_instance *world, struct world_pass *pass, c+=highscore_intl( buf+c, mdl_arrcount(&world->ent_challenge), 3 ); buf[c++] = '\0'; - f32 w = font3d_string_width( &gui.font, 1, buf ); + f32 w = font3d_string_width( 1, buf ); m4x3f mlocal; m3x3_identity( mlocal ); mlocal[3][0] = -w*0.5f; @@ -593,15 +604,7 @@ void world_render_challenges( world_instance *world, struct world_pass *pass, shader_scene_font_uOpacity( scale ); shader_scene_font_uColourize( colour ); - - struct font3d_render render = { - .font = &gui.font, - .variant_id = 1, - .shader = k_font_shader_world - }; - - font3d_begin( buf, &skaterift.cam, mmdl, &render ); - font3d_draw( &render ); + font3d_simple_draw( 1, buf, &skaterift.cam, mmdl ); } } @@ -659,20 +662,12 @@ static void bindpoint_override( world_instance *world, } } -static void render_terrain( world_instance *world, camera *cam ) -{ +static void render_terrain( world_instance *world, camera *cam ){ shader_scene_terrain_use(); shader_scene_terrain_uTexGarbage(0); shader_scene_terrain_uTexGradients(1); - world_link_lighting_ub( world, _shader_scene_terrain.id ); - world_bind_position_texture( world, _shader_scene_terrain.id, - _uniform_scene_terrain_g_world_depth, 2 ); - world_bind_light_array( world, _shader_scene_terrain.id, - _uniform_scene_terrain_uLightsArray, 3 ); - world_bind_light_index( world, _shader_scene_terrain.id, - _uniform_scene_terrain_uLightsIndex, 4 ); - + WORLD_BIND_LIGHT_BUFFERS_UB0_TEX234( world, scene_terrain ); glActiveTexture( GL_TEXTURE0 ); glBindTexture( GL_TEXTURE_2D, world_render.tex_terrain_noise ); @@ -690,8 +685,7 @@ static void render_terrain( world_instance *world, camera *cam ) world_render_both_stages( world, &pass ); } -static void render_sky( world_instance *world, camera *cam ) -{ +static void render_sky( world_instance *world, camera *cam ){ /* * Modify matrix to remove clipping and view translation */ @@ -719,15 +713,32 @@ static void render_sky( world_instance *world, camera *cam ) /* * Draw */ - shader_model_sky_use(); - shader_model_sky_uMdl( identity_matrix ); - shader_model_sky_uPv( pv ); - shader_model_sky_uPvmPrev( pv_prev ); - shader_model_sky_uTexGarbage(0); - world_link_lighting_ub( world, _shader_model_sky.id ); + if( world->skybox == k_skybox_default ){ + shader_model_sky_use(); + shader_model_sky_uMdl( identity_matrix ); + shader_model_sky_uPv( pv ); + shader_model_sky_uPvmPrev( pv_prev ); + shader_model_sky_uTexGarbage(0); + world_link_lighting_ub( world, _shader_model_sky.id ); + + glActiveTexture( GL_TEXTURE0 ); + glBindTexture( GL_TEXTURE_2D, world_render.tex_terrain_noise ); + } + else if( world->skybox == k_skybox_space ){ + shader_model_sky_space_use(); - glActiveTexture( GL_TEXTURE0 ); - glBindTexture( GL_TEXTURE_2D, world_render.tex_terrain_noise ); + shader_model_sky_space_uMdl( identity_matrix ); + shader_model_sky_space_uPv( pv ); + shader_model_sky_space_uPvmPrev( pv_prev ); + shader_model_sky_space_uTexGarbage(0); + world_link_lighting_ub( world, _shader_model_sky_space.id ); + + glActiveTexture( GL_TEXTURE0 ); + glBindTexture( GL_TEXTURE_2D, world_render.tex_terrain_noise ); + } + else { + assert(0); + } glDepthMask( GL_FALSE ); glDisable( GL_DEPTH_TEST ); @@ -748,7 +759,8 @@ static void render_world_gates( world_instance *world, camera *cam, for( u32 i=0; ient_gate); i++ ){ ent_gate *gi = mdl_arritm( &world->ent_gate, i ); - if( !(gi->flags & k_ent_gate_linked) ) + if( !(gi->flags & (k_ent_gate_linked|k_ent_gate_nonlocal_DELETED| + k_ent_gate_locked)) ) continue; float dist = v3_dist2( gi->co[0], cam->transform[3] ); @@ -762,30 +774,14 @@ static void render_world_gates( world_instance *world, camera *cam, } world->rendering_gate = gate; - if( gate ){ - if( gate->flags & k_ent_gate_locked ) return; - - if( gate->flags & k_ent_gate_nonlocal ){ - if( world_static.load_state != k_world_loader_none ){ - world->rendering_gate = NULL; - return; - } - - world_instance *dest_world = &world_static.instances[ gate->target ]; - render_gate( world, dest_world, gate, cam, layer_depth ); - } - else{ - render_gate( world, world, gate, cam, layer_depth ); - } - } + if( gate ) + render_gate( world, world, gate, cam, layer_depth ); } -static void world_prerender( world_instance *world ) -{ - +static void world_prerender( world_instance *world ){ if( mdl_arrcount( &world->ent_light ) ){ f32 rate = vg_maxf(0.1f, fabsf(k_day_length)) * vg_signf(k_day_length); - world->time += vg.time_delta * (1.0/(rate*60.0)); + world->time += vg.time_frame_delta * (1.0/(rate*60.0)); } else{ world->time = 0.834; @@ -893,9 +889,10 @@ static void render_world( world_instance *world, camera *cam, } -static -void render_world_override_pass( world_instance *world, - struct world_pass *pass ){ +static void render_world_override_pass( world_instance *world, + struct world_pass *pass, + m4x3f mmdl, m3x3f mnormal, + m4x4f mpvm_prev ){ for( int i=0; isurface_count; i++ ){ struct world_surface *mat = &world->surfaces[i]; @@ -910,48 +907,79 @@ void render_world_override_pass( world_instance *world, if( !sm->indice_count ) continue; - m4x3f mmdl; - m4x3_identity( mmdl ); pass->fn_set_mdl( mmdl ); - pass->fn_set_uPvmPrev( pass->cam->mtx_prev.pv ); + pass->fn_set_uNormalMtx( mnormal ); + pass->fn_set_uPvmPrev( mpvm_prev ); pass->fn_bind_textures( world, mat ); mdl_draw_submesh( sm ); } } -static void render_world_override( world_instance *world ){ +static void render_world_override( world_instance *world, + world_instance *lighting_source, + m4x3f mmdl ){ struct world_pass pass = { .cam = &skaterift.cam, .fn_bind_textures = bindpoint_override, .fn_set_mdl = shader_scene_override_uMdl, .fn_set_uPvmPrev = shader_scene_override_uPvmPrev, + .fn_set_uNormalMtx = shader_scene_override_uNormalMtx, .shader = k_shader_override }; shader_scene_override_use(); +#if 0 respawn_chooser_shader_uniforms(); +#endif shader_scene_override_uTexGarbage(0); shader_scene_override_uTexMain(1); shader_scene_override_uPv( pass.cam->mtx.pv ); - world_link_lighting_ub( world, _shader_scene_override.id ); - world_bind_position_texture( world, _shader_scene_override.id, - _uniform_scene_override_g_world_depth, 2 ); - world_bind_light_array( world, _shader_scene_override.id, - _uniform_scene_override_uLightsArray, 3 ); - world_bind_light_index( world, _shader_scene_override.id, - _uniform_scene_override_uLightsIndex, 4 ); - + WORLD_BIND_LIGHT_BUFFERS_UB0_TEX234( lighting_source, scene_override ); bind_terrain_noise(); + shader_scene_override_uCamera( pass.cam->transform[3] ); + m4x4f mpvm_prev; + m4x3_expand( mmdl, mpvm_prev ); + m4x4_mul( skaterift.cam.mtx_prev.pv, mpvm_prev, mpvm_prev ); + + m3x3f mnormal; + m3x3_inv( mmdl, mnormal ); + m3x3_transpose( mnormal, mnormal ); + v3_normalize( mnormal[0] ); + v3_normalize( mnormal[1] ); + v3_normalize( mnormal[2] ); + + v4f uPlayerPos, uSpawnPos; + v4_zero( uPlayerPos ); + v4_zero( uSpawnPos ); + + v3_copy( world->player_co, uPlayerPos ); + + m4x3f mmdl_inv; + m4x3_invert_full( mmdl, mmdl_inv ); + v3f localized; + m4x3_mulv( mmdl_inv, localplayer.rb.co, localized ); + ent_spawn *spawn = world_find_closest_spawn( world, localized ); + if( spawn ) + v3_copy( spawn->transform.co, uSpawnPos ); + + uPlayerPos[3] = v3_dist(uPlayerPos,uSpawnPos); + uSpawnPos[3] = 1.0f/uPlayerPos[3]; + + shader_scene_override_uPlayerPos( uPlayerPos ); + shader_scene_override_uSpawnPos( uSpawnPos ); + + + glDisable( GL_CULL_FACE ); mesh_bind( &world->mesh_geo ); pass.geo_type = k_world_geo_type_solid; - render_world_override_pass( world, &pass ); + render_world_override_pass( world, &pass, mmdl, mnormal, mpvm_prev ); mesh_bind( &world->mesh_no_collide ); pass.geo_type = k_world_geo_type_nonsolid; - render_world_override_pass( world, &pass ); + render_world_override_pass( world, &pass, mmdl, mnormal, mpvm_prev ); glEnable( GL_CULL_FACE ); } @@ -1021,8 +1049,7 @@ static void render_world_cubemaps( world_instance *world ){ } } -static void render_world_depth( world_instance *world, camera *cam ) -{ +static void render_world_depth( world_instance *world, camera *cam ){ m4x3f identity_matrix; m4x3_identity( identity_matrix ); @@ -1037,8 +1064,7 @@ static void render_world_depth( world_instance *world, camera *cam ) mesh_draw( &world->mesh_geo ); } -static void render_world_position( world_instance *world, camera *cam ) -{ +static void render_world_position( world_instance *world, camera *cam ){ m4x3f identity_matrix; m4x3_identity( identity_matrix );