Reply #121 on: July 01, 2009, 09:33:27 am » posted from:Taipei,T\'ai-pei,Taiwan

I created the following applet. It is similar to what you want. You can change initial positions with different initialization code and add rules for your game.

You can drag from the center of the blue particle to change it's velocity when it is in paused state. The blue particle will start to move when you release the mouse. You can change the friction coefficient mu and elastic coefficient k. k=1 means elastic collision without energy. k<1 then energy is loss due to collision.

Because the particle move in the same direction when there is no collision. The friction force , from The energy loss is where d is the distance traveled. d can be calculated between each time step. And kinetic energy will be loss due to friction. So I re-calculate velocity after each time step. And if the right hand side become smaller than zero, it means that the particle should have been stopped. (So velocity has to be set to zero).

I think I should only help you from the physics point of view. The rest work should be your job, waiting for you to finish it.

I will be glad to help you if you have questions related to physics!

Reply #123 on: July 17, 2009, 10:21:07 pm » posted from:Bangalore,Karnataka,India

Hello Professor!

Thank you for all that you have shared and helped people understand these concepts with more clarity. I recently started looking into graphics on Windows Mobile phones and thanks to you I was able to come up with a colliding marbles program pretty quickly. If you are interested here is the link:

Sometimes there is a problem with the program. The balls will stick or completely disappear from the screen. But it happens very rarely, maybe around 1 in 30 times. I haven't yet looked deeply into the problem. Well, that is my next task (:

Thank you again and I really appreciate your work. Prabhu

Reply #124 on: July 18, 2009, 08:30:02 am » posted from:Taipei,T\'ai-pei,Taiwan

There is an assumption for all the above discussion: The time step dt need to be smaller enough (which is depend on velocity V and diameter of the ball R). V*dt<< R ( dt<0.1*R/V should be fine).

If V*dt ≒ R , the approximation used in the calculation (finding the time collision really occurred) is not valid.

So you should adjust time step (or set maximum value for V) to satisfy the above condition.

Reply #126 on: September 03, 2009, 11:36:13 am » posted from:Taipei,T\'ai-pei,Taiwan

Conservation of momentum require

If , it reduced to

Velocity is a vector which is not the same a speed! You can check that the sum of x (or y) component of velocity should be the same before and after collision (when )

************** Note that there was a bug in the collision detection routine of the 2D-versions of my programs (this led in certain cases to collisions being detected when in fact there were none). I have corrected this now. I have also made minor changes to the code in order to improve speed. Furthermore I have added a simplified version to the 2D-routines that does not not contain the collision detection routine but just returns the new velocities assuming that the input coordinates are already those of the collision.

Thomas, 11.Dec.05 *******************

Please note that I modified the code in my routines now such as to work for (partially) inelastic collisions as well. This was simply achieved by subtracting the velocity of the center of mass from the final velocities for the elastic collision case, multiplying this by the restitution coefficient (which is an additional input parameter) and adding the velocity of the center of mass on again.

Reply #128 on: January 05, 2010, 02:14:51 am » posted from:Islamabad,Islamabad,Pakistan

hello professor i read your equations about 2d collision but did not understand these steps

// Projection of the velocities in these axes double va1=(vx1*ax+vy1*ay), vb1=(-vx1*ay+vy1*ax); double va2=(vx2*ax+vy2*ay), vb2=(-vx2*ay+vy2*ax); // New velocities in these axes (after collision): ed<=1, for elastic collision ed=1 double vaP1=va1 + (1+ed)*(va2-va1)/(1+mass1/mass2); double vaP2=va2 + (1+ed)*(va1-va2)/(1+mass2/mass1); // Undo the projections vx1=vaP1*ax-vb1*ay; vy1=vaP1*ay+vb1*ax;// new vx,vy for ball 1 after collision vx2=vaP2*ax-vb2*ay; vy2=vaP2*ay+vb2*ax;// new vx,vy for ball 2 after collision

