О чем этот пример

Создание плавных траекторий, построение пути для ИИ или реализация сетки для пошаговой стратегии — всё это требует получения точек линии. Встроенный в Phaser метод `Phaser.Geom.Line.BresenhamPoints` решает эту задачу, генерируя массив пиксельных координат по алгоритму Брезенхэма. Эта статья покажет, как использовать этот инструмент для визуализации и создания интерактивных механик, где важна каждая точка пути.

Версия Phaser: код и демо в этой статье рассчитаны на Phaser 3.90.0.

Живой запуск

Ниже встроен рабочий билд примера. Оригинальный источник: GitHub.

Исходный код


class Example extends Phaser.Scene
{
    create ()
    {
        const graphics = this.add.graphics({ lineStyle: { width: 4, color: 0xaa00aa }, fillStyle: { color: 0x0000aa } });

        const line = new Phaser.Geom.Line(0, 300, 400, 100);

        this.input.on('pointermove', pointer =>
        {

            line.x2 = pointer.x;
            line.y2 = pointer.y;

            redraw();
        });

        redraw();

        function redraw ()
        {
            graphics.clear();

            const points = Phaser.Geom.Line.BresenhamPoints(line, 30);

            for (let i = 0; i < points.length; i++)
            {

                graphics.fillPointShape(points[i], 30);

            }

            graphics.strokeLineShape(line);

        }
    }
}

const config = {
    width: 800,
    height: 600,
    type: Phaser.AUTO,
    parent: 'phaser-example',
    scene: Example
};

const game = new Phaser.Game(config);

Суть метода: от линии к массиву точек

Ключевой объект для работы — Phaser.Geom.Line, представляющий отрезок с координатами начала (x1, y1) и конца (x2, y2). Статический метод Phaser.Geom.Line.BresenhamPoints принимает этот отрезок и опциональный параметр — шаг (stepRate).

Он возвращает массив объектов Phaser.Geom.Point. Каждая точка — это координата на растровой сетке, через которую проходит наша линия. Алгоритм Брезенхэма эффективно вычисляет эти точки, что критично для производительности в реальном времени.

const line = new Phaser.Geom.Line(0, 300, 400, 100);
const points = Phaser.Geom.Line.BresenhamPoints(line, 30);

Визуализация: от точек к графике

Полученный массив точек — это просто данные. Чтобы их увидеть, используем объект Graphics. В примере мы задаём ему стили для контура и заливки, а затем в цикле рисуем каждую точку с помощью graphics.fillPointShape(). Важно: после изменения линии мы вызываем graphics.clear(), чтобы стереть предыдущий кадр.

Обратите внимание, что сама линия отрисовывается отдельно методом graphics.strokeLineShape() для наглядности.

const graphics = this.add.graphics({ lineStyle: { width: 4, color: 0xaa00aa }, fillStyle: { color: 0x0000aa } });
// ... внутри функции redraw
for (let i = 0; i < points.length; i++) {
    graphics.fillPointShape(points[i], 30);
}
graphics.strokeLineShape(line);

Интерактивность и параметр шага (stepRate)

Пример делает линию интерактивной, привязывая её конечную точку (x2, y2) к положению курсора через событие pointermove. При каждом движении мыши функция redraw() пересчитывает и перерисовывает точки.

Второй аргумент BresenhamPointsstepRate — определяет плотность точек. Значение 30 в примере означает, что точки будут браться примерно через каждые 30 пикселей вдоль линии. Если установить stepRate = 1, вы получите все пиксели линии, что может быть избыточно для визуализации, но необходимо для точных расчётов коллизий или пути.

this.input.on('pointermove', pointer => {
    line.x2 = pointer.x;
    line.y2 = pointer.y;
    redraw(); // Перерисовка при изменении линии
});

Практическое применение в играх

Где это может пригодиться?

* **Построение пути:** Полученный массив точек — готовый маршрут для перемещения объекта с постоянной скоростью (например, снаряда или юнита по клеткам). * **Лазерный прицел или луч:** Визуализация траектории выстрела до столкновения со стеной. * **Генерация карты:** Соединение двух комнат в процедурно генерируемом подземелье прямой линией коридора. * **Анализ линии обзора (Line of Sight):** Проверка, свободен ли путь между врагом и игроком, путём анализа точек на наличие препятствий.

Главное — помнить, что точки возвращаются в координатах пикселей холста, и для tile-based игр их可能需要 конвертировать в координаты сетки.

Что попробовать дальше

Метод BresenhamPoints — это мощный и производительный инструмент для работы с дискретным представлением линий. Поэкспериментируйте: измените stepRate на 1, чтобы увидеть сплошную линию, или используйте точки не для отрисовки, а для расчёта столкновений. Попробуйте привязать к точкам спрайты, создав цепочку эффектов, или реализуйте простую систему предсказания пути для стратегии.