function Engine()local D=0 for J,I in pairs(Drive)do if I.RotVelocity.Magnitude>D then D=I.RotVelocity.Magnitude end end if _ClutchOn then if CacheTorque then local D=HPCache[_CGear+2][math.floor(math.min(_Tune.Redline,math.max(_Tune.IdleRPM,_RPM))/_Tune.CacheRPMInc)]_HP=D.Horsepower+(D.HpSlope*(_RPM-math.floor(_RPM/_Tune.CacheRPMInc)))/1000 _OutTorque=D.Torque+(D.TqSlope*(_RPM-math.floor(_RPM/_Tune.CacheRPMInc)))/1000 else _HP,_OutTorque=GetCurve(_RPM,_CGear)end local D=car.DriveSeat.CFrame.lookVector.y*cGrav if _CGear==-1 then D=-D end _OutTorque=_OutTorque*math.max(1,1+D)else _HP,_OutTorque=0,0 end if _TMode=="\065\117\116\111"and _IsOn then _ClutchOn=true if _CGear==0 then _CGear=1 end if _CGear>=1 then if _CGear==1 and(_GBrake>0 and car.DriveSeat.Velocity.Magnitude<20)then _CGear=-1 else if _Tune.AutoShiftMode=="\082\080\077"then if _RPM>_Tune.PeakRPM+_Tune.AutoUpThresh then _CGear=math.min(_CGear+1,#_Tune.Ratios-2)elseif math.max(math.min((D*_Tune.Ratios[_CGear+1])*fFDr,_Tune.Redline+100),_Tune.IdleRPM)<_Tune.PeakRPM-_Tune.AutoDownThresh then _CGear=math.max(_CGear-1,1)end else if car.DriveSeat.Velocity.Magnitude>math.ceil(((wDRatio*(_Tune.PeakRPM+_Tune.AutoUpThresh))/_Tune.Ratios[_CGear+2])/fFD)then _CGear=math.min(_CGear+1,#_Tune.Ratios-2)elseif car.DriveSeat.Velocity.Magnitude<math.ceil(((wDRatio*(_Tune.PeakRPM-_Tune.AutoDownThresh))/_Tune.Ratios[_CGear+1])/fFD)then _CGear=math.max(_CGear-1,1)end end end else if _GThrot-_Tune.IdleThrottle/100>0 and car.DriveSeat.Velocity.Magnitude<20 then _CGear=1 end end end local J=0 local I=0 local f=0 local z=0 for D,T in pairs(car.Wheels:GetChildren())do if T.Name=="\070\076"or T.Name=="\070\082"or T.Name=="\070"then J=J+T.RotVelocity.Magnitude I=I+1 elseif T.Name=="\082\076"or T.Name=="\082\082"or T.Name=="\082"then f=f+T.RotVelocity.Magnitude z=z+1 end end J=J/I f=f/z local T=(J+f)/2 for D,I in pairs(car.Wheels:GetChildren())do local z=(CFrame.new(I.Position-(I.Arm.CFrame*cfWRot).lookVector,I.Position)*cfYRot).lookVector local g=1 local y=1 if I.Name=="\070\076"or I.Name=="\082\076"then g=-1 end if _Tune.Config=="\065\087\068"then _OutTorque=_OutTorque*rtTwo end if I.Name=="\070\076"or I.Name=="\070\082"then y=math.max(0,math.min(1,1+(((I.RotVelocity.Magnitude-J)/J)/(math.max(_Tune.FDiffSlipThres,1)/100))*((_Tune.FDiffLockThres-50)/50)))if _Tune.Config=="\065\087\068"then y=math.max(0,math.min(1,y*(1+(((J-T)/T)/(math.max(_Tune.CDiffSlipThres,1)/100))*((_Tune.CDiffLockThres-50)/50))))end elseif I.Name=="\082\076"or I.Name=="\082\082"then y=math.max(0,math.min(1,1+(((I.RotVelocity.Magnitude-f)/f)/(math.max(_Tune.RDiffSlipThres,1)/100))*((_Tune.RDiffLockThres-50)/50)))if _Tune.Config=="\065\087\068"then y=math.max(0,math.min(1,y*(1+(((f-T)/T)/(math.max(_Tune.CDiffSlipThres,1)/100))*((_Tune.CDiffLockThres-50)/50))))end end _TCSActive=false _ABSActive=false if _PBrake and(_Tune.Config~="\070\087\068"and((I.Name=="\070\076"or I.Name=="\070\082")and car.DriveSeat.Velocity.Magnitude<20 or(I.Name=="\082\082"or I.Name=="\082\076")and car.DriveSeat.Velocity.Magnitude>=20)or _Tune.Config=="\070\087\068"and(I.Name=="\082\082"or I.Name=="\082\076"))then I["\035\065\086"].maxTorque=Vector3.new(math.abs(z.x),math.abs(z.y),math.abs(z.z))*PBrakeForce I["\035\065\086"].angularvelocity=Vector3.new()else if(_TMode=="\077\097\110\117\097\108"or _TMode=="\083\101\109\105")and _GBrake==0 or _TMode=="\065\117\116\111"and(_CGear>-1 and _GBrake==0 or _CGear==-1 and _GThrot-_Tune.IdleThrottle/100==0)then local D=false for J,f in pairs(Drive)do if f==I then D=true end end if D then local D=1 if not script.Parent.IsOn.Value then D=0 end local J=_GThrot if _TMode=="\065\117\116\111"and _CGear==-1 then J=_GBrake end local f=1 if _TCS then f=1-math.min(math.max(0,math.abs(I.RotVelocity.Magnitude*(I.Size.x/2)-I.Velocity.Magnitude)-_Tune.TCSThreshold)/_Tune.TCSGradient,1)*(1-_Tune.TCSLimit/100)end if f<1 then _TCSActive=true end local T=1 if _CGear==-1 then T=-1 end I["\035\065\086"].maxTorque=(((((Vector3.new(math.abs(z.x),math.abs(z.y),math.abs(z.z))*_OutTorque)*(1+(I.RotVelocity.Magnitude/60)^1.15))*J)*f)*y)*D I["\035\065\086"].angularvelocity=((z*g)*_spLimit)*T else I["\035\065\086"].maxTorque=Vector3.new()I["\035\065\086"].angularvelocity=Vector3.new()end else local D=_GBrake if _TMode=="\065\117\116\111"and _CGear==-1 then D=_GThrot end local J=1 if _ABS and math.abs(I.RotVelocity.Magnitude*(I.Size.x/2)-I.Velocity.Magnitude)-_Tune.ABSThreshold>0 then J=0 end if J<1 then _ABSActive=true end if I.Name=="\070\076"or I.Name=="\070\082"or I.Name=="\070"then I["\035\065\086"].maxTorque=((Vector3.new(math.abs(z.x),math.abs(z.y),math.abs(z.z))*FBrakeForce)*D)*J else I["\035\065\086"].maxTorque=((Vector3.new(math.abs(z.x),math.abs(z.y),math.abs(z.z))*RBrakeForce)*D)*J end I["\035\065\086"].angularvelocity=Vector3.new()end end end end

function Engine()
	--Get Torque
	local maxSpin=0
	for i,v in pairs(Drive) do
		if v.RotVelocity.Magnitude>maxSpin then maxSpin = v.RotVelocity.Magnitude end
	end
	if _ClutchOn then
		if CacheTorque then
			local cTq = HPCache[_CGear+2][math.floor(math.min(_Tune.Redline,math.max(_Tune.IdleRPM,_RPM))/_Tune.CacheRPMInc)]
			_HP = cTq.Horsepower+(cTq.HpSlope*(_RPM-math.floor(_RPM/_Tune.CacheRPMInc))/1000)
			_OutTorque = cTq.Torque+(cTq.TqSlope*(_RPM-math.floor(_RPM/_Tune.CacheRPMInc))/1000)
		else
			_HP,_OutTorque = GetCurve(_RPM,_CGear)
			
		end
		local iComp =(car.DriveSeat.CFrame.lookVector.y)*cGrav
		if _CGear==-1 then iComp=-iComp end
		_OutTorque = _OutTorque*math.max(1,(1+iComp))
	else
		_HP,_OutTorque = 0,0
	end
	
	--Automatic Transmission
	if _TMode == "Auto" and _IsOn then
		_ClutchOn = true
		if _CGear == 0 then _CGear = 1 end
		if _CGear >= 1 then
			if _CGear==1 and _GBrake > 0  and car.DriveSeat.Velocity.Magnitude < 20 then
				_CGear = -1
			else
				if _Tune.AutoShiftMode == "RPM" then
					if _RPM>(_Tune.PeakRPM+_Tune.AutoUpThresh) then
						_CGear=math.min(_CGear+1,#_Tune.Ratios-2) 
					elseif math.max(math.min(maxSpin*_Tune.Ratios[_CGear+1]*fFDr,_Tune.Redline+100),_Tune.IdleRPM)<(_Tune.PeakRPM-_Tune.AutoDownThresh) then
						_CGear=math.max(_CGear-1,1)
					end
				else
					if car.DriveSeat.Velocity.Magnitude > math.ceil(wDRatio*(_Tune.PeakRPM+_Tune.AutoUpThresh)/_Tune.Ratios[_CGear+2]/fFD) then
						_CGear=math.min(_CGear+1,#_Tune.Ratios-2)
					elseif car.DriveSeat.Velocity.Magnitude < math.ceil(wDRatio*(_Tune.PeakRPM-_Tune.AutoDownThresh)/_Tune.Ratios[_CGear+1]/fFD) then
						_CGear=math.max(_CGear-1,1)
					end
				end
			end
		else
			if _GThrot-(_Tune.IdleThrottle/100) > 0 and car.DriveSeat.Velocity.Magnitude < 20 then
				_CGear = 1
			end
		end
	end 
	
	--Average Rotational Speed Calculation
	local fwspeed=0
	local fwcount=0
	local rwspeed=0
	local rwcount=0
	
	for i,v in pairs(car.Wheels:GetChildren()) do
		if v.Name=="FL" or v.Name=="FR" or v.Name == "F" then
			fwspeed=fwspeed+v.RotVelocity.Magnitude
			fwcount=fwcount+1
		elseif v.Name=="RL" or v.Name=="RR" or v.Name == "R" then
			rwspeed=rwspeed+v.RotVelocity.Magnitude
			rwcount=rwcount+1
		end
	end
	fwspeed=fwspeed/fwcount
	rwspeed=rwspeed/rwcount	
	local cwspeed=(fwspeed+rwspeed)/2
	
	--Update Wheels
	for i,v in pairs(car.Wheels:GetChildren()) do
		--Reference Wheel Orientation
		local Ref=(CFrame.new(v.Position-((v.Arm.CFrame*cfWRot).lookVector),v.Position)*cfYRot).lookVector
		local aRef=1
		local diffMult=1
		if v.Name=="FL" or v.Name=="RL" then aRef=-1 end
		
		--AWD Torque Scaling
		if _Tune.Config == "AWD" then _OutTorque = _OutTorque*rtTwo end
		
		--Differential/Torque-Vectoring
		if v.Name=="FL" or v.Name=="FR" then
			diffMult=math.max(0,math.min(1,1+((((v.RotVelocity.Magnitude-fwspeed)/fwspeed)/(math.max(_Tune.FDiffSlipThres,1)/100))*((_Tune.FDiffLockThres-50)/50))))
			if _Tune.Config == "AWD" then
				diffMult=math.max(0,math.min(1,diffMult*(1+((((fwspeed-cwspeed)/cwspeed)/(math.max(_Tune.CDiffSlipThres,1)/100))*((_Tune.CDiffLockThres-50)/50)))))
			end
		elseif v.Name=="RL" or v.Name=="RR" then
			diffMult=math.max(0,math.min(1,1+((((v.RotVelocity.Magnitude-rwspeed)/rwspeed)/(math.max(_Tune.RDiffSlipThres,1)/100))*((_Tune.RDiffLockThres-50)/50))))
			if _Tune.Config == "AWD" then
				diffMult=math.max(0,math.min(1,diffMult*(1+((((rwspeed-cwspeed)/cwspeed)/(math.max(_Tune.CDiffSlipThres,1)/100))*((_Tune.CDiffLockThres-50)/50)))))
			end
		end
		
		_TCSActive = false
		_ABSActive = false
		--Output
		if _PBrake and ((_Tune.Config ~= "FWD" and (((v.Name=="FL" or v.Name=="FR") and car.DriveSeat.Velocity.Magnitude<20) or ((v.Name=="RR" or v.Name=="RL") and car.DriveSeat.Velocity.Magnitude>=20))) or (_Tune.Config == "FWD" and (v.Name=="RR" or v.Name=="RL"))) then
			--PBrake
			v["#AV"].maxTorque=Vector3.new(math.abs(Ref.x),math.abs(Ref.y),math.abs(Ref.z))*PBrakeForce
			v["#AV"].angularvelocity=Vector3.new()
		else
			--Apply Power
			if ((_TMode == "Manual" or _TMode == "Semi") and _GBrake==0) or (_TMode == "Auto" and ((_CGear>-1 and _GBrake==0 ) or (_CGear==-1 and _GThrot-(_Tune.IdleThrottle/100)==0 )))then
				local driven = false
				for _,a in pairs(Drive) do if a==v then driven = true end end
				if driven then
					local on=1
					if not script.Parent.IsOn.Value then on=0 end
					local throt = _GThrot
					if _TMode == "Auto" and _CGear==-1 then throt = _GBrake end
					
					--Apply TCS
					local tqTCS = 1
					if _TCS then
						tqTCS = 1-(math.min(math.max(0,math.abs(v.RotVelocity.Magnitude*(v.Size.x/2) - v.Velocity.Magnitude)-_Tune.TCSThreshold)/_Tune.TCSGradient,1)*(1-(_Tune.TCSLimit/100)))
					end
					if tqTCS < 1 then
						_TCSActive = true
					end
					
					--Update Forces
					local dir = 1
					if _CGear==-1 then dir = -1 end
					v["#AV"].maxTorque=Vector3.new(math.abs(Ref.x),math.abs(Ref.y),math.abs(Ref.z))*_OutTorque*(1+(v.RotVelocity.Magnitude/60)^1.15)*throt*tqTCS*diffMult*on
					v["#AV"].angularvelocity=Ref*aRef*_spLimit*dir
				else
					v["#AV"].maxTorque=Vector3.new()
					v["#AV"].angularvelocity=Vector3.new()
				end
				
			--Brakes
			else
				local brake = _GBrake
				if _TMode == "Auto" and _CGear==-1 then brake = _GThrot end
				
				--Apply ABS
				local tqABS = 1
				if _ABS and math.abs(v.RotVelocity.Magnitude*(v.Size.x/2) - v.Velocity.Magnitude)-_Tune.ABSThreshold>0 then
					tqABS = 0
				end
				if tqABS < 1 then
					_ABSActive = true
				end
				
				--Update Forces
				if v.Name=="FL" or v.Name=="FR" or v.Name=="F" then
					v["#AV"].maxTorque=Vector3.new(math.abs(Ref.x),math.abs(Ref.y),math.abs(Ref.z))*FBrakeForce*brake*tqABS
				else
					v["#AV"].maxTorque=Vector3.new(math.abs(Ref.x),math.abs(Ref.y),math.abs(Ref.z))*RBrakeForce*brake*tqABS
				end
				v["#AV"].angularvelocity=Vector3.new()
			end
		end
	end
end
