76 lines
1.7 KiB
C#
76 lines
1.7 KiB
C#
|
|
|
|
using Sandbox;
|
|
using Sandbox.Audio;
|
|
using System;
|
|
|
|
namespace VeloX;
|
|
|
|
|
|
public partial class VeloXCar
|
|
{
|
|
public const float MIN_DRIFT_ANGLE = 10f;
|
|
public const float MIN_DRIFT_SPEED = 10f;
|
|
public const float MAX_DRIFT_ANGLE = 110f;
|
|
|
|
public static readonly SoundFile SkidSound = SoundFile.Load( "sounds/tire/skid.wav" );
|
|
|
|
private SoundHandle _skidHandle;
|
|
private float targetPitch;
|
|
private float targetVolume;
|
|
public float GetDriftAngle()
|
|
{
|
|
if ( !IsOnGround )
|
|
return 0;
|
|
|
|
var velocity = Body.Velocity;
|
|
var forward = WorldRotation.Forward;
|
|
|
|
// Early exit if speed is too low
|
|
if ( TotalSpeed < MIN_DRIFT_SPEED )
|
|
return 0f;
|
|
|
|
// Normalize the dot product calculation
|
|
float dotProduct = velocity.Normal.Dot( forward );
|
|
// Handle potential floating point precision issues
|
|
float cosAngle = dotProduct;
|
|
cosAngle = MathX.Clamp( cosAngle, -1f, 1f );
|
|
|
|
// Calculate angle in degrees
|
|
float angle = MathF.Abs( MathX.RadianToDegree( MathF.Acos( cosAngle ) ) );
|
|
|
|
|
|
// Check if angle is within drift range
|
|
if ( angle >= MIN_DRIFT_ANGLE && angle <= MAX_DRIFT_ANGLE )
|
|
return angle;
|
|
|
|
return 0f;
|
|
}
|
|
|
|
protected virtual void UpdateDrift( float dt )
|
|
{
|
|
|
|
var avgslip = 0f;
|
|
foreach ( var item in Wheels )
|
|
avgslip += item.NormalizedLongitudinalSlip + item.NormalizedLateralSlip;
|
|
|
|
float mul = Math.Clamp( avgslip, 0, 2 );
|
|
|
|
targetVolume = mul;
|
|
targetPitch = 0.75f + 0.25f * mul;
|
|
|
|
if ( mul > 0.1f && !_skidHandle.IsValid() )
|
|
{
|
|
_skidHandle = Sound.PlayFile( SkidSound );
|
|
_skidHandle.TargetMixer = Mixer.Default;
|
|
}
|
|
|
|
if ( !_skidHandle.IsValid() )
|
|
return;
|
|
|
|
_skidHandle.Pitch += (targetPitch - _skidHandle.Pitch) * dt * 5f;
|
|
_skidHandle.Volume += (targetVolume - _skidHandle.Volume) * dt * 10f;
|
|
_skidHandle.Position = WorldPosition;
|
|
}
|
|
}
|