Матрицы трансформации

В Two.js матрицы трансформации представляют собой ключевой механизм управления положением, масштабом, вращением и наклоном объектов на канве. Все трансформации основаны на матрицах 3x3, которые позволяют комбинировать несколько эффектов в одной операции, обеспечивая высокую производительность и точность.

В Two.js каждая фигура имеет свойства translation, rotation, scale, а также matrix, представляющую текущую матрицу трансформации. Внутренне Two.js использует аффинные матрицы, где вектор позиции хранится в третьем столбце, а масштаб и вращение — в первых двух.


Структура матрицы

Стандартная матрица 3x3 в Two.js имеет вид:

| a  c  e |
| b  d  f |
| 0  0  1 |
  • a и d отвечают за масштаб по осям X и Y.
  • b и c задают наклон (shear) и вращение.
  • e и f представляют смещение (translation) по X и Y.

Используя эти шесть параметров, можно полностью описать любые аффинные преобразования на плоскости.


Создание и применение матриц

Two.js предоставляет класс Two.Matrix, который поддерживает базовые операции:

let matrix = new Two.Matrix();
matrix.set(1, 0, 0, 1, 50, 100); // a, b, c, d, e, f
  • matrix.multiply(matrix2) — умножение на другую матрицу, объединяя трансформации.
  • matrix.inverse() — получение обратной матрицы, используемой для обратного преобразования координат.
  • matrix.toString() — преобразование в CSS-подобную строку для использования в SVG или canvas.

Применение к объектам Two.js

Каждый объект Two.Shape или Two.Path содержит ссылку на свою матрицу. Применение матрицы происходит через:

shape.matrix.multiply(matrix);
shape.translation.set(shape.matrix.e, shape.matrix.f);

Также можно напрямую использовать методы трансформации объекта:

  • shape.translation.set(x, y) — смещение объекта.
  • shape.rotation = angle — вращение в радианах.
  • shape.scale = s — равномерное масштабирование.

Эти методы автоматически обновляют внутреннюю матрицу shape.matrix, объединяя все трансформации.


Вращение, масштабирование и смещение через матрицы

Вращение вокруг точки (px, py) реализуется через комбинацию смещений и вращения:

matrix
  .translate(px, py)
  .rotate(angle)
  .translate(-px, -py);

Масштабирование по центру (cx, cy):

matrix
  .translate(cx, cy)
  .scale(sx, sy)
  .translate(-cx, -cy);

Комбинированные трансформации можно применять цепочкой:

matrix
  .translate(100, 50)
  .rotate(Math.PI / 4)
  .scale(2, 1.5);

Интерактивное обновление матриц

Two.js позволяет динамически изменять матрицы в анимациях:

two.bind('upd ate', function(frameCount, timeDelta) {
  shape.rotation += 0.01;
  shape.scale = 1 + 0.5 * Math.sin(frameCount * 0.05);
  shape.matrix.update(); // обновление внутренней матрицы
});

Метод update() синхронизирует все свойства трансформации объекта с его матрицей, гарантируя корректное отображение на канве.


Влияние матриц на дочерние элементы

Если объект является группой (Two.Group), матрица группы умножается на матрицы всех дочерних элементов. Это позволяет:

  • Смещать группу целиком.
  • Масштабировать несколько объектов одновременно.
  • Вращать композицию вокруг общего центра.

Пример:

let group = two.makeGroup(shape1, shape2);
group.rotation = Math.PI / 6;
group.translation.se t(200, 150);
group.matrix.update();

После этого все дочерние объекты наследуют преобразования группы.


Оптимизация через матрицы

Использование матриц трансформации позволяет:

  • Минимизировать количество вызовов рендеринга.
  • Комбинировать несколько эффектов в одну операцию.
  • Использовать обратные матрицы для проверки попадания курсора или столкновений.

Two.js хранит внутренние матрицы для каждого объекта, поэтому изменения через translation, rotation, scale автоматически обновляют их, но прямое управление через Two.Matrix позволяет создавать более сложные и оптимизированные анимации.


Практические советы

  • Для часто изменяющихся объектов рекомендуется использовать прямое изменение матрицы, а не отдельных свойств.
  • Объекты с одинаковыми трансформациями можно объединять в группы для снижения нагрузки на рендеринг.
  • Проверка matrix.isIdentity() позволяет определить, изменялась ли матрица или объект находится в исходном состоянии.

Матрицы трансформации в Two.js обеспечивают мощный и гибкий инструмент для работы с позициями, вращением, масштабом и сложными композициями, позволяя создавать динамичные и высокопроизводительные графические сцены.