Jump to content
  • Advertisement
Sign in to follow this  
escudo825

2d collision problems

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

If you intended to correct an error in the post then please contact us.

Recommended Posts

I'm doing some simple 2d collision detection and everything worked fine, I think. but when I threw in some very simple physics some collisions didn't work. for some reason about half the time on top or bottom collisions the sprite passes through another. but the left/right collisions work fine. does anyone know what could be wrong wrong?
for (i = 0; i < NUM_SPRITES; i++)
	{
		if (i != sprite)
		{	
			//top collisions
			RECT1.top = g_Sprite[sprite].fPosY;
			RECT1.left = g_Sprite[sprite].fPosX;
			RECT1.bottom = g_Sprite[sprite].fPosY + SPRITE_DIAMETER;
			RECT1.right = g_Sprite[sprite].fPosX + SPRITE_DIAMETER;

			RECT2.top = g_Sprite.fPosY + g_Sprite.fVelX;
			RECT2.left = g_Sprite.fPosX;
			RECT2.bottom = g_Sprite.fPosY - SPRITE_DIAMETER + g_Sprite.fVelX;
			RECT2.right = g_Sprite.fPosX + SPRITE_DIAMETER;

			collision = IntersectRects(RECT1, RECT2);

			if (collision == true)
			{
				hold = (-g_Sprite.fVelY + g_Sprite[sprite].fVelY)/2;
				g_Sprite.fVelY = hold;
				g_Sprite[sprite].fVelY = -hold;
			}	
		}
	}

	for (i = 0; i < NUM_SPRITES; i++)
	{
		if (i != sprite)
		{	
			//bottom collisions
			RECT1.top = g_Sprite[sprite].fPosY;
			RECT1.left = g_Sprite[sprite].fPosX;
			RECT1.bottom = g_Sprite[sprite].fPosY + SPRITE_DIAMETER;
			RECT1.right = g_Sprite[sprite].fPosX + SPRITE_DIAMETER;

			RECT2.top = g_Sprite.fPosY + g_Sprite.fVelX;
			RECT2.left = g_Sprite.fPosX;
			RECT2.bottom = g_Sprite.fPosY + SPRITE_DIAMETER + g_Sprite.fVelX;
			RECT2.right = g_Sprite.fPosX + SPRITE_DIAMETER;

			collision = IntersectRects(RECT1, RECT2);

			if (collision ==  true)
			{
				 hold = (g_Sprite.fVelY + -g_Sprite[sprite].fVelY)/2;
				 g_Sprite.fVelY = -hold;
				 g_Sprite[sprite].fVelY = hold;
			}	
		}
	}

	for (i = 0; i < NUM_SPRITES; i++)
	{
		if (i != sprite)
		{	
			//left collisions
			RECT1.top = g_Sprite[sprite].fPosY;
			RECT1.left = g_Sprite[sprite].fPosX;
			RECT1.bottom = g_Sprite[sprite].fPosY + SPRITE_DIAMETER;
			RECT1.right = g_Sprite[sprite].fPosX + SPRITE_DIAMETER;

			RECT2.top = g_Sprite.fPosY;
			RECT2.left = g_Sprite.fPosX + g_Sprite.fVelX;
			RECT2.bottom = g_Sprite.fPosY + SPRITE_DIAMETER;
			RECT2.right = g_Sprite.fPosX + SPRITE_DIAMETER + g_Sprite.fVelX;

			collision = IntersectRects(RECT1, RECT2);

			if (collision == true)
			{
				hold = (-g_Sprite.fVelX + g_Sprite[sprite].fVelX)/2;
				g_Sprite.fVelX = hold;
				g_Sprite[sprite].fVelX = -hold;				
			}	
		}
	}

	for (i = 0; i < NUM_SPRITES; i++)
	{
		if (i != sprite)
		{	
			//right collisions
			RECT1.top = g_Sprite[sprite].fPosY;
			RECT1.left = g_Sprite[sprite].fPosX;
			RECT1.bottom = g_Sprite[sprite].fPosY + SPRITE_DIAMETER;
			RECT1.right = g_Sprite[sprite].fPosX + SPRITE_DIAMETER;

			RECT2.top = g_Sprite.fPosY;
			RECT2.left = g_Sprite.fPosX + g_Sprite.fVelX;
			RECT2.bottom = g_Sprite.fPosY + SPRITE_DIAMETER;
			RECT2.right = g_Sprite.fPosX + SPRITE_DIAMETER + g_Sprite.fVelX;

			collision = IntersectRects(RECT1, RECT2);

			if (collision == true)
			{
				hold = (g_Sprite.fVelX + -g_Sprite[sprite].fVelX)/2;
				g_Sprite.fVelX = -hold;
				g_Sprite[sprite].fVelX = hold;
			}	
		}
	}

p.s. if you need to see anything else ask and I'll post it.

Share this post


Link to post
Share on other sites
Advertisement
that method seems to work fine. but here you go just in case:


bool IntersectRects(RECT rect1, RECT rect2)
{
if (rect1.right > rect2.left)
{
if (rect1.left < rect2.right)
{
if (rect1.top < rect2.bottom)
{
if (rect1.bottom > rect2.top)
{
return true;
}
}
}
}
return false;
}

Share this post


Link to post
Share on other sites
That's a one-way collision comparison - that is, you'd have to call IntersectRects(r1, r2) AND IntersectRects(r2, r1) to get a valid collision detection. You can write a rectangular collision detection function that goes both ways without too much trouble, though.

Share this post


Link to post
Share on other sites
Guest Anonymous Poster
No, that rectangle collision detection appears to be correct.

On the other hand:

RECT2.top = g_Sprite.fPosY + g_Sprite.fVelX;
RECT2.bottom = g_Sprite.fPosY - SPRITE_DIAMETER + g_Sprite.fVelX;

RECT2.top = g_Sprite.fPosY + g_Sprite.fVelX;
RECT2.bottom = g_Sprite.fPosY + SPRITE_DIAMETER + g_Sprite.fVelX;

Unless there's some sort of explanation for why x velocities are being added to y positions, I think this could be the problem.

Share this post


Link to post
Share on other sites
that may be the problem, I thought I fixed that :(. well I'm not at a computer with a compiler right now so I can't do anything. but if it works then I'll say, if not I'll say anyway.

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

We are the game development community.

Whether you are an indie, hobbyist, AAA developer, or just trying to learn, GameDev.net is the place for you to learn, share, and connect with the games industry. Learn more About Us or sign up!

Sign me up!