Skip to content
Banana090 edited this page May 31, 2018 · 1 revision

Однако хочу добавить небольшое усовершенствование, связанное с некоторыми недостатками движения по диагонали в этом варианте, а именно с тем, что при движении по диагонали и использовании lengthdir_ получаются дробные значения приращений hspd и vspd и как следствие дробные координаты Х и Y.

А координаты рисования объектов должны быть целыми числами, так как координатная сетка - наш экран, а каждая единица координат - один пиксель на экране. Пиксели не могут быть дробными, поэтому и перемещение на дробные пиксели приводит к непредсказуемым результатам.

Для того чтобы сделать дробные значения целыми, их можно округлить. Но важно, чтобы при этом округлении не потерялась нужная нам информация, поэтому поступим следующим образом:

  • в Create добавим
buf_x = x;
buf_y = y;

Переменные buf_x и buf_y будут сохранять дробные значения, получающиеся при перемещении, их мы будем округлять до ближайших целых, чтобы корректно перемещать нашего героя по координатной сетке.

  • в Step поменяем код следующим образом:
var move_x = keyboard_check(ord("D")) - keyboard_check(ord("A"));
var move_y = keyboard_check(ord("S")) - keyboard_check(ord("W"));

var hspd = 0;
var vspd = 0;

if (move_x != 0 || move_y != 0)
{
    var dir = point_direction(0, 0, move_x, move_y);
    hspd = lengthdir_x(spd, dir);
    vspd = lengthdir_y(spd, dir);

    if (place_meeting(x + hspd, y, obj_wall))
    {
        while (!place_meeting(x + sign(hspd), y, obj_wall))
        {
            x += sign(hspd);
        }
        buf_x = x;
        hspd = 0;
    }

    if (place_meeting(x, y + vspd, obj_wall))
    {
        while (!place_meeting(x, y + sign(vspd), obj_wall))
        {
            y += sign(vspd);
        }
        buf_y = y;
        vspd = 0;
    }

    buf_x += hspd;
    buf_y += vspd;

    x = round(buf_x);
    y = round(buf_y);
}

Теперь получившаяся скорость прибавляется к сохраняемым переменным buf_x и buf_y, которые мы потом округляем с помощью round().

Кроме этого у нас есть кусочек с while, который перемещает нас попиксельно до соприкосновения с объектом, здесь мы всегда будем двигаться на целое количество пикселей и врежемся в стену, поэтому результат этого перемещения сохраняется в buf_x и buf_y соответственно.

Clone this wiki locally