// https://www.edy.es/dev/docs/pacejka-94-parameters-explained-a-comprehensive-guide/ package physics import "core:math" Pacejka94_Longitudinal_Params :: [14]f32 Pacejka94_Lateral_Params :: [18]f32 PACEJKA94_LONGITUDINAL_PEAK_X :: 6.24 PACEJKA94_LONGITUDINAL_PARAMS :: Pacejka94_Longitudinal_Params { 1.5, 0, 1100, 0, 300, 0, 0, 0, -2, 0, 0, 0, 0, 0, } PACEJKA94_LATERAL_PEAK_X :: 6.26 PACEJKA94_LATERAL_PARAMS :: Pacejka94_Lateral_Params { 1.4, 0, 1100, 1100, 10, 0, 0, -2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, } // X is slip ratio percentage [-100, 100] or slip angle in degrees, where positive angle is turning left // Output is the friction coefficient pacejka_94_longitudinal :: proc( b: Pacejka94_Longitudinal_Params, x: f32, f_z: f32, s_v: f32 = 0, ) -> f32 { f_z_sq := f_z * f_z C := b[0] D := (b[1] * f_z + b[2]) * f_z BCD := (b[3] * f_z_sq + b[4] * f_z) * math.exp(-b[5] * f_z) B := BCD / (C * D) H := b[9] * f_z + b[10] E := (b[6] * f_z_sq + b[7] * f_z + b[8]) * (1.0 - b[13] * math.sign(x + H)) V := b[11] * f_z + b[12] Bx1 := B * (x + H) F := D * math.sin(C * math.atan(Bx1 - E * (Bx1 - math.atan(Bx1)))) + V return F / (f_z * 1000) } pacejka_94_lateral :: proc( a: Pacejka94_Lateral_Params, slip_angle: f32, f_z: f32, camber_angle: f32, ) -> f32 { camber_angle_sq := camber_angle * camber_angle C := a[0] D := f_z * (a[1] * f_z + a[2]) * (1.0 - a[15] * camber_angle_sq) BCD := a[3] * math.sin(math.atan(f_z / a[4]) * 2.0) * (1.0 - a[5] * abs(camber_angle)) B := BCD / (C * D) H := a[8] * f_z + a[9] + a[10] * camber_angle E := (a[6] * f_z + a[7]) * (1.0 - (a[16] * camber_angle + a[17]) * math.sign(slip_angle + H)) V := a[11] * f_z + a[12] + (a[13] * f_z + a[14]) * camber_angle * f_z Bx1 := B * (slip_angle + H) F := D * math.sin(C * math.atan(Bx1 - E * (Bx1 - math.atan(Bx1)))) + V return F / (f_z * 1000) }