forked from SwagSoftware/Kisak-Strike
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathphysics_airboat.h
executable file
·303 lines (226 loc) · 12.8 KB
/
physics_airboat.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
//========= Copyright Valve Corporation, All rights reserved. ============//
//
// Purpose:
//
//=============================================================================//
#ifndef PHYSICS_AIRBOAT_H
#define PHYSICS_AIRBOAT_H
#ifdef _WIN32
#pragma once
#endif
#include "ivp_controller.hxx"
#include "ivp_car_system.hxx"
class IPhysicsObject;
class IVP_Ray_Solver_Template;
class IVP_Ray_Hit;
class IVP_Event_Sim;
#define IVP_RAYCAST_AIRBOAT_MAX_WHEELS 4
//-----------------------------------------------------------------------------
//-----------------------------------------------------------------------------
class IVP_Raycast_Airboat_Wheel
{
public:
// static section
IVP_U_Float_Point hp_cs; // hard point core system projected on y plane
IVP_U_Float_Point raycast_start_cs; // ray cast start position
IVP_U_Float_Point raycast_dir_cs;
IVP_FLOAT raycast_length;
IVP_U_Float_Point spring_direction_cs; // spring direction in core-space
IVP_FLOAT distance_orig_hp_to_hp; // distance hp is moved by projecting it onto the y - plane
IVP_FLOAT spring_len; // == pretension + distance_orig_hp_to_hp
IVP_FLOAT spring_constant; // shock at wheel spring constant
IVP_FLOAT spring_damp_relax; // shock at wheel spring dampening during relaxation
IVP_FLOAT spring_damp_compress; // shock at wheel spring dampening during compression
IVP_FLOAT max_rotation_speed; // max rotational speed of the wheel
IVP_FLOAT wheel_radius; // wheel radius
IVP_FLOAT inv_wheel_radius; // inverse wheel radius
IVP_FLOAT friction_of_wheel; // wheel friction
// dynamic section
IVP_FLOAT torque; // torque applied to wheel
IVP_BOOL wheel_is_fixed; // eg. handbrake (fixed = stationary)
IVP_U_Float_Point axis_direction_cs; // axle direction in core-space
IVP_FLOAT angle_wheel; // wheel angle
IVP_FLOAT wheel_angular_velocity; // angular velocity of wheel
// out
IVP_U_Float_Point surface_speed_of_wheel_on_ground_ws; // actual speed in world-space
IVP_FLOAT pressure; // force from gravity, mass of car, stabilizers, etc. on wheel
IVP_FLOAT raycast_dist; // raycast distance to impact for wheel
};
//-----------------------------------------------------------------------------
//-----------------------------------------------------------------------------
class IVP_Raycast_Airboat_Impact
{
public:
IVP_FLOAT friction_value; // combined (multiply) frictional value of impact surface and wheel
IVP_FLOAT stabilizer_force; // force on wheel due to axle stabilization
IVP_Real_Object *moveable_object_hit_by_ray; // moveable physics object hit by raycast
IVP_U_Float_Point raycast_dir_ws; // raycast direction in world-space
IVP_U_Float_Point spring_direction_ws; // spring direction (raycast for impact direction) in world-space
IVP_U_Float_Point surface_speed_wheel_ws; // wheel speed in world-space
IVP_U_Float_Point projected_surface_speed_wheel_ws; // ???
IVP_U_Float_Point axis_direction_ws; // axle direction in world-space
IVP_U_Float_Point projected_axis_direction_ws; // ???
IVP_FLOAT forces_needed_to_drive_straight; // forces need to keep the vehicle driving straight (attempt and directional wheel friction)
IVP_FLOAT inv_normal_dot_dir; // ???
// Impact information.
IVP_BOOL bImpact; // Had an impact?
IVP_BOOL bImpactWater; // Impact with water?
IVP_BOOL bInWater; // Point in water?
IVP_U_Point vecImpactPointWS; // Impact point in world-space.
IVP_U_Float_Point vecImpactNormalWS; // Impact normal in world-space.
IVP_FLOAT flDepth; // Distance to water surface.
IVP_FLOAT flFriction; // Friction at impact point.
IVP_FLOAT flDampening; // Dampening at surface.
int nSurfaceProps; // Surface property!
};
//-----------------------------------------------------------------------------
//-----------------------------------------------------------------------------
class IVP_Raycast_Airboat_Axle
{
public:
IVP_FLOAT stabilizer_constant; // axle (for wheels) stabilizer constant
};
//-----------------------------------------------------------------------------
//-----------------------------------------------------------------------------
class IVP_Controller_Raycast_Airboat_Vector_of_Cores_1: public IVP_U_Vector<IVP_Core>
{
void *elem_buffer[1];
public:
IVP_Controller_Raycast_Airboat_Vector_of_Cores_1();
};
//-----------------------------------------------------------------------------
//-----------------------------------------------------------------------------
class CPhysics_Airboat : public IVP_Car_System, protected IVP_Controller_Dependent
{
public:
CPhysics_Airboat( IVP_Environment *env, const IVP_Template_Car_System *t, IPhysicsGameTrace *pGameTrace );
virtual ~CPhysics_Airboat();
void update_wheel_positions( void ) {}
void SetWheelFriction( int iWheel, float flFriction );
IPhysicsObject *GetWheel( int index );
virtual const char *get_controller_name() { return "sys:airboat"; }
protected:
void InitAirboat( const IVP_Template_Car_System *pCarSystem );
float GetWaterDepth( Ray_t *pGameRay, IPhysicsObject *pPhysAirboat );
// Purpose: Deconstructor
void PerformFrictionNotification( float flEliminatedEnergy, float dt, int nSurfaceProp, IPhysicsCollisionData *pCollisionData );
void do_raycasts_gameside( int nRaycastCount, IVP_Ray_Solver_Template *pRays, IVP_Raycast_Airboat_Impact *pImpacts );
void pre_raycasts_gameside( int nRaycastCount, IVP_Ray_Solver_Template *pRays, Ray_t *pGameRays, IVP_Raycast_Airboat_Impact *pImpacts );
IVP_Real_Object *m_pWheels[IVP_RAYCAST_AIRBOAT_MAX_WHEELS];
IPhysicsGameTrace *m_pGameTrace;
public:
// Steering
void do_steering_wheel(IVP_POS_WHEEL wheel_pos, IVP_FLOAT s_angle); // called by do_steering()
// Car Adjustment
void change_spring_constant(IVP_POS_WHEEL pos, IVP_FLOAT spring_constant); // [Newton/meter]
void change_spring_dampening(IVP_POS_WHEEL pos, IVP_FLOAT spring_dampening); // when spring is relaxing spring
void change_spring_dampening_compression(IVP_POS_WHEEL pos, IVP_FLOAT spring_dampening); // [Newton/meter] for compressing spring
void change_max_body_force(IVP_POS_WHEEL , IVP_FLOAT mforce) {}
void change_spring_pre_tension(IVP_POS_WHEEL pos, IVP_FLOAT pre_tension_length);
void change_spring_length(IVP_POS_WHEEL pos, IVP_FLOAT spring_length);
void change_stabilizer_constant(IVP_POS_AXIS pos, IVP_FLOAT stabi_constant); // [Newton/meter]
void change_fast_turn_factor( IVP_FLOAT fast_turn_factor_ ); // not implemented for raycasts
void change_wheel_torque(IVP_POS_WHEEL pos, IVP_FLOAT torque);
IVP_FLOAT get_wheel_torque(IVP_POS_WHEEL wheel_nr);
void update_throttle( IVP_FLOAT flThrottle );
void update_body_countertorque() {}
void change_body_downforce(IVP_FLOAT force); // extra force to keep flipped objects flipped over
void fix_wheel( IVP_POS_WHEEL, IVP_BOOL stop_wheel ); // stop wheel completely (e.g. handbrake )
void change_friction_of_wheel( IVP_POS_WHEEL pos, IVP_FLOAT friction );
void set_powerslide( float frontAccel, float rearAccel ) {}
// Car Info
IVP_DOUBLE get_body_speed(IVP_COORDINATE_INDEX idx_z = IVP_INDEX_Z); // km/h in 'z' direction
IVP_DOUBLE get_wheel_angular_velocity(IVP_POS_WHEEL);
IVP_DOUBLE get_orig_front_wheel_distance();
IVP_DOUBLE get_orig_axles_distance();
void get_skid_info( IVP_Wheel_Skid_Info *array_of_skid_info_out);
void get_wheel_position(IVP_U_Point *position_ws_out, IVP_U_Quat *direction_ws_out);
// Methods: 2nd Level, based on primitives
virtual void do_steering(IVP_FLOAT steering_angle_in, bool bAnalog); // default implementation updates this->steering_angle
//
// Booster (the airboat has no booster).
//
virtual bool IsBoosting(void) { return false; }
virtual void set_booster_acceleration( IVP_FLOAT acceleration) {}
virtual void activate_booster(IVP_FLOAT thrust, IVP_FLOAT duration, IVP_FLOAT delay) {}
virtual void update_booster(IVP_FLOAT delta_time) {}
virtual IVP_FLOAT get_booster_delay() { return 0; }
virtual IVP_FLOAT get_booster_time_to_go() { return 0; }
// Debug
void SetCarSystemDebugData( const IVP_CarSystemDebugData_t &carSystemDebugData );
void GetCarSystemDebugData( IVP_CarSystemDebugData_t &carSystemDebugData );
protected:
IVP_Core *m_pCore;
IVP_U_Float_Point m_vecLocalVelocity;
float m_flSpeed;
IVP_Real_Object *m_pAirboatBody; // *car_body
// Wheels/Axles.
short n_wheels;
short n_axis;
short wheels_per_axis;
IVP_Raycast_Airboat_Wheel m_aAirboatWheels[IVP_RAYCAST_AIRBOAT_MAX_WHEELS]; // wheel_of_car
IVP_Raycast_Airboat_Axle m_aAirboatAxles[IVP_RAYCAST_AIRBOAT_MAX_WHEELS/2]; // axis_of_car
// Gravity.
IVP_FLOAT gravity_y_direction; // +/-1
IVP_U_Float_Point normized_gravity_ws;
IVP_FLOAT extra_gravity;
// Orientation.
IVP_COORDINATE_INDEX index_x;
IVP_COORDINATE_INDEX index_y;
IVP_COORDINATE_INDEX index_z;
IVP_BOOL is_left_handed;
// Speed.
IVP_FLOAT max_speed;
//
IVP_FLOAT down_force;
IVP_FLOAT down_force_vertical_offset;
// Steering
IVP_FLOAT m_SteeringAngle;
bool m_bSteeringReversed;
bool m_bAnalogSteering;
IVP_FLOAT m_flPrevSteeringAngle;
IVP_FLOAT m_flSteerTime; // Number of seconds we've steered in this direction.
// Thrust.
IVP_FLOAT m_flThrust;
bool m_bAirborne; // Whether we are airborne or not.
IVP_FLOAT m_flAirTime; // How long we've been airborne (if we are).
bool m_bWeakJump; // Set when we become airborne while going slow.
// Pitch and roll stabilizers.
IVP_FLOAT m_flPitchErrorPrev;
IVP_FLOAT m_flRollErrorPrev;
// Debugging!
IVP_CarSystemDebugData_t m_CarSystemDebugData;
protected:
IVP_Raycast_Airboat_Wheel *get_wheel( IVP_POS_WHEEL i );
IVP_Raycast_Airboat_Axle *get_axle( IVP_POS_AXIS i );
virtual void core_is_going_to_be_deleted_event( IVP_Core * );
virtual IVP_U_Vector<IVP_Core> *get_associated_controlled_cores( void );
virtual void do_simulation_controller(IVP_Event_Sim *,IVP_U_Vector<IVP_Core> *core_list);
virtual IVP_CONTROLLER_PRIORITY get_controller_priority();
private:
// Initialization.
void InitRaycastCarEnvironment( IVP_Environment *pEnvironment, const IVP_Template_Car_System *pCarSystemTemplate );
void InitRaycastCarBody( const IVP_Template_Car_System *pCarSystemTemplate );
void InitRaycastCarWheels( const IVP_Template_Car_System *pCarSystemTemplate );
void InitRaycastCarAxes( const IVP_Template_Car_System *pCarSystemTemplate );
// Raycasts for simulation.
void PreRaycasts( IVP_Ray_Solver_Template *pRaySolverTemplates, const IVP_U_Matrix *m_world_f_core, IVP_Raycast_Airboat_Impact *pImpacts );
bool PostRaycasts( IVP_Ray_Solver_Template *pRaySolverTemplates, const IVP_U_Matrix *matWorldFromCore, IVP_Raycast_Airboat_Impact *pImpacts );
// Simulation.
void DoSimulationPontoons( IVP_Raycast_Airboat_Impact *pImpacts, IVP_Event_Sim *pEventSim );
void DoSimulationPontoonsGround( IVP_Raycast_Airboat_Wheel *pPontoonPoint, IVP_Raycast_Airboat_Impact *pImpact, IVP_Event_Sim *pEventSim );
void DoSimulationPontoonsWater( IVP_Raycast_Airboat_Wheel *pPontoonPoint, IVP_Raycast_Airboat_Impact *pImpact, IVP_Event_Sim *pEventSim );
void DoSimulationDrag( IVP_Raycast_Airboat_Impact *pImpacts, IVP_Event_Sim *pEventSim );
void DoSimulationTurbine( IVP_Event_Sim *pEventSim );
void DoSimulationSteering( IVP_Event_Sim *pEventSim );
void DoSimulationKeepUprightPitch( IVP_Raycast_Airboat_Impact *pImpacts, IVP_Event_Sim *pEventSim );
void DoSimulationKeepUprightRoll( IVP_Raycast_Airboat_Impact *pImpacts, IVP_Event_Sim *pEventSim );
void DoSimulationGravity( IVP_Event_Sim *pEventSim );
int CountSurfaceContactPoints( IVP_Raycast_Airboat_Impact *pImpacts );
void UpdateAirborneState( IVP_Raycast_Airboat_Impact *pImpacts, IVP_Event_Sim *pEventSim );
float ComputeFrontPontoonWaveNoise( int nPontoonIndex, float flSpeedRatio );
void CalcImpactPosition( IVP_Ray_Solver_Template *pRaySolver, IVP_Raycast_Airboat_Wheel *pPontoonPoint,
IVP_Raycast_Airboat_Impact *pImpacts );
IVP_Controller_Raycast_Airboat_Vector_of_Cores_1 vector_of_cores;
};
#endif // PHYSICS_AIRBOAT_H