Collision problem

This topic is 4934 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

Recommended Posts

Hi I have two circles when they collide I trade their velocities just for right now, but it seems sometimes they stick together, thats probably because I trade the velocities and i keeps trading it because its colliding, the way I want to deal with this is pull them apart so there not colliding anymore and then trade their velocities. Would I need to find out the angle they collide at? I dont know how to do any of this, If there is a better way please let me know, or if you know a way to do it the way im thinking, thanks.

Share on other sites
For my E-Motion remake, which is all about colliding spheres, I used the info on this subject from this page:

Collision detection in AniSprite

Very clearly written, with illustrations and everything.

Share on other sites
I don't understand a single word on there, I am really lost.

Share on other sites
it's using te reflection angle. I prefer the vector maths version. Much easier. Incidently, this is also tied with Newton's principle of the conservation of momentum for elastic collisions.

1) Newton's laws of physics
2) vector maths, trigonometry, linear algebra. And possibly matrices if you wanna go one step further.

That's all there is. You can't do game phyiscs without those well covered. Most of it is A-level phyiscs and maths.

If you do understand those principles, maybe this will help.

http://www.gamedev.net/community/forums/topic.asp?topic_id=318145

Share on other sites
If it helps, here is the (simplified) function that handles the sphere collisions in my game E-Motion Deluxe. I left out the big-small-sphere collision and the new-sphere-spawn part, because that is irrelevant here. It is written in BlitzBasic, a BASIC language, and i'll explain a few things that are particular to this specific basic "dialect" so you'll understand.

For example the code Spheres(4)\ySpeed# means, look in the array called Spheres, take the 4th record and look at the ySpeed# variable (or "property") of that record. In BlitzBasic a # (pound sign) means it is a floating point variable or constant. All variables without a # are integers. And the ; (semi-colon) is the comment indicator.

So here goes. [grin]

Const THRESHOLD_FORCE# = 0.1; Nr1, Nr2 are Spheres array indexes; X1#, Y1# and X2#, Y2# are the centre position of the 2 spheresFunction HandleSphereCollision(Nr1, Nr2, X1#, Y1#, X2#, Y2#)  ; collision angle, angle of line through centre of the spheres  CollisionAngle = ATan2((Y2 - Y1), (X2 - X1))  ; align sphere speed vectors to the collision angle  AngleBall1 = ATan2(Spheres(Nr1)\ySpeed#, Spheres(Nr1)\xSpeed#) - CollisionAngle  AngleBall2 = ATan2(Spheres(Nr2)\ySpeed#, Spheres(Nr2)\xSpeed#) - CollisionAngle  ;preserve kinetic energy, E(k), the speed vector  Ek1# = Sqr((Spheres(Nr1)\ySpeed#^2) + (Spheres(Nr1)\xSpeed#^2)) ; ^2 means to the 2nd power  Ek2# = Sqr((Spheres(Nr2)\ySpeed#^2) + (Spheres(Nr2)\xSpeed#^2))  ;speed vectors aligned, so now the x-axis IS the collision angle, swap the x-vectors  CollisionXspeed1# = Ek1# * Cos(AngleBall1)  CollisionYspeed1# = Ek1# * Sin(AngleBall1)  CollisionXspeed2# = Ek2# * Cos(AngleBall2)  CollisionYspeed2# = Ek2# * Sin(AngleBall2)  ; if spheres are already moving away from each other, then they cannot collide  ; this situation can occur when spheres is spawned, and overlaps another sphere  If ((CollisionXspeed2# - CollisionXspeed1#) < 0) Then    ;spheres not already moving away, so swap the x-vectors    tmpX# = CollisionXspeed1#    CollisionXspeed1# = CollisionXspeed2#    CollisionXspeed2# = tmpX#  End If  ; when colliding, spheres MUST move away from each other, must have at least some speed  If (CollisionXspeed1# > -1*THRESHOLD_FORCE#) Then CollisionXspeed1# = -1 * THRESHOLD_FORCE#  If (CollisionXspeed2# < THRESHOLD_FORCE#) Then CollisionXspeed2# = THRESHOLD_FORCE#  ;preserve new calculated kinetic energy  Ek1# = Sqr(CollisionYspeed1#^2 + CollisionXspeed1#^2) ; ^2 means to the 2nd power  Ek2# = Sqr(CollisionYspeed2#^2 + CollisionXspeed2#^2)  ;reverse aligning speed vectors  AngleBall1 = ATan2(CollisionYspeed1, CollisionXspeed1) + CollisionAngle  AngleBall2 = ATan2(CollisionYspeed2, CollisionXspeed2) + CollisionAngle  ;store new xSpeed and ySpeed values  Spheres(Nr1)\xSpeed# = Ek1# * Cos(AngleBall1)  Spheres(Nr1)\ySpeed# = Ek1# * Sin(AngleBall1)  Spheres(Nr2)\xSpeed# = Ek2# * Cos(AngleBall2)  Spheres(Nr2)\ySpeed# = Ek2# * Sin(AngleBall2)End Function

