Initial commit
This commit is contained in:
39
simulation/collision.py
Normal file
39
simulation/collision.py
Normal file
@@ -0,0 +1,39 @@
|
||||
def collide2d(a, b, e):
|
||||
"""Returns the velocities of balls a and b after collision.
|
||||
|
||||
e is the *coefficient of restitution*, a parameter between 0 and 1
|
||||
which determines how much the objects bounce off each other.
|
||||
When e is 0, the two objects completely stick together.
|
||||
When e is 1, the two objects bounce off each other completely.
|
||||
|
||||
This is a 2-dimensional collision because a and b each have a 2d
|
||||
velocity vector, like two balls moving on a plane. We can separate
|
||||
each velocity vector into two components: a normal vector (pointed
|
||||
straight at the other ball) and a tangent vector (perpendicular to
|
||||
the normal). The tangent vectors don't participate in the collision
|
||||
at all, so we just need to calculate how the normal vectors change
|
||||
after the collision. This is easier, since it's a 1-dimensional
|
||||
collision.
|
||||
|
||||
Afterwards we combine the updated normal vector with the tangent
|
||||
vector to get the resulting velocity vector for each ball.
|
||||
"""
|
||||
a_to_b = b.position - a.position
|
||||
av_normal = a.velocity.project(a_to_b)
|
||||
av_tangent = a.velocity - av_normal
|
||||
bv_normal = b.velocity.project(-a_to_b)
|
||||
bv_tangent = b.velocity - bv_normal
|
||||
av_normal_after, bv_normal_after = collide1d(av_normal, a.mass, bv_normal, b.mass, e)
|
||||
av_after = av_normal_after + av_tangent
|
||||
bv_after = bv_normal_after + bv_tangent
|
||||
return av_after, bv_after
|
||||
|
||||
def collide1d(av, am, bv, bm, e):
|
||||
"""Returns the velicoties of a and b after a 1-dimensional collision,
|
||||
where a and b are headed directly at each other. This formula is from Wikipedia:
|
||||
https://en.wikipedia.org/wiki/Elastic_collision#One-dimensional_Newtonian
|
||||
"""
|
||||
velocity_center_of_mass = (av * am + bv * bm) / (am + bm)
|
||||
av_after = velocity_center_of_mass * (1 + e) - av * e
|
||||
bv_after = velocity_center_of_mass * (1 + e) - bv * e
|
||||
return av_after, bv_after
|
||||
Reference in New Issue
Block a user