X-Git-Url: https://harrygodden.com/git/?a=blobdiff_plain;f=player_device_skate.h;h=13f6398a0b549d37f338b2b25ffd0bacb7062320;hb=2f1dca88d325b4eebd030232c694627f5791ebce;hp=af95a7ff1a4a0531d855f9e835290d31afeb4836;hpb=38672ec938499ce9e610c3e1848e74880b78a845;p=carveJwlIkooP6JGAAIwe30JlM.git diff --git a/player_device_skate.h b/player_device_skate.h index af95a7f..13f6398 100644 --- a/player_device_skate.h +++ b/player_device_skate.h @@ -4,6 +4,7 @@ #include "player_interface.h" #include "skeleton.h" #include "player_model.h" +#include "player_device_common.h" struct player_device_skate { @@ -43,7 +44,11 @@ struct player_device_skate double start_push, cur_push; - v3f vl; + v3f prev_pos; + + + v3f vl, /* 1st */ + posl; /* 3rd */ } state, state_gate_storage; @@ -67,6 +72,8 @@ struct player_device_skate } predictions[22]; u32 prediction_count; + float land_dist; + v3f land_normal; /* animation */ struct skeleton_anim *anim_stand, *anim_highg, *anim_slide, @@ -597,7 +604,7 @@ VG_STATIC void skate_apply_air_model( player_interface *player, { v4f correction; q_axis_angle( correction, axis, - acosf(angle)*(1.0f-limiter)*3.0f*VG_TIMESTEP_FIXED ); + acosf(angle)*(1.0f-limiter)*2.0f*VG_TIMESTEP_FIXED ); q_mul( correction, player->rb.q, player->rb.q ); } } @@ -609,6 +616,8 @@ VG_STATIC void skate_apply_air_model( player_interface *player, s->state.steery -= steer[0] * k_steer_air * VG_TIMESTEP_FIXED; s->state.steerx += steer[1] * s->state.reverse * k_steer_air * limiter * k_rb_delta; + s->land_dist = time_to_impact; + v3_copy( target_normal, s->land_normal ); } VG_STATIC void skate_get_board_points( player_interface *player, @@ -710,12 +719,14 @@ VG_STATIC void skate_apply_interface_model( player_interface *player, float angle = -atan2f( dy, dx ); q_axis_angle( s->board_rotation, (v3f){1.0f,0.0f,0.0f}, angle ); + int lift_frames_limit = 1; + /* Surface connection */ if( len == 0 && !(spring_hit0 && spring_hit1) ) { s->state.lift_frames ++; - if( s->state.lift_frames >= 8 ) + if( s->state.lift_frames >= lift_frames_limit ) s->state.activity = k_skate_activity_air; } else @@ -731,7 +742,7 @@ VG_STATIC void skate_apply_interface_model( player_interface *player, { s->state.lift_frames ++; - if( s->state.lift_frames >= 8 ) + if( s->state.lift_frames >= lift_frames_limit ) s->state.activity = k_skate_activity_air; } else @@ -894,6 +905,16 @@ VG_STATIC void skate_apply_jump_model( player_interface *player, s->state.jump_charge = 0.0f; s->state.jump_time = vg.time; + + v2f steer = { player->input_js1h->axis.value, + player->input_js1v->axis.value }; + v2_normalize_clamp( steer ); + + float maxspin = k_steer_air * k_rb_delta * k_spin_boost; + s->state.steery_s = -steer[0] * maxspin; + s->state.steerx_s = steer[1] * s->state.reverse * maxspin; + s->state.steerx = s->state.steerx_s; + s->state.steery = s->state.steery_s; /* FIXME audio events */ #if 0 @@ -1084,6 +1105,7 @@ VG_STATIC void player_skate_update( player_interface *player, player_attachment *at ) { struct player_device_skate *s = at->storage; + v3_copy( player->rb.co, s->state.prev_pos ); s->state.activity_prev = s->state.activity; /* Setup colliders */ @@ -1106,9 +1128,35 @@ VG_STATIC void player_skate_update( player_interface *player, &s->sphere_front, manifold ), len_back = skate_collide_smooth( player, mtx_back, &s->sphere_back, &manifold[len_front] ), - interface_len = len_front + len_back; + /* try to slap both wheels onto the ground when landing to prevent mega + * angular velocities being added */ + if( (s->state.activity == k_skate_activity_air) && (len_front != len_back) ) + { + v3f trace_from, trace_dir; + v3_muls( player->rb.to_world[1], -1.0f, trace_dir ); + + if( len_front ) + v3_copy( mtx_back[3], trace_from ); + else + v3_copy( mtx_front[3], trace_from ); + + ray_hit ray; + ray.dist = 0.6f; + + if( ray_world( trace_from, trace_dir, &ray ) ) + { + rb_ct *ct = &manifold[ interface_len ]; + + v3_copy( ray.pos, ct->co ); + v3_copy( ray.normal, ct->n ); + ct->p = 0.0f; + + interface_len ++; + } + } + interface_manifold = manifold; grind_manifold = manifold + interface_len; @@ -1133,6 +1181,39 @@ VG_STATIC void player_skate_update( player_interface *player, skate_apply_air_model( player, s ); skate_integrate( player, s ); + + vg_line_pt3( s->state.cog, 0.1f, VG__WHITE ); + vg_line_pt3( s->state.cog, 0.11f, VG__WHITE ); + vg_line_pt3( s->state.cog, 0.12f, VG__WHITE ); + vg_line_pt3( s->state.cog, 0.13f, VG__WHITE ); + vg_line_pt3( s->state.cog, 0.14f, VG__WHITE ); + + vg_line( player->rb.co, s->state.cog, VG__RED ); + + + teleport_gate *gate; + if( (gate = world_intersect_gates( player->rb.co, s->state.prev_pos )) ) + { + m4x3_mulv( gate->transport, player->rb.co, player->rb.co ); + m3x3_mulv( gate->transport, player->rb.v, player->rb.v ); + m4x3_mulv( gate->transport, s->state.cog, s->state.cog ); + m3x3_mulv( gate->transport, s->state.cog_v, s->state.cog_v ); + m3x3_mulv( gate->transport, s->state.throw_v, s->state.throw_v ); + m4x3_mulv( gate->transport, s->state.posl, s->state.posl ); + m3x3_mulv( gate->transport, s->state.vl, s->state.vl ); + +#if 0 + mixedcam_transport( &s->state.cam, gate ); +#endif + + v4f transport_rotation; + m3x3_q( gate->transport, transport_rotation ); + q_mul( transport_rotation, player->rb.q, player->rb.q ); + rb_update_transform( &player->rb ); + + s->state_gate_storage = s->state; + player_pass_gate( player, gate ); + } } VG_STATIC void player_skate_post_update( player_interface *player, @@ -1161,11 +1242,13 @@ VG_STATIC void player_skate_ui( player_interface *player, "k_skate_activity_ground", "k_skate_activity_grind }" } [s->state.activity] ); + player_debugtext( 1, "steer_s: %5.2f %5.2f [%.2f %.2f]\n", + s->state.steerx_s, s->state.steery_s, + k_steer_ground, k_steer_air ); } -VG_STATIC void player_skate_pose( player_interface *player, - player_attachment *at, - player_pose pose, m4x3f transform ) +VG_STATIC void player_skate_animate( player_interface *player, + player_attachment *at ) { struct player_device_skate *s = at->storage; struct player_avatar *av = player->playeravatar; @@ -1192,6 +1275,9 @@ VG_STATIC void player_skate_pose( player_interface *player, v3f offset; v3_zero( offset ); + m4x3_mulv( player->rb.to_local, s->state.cog, offset ); + v3_muls( offset, -4.0f, offset ); + #if 0 m3x3_mulv( player.inv_visual_transform, phys->bob, offset ); #endif @@ -1327,7 +1413,7 @@ VG_STATIC void player_skate_pose( player_interface *player, skeleton_lerp_pose( sk, apose, bpose, s->state.grabbing, air_pose ); } - skeleton_lerp_pose( sk, ground_pose, air_pose, s->blend_fly, pose ); + skeleton_lerp_pose( sk, ground_pose, air_pose, s->blend_fly, at->pose ); float add_grab_mod = 1.0f - s->blend_fly; @@ -1341,13 +1427,13 @@ VG_STATIC void player_skate_pose( player_interface *player, for( int i=0; ipose[apply_to[i]-1].co[0] += offset[0]*add_grab_mod; + at->pose[apply_to[i]-1].co[2] += offset[2]*add_grab_mod; } - mdl_keyframe *kf_board = &pose[av->id_board-1], - *kf_foot_l = &pose[av->id_ik_foot_l-1], - *kf_foot_r = &pose[av->id_ik_foot_r-1]; + mdl_keyframe *kf_board = &at->pose[av->id_board-1], + *kf_foot_l = &at->pose[av->id_ik_foot_l-1], + *kf_foot_r = &at->pose[av->id_ik_foot_r-1]; v3f bo; v3_muls( s->board_offset, add_grab_mod, bo ); @@ -1373,12 +1459,10 @@ VG_STATIC void player_skate_pose( player_interface *player, } /* transform */ - rb_extrapolate_transform( &player->rb, transform ); + rb_extrapolate( &player->rb, at->pose_root_co, at->pose_root_q ); -#if 0 - v3_muladds( player.visual_transform[3], phys->rb.up, -0.2f, - player.visual_transform[3] ); -#endif + v3_muladds( at->pose_root_co, player->rb.to_world[1], -0.28f, + at->pose_root_co ); v4f qresy, qresx, qresidual; m3x3f mtx_residual; @@ -1387,29 +1471,26 @@ VG_STATIC void player_skate_pose( player_interface *player, q_axis_angle( qresx, player->rb.to_world[0], s->state.steerx_s*substep ); q_mul( qresy, qresx, qresidual ); - q_m3x3( qresidual, mtx_residual ); - m3x3_mul( transform, mtx_residual, transform ); + q_normalize( qresidual ); + q_mul( at->pose_root_q, qresidual, at->pose_root_q ); + q_normalize( at->pose_root_q ); + +#if 0 + if( cl_thirdperson ) + { + if( !followcam_will_hit_gate( player, &s->state.cam ) ) + { + m4x3f inverse; + m4x3_invert_affine( s->state.cam.gate->transport, inverse ); + m4x3_mul( inverse, transform, transform ); + } + } +#endif } -VG_STATIC void player_skate_get_camera( player_interface *player, - player_attachment *at, camera *cam ) +VG_STATIC void skate_camera_vector_look( camera *cam, v3f v, float C, float k ) { - struct player_device_skate *s = at->storage; - struct player_avatar *av = player->playeravatar; - - /* FIXME: viewpoint entity */ - v3f vp = {-0.1f,1.8f,0.0f}; - m4x3_mulv( av->sk.final_mtx[ av->id_head-1 ], vp, cam->pos ); - - v3_zero( cam->angles ); - cam->fov = 119.0f; - - /* TODO: smooth clamp lerp rate of change */ - - v3_lerp( s->state.vl, player->rb.v, 5.0f*vg.time_delta, s->state.vl ); - - float *v = s->state.vl, - yaw = atan2f( v[0], -v[2] ), + float yaw = atan2f( v[0], -v[2] ), pitch = atan2f ( -v[1], @@ -1417,30 +1498,112 @@ VG_STATIC void player_skate_get_camera( player_interface *player, ( v[0]*v[0] + v[2]*v[2] ) - ) - * 0.7f + 0.5f; + ) * C + k; cam->angles[0] = yaw; cam->angles[1] = pitch; } +VG_STATIC void skate_camera_firstperson( player_interface *player, + player_attachment *at ) +{ + struct player_device_skate *s = at->storage; + struct player_avatar *av = player->playeravatar; + + /* FIXME: viewpoint entity */ + v3f vp = {-0.1f,1.8f,0.0f}; + m4x3_mulv( av->sk.final_mtx[ av->id_head-1 ], vp, at->cam_1st.pos ); + + v3_zero( at->cam_1st.angles ); + at->cam_1st.fov = 119.0f; + + v3f flat_dir, + vel_dir, + look_dir; + + v3_copy( player->rb.v, vel_dir ); + //v3_normalize( vel_dir ); + + float tti = s->land_dist; + v3f norm; + v3_copy( s->land_normal, norm ); + + if( s->state.activity == k_skate_activity_ground ) + { + tti = 0.0f; + v3_copy( player->rb.to_world[1], norm ); + } + + v3_muladds( vel_dir, norm, -v3_dot(vel_dir,norm), flat_dir ); + //v3_normalize( flat_dir ); + + v3_lerp( flat_dir, vel_dir, vg_clampf( tti / 2.0f, 0.4f, 1.0f ), look_dir ); + v3_lerp( s->state.vl, look_dir, 4.0f*vg.time_delta, s->state.vl ); + + skate_camera_vector_look( &at->cam_1st, s->state.vl, 1.0f, 0.25f ); +} + +VG_STATIC void skate_camera_thirdperson( player_interface *player, + player_attachment *at ) +{ + struct player_device_skate *s = at->storage; + struct player_avatar *av = player->playeravatar; + + v3f origin, dir, target; + v3_copy( player->rb.co, origin ); + v3_add( origin, (v3f){0.0f,1.35f,0.0f}, origin ); + v3_sub( origin, s->state.posl, dir ); + + if( v3_length2( dir ) < 0.1f*0.1f ) + v3_copy( (v3f){ 0.0f, 0.0f, 1.0f }, dir ); /* FIXME */ + else + v3_normalize( dir ); + + v3_muladds( origin, dir, -2.0f, target ); + v3_lerp( s->state.posl, target, vg.frame_delta * 12.0f, s->state.posl ); + + v3_copy( s->state.posl, at->cam_3rd.pos ); + skate_camera_vector_look( &at->cam_3rd, dir, 1.0f, 0.0f ); + at->cam_3rd.fov = 100.0f; +} + +VG_STATIC void player_skate_post_animate( player_interface *player, + player_attachment *at ) +{ + struct player_device_skate *s = at->storage; + struct player_avatar *av = player->playeravatar; + + v3_zero( at->cam_1st.pos ); + v3_zero( at->cam_1st.angles ); + at->cam_1st.fov = 90.0f; + + skate_camera_thirdperson( player, at ); + skate_camera_firstperson( player, at ); + + /* FIXME: Organize this. Its int wrong fucking place */ + v3f vp0 = {0.0f,0.1f, 0.6f}, + vp1 = {0.0f,0.1f,-0.6f}; + + m4x3_mulv( av->sk.final_mtx[ av->id_board ], vp0, TEMP_BOARD_0 ); + m4x3_mulv( av->sk.final_mtx[ av->id_board ], vp1, TEMP_BOARD_1 ); +} + VG_STATIC void player_skate_transport( player_interface *player, player_attachment *at, teleport_gate *gate ) { - struct player_device_skate *s = at->storage; - - m4x3_mulv( gate->transport, player->rb.co, player->rb.co ); - m4x3_mulv( gate->transport, s->state.cog, s->state.cog ); - m3x3_mulv( gate->transport, s->state.cog_v, s->state.cog_v ); - m3x3_mulv( gate->transport, player->rb.v, player->rb.v ); - m3x3_mulv( gate->transport, s->state.vl, s->state.vl ); +} - v4f transport_rotation; - m3x3_q( gate->transport, transport_rotation ); - q_mul( transport_rotation, player->rb.q, player->rb.q ); +VG_STATIC void player_skate_reset( player_interface *player, + player_attachment *at, + struct respawn_point *rp ) +{ + struct player_device_skate *s = at->storage; + v3_muladds( player->rb.co, player->rb.to_world[1], 1.0f, s->state.cog ); - s->state_gate_storage = s->state; +#if 0 + mixedcam_reset( player, &s->state.cam ); +#endif } VG_STATIC player_device player_device_skate = @@ -1448,11 +1611,11 @@ VG_STATIC player_device player_device_skate = .pre_update = player_skate_pre_update, .update = player_skate_update, .post_update = player_skate_post_update, - .get_camera = player_skate_get_camera, + .animate = player_skate_animate, + .post_animate = player_skate_post_animate, .debug_ui = player_skate_ui, .bind = player_skate_bind, - .pose = player_skate_pose, - .gate_transport= player_skate_transport + .reset = player_skate_reset }; #endif /* PLAYER_DEVICE_SKATE_H */