From 72dc88c043984893bd3fb0c930394136b683ec7b Mon Sep 17 00:00:00 2001 From: Sally Coolatta Date: Mon, 5 Apr 2021 23:52:56 -0400 Subject: [PATCH] Attempt at a non-controller dependent compromise for turn easing Values are subject to tweaking. (AngleDelta stuff is a leftover of the previous attempt, but I think the code's useful so I kept it in this commit anyway) --- src/d_player.h | 1 + src/g_game.c | 4 ++++ src/k_hud.c | 24 ++++++++++++------------ src/k_kart.c | 40 ++++++++++++++++++++++++++++++++++------ src/k_kart.h | 1 + src/p_saveg.c | 2 ++ src/p_user.c | 5 ++++- src/tables.c | 15 +++++++++++++-- src/tables.h | 3 ++- 9 files changed, 73 insertions(+), 22 deletions(-) diff --git a/src/d_player.h b/src/d_player.h index 19a998f74..962119105 100644 --- a/src/d_player.h +++ b/src/d_player.h @@ -501,6 +501,7 @@ typedef struct player_s angle_t viewrollangle; angle_t tilt; + INT16 steering; angle_t angleturn; // Mouse aiming, where the guy is looking at! diff --git a/src/g_game.c b/src/g_game.c index 04fcf3508..925f71ca0 100644 --- a/src/g_game.c +++ b/src/g_game.c @@ -2105,6 +2105,7 @@ void G_PlayerReborn(INT32 player, boolean betweenmaps) INT16 rings; INT16 spheres; + INT16 steering; angle_t playerangleturn; UINT8 botdiffincrease; @@ -2142,6 +2143,8 @@ void G_PlayerReborn(INT32 player, boolean betweenmaps) spectator = players[player].spectator; pflags = (players[player].pflags & (PF_WANTSTOJOIN|PF_GAMETYPEOVER|PF_FAULT|PF_KICKSTARTACCEL)); + + steering = players[player].steering; playerangleturn = players[player].angleturn; // As long as we're not in multiplayer, carry over cheatcodes from map to map @@ -2254,6 +2257,7 @@ void G_PlayerReborn(INT32 player, boolean betweenmaps) p->quittime = quittime; p->splitscreenindex = splitscreenindex; p->spectator = spectator; + p->steering = steering; p->angleturn = playerangleturn; // save player config truth reborn diff --git a/src/k_hud.c b/src/k_hud.c index 8c6057721..31bf7cabc 100644 --- a/src/k_hud.c +++ b/src/k_hud.c @@ -885,7 +885,7 @@ void K_ObjectTracking(trackingResult_t *result, vector3_t *point, UINT8 cameraNu // Determine viewpoint factors. h = R_PointToDist2(point->x, point->y, viewpointX, viewpointY); - da = AngleDifference(viewpointAngle, R_PointToAngle2(point->x, point->y, viewpointX, viewpointY)); + da = AngleDeltaSigned(viewpointAngle, R_PointToAngle2(point->x, point->y, viewpointX, viewpointY)); // Set results! result->x = screenHalfW + FixedMul(NEWTAN(da), fg); @@ -893,7 +893,7 @@ void K_ObjectTracking(trackingResult_t *result, vector3_t *point, UINT8 cameraNu result->scale = FixedDiv(screenHalfW, h+1); - result->onScreen = ((abs(da) > ANG60) || (abs(AngleDifference(viewpointAiming, R_PointToAngle2(0, 0, h, viewpointZ))) > ANGLE_45)); + result->onScreen = ((abs(da) > ANG60) || (abs(AngleDeltaSigned(viewpointAiming, R_PointToAngle2(0, 0, h, viewpointZ))) > ANGLE_45)); if (encoremode) { @@ -3638,12 +3638,12 @@ static void K_drawBattleFullscreen(void) static void K_drawKartFirstPerson(void) { static INT32 pnum[4], turn[4], drift[4]; + const INT16 steerThreshold = KART_FULLTURN / 2; INT32 pn = 0, tn = 0, dr = 0; INT32 target = 0, splitflags = V_SNAPTOBOTTOM|V_SPLITSCREEN; INT32 x = BASEVIDWIDTH/2, y = BASEVIDHEIGHT; fixed_t scale; UINT8 *colmap = NULL; - ticcmd_t *cmd = &stplyr->cmd; if (stplyr->spectator || !stplyr->mo || (stplyr->mo->renderflags & RF_DONTDRAW)) return; @@ -3674,13 +3674,13 @@ static void K_drawKartFirstPerson(void) splitflags |= (stplyr->mo->frame & FF_TRANSMASK); } - if (cmd->turning > 400) // strong left turn + if (stplyr->steering > steerThreshold) // strong left turn target = 2; - else if (cmd->turning < -400) // strong right turn + else if (stplyr->steering < -steerThreshold) // strong right turn target = -2; - else if (cmd->turning > 0) // weak left turn + else if (stplyr->steering > 0) // weak left turn target = 1; - else if (cmd->turning < 0) // weak right turn + else if (stplyr->steering < 0) // weak right turn target = -1; else // forward target = 0; @@ -3703,8 +3703,8 @@ static void K_drawKartFirstPerson(void) x <<= FRACBITS; y <<= FRACBITS; - if (tn != cmd->turning/50) - tn -= (tn - (cmd->turning/50))/8; + if (tn != stplyr->steering/50) + tn -= (tn - (stplyr->steering/50))/8; if (dr != stplyr->kartstuff[k_drift]*16) dr -= (dr - (stplyr->kartstuff[k_drift]*16))/8; @@ -3834,14 +3834,14 @@ static void K_drawInput(void) y -= 1; - if (stplyr->exiting || !cmd->turning) // no turn + if (stplyr->exiting || !stplyr->steering) // no turn target = 0; else // turning of multiple strengths! { - target = ((abs(cmd->turning) - 1)/125)+1; + target = ((abs(stplyr->steering) - 1)/125)+1; if (target > 4) target = 4; - if (cmd->turning < 0) + if (stplyr->steering < 0) target = -target; } diff --git a/src/k_kart.c b/src/k_kart.c index fb899360a..3505dca01 100644 --- a/src/k_kart.c +++ b/src/k_kart.c @@ -6633,7 +6633,7 @@ static waypoint_t *K_GetPlayerNextWaypoint(player_t *player) R_PointToAngle2(waypoint->mobj->x, waypoint->mobj->y, nextwaypoint->mobj->x, nextwaypoint->mobj->y); // facing towards the finishline - if (abs(AngleDifference(angletonextwaypoint, angletowaypoint)) <= ANGLE_90) + if (AngleDelta(angletonextwaypoint, angletowaypoint) <= ANGLE_90) { finishlinehack = true; } @@ -7006,13 +7006,41 @@ static INT16 K_GetKartDriftValue(player_t *player, fixed_t countersteer) return basedrift + (FixedMul(driftadjust * FRACUNIT, countersteer) / FRACUNIT); } +void K_UpdateSteeringValue(player_t *player, INT16 destSteering) +{ + // player->steering is the turning value, but with easing applied. + // Keeps micro-turning from old easing, but isn't controller dependent. + + const INT16 amount = KART_FULLTURN/4; + INT16 diff = destSteering - player->steering; + + if (abs(diff) <= amount) + { + // Reached the intended value, set instantly. + player->steering = destSteering; + } + else + { + // Go linearly towards the value we wanted. + if (diff < 0) + { + player->steering -= amount; + } + else + { + player->steering += amount; + } + } +} + INT16 K_GetKartTurnValue(player_t *player, INT16 turnvalue) { - fixed_t p_maxspeed; - fixed_t p_speed; - fixed_t weightadjust; fixed_t turnfixed = turnvalue * FRACUNIT; + fixed_t currentSpeed = 0; + fixed_t p_maxspeed = INT32_MAX, p_speed = INT32_MAX; + + fixed_t weightadjust = INT32_MAX; if (player->mo == NULL || P_MobjWasRemoved(player->mo)) { @@ -7039,7 +7067,7 @@ INT16 K_GetKartTurnValue(player_t *player, INT16 turnvalue) return 0; } - currentSpeed = R_PointToDist2(0, 0, player->mo->momx, player->mo->momy); + currentSpeed = FixedHypot(player->mo->momx, player->mo->momy); if ((currentSpeed <= 0) // Not moving && ((K_GetKartButtons(player) & BT_EBRAKEMASK) != BT_EBRAKEMASK) // not e-braking @@ -7049,7 +7077,7 @@ INT16 K_GetKartTurnValue(player_t *player, INT16 turnvalue) } p_maxspeed = K_GetKartSpeed(player, false); - p_speed = min(FixedHypot(player->mo->momx, player->mo->momy), (p_maxspeed * 2)); + p_speed = min(currentSpeed, (p_maxspeed * 2)); weightadjust = FixedDiv((p_maxspeed * 3) - p_speed, (p_maxspeed * 3) + (player->kartweight * FRACUNIT)); if (K_PlayerUsesBotMovement(player)) diff --git a/src/k_kart.h b/src/k_kart.h index da40df761..c141aad69 100644 --- a/src/k_kart.h +++ b/src/k_kart.h @@ -72,6 +72,7 @@ player_t *K_FindJawzTarget(mobj_t *actor, player_t *source); INT32 K_GetKartRingPower(player_t *player, boolean boosted); void K_UpdateDistanceFromFinishLine(player_t *const player); boolean K_CheckPlayersRespawnColliding(INT32 playernum, fixed_t x, fixed_t y); +void K_UpdateSteeringValue(player_t *player, INT16 destSteering); INT16 K_GetKartTurnValue(player_t *player, INT16 turnvalue); INT32 K_GetKartDriftSparkValue(player_t *player); void K_SpawnDriftBoostExplosion(player_t *player, int stage); diff --git a/src/p_saveg.c b/src/p_saveg.c index ee7742495..87646d225 100644 --- a/src/p_saveg.c +++ b/src/p_saveg.c @@ -124,6 +124,7 @@ static void P_NetArchivePlayers(void) WRITEINT32(save_p, splitscreen_original_party[i][j]); } + WRITEINT16(save_p, players[i].steering); WRITEANGLE(save_p, players[i].angleturn); WRITEANGLE(save_p, players[i].aiming); WRITEANGLE(save_p, players[i].drawangle); @@ -364,6 +365,7 @@ static void P_NetUnArchivePlayers(void) splitscreen_original_party[i][j] = READINT32(save_p); } + players[i].steering = READINT16(save_p); players[i].angleturn = READANGLE(save_p); players[i].aiming = READANGLE(save_p); players[i].drawangle = READANGLE(save_p); diff --git a/src/p_user.c b/src/p_user.c index 09b8865fd..0b2e8a4d1 100644 --- a/src/p_user.c +++ b/src/p_user.c @@ -2040,9 +2040,12 @@ static void P_3dMovement(player_t *player) // static void P_UpdatePlayerAngle(player_t *player) { - angle_t angleChange = K_GetKartTurnValue(player, player->cmd.turning) << TICCMD_REDUCE; + angle_t angleChange = ANGLE_MAX; UINT8 i; + K_UpdateSteeringValue(player, player->cmd.turning); + angleChange = K_GetKartTurnValue(player, player->steering) << TICCMD_REDUCE; + P_SetPlayerAngle(player, player->angleturn + angleChange); player->mo->angle = player->angleturn; diff --git a/src/tables.c b/src/tables.c index 9223bb7ca..42ad6a73c 100644 --- a/src/tables.c +++ b/src/tables.c @@ -167,13 +167,24 @@ angle_t FixedAngle(fixed_t fa) return AngleAdj(cfa, cwf, ra); } -INT32 AngleDifference(angle_t a1, angle_t a2) +INT32 AngleDelta(angle_t a1, angle_t a2) +{ + angle_t delta = a1 - a2; + + if (delta > ANGLE_180) + { + delta = InvAngle(delta); + } + + return delta; +} + +INT32 AngleDeltaSigned(angle_t a1, angle_t a2) { // Silly but easy way to do it through integer conversion. return (INT32)(a1) - (INT32)(a2); } - #include "t_ftan.c" #include "t_fsin.c" diff --git a/src/tables.h b/src/tables.h index a34b95ad2..7f1591f2a 100644 --- a/src/tables.h +++ b/src/tables.h @@ -100,7 +100,8 @@ FUNCMATH angle_t FixedAngle(fixed_t fa); // and with a factor, with +factor for (fa/factor) and -factor for (fa*factor) FUNCMATH angle_t FixedAngleC(fixed_t fa, fixed_t factor); // difference between two angle_t -FUNCMATH INT32 AngleDifference(angle_t a1, angle_t a2); +FUNCMATH INT32 AngleDelta(angle_t a1, angle_t a2); +FUNCMATH INT32 AngleDeltaSigned(angle_t a1, angle_t a2); /// The FixedAcos function FUNCMATH angle_t FixedAcos(fixed_t x);