I have wrote a script in Python 3 to simulate elastic collisions in two dimensions. I don't know what I am doing wrong because when I run it, the balls seem to stick to each other and sometimes glitch to become one ball. Also, when a single ball hits any edge of the screen, it will bounce off, however when when another ball is stuck to it, it will cause one of them to come off the screen.
Snippet of the code:
class Particle(Sprite):
def __init__(self, image):
super(Particle, self).__init__(image)
self.Vxi, self.Vyi = random.randint(-3, 3), random.randint(-3, 3)
self.mass = random.randint(1, 100) / 1000
self.schedule_interval(self.update, 1/60)
def update(self, dt):
self.xpos, self.ypos = self.position
if self.xpos <= self.width/2 or self.xpos >= scr_width - self.width/2:
self.Vxi *= -1
if self.ypos <= self.width/2 or self.ypos >= scr_height - self.height/2:
self.Vyi *= -1
for particle in director.scene.children[0][1].particles:
particle_xpos, particle_ypos = particle.position
if abs(self.xpos - particle_xpos) <= self.width/2 + particle.width/2:
if abs(self.ypos - particle_ypos) <= self.height/2 + particle.height/2:
xmomentum = (particle.mass * particle.Vxi) + (self.mass * self.Vxi)
ymomentum = (particle.mass * particle.Vyi) + (self.mass * self.Vyi)
Vxf = (xmomentum - particle.mass * (self.Vxi - particle.Vxi)) / (particle.mass + self.mass)
Vyf = (ymomentum - particle.mass * (self.Vyi - particle.Vyi)) / (particle.mass + self.mass)
self.Vxi = Vxf
self.Vyi = Vyf
self.xpos += self.Vxi
self.ypos += self.Vyi
self.position = self.xpos, self.ypos
I think you forgot to update the other particle's velocity upon collision.
Before
there should also be
Style wise, I think the variables can be named better. A Particle object shouldn't have an attribute called
VxiorVxf. As far as the physical particle is concerned it only has one velocity. The concept of initial/final velocities is associated with the numerical simulation, which the attributes of the Particle class shouldn't model. In your current code, the "final" velocities ofselfis updated as its initial velocity, which can be confusing.The initial velocity (
Vxi,Vyi) should be taken fromself.Vxandself.Vyat the beginning ofupdate. At the very end,VfxandVfyshould be updated toself.Vxandself.Vy.Also, it's a good idea to indicate which particle it is in the local variables, eg
V1_x_initial,V2_x_initial, etc.