From: hgn Date: Thu, 2 Jun 2022 05:28:27 +0000 (+0100) Subject: refactor physsics steps X-Git-Url: https://harrygodden.com/git/?a=commitdiff_plain;h=fc32ce17923a42f9a0f250e4ab21a08411a41acb;hp=54ca09093b8d5f752b4a0897bd9703f3b2ad6ed1;p=carveJwlIkooP6JGAAIwe30JlM.git refactor physsics steps --- diff --git a/blender_export.py b/blender_export.py index 9c01c19..05f2b6f 100644 --- a/blender_export.py +++ b/blender_export.py @@ -140,3 +140,4 @@ write_model( "test" ) write_model( "free_dev" ) write_model( "char_dev" ) write_model( "skydome" ) +write_model( "cement_r1" ) diff --git a/main.c b/main.c index 8a81228..0b36899 100644 --- a/main.c +++ b/main.c @@ -7,12 +7,15 @@ vg_tex2d tex_grid = { .path = "textures/grid.qoi" }; vg_tex2d tex_sky = { .path = "textures/sky.qoi" }; vg_tex2d tex_gradients = { .path = "textures/gradients.qoi", .flags = VG_TEXTURE_CLAMP }; +vg_tex2d tex_cement = { .path = "textures/cement512.qoi" }; + vg_tex2d *texture_list[] = { &tex_norwey, &tex_gradients, &tex_grid, - &tex_sky + &tex_sky, + &tex_cement }; /* Convars */ @@ -35,28 +38,40 @@ m4x3f world_matrix; static struct gplayer { + /* Physics */ v3f co, v, a; v4f rot; float vswitch, slip_last; + float iY; /* Yaw inertia */ + int in_air; + + /* Input */ + v2f joy_l; + v3f view; v2f look_dir; /* TEMP */ + float pitch; m4x3f to_world, to_local; + + v3f handl_target, handr_target, + handl, handr; glmesh mesh; - submodel legl, legu, board, torso, - wheels; + wheels, + feet; } player; static struct gworld { glmesh skydome; + glmesh cement; scene foliage, /* Tree shader */ geo, /* Std shader, collisions */ @@ -148,7 +163,13 @@ void vg_start(void) player.board = *submodel_get( char_dev, "skateboard" ); player.torso = *submodel_get( char_dev, "torso" ); player.wheels = *submodel_get( char_dev, "wheels" ); + player.feet = *submodel_get( char_dev, "feet" ); free(char_dev); + + /* temp */ + model *cement_model = vg_asset_read("models/cement_r1.mdl" ); + model_unpack( cement_model, &world.cement ); + free( cement_model ); /* Setup scene */ scene_init( &world.geo ); @@ -245,153 +266,70 @@ void vg_start(void) player_transform_update(); } -v3f head; +static float ktimestep = 1.0f/60.0f; -void vg_update(void) +static void player_freecam(void) { - float timestep = 1.0f/60.0f; - - if( freecam ) - { - m4x3f cam_rot; - m4x3_identity( cam_rot ); - m4x3_rotate_y( cam_rot, -player.look_dir[0] ); - m4x3_rotate_x( cam_rot, -player.look_dir[1] ); - - v3f lookdir = { 0.0f, 0.0f, -1.0f }, - sidedir = { 1.0f, 0.0f, 0.0f }; - - m4x3_mulv( cam_rot, lookdir, lookdir ); - m4x3_mulv( cam_rot, sidedir, sidedir ); - - float movespeed = 5.0f; - static v2f mouse_last, - view_vel = { 0.0f, 0.0f }; - static v3f move_vel = { 0.0f, 0.0f, 0.0f }; - - if( vg_get_button_down( "primary" ) ) - { - v2_copy( vg_mouse, mouse_last ); - } - else if( vg_get_button( "primary" ) ) - { - v2f delta; - v2_sub( vg_mouse, mouse_last, delta ); - v2_copy( vg_mouse, mouse_last ); + m4x3f cam_rot; + m4x3_identity( cam_rot ); + m4x3_rotate_y( cam_rot, -player.look_dir[0] ); + m4x3_rotate_x( cam_rot, -player.look_dir[1] ); - v2_muladds( view_vel, delta, 0.005f, view_vel ); - } - - v2_muls( view_vel, 0.75f, view_vel ); - v2_add( view_vel, player.look_dir, player.look_dir ); - player.look_dir[1] = - vg_clampf( player.look_dir[1], -VG_PIf*0.5f, VG_PIf*0.5f ); - - if( vg_get_button( "forward" ) ) - v3_muladds( move_vel, lookdir, timestep * movespeed, move_vel ); - if( vg_get_button( "back" ) ) - v3_muladds( move_vel, lookdir, timestep *-movespeed, move_vel ); - if( vg_get_button( "left" ) ) - v3_muladds( move_vel, sidedir, timestep *-movespeed, move_vel ); - if( vg_get_button( "right" ) ) - v3_muladds( move_vel, sidedir, timestep * movespeed, move_vel ); - - v3_muls( move_vel, 0.75f, move_vel ); - v3_add( move_vel, player.view, player.view ); - } + v3f lookdir = { 0.0f, 0.0f, -1.0f }, + sidedir = { 1.0f, 0.0f, 0.0f }; + m4x3_mulv( cam_rot, lookdir, lookdir ); + m4x3_mulv( cam_rot, sidedir, sidedir ); + + float movespeed = 5.0f; + static v2f mouse_last, + view_vel = { 0.0f, 0.0f }; - static int in_air = 1; - - v3f ground_pos, ground_norm; - v3_copy( player.co, ground_pos ); + static v3f move_vel = { 0.0f, 0.0f, 0.0f }; - if( sample_scene_height( &world.geo, ground_pos, ground_norm ) ) + if( vg_get_button_down( "primary" ) ) + v2_copy( vg_mouse, mouse_last ); + else if( vg_get_button( "primary" ) ) { -#if 0 - v3f localup; - m3x3_mulv( player.to_world, (v3f){0.0f,1.0f,0.0f}, localup ); - v3_normalize(localup); - v3_normalize(ground_norm); - - float angle = v3_dot( localup, ground_norm ); - v3f axis; - v3_cross( localup, ground_norm, axis ); + v2f delta; + v2_sub( vg_mouse, mouse_last, delta ); + v2_copy( vg_mouse, mouse_last ); - if( angle < 0.999f && !in_air ) - { - v4f correction; - q_axis_angle( correction, axis, acosf(angle) ); - q_mul( correction, player.rot, player.rot ); - } -#endif + v2_muladds( view_vel, delta, 0.005f, view_vel ); } - if( freecam ) - return; - - if( in_air ) - { - v3f pco, pco1, pv; - - float pstep = timestep*10.0f; - - v3f gravity = { 0.0f, -9.6f, 0.0f }; - v3_copy( player.co, pco ); - v3_copy( player.v, pv ); - - v3f targetn; - - for( int i=0; i<20; i++ ) - { - v3_copy( pco, pco1 ); - v3_muladds( pv, gravity, pstep, pv ); - v3_muladds( pco, pv, pstep, pco ); - - vg_line( pco, pco1, i&0x1?0xff000000:0xffffffff ); - - v3f sh; - v3_copy( pco, sh ); - sample_scene_height( &world.geo, sh, targetn ); - - if( sh[1] >= pco[1] ) - { - v3f localup; - m3x3_mulv( player.to_world, (v3f){0.0f,1.0f,0.0f}, localup ); - - float angle = v3_dot( localup, targetn ); - v3f axis; - v3_cross( localup, targetn, axis ); - - if( angle < 0.99f ) - { - v4f correction; - q_axis_angle( correction, axis, acosf(angle)*0.1f ); - q_mul( correction, player.rot, player.rot ); - } - - break; - } - } - - if( ground_pos[1] > player.co[1] ) - { - in_air = 0; - } - } + v2_muls( view_vel, 0.75f, view_vel ); + v2_add( view_vel, player.look_dir, player.look_dir ); + player.look_dir[1] = + vg_clampf( player.look_dir[1], -VG_PIf*0.5f, VG_PIf*0.5f ); if( vg_get_button( "forward" ) ) - { - v3f dir = { 0.0f, 0.0f, -1.0f }; - - m3x3_mulv( player.to_world, dir, dir ); - v3_muladds( player.v, dir, 5.0f * timestep, player.v ); - } + v3_muladds( move_vel, lookdir, ktimestep * movespeed, move_vel ); + if( vg_get_button( "back" ) ) + v3_muladds( move_vel, lookdir, ktimestep *-movespeed, move_vel ); + if( vg_get_button( "left" ) ) + v3_muladds( move_vel, sidedir, ktimestep *-movespeed, move_vel ); + if( vg_get_button( "right" ) ) + v3_muladds( move_vel, sidedir, ktimestep * movespeed, move_vel ); + + v3_muls( move_vel, 0.75f, move_vel ); + v3_add( move_vel, player.view, player.view ); +} - /* Get front and back contact points */ +static void apply_gravity( v3f vel, float const timestep ) +{ + v3f gravity = { 0.0f, -9.6f, 0.0f }; + v3_muladds( vel, gravity, timestep, vel ); +} - v3f contact_front, contact_back, fwd, fwd1, contact_norm, vup, vside; - v3f axis; +static void player_physics_ground(void) +{ + /* + * Getting surface collision points, + * the contact manifold is a triangle for simplicity. + */ + v3f contact_front, contact_back, fwd, fwd1, contact_norm, vup, vside, + axis; m3x3_mulv( player.to_world, (v3f){0.0f,0.0f,-1.0f}, fwd ); m4x3_mulv( player.to_world, (v3f){ 0.15f,0.0f,-1.0f}, contact_norm ); @@ -404,6 +342,12 @@ void vg_update(void) sample_scene_height( &world.geo, contact_front, NULL ) && sample_scene_height( &world.geo, contact_back, NULL ) && sample_scene_height( &world.geo, contact_norm, NULL ); + + if( !all_contacting ) + { + player.in_air = 1; + return; + } v3f norm; v3f v0, v1; @@ -419,97 +363,202 @@ void vg_update(void) float angle = v3_dot( vup, norm ); v3_cross( vup, norm, axis ); - if( angle < 0.999f && !in_air ) + if( angle < 0.999f ) { v4f correction; q_axis_angle( correction, axis, acosf(angle) ); q_mul( correction, player.rot, player.rot ); } + float resistance = v3_dot( norm, player.v ); - v3f gravity = { 0.0f, -9.6f, 0.0f }; - v3_muladds( player.v, gravity, timestep, player.v ); - - if( !in_air ) + if( resistance >= 0.0f ) { - float resistance = v3_dot( norm, player.v ); - - if( resistance >= 0.0f ) - in_air = 1; - else - { - v3_muladds( player.v, norm, -resistance, player.v ); - } + player.in_air = 1; + return; + } + else + { + v3_muladds( player.v, norm, -resistance, player.v ); } - - /* vg_info( "%.3f | %.3f\n", player.v[1], resistance ); */ - v3_muladds( player.co, player.v, timestep, player.co ); + /* This is where velocity integration used to be */ + float slip = 0.0f; - float yawamt = 0.0f; - if( !in_air ) + player.co[1] = (contact_front[1]+contact_back[1])*0.5f; + + v3f vel; + m3x3_mulv( player.to_local, player.v, vel ); + + /* Calculate local forces */ + + slip = (-vel[0] / vel[2]) * player.vswitch; + if( fabsf( slip ) > 1.2f ) + slip = vg_signf( slip ) * 1.2f; + + + if( player.slip_last*slip < 0.0f && fabsf(slip) > 0.7f ) { - player.co[1] = (contact_front[1]+contact_back[1])*0.5f; + vg_warn( "SWITCH\n" ); + player.vswitch = -player.vswitch; + slip = -slip; + } - v3f vel; - m3x3_mulv( player.to_local, player.v, vel ); + player.slip_last = slip; - /* Calculate local forces */ + float substep = ktimestep * 0.2f; + + for( int i=0; i<5; i++ ) + { + if( fabsf(vel[2]) >= 0.02f*substep ) + vel[2] += vg_signf( vel[2] ) * -0.02f * substep; + if( fabsf(vel[0]) >= 7.0f*substep ) + vel[0] += vg_signf( vel[0] ) * -7.0f * substep; + } + + m3x3_mulv( player.to_world, vel, player.v ); - slip = (-vel[0] / vel[2]) * player.vswitch; - if( fabsf( slip ) > 1.2f ) - slip = vg_signf( slip ) * 1.2f; + if( vg_get_button( "yawl" ) ) + player.iY += 3.6f * ktimestep; + if( vg_get_button( "yawr" ) ) + player.iY -= 3.6f * ktimestep; + + float steer = vg_get_axis( "horizontal" ); + player.iY -= vg_signf(steer)*powf(steer,2.0f) * 3.5f * ktimestep; +} - - if( player.slip_last*slip < 0.0f && fabsf(slip) > 0.7f ) +static void player_physics_air(void) +{ + v3f ground_pos, ground_norm; + v3_copy( player.co, ground_pos ); + + if( sample_scene_height( &world.geo, ground_pos, ground_norm ) ) + { + if( ground_pos[1] > player.co[1] ) { - vg_warn( "SWITCH\n" ); - player.vswitch = -player.vswitch; - slip = -slip; + player.in_air = 0; + return; } + } + + /* Prediction + * + * TODO: Find best landing surface and guide player towords it + */ + float pstep = ktimestep*10.0f; + + v3f pco, pco1, pv; + v3_copy( player.co, pco ); + v3_copy( player.v, pv ); + + v3f targetn; + for( int i=0; i<50; i++ ) + { + v3_copy( pco, pco1 ); + apply_gravity( pv, pstep ); + v3_muladds( pco, pv, pstep, pco ); - player.slip_last = slip; - - float substep = timestep * 0.2f; + vg_line( pco, pco1, i&0x1?0xff000000:0xffffffff ); - for( int i=0; i<5; i++ ) + v3f sh; + v3_copy( pco, sh ); + int hit = sample_scene_height( &world.geo, sh, targetn ); + + if( sh[1] >= pco[1] && hit ) { - if( fabsf(vel[2]) >= 0.02f*substep ) - vel[2] += vg_signf( vel[2] ) * -0.02f * substep; - if( fabsf(vel[0]) >= 6.0f*substep ) - vel[0] += vg_signf( vel[0] ) * -6.0f * substep; - } - - m3x3_mulv( player.to_world, vel, player.v ); + v3f localup; + m3x3_mulv( player.to_world, (v3f){0.0f,1.0f,0.0f}, localup ); - if( vg_get_button( "yawl" ) ) - yawamt = 1.6f * timestep; - if( vg_get_button( "yawr" ) ) - yawamt = -1.6f * timestep; - - yawamt -= vg_get_axis( "horizontal" ) * 1.6f * timestep; + float angle = v3_dot( localup, targetn ); + v3f axis; + v3_cross( localup, targetn, axis ); + if( angle < 0.99f ) + { + v4f correction; + q_axis_angle( correction, axis, acosf(angle)*0.01f ); + q_mul( correction, player.rot, player.rot ); + } + + break; + } } - else + + player.iY -= vg_get_axis( "horizontal" ) * 3.6f * ktimestep; +} + +static void player_update(void) +{ + /* temp */ + if( vg_get_axis("grabl")>0.0f) + reset_player(0,NULL); + if( vg_get_button( "forward" ) ) { - yawamt -= vg_get_axis( "horizontal" ) * 3.6f * timestep; + v3f dir = { 0.0f, 0.0f, -1.0f }; - v4f pitch; - q_axis_angle( pitch, vside, vg_get_axis( "vertical" ) * 3.6f *timestep ); - q_mul( pitch, player.rot, player.rot ); + m3x3_mulv( player.to_world, dir, dir ); + v3_muladds( player.v, dir, 5.0f * ktimestep, player.v ); } + + + float horizontal = vg_get_axis("horizontal"), + vertical = vg_get_axis("vertical"); + + player.joy_l[0] = vg_signf(horizontal) * powf( horizontal, 2.0f ); + player.joy_l[1] = vg_signf(vertical) * powf( vertical, 2.0f ); + + if( freecam ) + { + player_freecam(); + return; + } + + /* Integrate velocity */ + apply_gravity( player.v, ktimestep ); + v3_muladds( player.co, player.v, ktimestep, player.co ); - v4f rotate; - q_axis_angle( rotate, vup, yawamt ); + /* Integrate inertia */ + v4f rotate; v3f vup = {0.0f,1.0f,0.0f}; + m3x3_mulv( player.to_world, vup, vup ); + + q_axis_angle( rotate, vup, player.iY ); q_mul( rotate, player.rot, player.rot ); player.look_dir[0] = atan2f( player.v[0], -player.v[2] ); + player.look_dir[1] = atan2f( -player.v[1], sqrtf(player.v[0]*player.v[0]+ + player.v[2]*player.v[2]) ) * 0.3f; + + player.iY = 0.0f; /* temp */ + + if( player.in_air ) + player_physics_air(); + + if( !player.in_air ) + player_physics_ground(); - /* Creating a skeleton of the player dynamically */ + /* Camera and character */ float kheight = 1.8f, kleg = 0.6f; + v3f head; + head[0] = 0.0f; + head[1] = kheight; + head[2] = 0.0f; + + m4x3_mulv( player.to_world, head, head ); + v3_copy( head, player.view ); + + player_transform_update(); + q_normalize(player.rot); +} + +void vg_update(void) +{ + player_update(); + + /* Creating a skeleton of the player dynamically */ + v2f ac; static v3f last_vel = { 0.0f, 0.0f, 0.0f }; @@ -531,9 +580,16 @@ void vg_update(void) v3_lerp( bob, target, 0.2f, bob ); /* Head */ +#if 0 float lslip = fabsf(slip); //vg_minf( 0.4f, slip ); + + static float grab = 0.0f; + float grabt = vg_get_axis( "grabr" )*0.5f+0.5f; + grab = vg_lerpf( grab, grabt, 0.04f ); + + v3f head; head[0] = 0.0f;//(-sinf(lslip)*0.9f * kheight) * 0.44f; - head[1] = (0.3f + cosf(lslip)*0.5f) * kheight; + head[1] = (0.3f + cosf(lslip)*0.5f) * kheight - grab*0.7f; head[2] = 0.0f; v3f offset; @@ -541,14 +597,42 @@ void vg_update(void) offset[0] *= 0.25f; offset[1] *= -0.25f; offset[2] *= 0.7f; - v3_muladds( head, offset, 1.0f, head ); + v3_muladds( head, offset, 0.7f, head ); - player_transform_update(); + head[1] = vg_clampf( head[1], 0.3f, 20.0f ); - m4x3_mulv( player.to_world, head, head ); - v3_copy( head, player.view ); + player.handl_target[0] = head[0] + 0.2f; + player.handl_target[1] = head[1] - 0.8f*(1.0f-fabsf(slip)); + player.handl_target[2] = head[2] + 0.2f + 0.7f*fabsf(slip); + + player.handr_target[0] = head[0] + 0.2f; + player.handr_target[1] = head[1] - 0.8f*(1.0f-fabsf(slip)); + player.handr_target[2] = head[2] - (0.2f + 0.7f*fabsf(slip)); + + if( vg_maxf(lslip,grab) > 0.5f ) + { + if( slip < 0.0f && in_air ) + { + player.handl_target[0] = 0.15f; + player.handl_target[1] = 0.1f; + player.handl_target[2] = 0.4f; + } + else + { + player.handr_target[0] = 0.15f; + player.handr_target[1] = 0.1f; + player.handr_target[2] = -0.4f; + } + + if( grab > 0.5f ) + { + player.handr_target[0] = -0.15f; + player.handr_target[1] = 0.1f; + player.handr_target[2] = 0.4f; + } + } +#endif - q_normalize(player.rot); } static void debug_grid( v3f at ) @@ -574,11 +658,16 @@ static void draw_player(void) { mesh_bind( &player.mesh ); float const kleg_upper = 0.53f, - kleg_lower = 0.5f; + kleg_lower = 0.5f, + karm_ratio = 0.75f, + karm_upper = kleg_upper*karm_ratio, + karm_lower = kleg_lower*karm_ratio; /* Create IK targets */ struct ik_basic ik_leg_l = { .l1 = kleg_upper, .l2 = kleg_lower }, - ik_leg_r = { .l1 = kleg_upper, .l2 = kleg_lower }; + ik_leg_r = { .l1 = kleg_upper, .l2 = kleg_lower }, + ik_arm_l = { .l1 = karm_upper, .l2 = karm_lower }, + ik_arm_r = { .l1 = karm_upper, .l2 = karm_lower }; v3f butt, fwd; @@ -599,7 +688,32 @@ static void draw_player(void) ik_basic( &ik_leg_r, mleg_r, mknee_r ); ik_basic( &ik_leg_l, mleg_l, mknee_l ); + + /* Arms */ + v3f hl, hr, neckl = {0.2f,-0.1f, 0.2f}, + neckr = {0.2f,-0.1f,-0.2f}; + + v3_lerp( player.handl, player.handl_target, 0.04f, player.handl ); + v3_lerp( player.handr, player.handr_target, 0.04f, player.handr ); + + m3x3_mulv( player.to_world, neckl, neckl ); + m3x3_mulv( player.to_world, neckr, neckr ); + + v3_add( player.view, neckl, ik_arm_l.base ); + v3_add( player.view, neckr, ik_arm_r.base ); + m4x3_mulv( player.to_world, player.handl, ik_arm_l.end ); + m4x3_mulv( player.to_world, player.handr, ik_arm_r.end ); + m4x3_mulv( player.to_world, (v3f){ 0.6f,0.7f, 0.4f }, ik_arm_l.pole ); + m4x3_mulv( player.to_world, (v3f){ 0.6f,0.7f,-0.35f }, ik_arm_r.pole ); + m4x3f marm_l, melbow_l, marm_r, melbow_r; + ik_basic( &ik_arm_l, marm_l, melbow_l ); + ik_basic( &ik_arm_r, marm_r, melbow_r ); + m4x3_scale( marm_l, karm_ratio ); + m4x3_scale( marm_r, karm_ratio ); + m4x3_scale( melbow_l, karm_ratio ); + m4x3_scale( melbow_r, karm_ratio ); + /* Draw */ vg_tex2d_bind( &tex_grid, 0 ); scene_tree_sway = 0.0f; @@ -618,14 +732,14 @@ static void draw_player(void) float kscale = 0.7f; glUniform4f( SHADER_UNIFORM(shader_standard_lit,"uColour"), - 0.9f*kscale,0.6f*kscale,0.1f*kscale,1.0f ); + 0.35f*kscale,0.35f*kscale,0.35f*kscale,1.0f ); m4x3_expand( player.to_world, mat ); glUniformMatrix4fv( kuMdl, 1, GL_FALSE, (float *)mat ); submodel_draw( &player.board ); glUniform4f( SHADER_UNIFORM(shader_standard_lit,"uColour"), - 0.2f*kscale,0.3f*kscale,1.0f*kscale,1.0f ); + 0.7f*kscale,0.7f*kscale,0.7f*kscale,1.0f ); submodel_draw( &player.wheels ); glEnable(GL_BLEND); @@ -633,7 +747,9 @@ static void draw_player(void) glBlendEquation(GL_FUNC_ADD); glDisable( GL_DEPTH_TEST ); glUniform4f( SHADER_UNIFORM(shader_standard_lit,"uColour"), - 0.2f*kscale,0.3f*kscale,1.0f*kscale,0.2f ); + 0.2f*kscale,0.8f*kscale,0.4f*kscale,0.14f ); + + submodel_draw( &player.feet ); m4x3_expand( mleg_l, mat ); glUniformMatrix4fv( kuMdl, 1, GL_FALSE, (float *)mat ); @@ -651,6 +767,24 @@ static void draw_player(void) glUniformMatrix4fv( kuMdl, 1, GL_FALSE, (float *)mat ); submodel_draw( &player.legl ); + /* arms */ + m4x3_expand( marm_l, mat ); + glUniformMatrix4fv( kuMdl, 1, GL_FALSE, (float *)mat ); + submodel_draw( &player.legu ); + + m4x3_expand( melbow_l, mat ); + glUniformMatrix4fv( kuMdl, 1, GL_FALSE, (float *)mat ); + submodel_draw( &player.legl ); + + m4x3_expand( marm_r, mat ); + glUniformMatrix4fv( kuMdl, 1, GL_FALSE, (float *)mat ); + submodel_draw( &player.legu ); + + m4x3_expand( melbow_r, mat ); + glUniformMatrix4fv( kuMdl, 1, GL_FALSE, (float *)mat ); + submodel_draw( &player.legl ); + + /* body */ m4x3f mbutt; m3x3_copy( player.to_world, mbutt ); v3_copy( butt, mbutt[3] ); @@ -679,10 +813,14 @@ void vg_render(void) v3f shake = { vg_randf()-0.5f, vg_randf()-0.5f, vg_randf()-0.5f }; v3_muls( shake, speed*0.01f, shake ); + static v2f look_lerped = {0.0f,0.0f}; + v2_lerp( look_lerped, player.look_dir, 0.03f, look_lerped ); + m4x3_identity( world_matrix ); m4x3_rotate_x( world_matrix, - freecam? player.look_dir[1]: 0.5f+shake[1]*0.04f ); - m4x3_rotate_y( world_matrix, player.look_dir[0]+shake[0]*0.02f ); + freecam? look_lerped[1]: 0.6f+shake[1]*0.04f+look_lerped[1] ); + + m4x3_rotate_y( world_matrix, look_lerped[0]+shake[0]*0.02f ); m4x3_translate( world_matrix, pos_inv ); m4x4f world_4x4; @@ -726,6 +864,13 @@ void vg_render(void) glUniform1i( SHADER_UNIFORM( shader_unlit, "uTexMain" ), 0 ); vg_tex2d_bind( &tex_sky, 0 ); + mesh_bind( &world.skydome ); + mesh_draw( &world.skydome ); + + vg_tex2d_bind( &tex_cement, 0 ); + mesh_bind( &world.cement ); + mesh_draw( &world.cement ); + SHADER_USE(shader_standard_lit); glUniformMatrix4fv( SHADER_UNIFORM( shader_standard_lit, "uPv" ), @@ -738,6 +883,7 @@ void vg_render(void) vg_tex2d_bind( &tex_grid, 0 ); scene_bind( &world.geo ); +#if 0 glUniform4f( SHADER_UNIFORM(shader_standard_lit,"uColour"), 0.2f,0.36f,0.25f,1.0f ); submodel_draw( &world.terrain ); @@ -745,10 +891,10 @@ void vg_render(void) glUniform4f( SHADER_UNIFORM(shader_standard_lit,"uColour"), 0.2f,0.2f,0.21f,1.0f ); submodel_draw( &world.terrain_rocks ); - glUniform4f( SHADER_UNIFORM(shader_standard_lit,"uColour"), 0.4f,0.4f,0.4f,1.0f ); submodel_draw( &world.terrain_road ); +#endif scene_bind( &world.detail ); scene_draw( &world.detail ); diff --git a/scene.h b/scene.h index bf61fba..d5fa275 100644 --- a/scene.h +++ b/scene.h @@ -318,7 +318,7 @@ SHADER_DEFINE( shader_unlit, "void main()" "{" "vec3 diffuse = texture( uTexMain, aUv ).rgb;" - "FragColor = vec4(pow(diffuse,vec3(1.0/2.2)),1.0);" + "FragColor = vec4(pow(diffuse,vec3(1.0)),1.0);" "}" , UNIFORMS({ "uTexMain", "uPv", "uMdl" }) diff --git a/textures/cement512.png b/textures/cement512.png new file mode 100644 index 0000000..cd94f96 Binary files /dev/null and b/textures/cement512.png differ diff --git a/vg_config.h b/vg_config.h index b1348a0..c1e7512 100644 --- a/vg_config.h +++ b/vg_config.h @@ -18,7 +18,11 @@ static struct button_binding vg_button_binds[] = static struct axis_binding vg_axis_binds[] = { { .name = "horizontal", .axis = GLFW_GAMEPAD_AXIS_LEFT_X }, - { .name = "vertical", .axis = GLFW_GAMEPAD_AXIS_LEFT_Y } + { .name = "vertical", .axis = GLFW_GAMEPAD_AXIS_LEFT_Y }, + { .name = "grabr", .axis = GLFW_GAMEPAD_AXIS_RIGHT_TRIGGER }, + { .name = "grabl", .axis = GLFW_GAMEPAD_AXIS_LEFT_TRIGGER }, + { .name = "h1", .axis = GLFW_GAMEPAD_AXIS_RIGHT_X }, + { .name = "v1", .axis = GLFW_GAMEPAD_AXIS_RIGHT_Y } }; static struct vg_achievement vg_achievements[] =