why we need vb1 and vb2 ?? and also what is your means by undo projection.. actually sir i am doing work on molecular dynamics in gas and when particals are collide we use your model of 2d collision is this correct for us to use these equations at the time of collision ??

Reply #129 on: January 05, 2010, 10:20:56 pm » posted from:Taipei,T\'ai-pei,Taiwan

In the real world, time move continuously. However, we can not do the calculation continuously. It is always a finite time step (no matter how small it might be).

The time step dt is the same during the simulation. However, collision often occurred in between time steps (between time t to t+dt).

We tried to detect if two object overlap each to know colllision should have occurred. Then, we need to find the exact time when collision occurred. If this 2D collision, we use an approximation method to find the time when collision occurred. Support the rasius of two particles are r1 and r2, and the distance between two center is d. And the relative velocity along two center is vp, then we move back time step ddt=(d-(r1+r2))/vp to find the time collision occurred. (The above approximation is only good if the relative velocity is small enrough, i.e. vp*dt< After we take care of collision, we need to move time forward ddt again.

The time step dt is the same during the simulation. However, collision often occurred in between time steps (between time t to t+dt).

We tried to detect if two object overlap each to know collision should have occurred. Then, we need to find the exact time when collision occurred. If this 2D collision, we use an approximation method to find the time when collision occurred. Support the radius of two particles are r1 and r2, and the distance between two center is d. And the relative velocity along two center is vp, then we move back time step ddt=(d-(r1+r2))/vp to find the time collision occurred. (The above approximation is only good if the relative velocity is small enough, i.e. vp*dt< After we take care of collision, we need to move time forward ddt again.

This is a computational logic that i only appreciated and understood after using Ejs to make simulations, because i was trying to do the same thing. "detect if two object overlap each to know collision should have occurred."

In Ejs i think it is called Event Handlers. Thanks! it is good explanation.

Reply #132 on: July 23, 2010, 08:07:04 pm » posted from:Mumbai,Maharashtra,India

If you do not believe that the bounding box collision would be good for your preflight you should try the circle of its bounding box .. then it really does not matter. Check two circles overlap is much easier to see, too, at least in my opinion.

double dx = x2-x1, dy = y2-y1; // where x1,y1 are center of ball1, and x2,y2 are center of ball2 double distance = sqrt(dx*dx+dy*dy); // Unit vector in the direction of the collision double ax=dx/distance, ay=dy/distance; // Projection of the velocities in these axes double va1=(vx1*ax+vy1*ay), vb1=(-vx1*ay+vy1*ax); double va2=(vx2*ax+vy2*ay), vb2=(-vx2*ay+vy2*ax); // New velocities in these axes (after collision): ed<=1, for elastic collision ed=1 double vaP1=va1 + (1+1)*(va2-va1)/(1+1); double vaP2=va2 + (1+1)*(va1-va2)/(1+1); // Undo the projections vx1=vaP1*ax-vb1*ay; vy1=vaP1*ay+vb1*ax;// new vx,vy for ball 1 after collision vx2=vaP2*ax-vb2*ay; vy2=vaP2*ay+vb2*ax;// new vx,vy for ball 2 after collision

double dx = x2-x1, dy = y2-y1; // where x1,y1 are center of ball1, and x2,y2 are center of ball2 double distance = sqrt(dx*dx+dy*dy); // Unit vector in the direction of the collision double ax=dx/distance, ay=dy/distance; // Projection of the velocities in these axes double va1=(vx1*ax+vy1*ay), vb1=(-vx1*ay+vy1*ax); double va2=(vx2*ax+vy2*ay), vb2=(-vx2*ay+vy2*ax); // New velocities in these axes (after collision): ed<=1, for elastic collision ed=1 double vaP1=va1 + (1+1)*(va2-va1)/(1+1); double vaP2=va2 + (1+1)*(va1-va2)/(1+1); // Undo the projections vx1=vaP1*ax-vb1*ay; vy1=vaP1*ay+vb1*ax;// new vx,vy for ball 1 after collision vx2=vaP2*ax-vb2*ay; vy2=vaP2*ay+vb2*ax;// new vx,vy for ball 2 after collision

the same in both programs. example: ballspeedx=0;ballspeedy=4;balltwospeedx=0;balltwospeedy=-4;

3. After the collision the ball is stopped and disappear from the screen. vx1 ,vy1,vx2,vy2 values is -2145444... please help me, collision problems like this a month to go before me...

Reply #134 on: September 05, 2010, 09:45:39 pm » posted from:,,Taiwan

The above code works under the following assumption: v*dt<< R, where R is the radius of the ball. It means that the time step need to be chose properly.

double dx = x2-x1, dy = y2-y1; // where x1,y1 are center of ball1, and x2,y2 are center of ball2 double distance = sqrt(dx*dx+dy*dy); // Unit vector in the direction of the collision double ax=dx/distance, ay=dy/distance; // Projection of the velocities in these axes double va1=(vx1*ax+vy1*ay), vb1=(-vx1*ay+vy1*ax); double va2=(vx2*ax+vy2*ay), vb2=(-vx2*ay+vy2*ax); // New velocities in these axes (after collision): ed<=1, for elastic collision ed=1 double vaP1=va1 + (1+1)*(va2-va1)/(1+1); double vaP2=va2 + (1+1)*(va1-va2)/(1+1); // Undo the projections vx1=vaP1*ax-vb1*ay; vy1=vaP1*ay+vb1*ax;// new vx,vy for ball 1 after collision vx2=vaP2*ax-vb2*ay; vy2=vaP2*ay+vb2*ax;// new vx,vy for ball 2 after collision

Reply #136 on: September 10, 2010, 05:40:28 pm » posted from:Montefalco,Umbria,Italy

Hi!

I have some problems to manage 3D Collisions!!! I try to transform this 2D collision detection into 3d collision detection, but I have some problems to compute the dt!!!

Sometimes, I have dt>>1.

Anyone has some simple ideas to transform this 2d collision to 3d collision detection?

Reply #140 on: September 10, 2010, 11:50:11 pm » posted from:,,Taiwan

I do not understand the way you defined those angle? I would suggest you use (x,y,z) coordinate.

Assume and are center of those two balls. And the radius are . Let which is the relative vector between two centers. Collision occurred if the length : The next step is to find two components of velocity vectors : 1. velocity components parallel to

The time step to move backward

Hints: how to calculate inner product

2. velocity components perpendicular to

The above two component will not change before and after collision

I do not understand the way you defined those angle? I would suggest you use (x,y,z) coordinate.

Assume and are center of those two balls. And the radius are . Let which is the relative vector between two centers. Collision occurred if the length math_failure (math_unknown_error): |\vec{d}|<R_a+R_b
: The next step is to find two components of velocity vectors : 1. velocity components parallel to

The time step to move backward

Hints: how to calculate inner product

2. velocity components perpendicular to

The above two component will not change before and after collision

Reply #143 on: September 24, 2010, 09:45:07 pm » posted from:Detroit,Michigan,United States

Hi professor, quick question:

What dictates the direction of the normal vector? While i understand that it's perpendicular to the angle of collision(AoC), what determines whether its AoC+PI/2 or AoC-PI/2?

Reply #145 on: October 07, 2010, 12:35:22 pm » posted from:Jakarta,Jakarta Raya,Indonesia

Sir, I'm implementing 2d collision on objective - c using opengl. but it didn't work . if i didn't calculate and apply dt to ball 1 position (translation) , the ball is stuck together (but it is moving) . but if i apply dt, the ball seems going messy when collideed. can you see what is going on with the code? the variable dt can be minus when check through console, is it right?

CGFloat r1,r2; r1 = r2 = self.collider.maxRadius; CGFloat dx=collideeTranslation.x-translation.x, dy=collideeTranslation.y-translation.y; CGFloat d=sqrt(dx*dx+dy*dy); //First calculate the component of velocity in the direction of (dx,dy) CGFloat vp1= speed.x*dx/d+speed.y*dy/d; CGFloat vp2= collideeSpeed.x*dx/d+collideeSpeed.y*dy/d; //Collision should have happened dt before you have detected r1+r2 CGFloat dt = (r1+r2-d)/(vp1-vp2);// the collision should have occurred at t-dt (Actually this is also an approximation).

//So you should move those two ball backward translation.x -= speed.x*dt; translation.y -= speed.y*dt; collideeTranslation.x -=collideeSpeed.x*dt; collideeTranslation.y-=collideeSpeed.y*dt;

dx=collideeTranslation.x-translation.x, dy=collideeTranslation.y-translation.y; // where x1,y1 are center of ball1, and x2,y2 are center of ball2 CGFloat distance = sqrt(dx*dx+dy*dy); // Unit vector in the direction of the collision CGFloat ax=dx/distance, ay=dy/distance; // Projection of the velocities in these axes CGFloat va1=(speed.x*ax+speed.y*ay), vb1=(-speed.x*ay+speed.y*ax); CGFloat va2=(collideeSpeed.x*ax+speed.y*ay), vb2=(-collideeSpeed.x*ay+collideeSpeed.y*ax); // New velocities in these axes (after collision): ed<=1, for elastic collision ed=1 CGFloat ed = 0.8; CGFloat vaP1=va1 + (1+ed)*(va2-va1)/(1+self.mass/collideeMass); CGFloat vaP2=va2 + (1+ed)*(va1-va2)/(1+collideeMass/self.mass); // Undo the projections speed.x=vaP1*ax-vb1*ay; speed.y=vaP1*ay+vb1*ax;// new vx,vy for ball 1 after collision collideeSpeed.x=vaP2*ax-vb2*ay; collideeSpeed.y=vaP2*ay+vb2*ax;// new vx,vy for ball 2 after collision

//Because we have move time backward dt, we need to move time forward dt. translation.x+= speed.x*dt; translation.y+= speed.y*dt; collideeTranslation.x+=collideeSpeed.x*dt; collideeTranslation.x+=collideeSpeed.y*dt;

Reply #146 on: October 07, 2010, 04:49:43 pm » posted from:Taipei,T'ai-pei,Taiwan

The problem could be due to the parameters used in the simulation.

The above model of calculation assume: the time step is small enough so that the distance move in each time step is smaller than the radius of both particles.

The problem you found much be due to the time step is too large or the velocity is too large.

1. r1 and r2 are about the same or similar order. 2. v_1 *dt<< r_1+r_2 , v_2*dt<< r_1+r_2

Reply #147 on: October 08, 2010, 01:50:18 am » posted from:Jakarta,Jakarta Raya,Indonesia

Quote

The problem could be due to the parameters used in the simulation.

The above model of calculation assume: the time step is small enough so that the distance move in each time step is smaller than the radius of both particles.

The problem you found much be due to the time step is too large or the velocity is too large.

1. r1 and r2 are about the same or similar order. 2. v_1 *dt<< r_1+r_2 , v_2*dt<< r_1+r_2

What should i change if the velocity is too large or the time step is too large? (I'm using 60 frame per second in the simulation)

Reply #148 on: October 08, 2010, 03:14:36 pm » posted from:Taipei,T'ai-pei,Taiwan

Make the velocity smaller or change the time step to smaller value.

May be you are updating the view 60frame per second. You can make the time step 1/600 second, and update the view every 10 second. So it is up to you to change the time step to any suitable precision you want.

Reply #149 on: October 08, 2010, 04:04:36 pm » posted from:Jakarta,Jakarta Raya,Indonesia

Sir, why the dt can be result of nan? what can cause that? how to solve it? and i found that when ball1 collideed with ball2 with mass1/mass2 = 1.0, velocity x ball1 200 , velocity x ball 2 -100 (moving opposite) and ed = 0.8, ball1 didn't bounce a bit, instead ball1 just moving forward.

« Last Edit: October 08, 2010, 04:31:22 pm by lunayo »