[Game Maker] Pathfinding

edited in Questions and Answers
Game Maker 8.1 Lite Pathfinding

Hi

I am trying to get my character to where I left click my mouse while avoiding solid objects. Thusfar I have managed to get just about all the way there (except not at all) by setting waypoint objects that won't be displayed, where I click and then the toon will move there with the move functions. The move functions however will not avoid solid objects, so I used step avoiding, which works great, except that as soon as you let go of the mouse button the toon stops. I have tried all of the left mouse button events and they all do this. I have also tried the various mp_step commands via script and I can manage to do exactly what 'step avoiding' does.

Basically, where is the 'move avoiding' (as opposed to the 'step avoiding') option? Nowehere it seems and I suppose there is a reason for that. I can definitely just not have 'pathfinding' and keep it simpler that way, but why should I when I am this close.

How do I solve this, any advice?

image

Comments

  • edited
    Welcome to the forums!

    Mouse events happen only when the mouse is clicked (or held down). In order to have something continue happening when the mouse is released, it needs to be in the Step event, which occurs once every frame.

    There is no "Move Avoiding", so we need to implement that logic ourselves. Try this:

    First we need two variables to store the coordinates of the mouse click:

    Create event:
    
    Set variable: name = "destinationX", value = "x"
    Set variable: name = "destinationY", value = "y"


    Now we need to store the position of a mouse click in those variables:

    Global Left Pressed event:
    
    Set variable: name = "destinationX", value = "mouse_x"
    Set variable: name = "destinationY", value = "mouse_y"


    Finally, we need to make the object move towards that destination in every frame:

    Step event:
    
    Step avoiding: x = "destinationX", y = "destinationY", speed = "2", avoid = "solid only"


  • Thanks very much for the welcome and waaaay more so for your detailed response. I have spent more than 8 hours trying to figure that out and can now see that I would never have without help.

    At the very least I have now learnt exactly what the step event is for and I can see how the correct way in stead of the waypoint objects I used to try and force a solution.

    Mostly though, IT WORKS!!! :)

    Thanks again!


  • edited
    I have now added 'change sprite' to an animation of the toon walking when the left mouse is pressed and then ofc the toon is now also walking to the position when the left mouse button was clicked, all the while avoiding solid objects... brilliant.

    How do I change the sprite back to the static one once he reaches his destination and stops?

    I have tried 'end step' as well as 'animation end' events, but both will then only play the animation sequence once, regardless if the toon instance has reached the destination or not.

    So, the logic of what I'm trying to do:

    - If instance reaches destination, change sprite to

    While I'm at it... is there a way to check movement direction and perform actions accordingly? More specifically: I have sprites for standing still is well as animation sprites for walking in 8 cardinal directions. It would be brilliant (even though I could live without this) if I could do some sort of logic that says:

    - If instance is moving in direction range(x:y), change sprite to

    for each of the 8 direction ranges. Which would ofc mean that my toon would have a sprite facing in the direction he is moving with animation and facing the appropriate static direction when he reaches his destination.
  • An easy way to check when your character has reached its destination is simply to compare the coordinates. As for the cardinal directions, you can make use of the built in direction variable.

    Here is some script to try:

    if (x == destinationX and y == destination Y)
    {
    
        sprite_index = standing_spr;
    
    } else {
    
       //North
       if (direction >= 67.5 and direction < 112.5)
       {
           sprite_index = walkingNorth_spr;
       }
    
       //North west
       if (direction >= 112.5 and direction < 157.5)
       {
           sprite_index = walkingNorthWest_spr;
       }
    
       //Repeat for remaining cardinals...
    
    }


    Again, we want these checks to happen every frame, so put this code in the step event. The same thing can be done with the drag-and-drop interface, but it's often cleaner and less confusing to write code instead.
  • edited
    sprite_index = ((direction + 45) div 90) mod 4;


    or, generalised:

    numSprites = 4;
    degreesPerSprite = 360 / numSprites;
    sprite_index = (direction + (degreesPerSprite / 2)) div degreesPerSprite) mod numSprites;


    ;P
Sign In or Register to comment.