[Edited by - BdR on June 1, 2005 1:14:59 PM]

Share on other sites
thanks for all the help guys.
BdR I tried to implement your code but when the two circles touch they disappear, I put a break point to see what where there new velocities and they seem fine.

Share on other sites
I put about 50 circles moving around and somtimes it works, but mostly when the two circles touch the disappear or go up in the top left corner.

Share on other sites
he is using divisions. Check for divide by zeroes, and generally values of vectors. If it works most of the time, likely to be a math bug. can't help you with that.

Share on other sites
No, i'm not using division in my example, there is no dividing at all. Remember that in code Spheres(Nr1)\xSpeed#, the \ (backslash) is a property indicator, not a division operator. Division is done with a / (slash) it's a bit confusing, i know..

In Visual Basic code it would look something like this Spheres(Nr1).xSpeed so which programming language do you use anyway?

Share on other sites
I am using C# .net
here is my code

public void TradeVelocity(xVolume volume)		{			double THRESHOLD_FORCE = 0.1f;			double x1, y1, x2, y2;			x1 = XPos + Radius;			y1 = YPos + Radius;			x2 = volume.XPos + volume.Radius;			y2 = volume.YPos + volume.Radius;			double CollisionAngle = Math.Atan2((y2 - y1), (x2 - x1));			double AngleBall1 = Math.Atan2(velocity.Y, velocity.X) - CollisionAngle;			double AngleBall2 = Math.Atan2(volume.velocity.Y, volume.velocity.X) - CollisionAngle;			double ek1 = (velocity.Y * velocity.Y) + (velocity.X * velocity.X);			ek1 = ek1 * ek1;			double ek2 = (volume.velocity.Y * volume.velocity.Y) + (volume.velocity.X * volume.velocity.X);			ek2 = ek2 * ek2;			Vector3 CollisionSpeed1;			CollisionSpeed1.X = (float)(ek1 * Math.Cos(AngleBall1));			CollisionSpeed1.Y = (float)(ek1 * Math.Sin(AngleBall1));			Vector3 CollisionSpeed2;			CollisionSpeed2.X = (float)(ek2 * Math.Cos(AngleBall2));			CollisionSpeed2.Y = (float)(ek2 * Math.Sin(AngleBall2));			if((CollisionSpeed2.X - CollisionSpeed1.X) < 0)			{				float tempX = CollisionSpeed1.X;				CollisionSpeed1.X = CollisionSpeed2.X;				CollisionSpeed2.X = tempX;			}			if(CollisionSpeed1.X > -1 * THRESHOLD_FORCE)			{				CollisionSpeed1.X = -1 * (float)(THRESHOLD_FORCE);			}			if(CollisionSpeed2.X < THRESHOLD_FORCE)			{				CollisionSpeed2.X = (float)(THRESHOLD_FORCE);			}			ek1 = (CollisionSpeed1.Y * CollisionSpeed1.Y) + (CollisionSpeed1.X * CollisionSpeed1.X);			ek1 = ek1 * ek1;			ek2 = (CollisionSpeed2.Y * CollisionSpeed2.Y) + (CollisionSpeed2.X * CollisionSpeed2.X);			ek2 = ek2 * ek2;			AngleBall1 = Math.Atan2(CollisionSpeed1.Y, CollisionSpeed1.X) + CollisionAngle;			AngleBall2 = Math.Atan2(CollisionSpeed2.Y, CollisionSpeed2.X) + CollisionAngle;			velocity.X = (float)(ek1 * Math.Cos(AngleBall1));			velocity.Y = (float)(ek1 * Math.Sin(AngleBall1));			volume.velocity.X = (float)(ek2 * Math.Cos(AngleBall2));			volume.velocity.Y = (float)(ek2 * Math.Sin(AngleBall2));		}

1. 1
2. 2
3. 3
Rutin
19
4. 4
khawk
14
5. 5
frob
12

• 9
• 11
• 11
• 23
• 12
• Forum Statistics

• Total Topics
633657
• Total Posts
3013198
×