• Hey Guest! Ever feel like entering a Game Jam, but the time limit is always too much pressure? We get it... You lead a hectic life and dedicating 3 whole days to make a game just doesn't work for you! So, why not enter the GMC SLOW JAM? Take your time! Kick back and make your game over 4 months! Interested? Then just click here!

Enemy floating trough solid blocks

S

SashoTAI

Guest
So I was trying to program the code for an enemy in a platformer game. I made it so if it touches the ground (obj_solid) it follows the player. So I added the gravity and the horizontal and vertical collision but it somehow still floats trough the ground. Any ideas? Here's my code:
Create event:
  1. //Variables
  2. hspeed_ = 0;
  3. max_hspeed_= 10;
  4. vspeed_ = 0;
  5. gravity_ = 0.7;
  6. acceleration_ = 1;
  7. jump_height_ = -16;
And my step event:
  1. //Add physics
  2. if place_meeting (x + hspeed_, y, obj_solid)
  3. {
  4. while !place_meeting (x + sign(hspeed_), y, obj_solid)
  5. {
  6. x += sign(hspeed_);
  7. }
  8. hspeed_ = 0
  9. }
  10. x = x + hspeed_
  11. if place_meeting (x, y + vspeed_, obj_solid)
  12. {
  13. if instance_exists(obj_player)
  14. {
  15. move_towards_point(obj_player.x, obj_player.y, max_hspeed_)
  16. }
  17. while !place_meeting (x, y + sign(vspeed_), obj_solid)
  18. {
  19. y += sign(vspeed_);
  20. }
  21. vspeed_ = 0
  22. }
  23. y = y + vspeed_
  24. if hspeed_ != 0
  25. {
  26. hspeed_ += acceleration_;
  27. hspeed_ = clamp (hspeed_, -max_hspeed_, max_hspeed_)
  28. } else
  29. {
  30. hspeed_ = lerp (hspeed_, 0, .3)
  31. }
  32. if !place_meeting (x, y+1, obj_solid)
  33. {
  34. vspeed_ = vspeed_ + gravity_;
  35. }
The AI is also terrible, meaning that if I get on the highest block it just jumps in place XD.
 

Nocturne

Friendly Tyrant
Forum Staff
Admin
You don't want to use move_towards_point in your code there. That is moving the instance and then doing the check for the floor... so it's floating. What you want to do is simply check if the player is to the left or right of the enemy object and then set the hspeed to +/- as required.
 
S

SashoTAI

Guest
What you want to do is simply check if the player is to the left or right of the enemy object and then set the hspeed to +/- as required.
I tried this but it still doesn't seem to work:
  1. if place_meeting (x + hspeed_, y, obj_solid)
  2. {
  3. if obj_player = x
  4. {
  5. hspeed_ = 4;
  6. } else if obj_player = -x
  7. {
  8. hspeed_ = -4;
  9. } else
  10. {
  11. hspeed_ = 0;
  12. }
  13. while !place_meeting (x + sign(hspeed_), y, obj_solid)
  14. {
  15. x += sign(hspeed_);
  16. }
  17. hspeed_ = 0
  18. }
  19. x = x + hspeed_
Any ideas?
 
Last edited by a moderator:
S

SashoTAI

Guest
Has anybody got an idea on how to fix this? It will be appreciated if you leave a comment. Thanks :)
 

Simon Gust

Member
Don't check wether obj_player is x or -x, that doesn't make much sense. Check if obj_player's x is less or more than the enemy's x
Code:
if (x < obj_player.x - 10)
{
    hspeed_ = 4;
} 
else 
if (x > obj_player.x + 10)
{
    hspeed_ = -4;
}

if place_meeting (x + hspeed_, y, obj_solid)
{
    while (!place_meeting (x + sign(hspeed_), y, obj_solid))
    {
        x += sign(hspeed_);
    }
    hspeed_ = 0;
}
x = x + hspeed_;
Maybe it's even better if you handle the ai outside the collision.
 
S

SashoTAI

Guest
Don't check wether obj_player is x or -x, that doesn't make much sense. Check if obj_player's x is less or more than the enemy's x
Code:
if (x < obj_player.x - 10)
{
    hspeed_ = 4;
}
else
if (x > obj_player.x + 10)
{
    hspeed_ = -4;
}

if place_meeting (x + hspeed_, y, obj_solid)
{
    while (!place_meeting (x + sign(hspeed_), y, obj_solid))
    {
        x += sign(hspeed_);
    }
    hspeed_ = 0;
}
x = x + hspeed_;
Maybe it's even better if you handle the ai outside the collision.
Ok thank you :)
 
S

SashoTAI

Guest
Code:
if (x < obj_player.x - 10)
{
    hspeed_ = 4;
}
else
if (x > obj_player.x + 10)
{
    hspeed_ = -4;
}
Last question: why do you need to take-away 10 on the first one and add on 10 on the second one? I've told myself that I want to understand what a particular code does before going on to the next one, because it helps me remember it, so I wanted to see WHY it worked. :)
 

Simon Gust

Member
Last question: why do you need to take-away 10 on the first one and add on 10 on the second one? I've told myself that I want to understand what a particular code does before going on to the next one, because it helps me remember it, so I wanted to see WHY it worked. :)
Just a minor design choice, if you don't add / subtract them, your enemy is going to walk towards the player and start turning around wildly at the exact location of the player. The more you add / subtract, the farther they stride out before turning towards the player again.
 
S

SashoTAI

