В Snap.svg точка на пути представляет собой координату, расположенную
на контуре SVG-элемента. Путь определяется атрибутом d в
элементе <path>, содержащим команды перемещения и
кривых линий. Для работы с точками на пути используются методы Snap,
которые позволяют извлекать координаты точки по длине пути и выполнять
точные манипуляции с элементами вдоль контура.
getPointAtLengthКлючевой метод для работы с точками на пути —
getPointAtLength(length). Он принимает длину пути в
пикселях и возвращает объект с координатами и углом касательной в этой
точке:
var path = Snap("#svg").path("M10 80 C 40 10, 65 10, 95 80");
var point = path.getPointAtLength(50);
console.log(point.x, point.y, point.alpha);
Возвращаемый объект содержит:
x — координата X точки на пути.y — координата Y точки на пути.alpha — угол касательной в радианах в этой точке,
направление движения вдоль пути.length — длина пути до этой точки (полезно для
обратного отслеживания позиции).Это позволяет размещать объекты точно на кривых линиях и создавать анимации вдоль пути.
Перед вычислением точки на пути часто требуется знать общую длину
контура. Snap.svg предоставляет метод getTotalLength():
var totalLength = path.getTotalLength();
console.log(totalLength);
Этот метод возвращает число пикселей, соответствующее длине всего пути, и используется для пропорционального вычисления позиции на кривой.
Для равномерного распределения точек на пути можно использовать отношение длины пути к общему размеру:
var steps = 10;
for (var i = 0; i <= steps; i++) {
var pos = path.getPointAtLength((i / steps) * path.getTotalLength());
Snap("#svg").circle(pos.x, pos.y, 3).attr({fill: "red"});
}
Здесь создаются малые круги, расположенные с одинаковым интервалом вдоль пути, независимо от формы кривой.
Метод getPointAtLength возвращает угол касательной
alpha, который позволяет вращать объекты в направлении
пути:
var pos = path.getPointAtLength(75);
var rect = Snap("#svg").rect(-10, -5, 20, 10).attr({fill: "blue"});
rect.transform(`t${pos.x},${pos.y}r${pos.alpha * 180 / Math.PI}`);
t${pos.x},${pos.y} — перемещение объекта к точке.r${pos.alpha * 180 / Math.PI} — поворот по касательной,
переведенной в градусы.Такой подход незаменим для создания анимации движения объектов вдоль кривой с правильным ориентированием.
Для анимаций удобно использовать процент длины пути. Это позволяет интерполировать позиции без необходимости вручную вычислять абсолютные пиксели:
function getPointAtPercent(path, percent) {
var length = path.getTotalLength();
return path.getPointAtLength(percent * length);
}
var pos50 = getPointAtPercent(path, 0.5);
console.log(pos50.x, pos50.y);
Такой метод применяется при анимациях объектов, движущихся по сложным кривым, например, для движения машинок, шариков или стрелок вдоль дорожки.
Snap.svg поддерживает кривые Cubic Bezier
(C) и Quadratic Bezier
(Q). Метод getPointAtLength
автоматически интерполирует координаты на кривой, независимо от её
степени. При этом:
C x1 y1, x2 y2, x y можно
получить точку в любом месте кривой.Q x1 y1, x y расчёт также точен
и корректно возвращает касательную.Это позволяет создавать плавные движения по сложным контурам, не разбирая кривые вручную.
Snap.svg позволяет создавать анимированные движения вдоль
пути через Snap.animate:
var obj = Snap("#svg").circle(0, 0, 5).attr({fill: "green"});
Snap.animate(0, path.getTotalLength(), function(value) {
var pos = path.getPointAtLength(value);
obj.attr({cx: pos.x, cy: pos.y});
}, 2000);
Здесь объект плавно перемещается по пути за 2 секунды, используя точные координаты и длину пути для интерполяции.
getPointAtLength
обеспечивает пиксельную точность координат.alpha позволяет правильно
ориентировать объекты на кривой.Использование этих инструментов позволяет строить сложные визуальные эффекты и анимации с абсолютной точностью на основе пути в Snap.svg.