109 lines
2.9 KiB
C#
109 lines
2.9 KiB
C#
using Sandbox;
|
|
using System;
|
|
using System.Collections.Generic;
|
|
using System.Threading;
|
|
|
|
namespace VeloX;
|
|
|
|
|
|
public partial class VeloXWheel
|
|
{
|
|
private static readonly GameObject SmokePrefab = GameObject.GetPrefab( "prefabs/particles/tire_smoke.prefab" );
|
|
|
|
private GameObject SmokeObject { get; set; }
|
|
public const float MIN_DRIFT_ANGLE = 10f;
|
|
public const float MIN_DRIFT_SPEED = 30f;
|
|
public const float MAX_DRIFT_ANGLE = 110f;
|
|
private float smokeMul;
|
|
private float timeMul;
|
|
protected override void OnStart()
|
|
{
|
|
base.OnStart();
|
|
if ( IsProxy )
|
|
return;
|
|
|
|
if ( !SmokeObject.IsValid() )
|
|
SmokeObject = GameObject.GetPrefab( "prefabs/particles/tire_smoke.prefab" ).Clone( new CloneConfig() { Parent = GameObject, StartEnabled = true } );
|
|
}
|
|
public float GetSlip()
|
|
{
|
|
if ( !IsOnGround )
|
|
return 0;
|
|
var val = Math.Abs( LateralSlip ) + Math.Abs( LongitudinalSlip );
|
|
timeMul = timeMul.LerpTo( val, 0.1f );
|
|
|
|
//if ( timeMul > 2 )
|
|
// return val;
|
|
return val * 5;
|
|
}
|
|
protected override void OnUpdate()
|
|
{
|
|
base.OnUpdate();
|
|
if ( IsProxy )
|
|
return;
|
|
UpdateSkid();
|
|
SmokeObject.WorldPosition = ContactPosition + Vehicle.WorldRotation.Down * Radius.MeterToInch();
|
|
smokeMul = Math.Max( 0, GetSlip() - 3 );
|
|
|
|
bool density = false;
|
|
|
|
if ( smokeMul > 0 )
|
|
density = true;
|
|
var emitter = SmokeObject.Components.Get<ParticleSphereEmitter>( FindMode.EverythingInSelfAndDescendants );
|
|
emitter.Enabled = density;
|
|
emitter.Radius = 0f;
|
|
emitter.Velocity = 0;
|
|
emitter.Duration = 5;
|
|
emitter.Burst = 5;
|
|
float sizeMul = 0.7f + smokeMul * 0.3f;
|
|
emitter.Rate = smokeMul * 100f;
|
|
emitter.RateOverDistance = smokeMul * 10f;
|
|
|
|
var effect = SmokeObject.Components.Get<ParticleEffect>( FindMode.EverythingInSelfAndDescendants );
|
|
|
|
effect.MaxParticles = 500;
|
|
effect.Damping = 0.9f;
|
|
effect.ApplyRotation = true;
|
|
effect.ApplyShape = true;
|
|
|
|
effect.Roll = new()
|
|
{
|
|
Type = ParticleFloat.ValueType.Range,
|
|
Evaluation = ParticleFloat.EvaluationType.Seed,
|
|
ConstantA = 0,
|
|
ConstantB = 360,
|
|
};
|
|
effect.Scale = new()
|
|
{
|
|
Type = ParticleFloat.ValueType.Curve,
|
|
Evaluation = ParticleFloat.EvaluationType.Life,
|
|
CurveA = new( new List<Curve.Frame>() { new( 0, 10f ), new( 0.8f, 50f ), new( 1f, 160f ) } ),
|
|
};
|
|
effect.StartDelay = 0.025f + (1 - smokeMul) * 0.03f;
|
|
|
|
effect.ApplyColor = true;
|
|
effect.Gradient = new()
|
|
{
|
|
Type = ParticleGradient.ValueType.Range,
|
|
Evaluation = ParticleGradient.EvaluationType.Particle,
|
|
ConstantA = Color.White,
|
|
ConstantB = Color.Transparent,
|
|
};
|
|
effect.StartVelocity = new()
|
|
{
|
|
Type = ParticleFloat.ValueType.Range,
|
|
Evaluation = ParticleFloat.EvaluationType.Seed,
|
|
ConstantA = 10,
|
|
ConstantB = 70,
|
|
};
|
|
effect.Force = true;
|
|
effect.InitialVelocity = Vehicle.Body.Velocity / 3 + hitForwardDirection * LongitudinalSlip * 10f;
|
|
effect.ForceDirection = 0;
|
|
effect.SheetSequence = true;
|
|
effect.SequenceSpeed = 0.5f;
|
|
effect.SequenceTime = 1f;
|
|
|
|
|
|
}
|
|
}
|