Legacy GM [SOLVED] Collisions: 'Buttery Smooth' with hspeed, vspeed


I have attempted to implement the "Buttery Smooth Movement" wall collision tech blog project, using hspeed and vspeed instead of the single direction variable, with limited success; the object gets stuck in the wall.
Would anyone have any tips on how to fix it?

image_angle = point_direction(x, y, mouse_x, mouse_y);
acceleration = 1;
var xtarg = 0;
var ytarg = 0;

var _c = dcos(image_angle);
var _s = dsin(image_angle);

h_speed += acceleration * (keyboard_check(ord("W")) - keyboard_check(ord("S")));
v_speed += acceleration * (keyboard_check(ord("D")) - keyboard_check(ord("A")));

var xtarg = x + lengthdir_x(h_speed, image_angle);
var ytarg = y + lengthdir_y(v_speed, image_angle);
if (place_free(xtarg, ytarg))
    x += _c * h_speed + _s * v_speed; // cos * hspeed + sin * vspeed
    y += _c * v_speed - _s * h_speed; // cos * vspeed - sin * hspeed

    var sweep_interval = 10;
    for (var angle = sweep_interval; angle <= 180; angle += sweep_interval)
        for (var multiplier = -1; multiplier <= 1; multiplier += 8)
            var angle_to_check = image_angle + angle * multiplier;
            xtarg = x + lengthdir_x(h_speed, angle_to_check) + _c * h_speed + _s * v_speed;
            ytarg = y + lengthdir_y(v_speed, angle_to_check) + _c * v_speed - _s * h_speed;
           if (place_free(xtarg, ytarg))
                x = xtarg + _c * h_speed + _s * v_speed;
                y = ytarg + _c * v_speed - _s * h_speed;

Last edited:


When you change the image_angle, the collision box changes its size to envelop the whole sprite, it does not rotate with the sprite. You could try using an instance variable in the place of image_angle and then in the draw event use draw_sprite_ext which has a parameter for the angle at which you wish to draw the sprite. You'd rhen just pass your own angle variable here.
That's some interesting information there Paskaler! I did what you suggested, and, after experimenting I believe the object no longer gets stuck in the wall. However, it is not "buttery smooth", and I need to "reverse" the object out of the wall before it can move again.

// using _image_angle, not image_angle, also used this variable in step event

draw_sprite_ext(spr_test_object, 0, x, y, 1, 1, _image_angle, c_white, 1);
Hello again,
After further testing, I can see that the player object does slide against the wall, but only after it has begun moving at an unusual angle -- pointing in one direction, but moving in a direction slightly different from that direction.
Mathematically, I am unsure how to proceed. I've attached a link to the mini project dedicated to testing this problem, if anyone wouldn't mind taking a look.
Please allow me to bump this, with an image for further clarification. (the project link above is still active)

So from the looks of it, the player can face in 8 directions in your game instead of 4 correct?
I suggest you change your player collision mask to a sphere shape, which should eliminate all of the corners on the player object and should give you smooth movement at every angle.
The player can face in 360 directions, as they point in the direction of the mouse. Nice suggestion Silver_Mantis, I changed the sprite collision mask to an ellipse, sadly however this did not solve the problem. I suspect it has to do with the math/angles I am using.