We help IT Professionals succeed at work.

We've partnered with Certified Experts, Carl Webster and Richard Faulkner, to bring you a podcast all about Citrix Workspace, moving to the cloud, and analytics & intelligence. Episode 2 coming soon!Listen Now

x

How to jump with gravity always pulling down

jschmuff
jschmuff asked
on
Medium Priority
3,667 Views
Last Modified: 2013-12-08
I have created a program that makes my blob fall from the sky and when it hits the block sprite it stops from falling. If I walk off of it I fall again (When I fall past a certain spot I come back from the top just to make it easier to work with for now). Anyways, but one of my problems here is my collision isn't working properly, I am going about half way into the object before I stop. So how can I fix that?

My next problem is jumping with the gravity being consistent, I press space but I only go up a very small amount and I am back down. I can I fix this so I jump say about 200 pixels high and then gravity kicks back in and pulls me down again? I want to fix this problem with the gravity not being set to 0 all the time. (If that is possible).

Here is my code(C++),

//set sprites properties
	blob.x = 150;
	blob.y = 0;
	blob.width = 64;
	blob.height = 64;
	blob.speed.x = 0;
	blob.speed.y = 0;
	blob.accel.x = 2;
	blob.accel.y = 10;
	blob.direct.x = 0;
	blob.direct.y = 0;
	blob.gravity = 2;
	blob.inAir = true;
 
	land.x = 100;
	land.y = SCREEN_HEIGHT - 192;
	land.width = 800;
	land.height = 64;
 
	block.x = 400;
	block.y = land.y - 64;
	block.width = 64;
	block.height = 64;
 
//collision function
int Collision(SPRITE sprite1, SPRITE sprite2)
{
	RECT rect1;
    rect1.left = sprite1.x + 1;
    rect1.top = sprite1.y + 1;
    rect1.right = sprite1.x + sprite1.width - 1;
    rect1.bottom = sprite1.y + sprite1.height - 1;
 
    RECT rect2;
    rect2.left = sprite2.x + 1;
    rect2.top = sprite2.y + 1;
    rect2.right = sprite2.x + sprite2.width - 1;
    rect2.bottom = sprite2.y + sprite2.height - 1;
 
	RECT dest;
	return IntersectRect(&dest, &rect1, &rect2);
}
 
//jump function
void jump()
{
	if(!blob.inAir) //if inAir = false
	{
		blob.inAir = true;
		blob.direct.y = -1;
		blob.speed.y += blob.accel.y;
	}
 
}
 
//movement function
void movement()
{
	if(Key_Down(DIK_LEFT))
	{
		blob.speed.x += blob.accel.x;
		blob.direct.x = -1;
		if(blob.speed.x > 8) //allow only a certain speed
			blob.speed.x = 8;
	}
	else if(Key_Down(DIK_RIGHT))
	{
		blob.speed.x += blob.accel.x;
		blob.direct.x = 1;
		if(blob.speed.x > 8) //allows only a certain speed
			blob.speed.x = 8;
	}
	else
		blob.speed.x = 0; //if I am not pressing button my speed is 0
 
	if(Key_Down(DIK_SPACE))
	{
		jump(); //call to jump function
	}
}
//check collision function
void checkCollision()
{
	if(Collision(blob, land))
	{
		blob.speed.y = 0;
		blob.direct.y = 0;
		blob.inAir = false;
	}
	else if(!Collision(blob, land))
	{
		blob.speed.y += blob.gravity;
		blob.direct.y = 1;
		blob.inAir = true;
	}
}
 
//update function
void update()
{
	blob.x += blob.speed.x * blob.direct.x;
	blob.y += blob.speed.y * blob.direct.y;
 
	if(blob.inAir == true)
	{
		blob.direct.y = 1;
		if(blob.speed.y > 30)
			blob.speed.y = 30;
	}
 
	if(blob.y >= SCREEN_HEIGHT + 64)
	{
		blob.y = -64;
	}
}

Open in new window

Comment
Watch Question

Here are some pointers:
In your checkCollision function - no need to call Collision twice - not effective ,
change to:
if(Collision(blob, land))
{
blob.speed.y = 0;
blob.direct.y = 0;
blob.inAir = false;
}
else {
blob.speed.y += blob.gravity;
blob.direct.y = 1;
blob.inAir = true;
}
 
In you update function:
if(blob.inAir == true)
{
blob.direct.y = 1; <=====
You are effectively reversing the direction of the blob so that the next update call will reverce the speed as well wich probably just a little smaller then the initial speed of the jump due to gravity (I also don't see you calling checkCollision anywhere but I imagine you do...)
So instead you should just reduce the speed (up)  by the gravity until it reached zero... then reverse direction and increase with gravity.
 
Hope it helps.


Not the solution you were looking for? Getting a personalized solution is easy.

Ask the Experts

Commented:
Is IntersectRect in your sample the windows version?

If so, you might be running into issues because you haven't normalized the rectangles that you're comparing.

Basically, the longest side of each rectangle shouldn't be any bigger than 1, and the small sides should be the fractional amount that's left from (short side length)/(long side length)

Odd things result sometimes if you don't do this.

http://msdn.microsoft.com/en-us/library/dd145001(VS.85).aspx

-john
Access more of Experts Exchange with a free account
Thanks for using Experts Exchange.

Create a free account to continue.

Limited access with a free account allows you to:

  • View three pieces of content (articles, solutions, posts, and videos)
  • Ask the experts questions (counted toward content limit)
  • Customize your dashboard and profile

*This site is protected by reCAPTCHA and the Google Privacy Policy and Terms of Service apply.

OR

Please enter a first name

Please enter a last name

8+ characters (letters, numbers, and a symbol)

By clicking, you agree to the Terms of Use and Privacy Policy.