Files
wnsrc/lua/entities/gmod_sent_vehicle_fphysics_base/cl_init.lua
lifestorm 6a58f406b1 Upload
2024-08-04 23:54:45 +03:00

678 lines
20 KiB
Lua

--[[
| This file was obtained through the combined efforts
| of Madbluntz & Plymouth Antiquarian Society.
|
| Credits: lifestorm, Gregory Wayne Rossel JR.,
| Maloy, DrPepper10 @ RIP, Atle!
|
| Visit for more: https://plymouth.thetwilightzone.ru/
--]]
include("shared.lua")
include("cl_tiresounds.lua")
function ENT:LVSHudPaint( X, Y, ply )
local Pos2D = {
visible = true,
x = ScrW() * 0.5,
y = ScrH() * 0.5,
}
self:LVSPaintHitMarker( Pos2D )
end
function ENT:GetViewOverride()
return self.customview or vector_origin
end
function ENT:LVSCalcView( ply, pos, angles, fov, pod )
if pod:GetNWBool( "simfphys_SpecialCam" ) then return end
local IsDriverSeat = ply == self:GetDriver()
if IsDriverSeat and ply:lvsMouseAim() then
angles = ply:EyeAngles()
end
self.ZoomFov = fov
local view_origin = pos
if not pod:GetThirdPersonMode() then
local viewoverride = self:GetViewOverride()
local X = viewoverride.X
local Y = viewoverride.Y
local Z = viewoverride.Z
view_origin = view_origin + (IsDriverSeat and pod:GetForward() * X + pod:GetRight() * Y + pod:GetUp() * Z or pod:GetUp() * 5)
end
if not IsDriverSeat then return LVS:CalcView( self, ply, view_origin, angles, fov, pod ) end
return LVS:CalcView( self, ply, view_origin, angles, fov, pod )
end
function ENT:Initialize()
self.SmoothRPM = 0
self.OldDist = 0
self.PitchOffset = 0
self.OldActive = false
self.OldGear = 0
self.OldThrottle = 0
self.FadeThrottle = 0
self.SoundMode = 0
self.DamageSnd = CreateSound(self, "simulated_vehicles/engine_damaged.wav")
self.EngineSounds = {}
end
function ENT:Think()
local T = CurTime()
local Active = self:GetActive()
local Throttle = self:GetThrottle()
local LimitRPM = self:GetLimitRPM()
self:ManageSounds( Active, Throttle, LimitRPM )
self.RunNext = self.RunNext or 0
if self.RunNext < T then
self:ManageEffects( Active, Throttle, LimitRPM )
self:CalcFlasher()
self.RunNext = T + 0.06
end
self:SetPoseParameters( T )
self:TireSoundThink()
end
function ENT:CalcFlasher()
self.Flasher = self.Flasher or 0
local flashspeed = self.turnsignals_damaged and 0.06 or 0.0375
self.Flasher = self.Flasher and self.Flasher + flashspeed or 0
if self.Flasher >= 1 then
self.Flasher = self.Flasher - 1
end
self.flashnum = math.min( math.abs( math.cos( math.rad( self.Flasher * 360 ) ) ^ 2 * 1.5 ) , 1)
if not self.signal_left and not self.signal_right then return end
if LocalPlayer() == self:GetDriver() then
local fl_snd = self.flashnum > 0.9
if fl_snd ~= self.fl_snd then
self.fl_snd = fl_snd
if fl_snd then
self:EmitSound( "simulated_vehicles/sfx/flasher_on.ogg" )
else
self:EmitSound( "simulated_vehicles/sfx/flasher_off.ogg" )
end
end
end
end
function ENT:GetFlasher()
self.flashnum = self.flashnum or 0
return self.flashnum
end
function ENT:SetPoseParameters( curtime )
self.sm_vSteer = self.sm_vSteer and self.sm_vSteer + (self:GetVehicleSteer() - self.sm_vSteer) * 0.3 or 0
self:SetPoseParameter("vehicle_steer", self.sm_vSteer )
if not istable( self.pp_data ) then
self.ppNextCheck = self.ppNextCheck or curtime + 0.5
if self.ppNextCheck < curtime then
self.ppNextCheck = curtime + 0.5
net.Start("simfphys_request_ppdata",true)
net.WriteEntity( self )
net.SendToServer()
end
else
if not self.CustomWheels then
for i = 1, table.Count( self.pp_data ) do
local Wheel = self.pp_data[i].entity
if IsValid( Wheel ) then
local addPos = Wheel:GetDamaged() and self.pp_data[i].dradius or 0
local Pose = (self.pp_data[i].pos - self:WorldToLocal( Wheel:GetPos()).z + addPos ) / self.pp_data[i].travel
self:SetPoseParameter( self.pp_data[i].name, Pose )
end
end
end
end
self:InvalidateBoneCache()
end
function ENT:GetEnginePos()
if isvector( self.EnginePos ) then return self:LocalToWorld( self.EnginePos ) end
local Attachment = self:GetAttachment( self:LookupAttachment( "vehicle_engine" ) )
if Attachment then return Attachment.Pos end
return self:GetPos()
end
function ENT:GetRPM()
local RPM = self.SmoothRPM and self.SmoothRPM or 0
return RPM
end
function ENT:DamageEffects()
local Pos = self:GetEnginePos()
local Scale = self:GetCurHealth() / self:GetMaxHealth()
local smoke = self:OnSmoke() and Scale <= 0.5
local fire = self:OnFire()
if self.wasSmoke ~= smoke then
self.wasSmoke = smoke
if smoke then
self.smokesnd = CreateSound(self, "ambient/gas/steam2.wav")
self.smokesnd:PlayEx(0.2,90)
else
if self.smokesnd then
self.smokesnd:Stop()
end
end
end
if self.wasFire ~= fire then
self.wasFire = fire
if fire then
self:EmitSound( "ambient/fire/mtov_flame2.wav" )
self.firesnd = CreateSound(self, "ambient/fire/fire_small1.wav")
self.firesnd:Play()
else
if self.firesnd then
self.firesnd:Stop()
end
end
end
if smoke then
if Scale <= 0.5 then
local HP = self:GetCurHealth()
local MaxHP = self:GetMaxHealth()
local effectdata = EffectData()
effectdata:SetOrigin( Pos )
effectdata:SetEntity( self )
effectdata:SetMagnitude( math.max(HP - MaxHP * 0.25,0) / (MaxHP * 0.25) )
util.Effect( "simfphys_engine_smoke", effectdata )
end
end
if fire then
local effectdata = EffectData()
effectdata:SetOrigin( Pos )
effectdata:SetEntity( self )
util.Effect( "simfphys_engine_fire", effectdata )
end
end
function ENT:ManageEffects( Active, fThrottle, LimitRPM )
self:DamageEffects()
Active = Active and (self:GetFlyWheelRPM() ~= 0)
if not Active then return end
if not self.ExhaustPositions then return end
local Scale = fThrottle * (0.2 + math.min(self:GetRPM() / LimitRPM,1) * 0.8) ^ 2
for i = 1, table.Count( self.ExhaustPositions ) do
if self.ExhaustPositions[i].OnBodyGroups then
if self:BodyGroupIsValid( self.ExhaustPositions[i].OnBodyGroups ) then
local effectdata = EffectData()
effectdata:SetOrigin( self.ExhaustPositions[i].pos )
effectdata:SetAngles( self.ExhaustPositions[i].ang )
effectdata:SetMagnitude( Scale )
effectdata:SetEntity( self )
util.Effect( "simfphys_exhaust", effectdata )
end
else
local effectdata = EffectData()
effectdata:SetOrigin( self.ExhaustPositions[i].pos )
effectdata:SetAngles( self.ExhaustPositions[i].ang )
effectdata:SetMagnitude( Scale )
effectdata:SetEntity( self )
util.Effect( "simfphys_exhaust", effectdata )
end
end
end
function ENT:ManageSounds( Active, fThrottle, LimitRPM )
local EngineVolume = LVS.EngineVolume
local FlyWheelRPM = self:GetFlyWheelRPM()
local Active = Active and (FlyWheelRPM ~= 0)
local IdleRPM = self:GetIdleRPM()
local IsCruise = self:GetIsCruiseModeOn()
local CurDist = (LocalPlayer():GetPos() - self:GetPos()):Length()
local Throttle = IsCruise and math.Clamp(self:GetThrottle() ^ 3,0.01,0.7) or fThrottle
local Gear = self:GetGear()
local Clutch = self:GetClutch()
local FadeRPM = LimitRPM * 0.5
local FT = FrameTime()
local Rate = 3.33 * FT
self.FadeThrottle = self.FadeThrottle + math.Clamp(Throttle - self.FadeThrottle,-Rate,Rate)
self.PitchOffset = self.PitchOffset + ((CurDist - self.OldDist) * 0.23 - self.PitchOffset) * 0.5
self.OldDist = CurDist
self.SmoothRPM = self.SmoothRPM + math.Clamp(FlyWheelRPM - self.SmoothRPM,-0.972 * FT * LimitRPM,1.66 * FT * LimitRPM)
self.OldThrottle2 = self.OldThrottle2 or 0
if Throttle ~= self.OldThrottle2 then
self.OldThrottle2 = Throttle
if Throttle == 0 then
if self.SmoothRPM > LimitRPM * 0.6 then
self:Backfire()
end
end
end
if self:GetRevlimiter() and LimitRPM > 2500 then
if (self.SmoothRPM >= LimitRPM - 200) and self.FadeThrottle > 0 then
self.SmoothRPM = self.SmoothRPM - 0.2 * LimitRPM
self.FadeThrottle = 0.2
self:Backfire()
end
end
if Active ~= self.OldActive then
local preset = self:GetEngineSoundPreset()
local UseGearResetter = self:SetSoundPreset( preset )
self.SoundMode = UseGearResetter and 2 or 1
self.OldActive = Active
if Active then
local MaxHealth = self:GetMaxHealth()
local Health = self:GetCurHealth()
if Health <= (MaxHealth * 0.6) then
self.DamageSnd:PlayEx(0,0)
end
if self.SoundMode == 2 then
self.HighRPM = CreateSound(self, self.EngineSounds[ "HighRPM" ] )
self.LowRPM = CreateSound(self, self.EngineSounds[ "LowRPM" ])
self.Idle = CreateSound(self, self.EngineSounds[ "Idle" ])
self.HighRPM:PlayEx(0,0)
self.LowRPM:PlayEx(0,0)
self.Idle:PlayEx(0,0)
else
local IdleSound = self.EngineSounds[ "IdleSound" ]
local LowSound = self.EngineSounds[ "LowSound" ]
local HighSound = self.EngineSounds[ "HighSound" ]
local ThrottleSound = self.EngineSounds[ "ThrottleSound" ]
if IdleSound then
self.Idle = CreateSound(self, IdleSound)
self.Idle:PlayEx(0,0)
end
if LowSound then
self.LowRPM = CreateSound(self, LowSound)
self.LowRPM:PlayEx(0,0)
end
if HighSound then
self.HighRPM = CreateSound(self, HighSound)
self.HighRPM:PlayEx(0,0)
end
if ThrottleSound then
self.Valves = CreateSound(self, ThrottleSound)
self.Valves:PlayEx(0,0)
end
end
else
self:SaveStopSounds()
end
end
if Active then
local Volume = 0.25 + 0.25 * ((self.SmoothRPM / LimitRPM) ^ 1.5) + self.FadeThrottle * 0.5
local Pitch = math.Clamp( (20 + self.SmoothRPM / 50 - self.PitchOffset) * self.PitchMulAll,0,255)
if self.DamageSnd then
self.DamageSnd:ChangeVolume( ((self.SmoothRPM / LimitRPM) * 0.6 ^ 1.5) * EngineVolume )
self.DamageSnd:ChangePitch( 100 )
end
if self.SoundMode == 2 then
if self.FadeThrottle ~= self.OldThrottle then
self.OldThrottle = self.FadeThrottle
if self.FadeThrottle == 0 and Clutch == 0 then
if self.SmoothRPM >= FadeRPM then
if IsCruise ~= true then
if self.LowRPM then
self.LowRPM:Stop()
end
self.LowRPM = CreateSound(self, self.EngineSounds[ "RevDown" ] )
self.LowRPM:PlayEx(0,0)
end
end
end
end
if Gear ~= self.OldGear then
if self.SmoothRPM >= FadeRPM and Gear > 3 then
if Clutch ~= 1 then
if self.OldGear < Gear then
if self.HighRPM then
self.HighRPM:Stop()
end
self.HighRPM = CreateSound(self, self.EngineSounds[ "ShiftUpToHigh" ] )
self.HighRPM:PlayEx(0,0)
if self.SmoothRPM > LimitRPM * 0.6 then
if math.random(0,4) >= 3 then
timer.Simple(0.4, function()
if not IsValid( self ) then return end
self:Backfire()
end)
end
end
else
if self.FadeThrottle > 0 then
if self.HighRPM then
self.HighRPM:Stop()
end
self.HighRPM = CreateSound(self, self.EngineSounds[ "ShiftDownToHigh" ] )
self.HighRPM:PlayEx(0,0)
end
end
end
else
if Clutch ~= 1 then
if self.OldGear > Gear and self.FadeThrottle > 0 and Gear >= 3 then
if self.HighRPM then
self.HighRPM:Stop()
end
self.HighRPM = CreateSound(self, self.EngineSounds[ "ShiftDownToHigh" ] )
self.HighRPM:PlayEx(0,0)
else
if self.HighRPM then
self.HighRPM:Stop()
end
if self.LowRPM then
self.LowRPM:Stop()
end
self.HighRPM = CreateSound(self, self.EngineSounds[ "HighRPM" ] )
self.LowRPM = CreateSound(self, self.EngineSounds[ "LowRPM" ])
self.HighRPM:PlayEx(0,0)
self.LowRPM:PlayEx(0,0)
end
end
end
self.OldGear = Gear
end
self.Idle:ChangeVolume( math.Clamp( math.min((self.SmoothRPM / IdleRPM) * 3,1.5 + self.FadeThrottle * 0.5) * 0.7 - self.SmoothRPM / 2000 ,0,1) * EngineVolume )
self.Idle:ChangePitch( math.Clamp( Pitch * 3,0,255) )
self.LowRPM:ChangeVolume( math.Clamp(Volume - (self.SmoothRPM - 2000) / 2000 * self.FadeThrottle,0,1) * EngineVolume )
self.LowRPM:ChangePitch( math.Clamp( Pitch * self.PitchMulLow,0,255) )
local hivol = math.max((self.SmoothRPM - 2000) / 2000,0) * Volume
self.HighRPM:ChangeVolume( (self.FadeThrottle < 0.4 and hivol * self.FadeThrottle or hivol * self.FadeThrottle * 2.5) * EngineVolume )
self.HighRPM:ChangePitch( math.Clamp( Pitch * self.PitchMulHigh,0,255) )
else
if Gear ~= self.OldGear then
if self.SmoothRPM >= FadeRPM and Gear > 3 then
if Clutch ~= 1 then
if self.OldGear < Gear then
if self.SmoothRPM > LimitRPM * 0.6 then
if math.random(0,4) >= 3 then
timer.Simple(0.4, function()
if not IsValid( self ) then return end
self:Backfire()
end)
end
end
end
end
end
self.OldGear = Gear
end
local IdlePitch = self.Idle_PitchMul
self.Idle:ChangeVolume( math.Clamp( math.min((self.SmoothRPM / IdleRPM) * 3,1.5 + self.FadeThrottle * 0.5) * 0.7 - self.SmoothRPM / 2000,0,1) * EngineVolume )
self.Idle:ChangePitch( math.Clamp( Pitch * 3 * IdlePitch,0,255) )
local LowPitch = self.Mid_PitchMul
local LowVolume = self.Mid_VolumeMul
local LowFadeOutRPM = LimitRPM * (self.Mid_FadeOutRPMpercent / 100)
local LowFadeOutRate = LimitRPM * self.Mid_FadeOutRate
self.LowRPM:ChangeVolume( math.Clamp( (Volume - math.Clamp((self.SmoothRPM - LowFadeOutRPM) / LowFadeOutRate,0,1)) * LowVolume,0,1) * EngineVolume )
self.LowRPM:ChangePitch( math.Clamp(Pitch * LowPitch,0,255) )
local HighPitch = self.High_PitchMul
local HighVolume = self.High_VolumeMul
local HighFadeInRPM = LimitRPM * (self.High_FadeInRPMpercent / 100)
local HighFadeInRate = LimitRPM * self.High_FadeInRate
self.HighRPM:ChangeVolume( math.Clamp( math.Clamp((self.SmoothRPM - HighFadeInRPM) / HighFadeInRate,0,Volume) * HighVolume,0,1) * EngineVolume)
self.HighRPM:ChangePitch( math.Clamp(Pitch * HighPitch,0,255) )
local ThrottlePitch = self.Throttle_PitchMul
local ThrottleVolume = self.Throttle_VolumeMul
self.Valves:ChangeVolume( math.Clamp((self.SmoothRPM - 2000) / 2000,0,Volume) * (0.2 + 0.15 * self.FadeThrottle) * ThrottleVolume * EngineVolume )
self.Valves:ChangePitch( math.Clamp(Pitch * ThrottlePitch,0,255) )
end
end
end
function ENT:Backfire( damaged )
if not self:GetBackFire() and not damaged then return end
if not self.ExhaustPositions then return end
local expos = self.ExhaustPositions
for i = 1, table.Count( expos ) do
if math.random(1,3) >= 2 or damaged then
local Pos = expos[i].pos
local Ang = expos[i].ang - Angle(90,0,0)
if expos[i].OnBodyGroups then
if self:BodyGroupIsValid( expos[i].OnBodyGroups ) then
local effectdata = EffectData()
effectdata:SetOrigin( Pos )
effectdata:SetAngles( Ang )
effectdata:SetEntity( self )
effectdata:SetFlags( damaged and 1 or 0 )
util.Effect( "simfphys_backfire", effectdata )
end
else
local effectdata = EffectData()
effectdata:SetOrigin( Pos )
effectdata:SetAngles( Ang )
effectdata:SetEntity( self )
effectdata:SetFlags( damaged and 1 or 0 )
util.Effect( "simfphys_backfire", effectdata )
end
end
end
end
function ENT:SetSoundPreset(index)
if index == -1 then
local soundoverride = self:GetSoundoverride()
local data = string.Explode( ",", soundoverride)
if soundoverride ~= "" and data[1] == "1" then
self.EngineSounds[ "Idle" ] = data[4]
self.EngineSounds[ "LowRPM" ] = data[6]
self.EngineSounds[ "HighRPM" ] = data[2]
self.EngineSounds[ "RevDown" ] = data[8]
self.EngineSounds[ "ShiftUpToHigh" ] = data[10]
self.EngineSounds[ "ShiftDownToHigh" ] = data[9]
self.PitchMulLow = data[7]
self.PitchMulHigh = data[3]
self.PitchMulAll = data[5]
else
local idle = self.snd_idle or ""
local low = self.snd_low or ""
local mid = self.snd_mid or ""
local revdown = self.snd_low_revdown or ""
local gearup = self.snd_mid_gearup or ""
local geardown = self.snd_mid_geardown or ""
self.EngineSounds[ "Idle" ] = idle ~= "" and idle or false
self.EngineSounds[ "LowRPM" ] = low ~= "" and low or false
self.EngineSounds[ "HighRPM" ] = mid ~= "" and mid or false
self.EngineSounds[ "RevDown" ] = revdown ~= "" and revdown or low
self.EngineSounds[ "ShiftUpToHigh" ] = gearup ~= "" and gearup or mid
self.EngineSounds[ "ShiftDownToHigh" ] = geardown ~= "" and geardown or gearup
self.PitchMulLow = self.snd_low_pitch or 1
self.PitchMulHigh = self.snd_mid_pitch or 1
self.PitchMulAll = self.snd_pitch or 1
end
if self.EngineSounds[ "Idle" ] ~= false and self.EngineSounds[ "LowRPM" ] ~= false and self.EngineSounds[ "HighRPM" ] ~= false then
return true
else
self:SetSoundPreset( 0 )
return false
end
end
if index == 0 then
local soundoverride = self:GetSoundoverride()
local data = string.Explode( ",", soundoverride)
if soundoverride ~= "" and data[1] ~= "1" then
self.EngineSounds[ "IdleSound" ] = data[1]
self.Idle_PitchMul = data[2]
self.EngineSounds[ "LowSound" ] = data[3]
self.Mid_PitchMul = data[4]
self.Mid_VolumeMul = data[5]
self.Mid_FadeOutRPMpercent = data[6]
self.Mid_FadeOutRate = data[7]
self.EngineSounds[ "HighSound" ] = data[8]
self.High_PitchMul = data[9]
self.High_VolumeMul = data[10]
self.High_FadeInRPMpercent = data[11]
self.High_FadeInRate = data[12]
self.EngineSounds[ "ThrottleSound" ] = data[13]
self.Throttle_PitchMul = data[14]
self.Throttle_VolumeMul = data[15]
else
self.EngineSounds[ "IdleSound" ] = self.Sound_Idle or "simulated_vehicles/misc/e49_idle.wav"
self.Idle_PitchMul = self.Sound_IdlePitch or 1
self.EngineSounds[ "LowSound" ] = self.Sound_Mid or "simulated_vehicles/misc/gto_onlow.wav"
self.Mid_PitchMul = self.Sound_MidPitch or 1
self.Mid_VolumeMul = self.Sound_MidVolume or 0.75
self.Mid_FadeOutRPMpercent = self.Sound_MidFadeOutRPMpercent or 68
self.Mid_FadeOutRate = self.Sound_MidFadeOutRate or 0.4
self.EngineSounds[ "HighSound" ] = self.Sound_High or "simulated_vehicles/misc/nv2_onlow_ex.wav"
self.High_PitchMul = self.Sound_HighPitch or 1
self.High_VolumeMul = self.Sound_HighVolume or 1
self.High_FadeInRPMpercent = self.Sound_HighFadeInRPMpercent or 26.6
self.High_FadeInRate = self.Sound_HighFadeInRate or 0.266
self.EngineSounds[ "ThrottleSound" ] = self.Sound_Throttle or "simulated_vehicles/valve_noise.wav"
self.Throttle_PitchMul = self.Sound_ThrottlePitch or 0.65
self.Throttle_VolumeMul = self.Sound_ThrottleVolume or 1
end
self.PitchMulLow = 1
self.PitchMulHigh = 1
self.PitchMulAll = 1
return false
end
if index > 0 then
local clampindex = math.Clamp(index,1,table.Count(simfphys.SoundPresets))
self.EngineSounds[ "Idle" ] = simfphys.SoundPresets[clampindex][1]
self.EngineSounds[ "LowRPM" ] = simfphys.SoundPresets[clampindex][2]
self.EngineSounds[ "HighRPM" ] = simfphys.SoundPresets[clampindex][3]
self.EngineSounds[ "RevDown" ] = simfphys.SoundPresets[clampindex][4]
self.EngineSounds[ "ShiftUpToHigh" ] = simfphys.SoundPresets[clampindex][5]
self.EngineSounds[ "ShiftDownToHigh" ] = simfphys.SoundPresets[clampindex][6]
self.PitchMulLow = simfphys.SoundPresets[clampindex][7]
self.PitchMulHigh = simfphys.SoundPresets[clampindex][8]
self.PitchMulAll = simfphys.SoundPresets[clampindex][9]
return true
end
return false
end
function ENT:GetVehicleInfo()
return self.VehicleInfo
end
function ENT:SaveStopSounds()
if self.HighRPM then
self.HighRPM:Stop()
end
if self.LowRPM then
self.LowRPM:Stop()
end
if self.Idle then
self.Idle:Stop()
end
if self.Valves then
self.Valves:Stop()
end
if self.DamageSnd then
self.DamageSnd:Stop()
end
end
function ENT:StopFireSound()
if self.smokesnd then
self.smokesnd:Stop()
end
if self.firesnd then
self.firesnd:Stop()
end
end
function ENT:OnRemove()
self:SaveStopSounds()
self:StopFireSound()
self:TireSoundRemove()
end