From 8f5e45feb30abfe08714b7dc2b84df056561908c Mon Sep 17 00:00:00 2001 From: Bryce Hutchings Date: Fri, 26 Apr 2002 05:29:38 +0000 Subject: [PATCH] PHYSICS, Take 2 --- reaction/game/bg_pmove.c | 705 +++-------------------------------- reaction/game/bg_slidemove.c | 271 +++++++++----- 2 files changed, 245 insertions(+), 731 deletions(-) diff --git a/reaction/game/bg_pmove.c b/reaction/game/bg_pmove.c index 7d61d4b4..dfada128 100644 --- a/reaction/game/bg_pmove.c +++ b/reaction/game/bg_pmove.c @@ -5,6 +5,9 @@ //----------------------------------------------------------------------------- // // $Log$ +// Revision 1.68 2002/04/26 05:29:38 niceass +// PHYSICS, Take 2 +// // Revision 1.67 2002/04/20 15:03:47 makro // More footstep sounds, a few other things // @@ -94,44 +97,7 @@ float pm_ladderfriction = 3000; int c_pmove = 0; -/* -// rxn - agt -// Not used now, but will be used when the numbers are finalized. -float rxn_rampAccelerate = 130; -float rxn_rampAccelerateVert = 110; - -=============== -RXN_RampMunge - -=============== -*/ -/* -void RXN_RampMunge ( void ) { - vec3_t owishdir; - int i; -// char raustring[25]; -// char rafstring[25]; - float acc; - float upacc; -// int goodslope; - - - upacc = rxn_rampAccelerate; - acc = rxn_rampAccelerateVert; - - if (pml.groundTrace.plane.normal[2] < 1.0 && pml.groundTrace.plane.normal[2] > 0.7) { - if (VectorLength(pm->ps->velocity) > 200) { - VectorCopy(pm->ps->velocity, owishdir); - VectorNormalize(owishdir); - for (i=0 ; i<3 ; i++) { - pm->ps->velocity[i] += acc * owishdir[i]; - } - pm->ps->velocity[2] += upacc; - } - } -} -*/ /* [QUARANTINE] - Weapon Animations =================== PM_StartWeaponAnim, PM_ContinueWeaponAnim @@ -311,7 +277,7 @@ static void PM_Friction( void ) { // apply ground friction if ( pm->waterlevel <= 1 ) { - if ( pml.walking && !(pml.groundTrace.surfaceFlags & SURF_SLICK) ) { + if ( pml.walking && !(pml.groundTrace.surfaceFlags & SURF_SLICK) && pm->ps->groundEntityNum) { // if getting knocked back, no friction if ( ! (pm->ps->pm_flags & PMF_TIME_KNOCKBACK) ) { control = speed < pm_stopspeed ? pm_stopspeed : speed; @@ -472,58 +438,24 @@ static qboolean PM_CheckJump( void ) { return qfalse; } + if (!pml.groundPlane) return qfalse; + pml.groundPlane = qfalse; // jumping away pml.walking = qfalse; pm->ps->pm_flags |= PMF_JUMP_HELD; pm->ps->groundEntityNum = ENTITYNUM_NONE; - // Blaze: check for double jump + pm->ps->velocity[2] += JUMP_VELOCITY; - if (pm->ps->stats[STAT_JUMPTIME] > 0) { - pm->ps->velocity[2] += JUMP_VELOCITY; - // Elder: ladder jump boost - if (pml.ladder == qtrue) - { - if (pm->debugLevel) - Com_Printf("^3Ladder jump boost^7\n"); - pm->ps->velocity[2] += 135; - } - else - pm->ps->velocity[2] += 75; // More velocity ; was 100 - if (pm->debugLevel) - Com_Printf("^4Hit a double jump^7\n"); - //Com_Printf("%i:CPM->Double Jump, after %ims\n", c_pmove, (pm->jumpTime - pm->ps->stats[STAT_JUMPTIME])); - } else { - pm->ps->velocity[2] += JUMP_VELOCITY; - if (pm->ps->velocity[2] < JUMP_VELOCITY) - pm->ps->velocity[2] = JUMP_VELOCITY; - } - - // Time that the second jump is within to get the higher jump - if (pml.ladder == qtrue) - { - // Elder: more for ladder jumps - pm->ps->stats[STAT_JUMPTIME] = 500; - } - else - pm->ps->stats[STAT_JUMPTIME] = 250; // 400 - // end Blaze + if (pm->ps->velocity[2] < JUMP_VELOCITY) + pm->ps->velocity[2] = JUMP_VELOCITY; PM_AddEvent( EV_JUMP ); -// JBravo: we dont want backflips. PM_ForceLegsAnim( LEGS_JUMP ); pm->ps->pm_flags &= ~PMF_BACKWARDS_JUMP; -/* if ( pm->cmd.forwardmove >= 0 ) { - PM_ForceLegsAnim( LEGS_JUMP ); - pm->ps->pm_flags &= ~PMF_BACKWARDS_JUMP; - } else { - PM_ForceLegsAnim( LEGS_JUMPB ); - pm->ps->pm_flags |= PMF_BACKWARDS_JUMP; - } */ return qtrue; - } /* @@ -614,20 +546,7 @@ static void PM_WaterMove( void ) { PM_WaterJumpMove(); return; } -#if 0 - // jump = head for surface - if ( pm->cmd.upmove >= 10 ) { - if (pm->ps->velocity[2] > -300) { - if ( pm->watertype == CONTENTS_WATER ) { - pm->ps->velocity[2] = 100; - } else if (pm->watertype == CONTENTS_SLIME) { - pm->ps->velocity[2] = 80; - } else { - pm->ps->velocity[2] = 50; - } - } - } -#endif + PM_Friction (); scale = PM_CmdScale( &pm->cmd ); @@ -658,6 +577,8 @@ static void PM_WaterMove( void ) { if ( pml.groundPlane && DotProduct( pm->ps->velocity, pml.groundTrace.plane.normal ) < 0 ) { vel = VectorLength(pm->ps->velocity); // slide along the ground plane + PM_ClipVelocity (pm->ps->velocity, pml.groundTrace.plane.normal, + pm->ps->velocity, OVERCLIP ); VectorNormalize(pm->ps->velocity); VectorScale(pm->ps->velocity, vel, pm->ps->velocity); @@ -666,22 +587,6 @@ static void PM_WaterMove( void ) { PM_StepSlideMove( qfalse ); } -#ifdef MISSIONPACK -/* -=================== -PM_InvulnerabilityMove - -Only with the invulnerability powerup -=================== -*/ -static void PM_InvulnerabilityMove( void ) { - pm->cmd.forwardmove = 0; - pm->cmd.rightmove = 0; - pm->cmd.upmove = 0; - VectorClear(pm->ps->velocity); -} -#endif - /* =================== PM_FlyMove @@ -737,41 +642,48 @@ static void PM_AirMove( void ) { vec3_t wishdir; float wishspeed; float scale; - float maxspeed; + usercmd_t cmd; + PM_CheckJump(); PM_Friction(); fmove = pm->cmd.forwardmove; smove = pm->cmd.rightmove; - scale = PM_CmdScale( &pm->cmd ); + cmd = pm->cmd; + scale = PM_CmdScale( &cmd ); // set the movementDir so clients can rotate the legs for strafing PM_SetMovementDir(); + // project moves down to flat plane + + pml.forward[2] = 0; + pml.right[2] = 0; + VectorNormalize (pml.forward); + VectorNormalize (pml.right); + for ( i = 0 ; i < 2 ; i++ ) { - wishvel[i] = scale*pml.forward[i]*fmove + scale*pml.right[i]*smove; + wishvel[i] = pml.forward[i]*fmove*scale + pml.right[i]*smove*scale; } wishvel[2] = 0; VectorCopy (wishvel, wishdir); wishspeed = VectorNormalize(wishdir); - - if (pm->ps->pm_flags & PMF_DUCKED) - maxspeed = 100; // the ducking speed - else - maxspeed = pm_maxspeed; - - if (wishspeed > maxspeed) { - VectorScale (wishvel, maxspeed/wishspeed, wishvel); - wishspeed = maxspeed; - } + //wishspeed *= scale; // not on ground, so little effect on velocity PM_Accelerate (wishdir, wishspeed, pm_airaccelerate); - pm->ps->velocity[2] -= pm->ps->gravity * pml.frametime; - PM_StepSlideMove ( qfalse ); + // we may have a ground plane that is very steep, even + // though we don't have a groundentity + // slide along the steep plane + /*if ( pml.groundPlane ) { + PM_ClipVelocity (pm->ps->velocity, pml.groundTrace.plane.normal, + pm->ps->velocity, OVERCLIP ); + } + */ + PM_StepSlideMove ( qtrue ); } /* @@ -799,139 +711,6 @@ static void PM_GrappleMove( void ) { pml.groundPlane = qfalse; } -/* -=================================== -PM_LimpMove -Movement while you have leg damage -=================================== -// JBravo: apparently this isnt used. -*/ -/* -static void PM_LimpMove( void) -{ - int i; - vec3_t wishvel; - float fmove, smove; - vec3_t wishdir; - float wishspeed; - float scale; - usercmd_t cmd; - float accelerate; - float vel; - - //Com_Printf("(%d)(%d)(%d)\n", pm->cmd.serverTime, pm->ps->commandTime, pm->ps->pm_time ); - - if ( pm->cmd.serverTime % 1000 > 333) - { - // Com_Printf("(%d)\n",pm->cmd.serverTime % 1000); - if ( PM_CheckJump () ) { - // jumped away - if ( pm->waterlevel > 1 ) { - PM_WaterMove(); - } else { - PM_AirMove(); - } - return; - } - - PM_Friction (); - - fmove = pm->cmd.forwardmove; - smove = pm->cmd.rightmove; - - cmd = pm->cmd; - scale = PM_CmdScale( &cmd ); - - // set the movementDir so clients can rotate the legs for strafing - PM_SetMovementDir(); - - // project moves down to flat plane -//Blaze: ram jump test - pml.forward[2] = 0; - pml.right[2] = 0; - - // project the forward and right directions onto the ground plane -//Blaze: ramp jumping test - PM_ClipVelocity (pml.forward, pml.groundTrace.plane.normal, pml.forward, OVERCLIP ); - PM_ClipVelocity (pml.right, pml.groundTrace.plane.normal, pml.right, OVERCLIP ); - // -//Blaze: Ramp jump test - VectorNormalize (pml.forward); - VectorNormalize (pml.right); - - for ( i = 0 ; i < 3 ; i++ ) { - wishvel[i] = pml.forward[i]*fmove + pml.right[i]*smove; - } - // when going up or down slopes the wish velocity should Not be zero -// wishvel[2] = 0; - - VectorCopy (wishvel, wishdir); - wishspeed = VectorNormalize(wishdir); - wishspeed *= scale; - - // clamp the speed lower if ducking - if ( pm->ps->pm_flags & PMF_DUCKED ) { - if ( wishspeed > pm->ps->speed * pm_duckScale ) { - wishspeed = pm->ps->speed * pm_duckScale; - } - } - - // clamp the speed lower if wading or walking on the bottom - if ( pm->waterlevel ) { - float waterScale; - - waterScale = pm->waterlevel / 3.0; - waterScale = 1.0 - ( 1.0 - pm_swimScale ) * waterScale; - if ( wishspeed > pm->ps->speed * waterScale ) { - wishspeed = pm->ps->speed * waterScale; - } - } - - // when a player gets hit, they temporarily lose - // full control, which allows them to be moved a bit - if ( ( pml.groundTrace.surfaceFlags & SURF_SLICK ) || pm->ps->pm_flags & PMF_TIME_KNOCKBACK ) { - accelerate = pm_airaccelerate; - } else { - accelerate = pm_accelerate; - } - - PM_Accelerate (wishdir, wishspeed, accelerate); - - //Com_Printf("velocity = %1.1f %1.1f %1.1f\n", pm->ps->velocity[0], pm->ps->velocity[1], pm->ps->velocity[2]); - //Com_Printf("velocity1 = %1.1f\n", VectorLength(pm->ps->velocity)); - - if ( ( pml.groundTrace.surfaceFlags & SURF_SLICK ) || pm->ps->pm_flags & PMF_TIME_KNOCKBACK ) { - pm->ps->velocity[2] -= pm->ps->gravity * pml.frametime; - } else { - // don't reset the z velocity for slopes -// pm->ps->velocity[2] = 0; - } - - vel = VectorLength(pm->ps->velocity); - - // slide along the ground plane -//Blaze: ramp jump test - PM_ClipVelocity (pm->ps->velocity, pml.groundTrace.plane.normal, - pm->ps->velocity, OVERCLIP ); - - // don't decrease velocity when going up or down a slope - VectorNormalize(pm->ps->velocity); - VectorScale(pm->ps->velocity, vel, pm->ps->velocity); - - // don't do anything if standing still - if (!pm->ps->velocity[0] && !pm->ps->velocity[1]) { - return; - } - - PM_StepSlideMove( qfalse ); - - //Com_Printf("velocity2 = %1.1f\n", VectorLength(pm->ps->velocity)); - - } - - -} -*/ /* =================== @@ -948,7 +727,6 @@ static void PM_WalkMove( void ) { float scale; usercmd_t cmd; float accelerate; -// float vel; if ( pm->waterlevel > 2 && DotProduct( pml.forward, pml.groundTrace.plane.normal ) > 0 ) { // begin swimming @@ -1025,19 +803,27 @@ static void PM_WalkMove( void ) { } pm->ps->velocity[2] = 0; - PM_Accelerate (wishdir, wishspeed, accelerate); - //Com_Printf("velocity = %1.1f %1.1f %1.1f\n", pm->ps->velocity[0], pm->ps->velocity[1], pm->ps->velocity[2]); - //Com_Printf("velocity1 = %1.1f\n", VectorLength(pm->ps->velocity)); - - if ( ( pml.groundTrace.surfaceFlags & SURF_SLICK ) || pm->ps->pm_flags & PMF_TIME_KNOCKBACK ) { - pm->ps->velocity[2] -= pm->ps->gravity * pml.frametime; + if (pm->ps->gravity > 0) + pm->ps->velocity[2] = 0; + else { + if ( ( pml.groundTrace.surfaceFlags & SURF_SLICK ) || pm->ps->pm_flags & PMF_TIME_KNOCKBACK ) { + pm->ps->velocity[2] -= pm->ps->gravity * pml.frametime; + } } - if (pm->ps->gravity < 0) - pm->ps->velocity[2] -= pm->ps->gravity * pml.frametime; + /* + vel = VectorLength(pm->ps->velocity); + // slide along the ground plane + PM_ClipVelocity (pm->ps->velocity, pml.groundTrace.plane.normal, + pm->ps->velocity, OVERCLIP ); + + // don't decrease velocity when going up or down a slope + VectorNormalize(pm->ps->velocity); + VectorScale(pm->ps->velocity, vel, pm->ps->velocity); + */ // don't do anything if standing still if (!pm->ps->velocity[0] && !pm->ps->velocity[1]) { return; @@ -1243,49 +1029,17 @@ static void PM_CrashLand( void ) { //float a, b, c, den; int damage; -// JBravo: no falling at all during LCA in Teamplay + // JBravo: no falling at all during LCA in Teamplay if (pm->lca) { return; } - // decide which landing animation to use -// JBravo: we dont want backflips. PM_ForceLegsAnim( LEGS_LAND ); -/* if ( pm->ps->pm_flags & PMF_BACKWARDS_JUMP ) { - PM_ForceLegsAnim( LEGS_LANDB ); - } else { - PM_ForceLegsAnim( LEGS_LAND ); - } */ - pm->ps->legsTimer = TIMER_LAND; - - // calculate the exact velocity on landing - /*dist = pm->ps->origin[2] - pml.previous_origin[2]; - vel = pml.previous_velocity[2]; - acc = -pm->ps->gravity; - - a = acc / 2; - b = vel; - c = -dist; - - den = b * b - 4 * a * c; - if ( den < 0 ) { - return; - } - t = (-b - sqrt( den ) ) / ( 2 * a ); -*/ - //delta = vel + t * acc; - //Blaze: added to make it more like aq2 - //delta = pm->ps->velocity[2] - pml.previous_velocity[2]; // Elder: 300/320 factor included delta = 0.9375f * (pm->ps->velocity[2] - pml.previous_velocity[2]); delta = delta*delta * 0.0001; - // ducking while falling doubles damage -// if ( pm->ps->pm_flags & PMF_DUCKED ) { -// delta *= 2; -// } - // never take falling damage if completely underwater if ( pm->waterlevel == 3 ) { return; @@ -1303,24 +1057,16 @@ static void PM_CrashLand( void ) { return; } - // create a local entity event to play the sound - - // SURF_NODAMAGE is used for bounce pads where you don't ever - // want to take damage or play a crunch sound - - if (delta > 30) { - - //Com_Printf("delta =(%f), delta - 30 = (%f), damage = (%d)",delta,delta-30,(int)(((delta-30)/2))); damage = (int)(((delta-30)/2)); if (damage < 1) damage = 1; damage *= 10; if ( !(pml.groundTrace.surfaceFlags & SURF_NODAMAGE) ) { - //Blaze lots of changes to make it more like aq2 - // this is a pain grunt, so don't play it if dead + //Blaze lots of changes to make it more like aq2 + // this is a pain grunt, so don't play it if dead if ( pm->ps->stats[STAT_HEALTH] > 0 && damage > 0) { if (bg_itemlist[pm->ps->stats[STAT_HOLDABLE_ITEM]].giTag == HI_SLIPPERS) PM_AddEvent( EV_FALL_FAR_NOSOUND ); @@ -1365,23 +1111,6 @@ static void PM_CrashLand( void ) { pm->ps->bobCycle = 0; } -/* -============= -PM_CheckStuck -============= -*/ -/* -void PM_CheckStuck(void) { - trace_t trace; - - pm->trace (&trace, pm->ps->origin, pm->mins, pm->maxs, pm->ps->origin, pm->ps->clientNum, pm->tracemask); - if (trace.allsolid) { - //Elder: LMAO! WTF is this? - //int shit = qtrue; - } -} -*/ - /* ============= PM_CorrectAllSolid @@ -1449,16 +1178,8 @@ static void PM_GroundTraceMissed( void ) { pm->trace (&trace, pm->ps->origin, pm->mins, pm->maxs, point, pm->ps->clientNum, pm->tracemask); if ( trace.fraction == 1.0 ) { -// JBravo: we dont want backflips. PM_ForceLegsAnim( LEGS_JUMP ); pm->ps->pm_flags &= ~PMF_BACKWARDS_JUMP; -/* if ( pm->cmd.forwardmove >= 0 ) { - PM_ForceLegsAnim( LEGS_JUMP ); - pm->ps->pm_flags &= ~PMF_BACKWARDS_JUMP; - } else { - PM_ForceLegsAnim( LEGS_JUMPB ); - pm->ps->pm_flags |= PMF_BACKWARDS_JUMP; - } */ } } @@ -1484,7 +1205,7 @@ static void PM_GroundTrace( void ) { pml.walking = qfalse; // Maybe not needed? return; } - + point[0] = pm->ps->origin[0]; point[1] = pm->ps->origin[1]; point[2] = pm->ps->origin[2] - 0.25; @@ -1498,10 +1219,8 @@ static void PM_GroundTrace( void ) { return; } - // if the trace didn't hit anything, we are in free fall - // Elder: added ladder check + // if the trace didn't hit anything and not on ladder, we are in free fall if ( trace.fraction == 1.0 && !pml.ladder) { - //if ( trace.fraction == 1.0 ) { PM_GroundTraceMissed(); pml.groundPlane = qfalse; pml.walking = qfalse; @@ -1513,17 +1232,11 @@ static void PM_GroundTrace( void ) { if ( pm->debugLevel ) { Com_Printf("%i:kickoff\n", c_pmove); } + // go into jump animation -// JBravo: we dont want backflips. PM_ForceLegsAnim( LEGS_JUMP ); pm->ps->pm_flags &= ~PMF_BACKWARDS_JUMP; -/* if ( pm->cmd.forwardmove >= 0 ) { - PM_ForceLegsAnim( LEGS_JUMP ); - pm->ps->pm_flags &= ~PMF_BACKWARDS_JUMP; - } else { - PM_ForceLegsAnim( LEGS_JUMPB ); - pm->ps->pm_flags |= PMF_BACKWARDS_JUMP; - } */ + pm->ps->groundEntityNum = ENTITYNUM_NONE; pml.groundPlane = qfalse; @@ -1540,8 +1253,7 @@ static void PM_GroundTrace( void ) { // FIXME: if they can't slide down the slope, let them // walk (sharp crevices) pm->ps->groundEntityNum = ENTITYNUM_NONE; -// pml.groundPlane = qtrue; // NiceAss - pml.groundPlane = qfalse; + pml.groundPlane = qtrue; pml.walking = qfalse; return; } @@ -1564,7 +1276,6 @@ static void PM_GroundTrace( void ) { PM_CrashLand(); - // Elder: added ladder check if (pml.ladder) { pml.groundPlane = qfalse; @@ -1574,7 +1285,6 @@ static void PM_GroundTrace( void ) { // don't do landing time if we were just going down a slope if ( pml.previous_velocity[2] < -200 ) { - // Elder: maybe this is keeping the strafe jumping too tight? // don't allow another jump for a little while pm->ps->pm_flags |= PMF_TIME_LAND; pm->ps->pm_time = 250; @@ -1583,9 +1293,6 @@ static void PM_GroundTrace( void ) { pm->ps->groundEntityNum = trace.entityNum; - // don't reset the z velocity for slopes -// pm->ps->velocity[2] = 0; - PM_AddTouchEnt( trace.entityNum ); } @@ -1706,9 +1413,7 @@ static void PM_CheckDuck (void) } } - // Elder: don't allow mid-air "crouching" - // Removed because it was causing problems -- WTF is the "jump" flag? - if (pm->ps->pm_flags & PMF_DUCKED )// && pm->ps->groundEntityNum != ENTITYNUM_NONE) + if (pm->ps->pm_flags & PMF_DUCKED ) { pm->maxs[2] = 16; pm->ps->viewheight = CROUCH_VIEWHEIGHT; @@ -1940,19 +1645,7 @@ static void PM_BeginWeaponChange( int weapon ) { break; } - //Elder: temp hack - /* - if (pm->ps->weapon == WP_PISTOL || - pm->ps->weapon == WP_M3 || - pm->ps->weapon == WP_HANDCANNON || - pm->ps->weapon == WP_SSG3000 || - pm->ps->weapon == WP_M4 || - pm->ps->weapon == WP_AKIMBO || - pm->ps->weapon == WP_GRENADE || - (pm->ps->weapon == WP_KNIFE && (pm->ps->persistant[PERS_WEAPONMODES] & RQ3_KNIFEMODE))) - PM_StartWeaponAnim(WP_ANIM_DISARM); - else - */ + if ( pm->ps->weapon == WP_KNIFE && !(pm->ps->persistant[PERS_WEAPONMODES] & RQ3_KNIFEMODE) ) PM_StartWeaponAnim(WP_ANIM_THROWDISARM); else { @@ -1981,21 +1674,6 @@ static void PM_BeginWeaponChange( int weapon ) { pm->ps->weaponstate = WEAPON_DROPPING; - - //Elder: temp hack - /* - if (pm->ps->weapon == WP_PISTOL || - pm->ps->weapon == WP_M3 || - pm->ps->weapon == WP_HANDCANNON || - pm->ps->weapon == WP_SSG3000 || - pm->ps->weapon == WP_M4 || - pm->ps->weapon == WP_MP5 || - pm->ps->weapon == WP_AKIMBO || - pm->ps->weapon == WP_GRENADE || - (pm->ps->weapon == WP_KNIFE && (pm->ps->persistant[PERS_WEAPONMODES] & RQ3_KNIFEMODE))) - PM_StartWeaponAnim(WP_ANIM_DISARM); - else*/ - if (pm->ps->weapon == WP_KNIFE && !(pm->ps->persistant[PERS_WEAPONMODES] & RQ3_KNIFEMODE)) PM_StartWeaponAnim(WP_ANIM_THROWDISARM); else { @@ -2043,7 +1721,6 @@ static void PM_FinishWeaponChange( void ) { pm->ps->weapon = weapon; pm->ps->weaponstate = WEAPON_RAISING; - //pm->ps->weaponTime += 250; //Elder: weapon-dependent timing switch (pm->ps->weapon) { case WP_PISTOL: @@ -2080,20 +1757,6 @@ static void PM_FinishWeaponChange( void ) { break; } - //Elder: temp hack - /* - if (pm->ps->weapon == WP_PISTOL || - pm->ps->weapon == WP_M3 || - pm->ps->weapon == WP_HANDCANNON || - pm->ps->weapon == WP_SSG3000 || - pm->ps->weapon == WP_M4 || - pm->ps->weapon == WP_MP5 || - pm->ps->weapon == WP_AKIMBO || - pm->ps->weapon == WP_GRENADE || - (pm->ps->weapon == WP_KNIFE && (pm->ps->persistant[PERS_WEAPONMODES] & RQ3_KNIFEMODE))) - PM_StartWeaponAnim(WP_ANIM_ACTIVATE); - */ - /*else*/ if (pm->ps->weapon == WP_KNIFE && !(pm->ps->persistant[PERS_WEAPONMODES] & RQ3_KNIFEMODE)) PM_StartWeaponAnim(WP_ANIM_THROWACTIVATE); else @@ -2118,21 +1781,8 @@ static void PM_TorsoAnimation( void ) { } // QUARANTINE - Weapon Animation // Should always draw the weapon when it is just ready - //Elder: temp hack if (pm->ps->ammo[pm->ps->weapon] == 0) PM_ContinueWeaponAnim( WP_ANIM_EMPTY ); - /* - else if (pm->ps->weapon == WP_PISTOL || - pm->ps->weapon == WP_M3 || - pm->ps->weapon == WP_HANDCANNON || - pm->ps->weapon == WP_SSG3000 || - pm->ps->weapon == WP_M4 || - pm->ps->weapon == WP_MP5 || - pm->ps->weapon == WP_AKIMBO || - pm->ps->weapon == WP_GRENADE || - (pm->ps->weapon == WP_KNIFE && (pm->ps->persistant[PERS_WEAPONMODES] & RQ3_KNIFEMODE))) - PM_ContinueWeaponAnim(WP_ANIM_IDLE); - */ else if (pm->ps->weapon == WP_KNIFE && !(pm->ps->persistant[PERS_WEAPONMODES] & RQ3_KNIFEMODE)) PM_ContinueWeaponAnim(WP_ANIM_THROWIDLE); else @@ -2144,28 +1794,6 @@ static void PM_TorsoAnimation( void ) { } } -/* -============== -PM_WeaponAnimation -JBravo: this isnt used either. -============== -*/ -/* -static void PM_WeaponAnimation( void ) { - //if (pm->ps->weaponstate == WEAPON_RELOADING) - //{ - //PM_ContinueWeaponAnim( WP_ANIM_RELOAD ); - //} - //else if (pm->ps->weaponstate == WEAPON_READY) - //PM_ContinueWeaponAnim( WP_ANIM_IDLE ); - //else if (pm->ps->weaponstate == WEAPON_DROPPING) - //PM_ContinueWeaponAnim( WP_ANIM_DISARM ); - //else if (pm->ps->weaponstate == WEAPON_RAISING) - //PM_ContinueWeaponAnim( WP_ANIM_ACTIVATE ); - return; -} -*/ - /* ============== PM_Reload @@ -2615,28 +2243,6 @@ static void PM_Weapon( void ) { } } - // check for item using - // Elder: removed - /* - if ( pm->cmd.buttons & BUTTON_USE_HOLDABLE ) { - if ( ! ( pm->ps->pm_flags & PMF_USE_ITEM_HELD ) ) { - - // Blaze: No more medkit - //if ( bg_itemlist[pm->ps->stats[STAT_HOLDABLE_ITEM]].giTag == HI_MEDKIT - //&& pm->ps->stats[STAT_HEALTH] >= (125) ) { //medikit check pm->ps->stats[STAT_MAX_HEALTH] + 25) ) { - // don't use medkit if at max health - //} else { - pm->ps->pm_flags |= PMF_USE_ITEM_HELD; - PM_AddEvent( EV_USE_ITEM0 + bg_itemlist[pm->ps->stats[STAT_HOLDABLE_ITEM]].giTag ); - pm->ps->stats[STAT_HOLDABLE_ITEM] = 0; - //} - return; - } - } else { - pm->ps->pm_flags &= ~PMF_USE_ITEM_HELD; - } - */ - //NiceAss: I added this smoother M4 rise. Should this be used? /* if ( ( pm->cmd.buttons & 1 || pm->ps->stats[STAT_BURST] ) && pm->ps->ammo[pm->ps->weapon]) { @@ -2647,11 +2253,6 @@ static void PM_Weapon( void ) { } */ - // NiceAss: Sorta a hack, but it looks better. -/* if ( pm->ps->weapon == WP_PISTOL && pm->ps->ammo[WP_PISTOL] == 0 && pm->ps->weaponTime < RQ3_PISTOL_DELAY*.3 ) { - PM_StartWeaponAnim( WP_ANIM_EMPTY ); - }*/ - // make weapon function if ( pm->ps->weaponTime > 0 ) { pm->ps->weaponTime -= pml.msec; @@ -2689,18 +2290,6 @@ static void PM_Weapon( void ) { if (pm->ps->ammo[pm->ps->weapon] == 0) { PM_ContinueWeaponAnim( WP_ANIM_EMPTY ); } - /* - else if (pm->ps->weapon == WP_PISTOL || - pm->ps->weapon == WP_M3 || - pm->ps->weapon == WP_HANDCANNON || - pm->ps->weapon == WP_SSG3000 || - pm->ps->weapon == WP_M4 || - pm->ps->weapon == WP_MP5 || - pm->ps->weapon == WP_AKIMBO || - pm->ps->weapon == WP_GRENADE || - (pm->ps->weapon == WP_KNIFE && (pm->ps->persistant[PERS_WEAPONMODES] & RQ3_KNIFEMODE))) - PM_ContinueWeaponAnim(WP_ANIM_IDLE); - */ else if (pm->ps->weapon == WP_KNIFE && !(pm->ps->persistant[PERS_WEAPONMODES] & RQ3_KNIFEMODE)) { PM_ContinueWeaponAnim(WP_ANIM_THROWIDLE); @@ -2711,23 +2300,6 @@ static void PM_Weapon( void ) { } } - - //Elder: drop the primed grenade if bandaging - /* - if ( pm->ps->weapon == WP_GRENADE && - pm->ps->ammo[WP_GRENADE] > 0 && - // - //pm->ps->weaponstate == WEAPON_DROPPING && - (pm->cmd.buttons & 1) && - (pm->ps->stats[STAT_RQ3] & RQ3_BANDAGE_WORK) == RQ3_BANDAGE_WORK) - { - PM_AddEvent( EV_FIRE_WEAPON ); - pm->ps->ammo[WP_GRENADE]--; - if (pm->ps->ammo[WP_GRENADE] == 0) - pm->ps->stats[STAT_WEAPONS] &= ~( 1 << WP_GRENADE); - }*/ - - // Elder: added STAT_RELOADTIME and STAT_WEAPONSTALLTIME check if ( pm->ps->weaponTime > 0 || pm->ps->stats[STAT_RELOADTIME] > 0 || pm->ps->stats[STAT_WEAPONSTALLTIME] > 0) { @@ -2771,25 +2343,11 @@ static void PM_Weapon( void ) { } else { PM_StartTorsoAnim( TORSO_STAND ); } - // QUARANTINE - Weapon Animation - // Should always draw the weapon when it is just ready -// PM_StartWeaponAnim( WP_ANIM_READY ); // temp hack if (pm->ps->ammo[pm->ps->weapon] == 0) { PM_ContinueWeaponAnim( WP_ANIM_EMPTY ); } - /* - else if (pm->ps->weapon == WP_PISTOL || - pm->ps->weapon == WP_M3 || - pm->ps->weapon == WP_HANDCANNON || - pm->ps->weapon == WP_SSG3000 || - pm->ps->weapon == WP_M4 || - pm->ps->weapon == WP_MP5 || - pm->ps->weapon == WP_AKIMBO || - pm->ps->weapon == WP_GRENADE || - (pm->ps->weapon == WP_KNIFE && !(pm->ps->persistant[PERS_WEAPONMODES] & RQ3_KNIFEMODE))) - PM_StartWeaponAnim( WP_ANIM_IDLE ); - */ + else if (pm->ps->weapon == WP_KNIFE && !(pm->ps->persistant[PERS_WEAPONMODES] & RQ3_KNIFEMODE)) PM_StartWeaponAnim( WP_ANIM_THROWIDLE ); else @@ -2809,7 +2367,6 @@ static void PM_Weapon( void ) { return; } - // Elder: fire on release - based on code from inolen // check for fire // if they are pressing attack and their current weapon is the grenade @@ -2841,25 +2398,6 @@ static void PM_Weapon( void ) { PM_StartWeaponAnim( WP_ANIM_THROWFIRE ); return; } - - /* - else if ( pm->ps->weapon == WP_KNIFE && - !(pm->ps->persistant[PERS_WEAPONMODES] & RQ3_KNIFEMODE) ) - { - if ( pm->ps->weaponstate == WEAPON_READY ) - { - pm->ps->weaponstate = WEAPON_STALL; - pm->ps->stats[STAT_WEAPONSTALLTIME] = 200; - PM_StartWeaponAnim( WP_ANIM_THROWFIRE ); - return; - } - else if ( pm->ps->weaponstate == WEAPON_STALL ) - { - pm->ps->stats[STAT_WEAPONSTALLTIME] = 0; - pm->ps->weaponstate = WEAPON_READY; - } - } - */ } // check for fireA release @@ -2917,22 +2455,6 @@ static void PM_Weapon( void ) { } } - /* - if ( ! (pm->cmd.buttons & BUTTON_ATTACK) ) { - pm->ps->weaponTime = 0; - pm->ps->weaponstate = WEAPON_READY; - // Homer: not firing, reset burst value (cheaper than a non-zero check) - //Elder: reset only if the max amount has been shot - //if ( pm->ps->weapon == WP_PISTOL) { - pm->ps->stats[STAT_BURST] = 0; - //} - //else if ( ( pm->ps->weapon == WP_M4 && pm->ps->stats[STAT_BURST] > 2 ) || - //( pm->ps->weapon == WP_MP5 && pm->ps->stats[STAT_BURST] > 2 ) ) { - //pm->ps->stats[STAT_BURST] = 0; - //} - return; - }*/ - // check for out of ammo if ( ! pm->ps->ammo[ pm->ps->weapon ]) { PM_AddEvent( EV_NOAMMO ); @@ -2950,23 +2472,6 @@ static void PM_Weapon( void ) { //Elder: custom player model fire animations go here // start the animation even if out of ammo -- Elder: NO WAY if ( pm->ps->weapon == WP_KNIFE || pm->ps->weapon == WP_GRENADE ) { - // the gauntlet only "fires" when it actually hits something -// if ( !pm->gauntletHit ) { -// pm->ps->weaponTime = 0; -// pm->ps->weaponstate = WEAPON_READY; -// return; -// } - // Elder: animations initiated after stall complete - /* - if ( pm->ps->weapon == WP_GRENADE || - (pm->ps->persistant[PERS_WEAPONMODES] & RQ3_KNIFEMODE) ) - PM_ContinueWeaponAnim( WP_ANIM_FIRE ); - else - { - //PM_StartWeaponAnim( WP_ANIM_THROWFIRE ); - PM_ContinueWeaponAnim( WP_ANIM_THROWFIRE ); - } - */ if ( pm->ps->weapon == WP_KNIFE && (pm->ps->persistant[PERS_WEAPONMODES] & RQ3_KNIFEMODE) ) // Modified by agt for slash "bursting" @@ -2995,13 +2500,6 @@ static void PM_Weapon( void ) { } } else { - /* if (pm->ps->weapon == WP_PISTOL || - pm->ps->weapon == WP_M3 || - pm->ps->weapon == WP_HANDCANNON || - pm->ps->weapon == WP_SSG3000 || - pm->ps->weapon == WP_M4 || - pm->ps->weapon == WP_MP5 || - pm->ps->weapon == WP_GRENADE) */ if ( pm->ps->ammo[pm->ps->weapon] > 1 ) PM_StartWeaponAnim( WP_ANIM_FIRE ); else if ( pm->ps->weapon == WP_PISTOL ) @@ -3039,13 +2537,6 @@ static void PM_Weapon( void ) { pm->ps->delta_angles[0] = ANGLE2SHORT(SHORT2ANGLE(pm->ps->delta_angles[0]) - 0.7); } - //if ( ! pm->ps->ammo[ pm->ps->weapon ] || - //pm->ps->weapon == WP_AKIMBO && pm->ps->ammo[ pm->ps->weapon ] == 1) { - //PM_AddEvent( EV_NOAMMO ); - //pm->ps->weaponTime += 500; - //return; - //} - // take an ammo away if not infinite if ( pm->ps->ammo[ pm->ps->weapon ] != -1 ) { @@ -3160,29 +2651,8 @@ static void PM_Weapon( void ) { case WP_GRENADE: addTime = RQ3_GRENADE_DELAY; break; -#ifdef MISSIONPACK - case WP_NAILGUN: - addTime = 1000; - break; - case WP_PROX_LAUNCHER: - addTime = 800; - break; - case WP_CHAINGUN: - addTime = 30; - break; -#endif } -#ifdef MISSIONPACK - if( bg_itemlist[pm->ps->stats[STAT_PERSISTANT_POWERUP]].giTag == PW_SCOUT ) { - addTime /= 1.5; - } - else - if( bg_itemlist[pm->ps->stats[STAT_PERSISTANT_POWERUP]].giTag == PW_AMMOREGEN ) { - addTime /= 1.3; - } - else -#endif if ( pm->ps->powerups[PW_HASTE] ) { addTime /= 1.3; } @@ -3210,38 +2680,6 @@ static void PM_Animate( void ) { pm->ps->torsoTimer = TIMER_GESTURE; PM_AddEvent( EV_TAUNT ); } -#ifdef MISSIONPACK - } else if ( pm->cmd.buttons & BUTTON_GETFLAG ) { - if ( pm->ps->torsoTimer == 0 ) { - PM_StartTorsoAnim( TORSO_GETFLAG ); - pm->ps->torsoTimer = 600; //TIMER_GESTURE; - } - } else if ( pm->cmd.buttons & BUTTON_GUARDBASE ) { - if ( pm->ps->torsoTimer == 0 ) { - PM_StartTorsoAnim( TORSO_GUARDBASE ); - pm->ps->torsoTimer = 600; //TIMER_GESTURE; - } - } else if ( pm->cmd.buttons & BUTTON_PATROL ) { - if ( pm->ps->torsoTimer == 0 ) { - PM_StartTorsoAnim( TORSO_PATROL ); - pm->ps->torsoTimer = 600; //TIMER_GESTURE; - } - } else if ( pm->cmd.buttons & BUTTON_FOLLOWME ) { - if ( pm->ps->torsoTimer == 0 ) { - PM_StartTorsoAnim( TORSO_FOLLOWME ); - pm->ps->torsoTimer = 600; //TIMER_GESTURE; - } - } else if ( pm->cmd.buttons & BUTTON_AFFIRMATIVE ) { - if ( pm->ps->torsoTimer == 0 ) { - PM_StartTorsoAnim( TORSO_AFFIRMATIVE); - pm->ps->torsoTimer = 600; //TIMER_GESTURE; - } - } else if ( pm->cmd.buttons & BUTTON_NEGATIVE ) { - if ( pm->ps->torsoTimer == 0 ) { - PM_StartTorsoAnim( TORSO_NEGATIVE ); - pm->ps->torsoTimer = 600; //TIMER_GESTURE; - } -#endif } } @@ -3645,11 +3083,7 @@ void PmoveSingle (pmove_t *pmove) { PM_InvulnerabilityMove(); } else #endif - // Blaze: Double Jump - if (pm->ps->stats[STAT_JUMPTIME] > 0) - pm->ps->stats[STAT_JUMPTIME] -= pml.msec; - // Blaze - + if ( pm->ps->powerups[PW_FLIGHT] ) { // flight powerup doesn't allow jump and has different friction PM_FlyMove(); @@ -3681,7 +3115,6 @@ void PmoveSingle (pmove_t *pmove) { PM_AirMove(); } - PM_Animate(); // set groundentity, watertype, and waterlevel @@ -3692,20 +3125,6 @@ void PmoveSingle (pmove_t *pmove) { PM_Reload(); PM_Weapon(); - //weapon animations(rq3 specific) - //Elder: temp hack to avoid messing up fast-reloads - /* - if (pm->ps->weapon == WP_PISTOL || - pm->ps->weapon == WP_M3 || - pm->ps->weapon == WP_HANDCANNON || - pm->ps->weapon == WP_SSG3000 || - pm->ps->weapon == WP_M4 || - pm->ps->weapon == WP_AKIMBO || - pm->ps->weapon == WP_GRENADE || - pm->ps->weapon == WP_KNIFE) - PM_WeaponAnimation(); - */ - // torso animation PM_TorsoAnimation(); diff --git a/reaction/game/bg_slidemove.c b/reaction/game/bg_slidemove.c index 7f4d4375..62bb6381 100644 --- a/reaction/game/bg_slidemove.c +++ b/reaction/game/bg_slidemove.c @@ -5,6 +5,9 @@ //----------------------------------------------------------------------------- // // $Log$ +// Revision 1.12 2002/04/26 05:29:23 niceass +// PHYSICS, Take 2 +// // Revision 1.11 2002/03/31 03:31:24 jbravo // Compiler warning cleanups // @@ -29,6 +32,7 @@ // // bg_slidemove.c -- part of bg_pmove functionality + #include "q_shared.h" #include "bg_public.h" #include "bg_local.h" @@ -41,42 +45,78 @@ output: origin, velocity, impacts, stairup boolean */ -#define MIN_STEP_NORMAL 0.7 // can't step up onto very steep slopes -#define MAX_CLIP_PLANES 5 +/* +================== +PM_SlideMove -void PM_StepSlideMove_ ( void ) { +Returns qtrue if the velocity was clipped in some way +================== +*/ +#define MAX_CLIP_PLANES 5 +qboolean PM_SlideMove( qboolean gravity ) { int bumpcount, numbumps; vec3_t dir; float d; int numplanes; vec3_t planes[MAX_CLIP_PLANES]; vec3_t primal_velocity; - int i, j; - trace_t trace; + vec3_t clipVelocity; + int i, j, k; + trace_t trace; vec3_t end; float time_left; - - numbumps = 4; - numplanes = 0; - time_left = pml.frametime; + float into; + vec3_t endVelocity; + vec3_t endClipVelocity; - VectorCopy(pm->ps->velocity, primal_velocity); + numbumps = 4; - for (bumpcount=0 ; bumpcountps->origin, time_left, pm->ps->velocity, end); + VectorCopy (pm->ps->velocity, primal_velocity); - pm->trace (&trace, pm->ps->origin, pm->mins, pm->maxs, end, pm->ps->clientNum, pm->tracemask); + if ( gravity ) { + VectorCopy( pm->ps->velocity, endVelocity ); + endVelocity[2] -= pm->ps->gravity * pml.frametime; + pm->ps->velocity[2] = ( pm->ps->velocity[2] + endVelocity[2] ) * 0.5; + primal_velocity[2] = endVelocity[2]; +/* if ( pml.groundPlane ) { + // slide along the ground plane + PM_ClipVelocity (pm->ps->velocity, pml.groundTrace.plane.normal, + pm->ps->velocity, OVERCLIP ); + } +*/ + } + + time_left = pml.frametime; + + // never turn against the ground plane + if ( pml.groundPlane ) { + numplanes = 1; + VectorCopy( pml.groundTrace.plane.normal, planes[0] ); + } else { + numplanes = 0; + } + + // never turn against original velocity + VectorNormalize2( pm->ps->velocity, planes[numplanes] ); + numplanes++; + + for ( bumpcount=0 ; bumpcount < numbumps ; bumpcount++ ) { + + // calculate position we are trying to move to + VectorMA( pm->ps->origin, time_left, pm->ps->velocity, end ); + + // see if we can make it there + pm->trace ( &trace, pm->ps->origin, pm->mins, pm->maxs, end, pm->ps->clientNum, pm->tracemask); if (trace.allsolid) { // entity is completely trapped in another solid pm->ps->velocity[2] = 0; // don't build up falling damage, but allow sideways acceleration - return; // qtrue; + return qtrue; } if (trace.fraction > 0) { // actually covered some distance VectorCopy (trace.endpos, pm->ps->origin); - numplanes = 0; } if (trace.fraction == 1) { @@ -91,44 +131,109 @@ void PM_StepSlideMove_ ( void ) { if (numplanes >= MAX_CLIP_PLANES) { // this shouldn't really happen VectorClear( pm->ps->velocity ); - break; + return qtrue; } - VectorCopy (trace.plane.normal, planes[numplanes]); - numplanes++; - - for (i=0 ; i < numplanes ; i++) - { - PM_ClipVelocity(pm->ps->velocity, planes[i], pm->ps->velocity, OVERCLIP); //1.01); - for (j = 0; j < numplanes; j++) - if (DotProduct (pm->ps->velocity, planes[j]) < 0 && j != i) break; - - // Get through all planes okay? Then stop clipping the velocity. - if (j == numplanes) break; - } - - // Clipped velocity against all planes - if (i == numplanes) { - if (numplanes != 2) { - VectorClear(pm->ps->velocity); + // + // if this is the same plane we hit before, nudge velocity + // out along it, which fixes some epsilon issues with + // non-axial planes + // + for ( i = 0 ; i < numplanes ; i++ ) { + if ( DotProduct( trace.plane.normal, planes[i] ) > 0.99 ) { + VectorAdd( trace.plane.normal, pm->ps->velocity, pm->ps->velocity ); break; } - else { - CrossProduct (planes[0], planes[1], dir); - d = DotProduct (dir, pm->ps->velocity); - VectorScale (dir, d, pm->ps->velocity); - } } + if ( i < numplanes ) { + continue; + } + VectorCopy (trace.plane.normal, planes[numplanes]); + numplanes++; - if (DotProduct (pm->ps->velocity, primal_velocity) <= 0) { - VectorClear(pm->ps->velocity); + // + // modify velocity so it parallels all of the clip planes + // + + // find a plane that it enters + for ( i = 0 ; i < numplanes ; i++ ) { + into = DotProduct( pm->ps->velocity, planes[i] ); + if ( into >= 0.1 ) { + continue; // move doesn't interact with the plane + } + + // see how hard we are hitting things + if ( -into > pml.impactSpeed ) { + pml.impactSpeed = -into; + } + + // slide along the plane + PM_ClipVelocity (pm->ps->velocity, planes[i], clipVelocity, OVERCLIP ); + + // slide along the plane + PM_ClipVelocity (endVelocity, planes[i], endClipVelocity, OVERCLIP ); + + // see if there is a second plane that the new move enters + for ( j = 0 ; j < numplanes ; j++ ) { + if ( j == i ) { + continue; + } + if ( DotProduct( clipVelocity, planes[j] ) >= 0.1 ) { + continue; // move doesn't interact with the plane + } + + // try clipping the move to the plane + PM_ClipVelocity( clipVelocity, planes[j], clipVelocity, OVERCLIP ); + PM_ClipVelocity( endClipVelocity, planes[j], endClipVelocity, OVERCLIP ); + + // see if it goes back into the first clip plane + if ( DotProduct( clipVelocity, planes[i] ) >= 0 ) { + continue; + } + + // slide the original velocity along the crease + CrossProduct (planes[i], planes[j], dir); + VectorNormalize( dir ); + d = DotProduct( dir, pm->ps->velocity ); + VectorScale( dir, d, clipVelocity ); + + CrossProduct (planes[i], planes[j], dir); + VectorNormalize( dir ); + d = DotProduct( dir, endVelocity ); + VectorScale( dir, d, endClipVelocity ); + + // see if there is a third plane the the new move enters + for ( k = 0 ; k < numplanes ; k++ ) { + if ( k == i || k == j ) { + continue; + } + if ( DotProduct( clipVelocity, planes[k] ) >= 0.1 ) { + continue; // move doesn't interact with the plane + } + + // stop dead at a tripple plane interaction + VectorClear( pm->ps->velocity ); + return qtrue; + } + } + + // if we have fixed all interactions, try another move + VectorCopy( clipVelocity, pm->ps->velocity ); + VectorCopy( endClipVelocity, endVelocity ); break; } } - if (pm->ps->pm_time) { - VectorCopy (primal_velocity, pm->ps->velocity); + if ( gravity ) { + VectorCopy( endVelocity, pm->ps->velocity ); } + + // don't change velocity if in a timer (FIXME: is this correct?) + if ( pm->ps->pm_time ) { + VectorCopy( primal_velocity, pm->ps->velocity ); + } + + return ( bumpcount != 0 ); } /* @@ -137,26 +242,32 @@ PM_StepSlideMove ================== */ - -void PM_StepSlideMove ( qboolean gravity ) -{ +void PM_StepSlideMove( qboolean gravity ) { vec3_t start_o, start_v; vec3_t down_o, down_v; trace_t trace; - float DistanceDown, DistanceUp; vec3_t up, down; - - // use the step move -/* vec3_t old_normal; - float delta0; - float delta1; - float delta2; */ - vec3_t tmp_o; + vec3_t tmp; VectorCopy (pm->ps->origin, start_o); VectorCopy (pm->ps->velocity, start_v); - PM_StepSlideMove_ (); + if ( PM_SlideMove( gravity ) == 0 ) { + return; // we got exactly where we wanted to go first try + } + + /* + VectorCopy(start_o, down); + down[2] -= STEPSIZE; + pm->trace (&trace, start_o, pm->mins, pm->maxs, down, pm->ps->clientNum, pm->tracemask); + VectorSet(up, 0, 0, 1); + + // never step up when you still have up velocity + if ( pm->ps->velocity[2] > 0 && (trace.fraction == 1.0 || + DotProduct(trace.plane.normal, up) < 0.7)) { + return; + } + */ VectorCopy (pm->ps->origin, down_o); VectorCopy (pm->ps->velocity, down_v); @@ -164,60 +275,44 @@ void PM_StepSlideMove ( qboolean gravity ) VectorCopy (start_o, up); up[2] += STEPSIZE; + // test the player position if they were a stepheight higher pm->trace (&trace, up, pm->mins, pm->maxs, up, pm->ps->clientNum, pm->tracemask); - if (trace.allsolid) { - return; // can't step up - } + if ( trace.allsolid ) return; // can't step up - // try sliding above + // try slidemove from this position VectorCopy (up, pm->ps->origin); VectorCopy (start_v, pm->ps->velocity); - PM_StepSlideMove_ (); + PM_SlideMove( gravity ); // push down the final amount VectorCopy (pm->ps->origin, down); down[2] -= STEPSIZE; pm->trace (&trace, pm->ps->origin, pm->mins, pm->maxs, down, pm->ps->clientNum, pm->tracemask); - if (!trace.allsolid) - { + if ( !trace.allsolid ) { VectorCopy (trace.endpos, pm->ps->origin); } - - VectorCopy(pm->ps->origin, up); - - VectorSubtract(down_o, start_o, tmp_o); - DistanceDown = tmp_o[0]*tmp_o[0] + tmp_o[1]*tmp_o[1]; - VectorSubtract(up, start_o, tmp_o); - DistanceUp = tmp_o[0]*tmp_o[0] + tmp_o[1]*tmp_o[1]; - - //Com_Printf("%f ", trace.plane.normal[2]); - if (DistanceDown > DistanceUp || trace.plane.normal[2] < MIN_STEP_NORMAL) { + + if ( trace.plane.normal[2] < 0.7f) { VectorCopy (down_o, pm->ps->origin); - VectorCopy (down_v, pm->ps->velocity); + PM_ClipVelocity( pm->ps->velocity, trace.plane.normal, pm->ps->velocity, OVERCLIP ); return; } - // Flat/walking up: - else { - //!! Special case - // if we were walking along a plane, then we need to copy the Z over - pm->ps->velocity[2] = down_v[2]; - } - - // NiceAss Move the origin up a little... Seems hackish but needed. - VectorCopy(pm->ps->origin, tmp_o); - tmp_o[2] += 0.01f; - start_o[2] += 0.01f; - // if the trace can trace back to the original position directly, don't step - pm->trace ( &trace, tmp_o, pm->mins, pm->maxs, start_o, pm->ps->clientNum, pm->tracemask); - // If it didn't make it all the way.. + pm->ps->velocity[2] = down_v[2]; + VectorCopy(pm->ps->origin, tmp); + // NiceAss: nudge it up a little. + tmp[2] += 0.1f; + start_o[2] += 0.1f; + + // if the down trace can trace back to the original position directly, don't step + pm->trace( &trace, tmp, pm->mins, pm->maxs, start_o, pm->ps->clientNum, pm->tracemask); if ( trace.fraction != 1.0 ) { // use the step move float delta; - delta = tmp_o[2] - start_o[2]; + delta = pm->ps->origin[2] - start_o[2]; if ( delta > 2 ) { if ( delta < 7 ) { PM_AddEvent( EV_STEP_4 ); @@ -230,7 +325,7 @@ void PM_StepSlideMove ( qboolean gravity ) } } if ( pm->debugLevel ) { - Com_Printf("%d:stepped\n", c_pmove); + Com_Printf("%i:stepped\n", c_pmove); } } }