Skip to content

Commit dce9e1c

Browse files
authored
Allow mods to cap rotational velocity from collisions (#6890)
The `+Rotation Factor:` value in the ship collide section of the ships table has been around for many years, but raising that value beyond the default of 0.2 results in ship collisions that can result in the colliding ship spinning at ludicrous rotational velocities that last for over 10 seconds (this is especially evident with long ships with high speeds). This PR adds a field after `+Rotation Factor:` called `+Rotation Magnitude Maximum:` which serves as a maximum for the resulting rotational velocity from a ship collision in degrees per second. By default this is -1 and thus disabled. Tested and works as expected, and now properly allows mods to have ships spin out if they have collision while not spinning out at wild speeds that look immersion breaking.
1 parent b5f3edc commit dce9e1c

File tree

5 files changed

+17
-4
lines changed

5 files changed

+17
-4
lines changed

code/object/collideshipship.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -753,11 +753,11 @@ void calculate_ship_ship_collision_physics(collision_info_struct *ship_ship_hit_
753753
if (should_collide){
754754
vm_vec_scale(&impulse, impulse_mag);
755755
vm_vec_scale(&delta_rotvel_light, impulse_mag);
756-
physics_collide_whack(&impulse, &delta_rotvel_light, &lighter->phys_info, &lighter->orient, ship_ship_hit_info->is_landing);
756+
physics_collide_whack(&impulse, &delta_rotvel_light, &lighter->phys_info, &lighter->orient, ship_ship_hit_info->is_landing, light_sip->collision_physics.rotation_mag_max);
757757

758758
vm_vec_negate(&impulse);
759759
vm_vec_scale(&delta_rotvel_heavy, -impulse_mag);
760-
physics_collide_whack(&impulse, &delta_rotvel_heavy, &heavy->phys_info, &heavy->orient, true);
760+
physics_collide_whack(&impulse, &delta_rotvel_heavy, &heavy->phys_info, &heavy->orient, true, heavy_sip->collision_physics.rotation_mag_max);
761761
}
762762

763763
// If within certain bounds, we want to add some more rotation towards the "resting orientation" of the ship

code/physics/physics.cpp

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1084,7 +1084,7 @@ void physics_apply_shock(vec3d *direction_vec, float pressure, physics_info *pi,
10841084
// Warning: Do not change ROTVEL_COLLIDE_WHACK_CONST. This will mess up collision physics.
10851085
// If you need to change the rotation, change COLLISION_ROTATION_FACTOR in collide_ship_ship.
10861086
#define ROTVEL_COLLIDE_WHACK_CONST 1.0
1087-
void physics_collide_whack( vec3d *impulse, vec3d *world_delta_rotvel, physics_info *pi, matrix *orient, bool is_landing )
1087+
void physics_collide_whack( vec3d *impulse, vec3d *world_delta_rotvel, physics_info *pi, matrix *orient, bool is_landing, float max_rotvel )
10881088
{
10891089
vec3d body_delta_rotvel;
10901090

@@ -1096,6 +1096,13 @@ void physics_collide_whack( vec3d *impulse, vec3d *world_delta_rotvel, physics_i
10961096
// vm_vec_scale( &body_delta_rotvel, (float) ROTVEL_COLLIDE_WHACK_CONST );
10971097
vm_vec_add2( &pi->rotvel, &body_delta_rotvel );
10981098

1099+
if (max_rotvel > 0.0f) {
1100+
float rotvel_mag = vm_vec_mag(&pi->rotvel);
1101+
if (rotvel_mag > max_rotvel) {
1102+
vm_vec_scale(&pi->rotvel, max_rotvel / rotvel_mag);
1103+
}
1104+
}
1105+
10991106
pi->flags |= PF_REDUCED_DAMP;
11001107
update_reduced_damp_timestamp( pi, vm_vec_mag(impulse) );
11011108

code/physics/physics.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -164,7 +164,7 @@ extern bool whack_below_limit(float impulse);
164164
extern void physics_calculate_and_apply_whack(const vec3d *force, const vec3d *pos, physics_info *pi, const matrix *orient, const matrix *inv_moi);
165165
extern void physics_apply_whack(float orig_impulse, physics_info* pi, const vec3d *delta_rotvel, const vec3d* delta_vel, const matrix* orient);
166166
extern void physics_apply_shock(vec3d *direction_vec, float pressure, physics_info *pi, matrix *orient, vec3d *min, vec3d *max, float radius);
167-
extern void physics_collide_whack(vec3d *impulse, vec3d *delta_rotvel, physics_info *pi, matrix *orient, bool is_landing);
167+
extern void physics_collide_whack(vec3d *impulse, vec3d *delta_rotvel, physics_info *pi, matrix *orient, bool is_landing, float max_rotvel = -1.0f);
168168
int check_rotvel_limit( physics_info *pi );
169169
extern void physics_add_point_mass_moi(matrix *moi, float mass, vec3d *pos);
170170
extern bool physics_lead_ballistic_trajectory(const vec3d* start, const vec3d* end_pos, const vec3d* target_vel, float weapon_speed, const vec3d* gravity, vec3d* out_direction);

code/ship/ship.cpp

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1757,6 +1757,7 @@ ship_info::ship_info()
17571757
collision_physics.bounce = 5.0;
17581758
collision_physics.friction = COLLISION_FRICTION_FACTOR;
17591759
collision_physics.rotation_factor = COLLISION_ROTATION_FACTOR;
1760+
collision_physics.rotation_mag_max = -1.0f;
17601761
collision_physics.reorient_mult = 1.0f;
17611762
collision_physics.landing_sound_idx = gamesnd_id();
17621763
collision_physics.collision_sound_light_idx = gamesnd_id();
@@ -3337,6 +3338,10 @@ static void parse_ship_values(ship_info* sip, const bool is_template, const bool
33373338
if(optional_string("+Rotation Factor:")) {
33383339
stuff_float(&sip->collision_physics.rotation_factor);
33393340
}
3341+
if (optional_string("+Rotation Magnitude Maximum:")) {
3342+
stuff_float(&sip->collision_physics.rotation_mag_max);
3343+
sip->collision_physics.rotation_mag_max *= PI / 180.0f;
3344+
}
33403345
if(optional_string("+Landing Max Forward Vel:")) {
33413346
stuff_float(&sip->collision_physics.landing_max_z);
33423347
}

code/ship/ship.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1082,6 +1082,7 @@ typedef struct ship_collision_physics {
10821082
float bounce{}; // Bounce factor for all other cases
10831083
float friction{}; // Controls lateral velocity lost when colliding with a large ship
10841084
float rotation_factor{}; // Affects the rotational energy of collisions... TBH not sure how.
1085+
float rotation_mag_max{}; // Maximum value of the final rotational velocity resulting from a collision --wookieejedi
10851086

10861087
// Speed & angle constraints for a smooth landing
10871088
// Note that all angles are stored as a dotproduct between normalized vectors instead. This saves us from having

0 commit comments

Comments
 (0)