// Return true if object A is expected to collide with object B within time duration // For purposes of this check, the first object moves from current location to predicted // location. The second object is assumed to be where it will be at time duration, NOT // where it currently is. // radius_scale is used to control the precision of the check. // If 0.0, then use polygon models to perform check, slow and accurate // If !0.0, then use as a scale on the radius of the objects. 1.0 is Descent style // collisions. Larger values can be used to be sloppy about the collisions which // is useful if a moving object wants to prevent a collision. int objects_will_collide(object *A, object *B, float duration, float radius_scale) { object A_future; vec3d hitpos; A_future = *A; vm_vec_scale_add2(&A_future.pos, &A->phys_info.vel, duration); if (radius_scale == 0.0f) { return ship_check_collision_fast(B, &A_future, &hitpos ); } else { float size_A, size_B, dist, r; vec3d nearest_point; size_A = A->radius * radius_scale; size_B = B->radius * radius_scale; // If A is moving, check along vector. if (A->phys_info.speed != 0.0f) { r = find_nearest_point_on_line(&nearest_point, &A->pos, &A_future.pos, &B->pos); if (r < 0) { nearest_point = A->pos; } else if (r > 1) { nearest_point = A_future.pos; } dist = vm_vec_dist_quick(&B->pos, &nearest_point); return (dist < size_A + size_B); } else { return vm_vec_dist_quick(&B->pos, &A->pos) < size_A + size_B; } } }
// Return true if object A is expected to collide with object B within time duration // For purposes of this check, the first object moves from current location to predicted // location. The second object is assumed to be where it will be at time duration, NOT // where it currently is. // radius_scale is used to control the precision of the check. // If 0.0, then use polygon models to perform check, slow and accurate // If !0.0, then use as a scale on the radius of the objects. 1.0 is Descent style // collisions. Larger values can be used to be sloppy about the collisions which // is useful if a moving object wants to prevent a collision. int objects_will_collide(object *A, object *B, float duration, float radius_scale) { vec3d prev_pos; vec3d hitpos; int ret; prev_pos = A->pos; vm_vec_scale_add2(&A->pos, &A->phys_info.vel, duration); if (radius_scale == 0.0f) { ret = ship_check_collision_fast(B, A, &hitpos); } else { float size_A, size_B, dist, r; vec3d nearest_point; size_A = A->radius * radius_scale; size_B = B->radius * radius_scale; // If A is moving, check along vector. if (A->phys_info.speed != 0.0f) { r = find_nearest_point_on_line(&nearest_point, &prev_pos, &A->pos, &B->pos); if (r < 0) { nearest_point = prev_pos; } else if (r > 1) { nearest_point = A->pos; } dist = vm_vec_dist_quick(&B->pos, &nearest_point); ret = (dist < size_A + size_B); } else { ret = vm_vec_dist_quick(&B->pos, &prev_pos) < size_A + size_B; } } // Reset the position to the previous value A->pos = prev_pos; return ret; }