Guest
Just a minor design choice, if you don't add / subtract them, your enemy is going to walk towards the player and start turning around wildly at the exact location of the player. The more you add / subtract, the farther they stride out before turning towards the player again.
Ok thank you now I just write it down in my book. :D So if the sprite of the enemy is a square, it wouldn't matter as much if you add or take-away the tens?
 
S

SashoTAI

Guest
Don't check wether obj_player is x or -x, that doesn't make much sense. Check if obj_player's x is less or more than the enemy's x
Code:
if (x < obj_player.x - 10)
{
    hspeed_ = 4;
}
else
if (x > obj_player.x + 10)
{
    hspeed_ = -4;
}

if place_meeting (x + hspeed_, y, obj_solid)
{
    while (!place_meeting (x + sign(hspeed_), y, obj_solid))
    {
        x += sign(hspeed_);
    }
    hspeed_ = 0;
}
x = x + hspeed_;
Maybe it's even better if you handle the ai outside the collision.
So how would you make it jump so it follows the player when going vertically, too? I tried doing the same thing except with vspeed_ and y but it seems to kind of teleport it really high up so it falls again, but not really jumping. I tried this as well but it still doesn't seem to work.
  1. if keyboard_check_pressed (vk_space)
  2. {
  3. move_towards_point (obj_player.x, obj_player.x, hspeed_)
  4. } else if (x < obj_player.x)
  5. {
  6. hspeed_ = -4;
  7. } else if (x > obj_player.x)
  8. {
  9. hspeed_ = 4;
  10. } else
  11. {
  12. hspeed_ = 0;
  13. }
I tried this too:
  1. if keyboard_check_pressed (vk_space)
  2. {
  3. move_towards_point (obj_player.x, obj_player.x, hspeed_)
  4. } else if (y < obj_player.y)
  5. {
  6. vspeed_ = -4;
  7. } else if (y > obj_player.y)
  8. {
  9. vspeed_ = 4;
  10. } else
  11. {
  12. vspeed_ = 0;
  13. }
 

Simon Gust

Member
So how would you make it jump so it follows the player when going vertically, too? I tried doing the same thing except with vspeed_ and y but it seems to kind of teleport it really high up so it falls again, but not really jumping. I tried this as well but it still doesn't seem to work.
  1. if keyboard_check_pressed (vk_space)
  2. {
  3. move_towards_point (obj_player.x, obj_player.x, hspeed_)
  4. } else if (x < obj_player.x)
  5. {
  6. hspeed_ = -4;
  7. } else if (x > obj_player.x)
  8. {
  9. hspeed_ = 4;
  10. } else
  11. {
  12. hspeed_ = 0;
  13. }
I tried this too:
  1. if keyboard_check_pressed (vk_space)
  2. {
  3. move_towards_point (obj_player.x, obj_player.x, hspeed_)
  4. } else if (y < obj_player.y)
  5. {
  6. vspeed_ = -4;
  7. } else if (y > obj_player.y)
  8. {
  9. vspeed_ = 4;
  10. } else
  11. {
  12. vspeed_ = 0;
  13. }
First, you have to get rid of the move_towards_point again, it serves no purpose and breaks all other code.
The only thing you need to do for an enemy to jump is this
Code:
if (keyboard_check_pressed(vk_space))
{
     vspeed_ = -4;
}
and your gravity code should pull the enemy down by itself.
 
S

SashoTAI

Guest
First, you have to get rid of the move_towards_point again, it serves no purpose and breaks all other code.
The only thing you need to do for an enemy to jump is this
Code:
if (keyboard_check_pressed(vk_space))
{
     vspeed_ = -4;
}
and your gravity code should pull the enemy down by itself.
I tried it and it still doesn't seem to jump. Do I have to put it somewhere in the collision code?
 
S

SashoTAI

Guest
Do you mind showing all the code?
  1. //Follow the Player
  2. if (x < obj_player.x)
  3. {
  4. hspeed_ = 4;
  5. } else if (x > obj_player.x)
  6. {
  7. hspeed_ = -4;
  8. } else
  9. {
  10. hspeed_ = 0;
  11. }
  12. //Add Physics
  13. if place_meeting (x + hspeed_, y, obj_solid)
  14. {
  15. while !place_meeting (x + sign(hspeed_), y, obj_solid)
  16. {
  17. x += sign(hspeed_);
  18. }
  19. hspeed_ = 0
  20. }
  21. x = x + hspeed_
  22. if place_meeting (x, y + vspeed_, obj_solid)
  23. {
  24. while !place_meeting (x, y + sign(vspeed_), obj_solid)
  25. {
  26. y += sign(vspeed_);
  27. }
  28. vspeed_ = 0
  29. }
  30. y = y + vspeed_
  31. if !place_meeting (x, y+1, obj_solid)
  32. {
  33. vspeed_ = vspeed_ + gravity_;
  34. }
  35. if (keyboard_check_pressed(vk_space))
  36. {
  37. vspeed_ = 4;
  38. }
 

Simon Gust

Member
Ok, you need to make sure that collisions are always after physics.
Then you need to know that positive vspeed_ values make the y go down / negative vspeed_ make the y go up.
Finally you need to make sure, the enemy is on the ground when jumping.
 
S

SashoTAI

Guest
Ok, you need to make sure that collisions are always after physics.
Then you need to know that positive vspeed_ values make the y go down / negative vspeed_ make the y go up.
Finally you need to make sure, the enemy is on the ground when jumping.
Thank you! You helped me out a lot with the development of my game!
 
Top