Ответ 1
То же самое для дуги XAML. Просто закройте дугу 99.99% с помощью Z
, и у вас есть круг!
Короткий вопрос: используя путь SVG, мы можем нарисовать 99,99% круга, и он появляется, но если он равен 99,999999999% круга, то круг не будет отображаться. Как это можно исправить?
Следующий путь SVG может нарисовать 99,99% круга: (попробуйте это на http://jsfiddle.net/DFhUF/1381/ и посмотрите, видите ли вы 4 дуги или только 2 дуги, но обратите внимание, что если это IE, это отображается в VML, а не в SVG, но имеет похожую проблему)
M 100 100 a 50 50 0 1 0 0.00001 0
Но когда это 99,99999999% от круга, то вообще ничего не покажется?
M 100 100 a 50 50 0 1 0 0.00000001 0
И то же самое со 100% круга (это все еще дуга, не так ли, просто очень полная дуга)
M 100 100 a 50 50 0 1 0 0 0
Как это можно исправить? Причина в том, что я использую функцию для рисования в процентах от дуги, и если мне нужно "особый случай" для дуги 99,9999% или 100%, чтобы использовать функцию круга, это было бы глупо.
Опять же, тестовый пример для jsfiddle с использованием RaphaelJS находится по адресу http://jsfiddle.net/DFhUF/1381/
(и если это VML в IE 8, даже второй круг не будет отображаться... вы должны изменить его на 0,01)
Обновить:
Это потому, что я выставляю дугу для оценки в нашей системе, поэтому 3,3 балла получают 1/3 круга. 0,5 получает половину круга, а 9,9 балла - 99% круга. Но что, если в нашей системе есть 9,99 баллов? Нужно ли проверять, находится ли он близко к 99,999% круга, и использовать функцию arc
или функцию circle
соответственно? Тогда как насчет 9.987? Какой использовать? Смешно знать, какие оценки будут отображаться в "слишком полный круг" и переключаться на функцию круга, а когда это "определенный 99,9%" от круга или 9,9997, тогда использовать функцию дуги,
То же самое для дуги XAML. Просто закройте дугу 99.99% с помощью Z
, и у вас есть круг!
Я знаю это немного позже в игре, но я вспомнил этот вопрос, когда он был новым, и у меня была подобная диллемма, и я случайно нашел "правильное" решение, если кто-то еще ищет его:
<path
d="
M cx cy
m -r, 0
a r,r 0 1,0 (r * 2),0
a r,r 0 1,0 -(r * 2),0
"
/>
Другими словами, это:
<circle cx="100" cy="100" r="75" />
может быть достигнуто как путь с этим:
<path
d="
M 100, 100
m -75, 0
a 75,75 0 1,0 150,0
a 75,75 0 1,0 -150,0
"
/>
Уловка состоит в том, чтобы иметь две дуги, вторая - вверх, где первая остановилась, и используя отрицательный диаметр, чтобы вернуться к исходной точке начальной дуги.
Причина, по которой она не может быть выполнена как полный круг в одной дуге (и я просто размышляю), заключается в том, что вы будете говорить ей, чтобы рисовать дугу от себя (скажем 150 150) к себе (150,150), который он отображает как "о, я уже там, никакой дуги не нужно!".
Преимущества решения, которые я предлагаю:
Ничего из этого не имеет значения, если они просто позволят текстовым путям принимать фигуры. Но я думаю, что они избегают этого решения, поскольку элементы формы, такие как круг, технически не имеют точки начала.
jsfiddle demo: http://jsfiddle.net/crazytonyi/mNt2g/
Если вы используете путь для ссылки textPath
, и вы хотите, чтобы текст отображался на внешнем краю дуги, вы использовали бы тот же самый метод, но изменили бы флаг развертки от 0 до 1, чтобы он рассматривает внешнюю сторону пути как поверхность вместо внутренней (думайте о 1,0
как кто-то, сидящий в центре и рисующий круг вокруг себя, а 1,1
, когда кто-то ходит по центру на расстоянии радиуса и перетаскивает их мелом рядом с ними, если это поможет). Вот код, как указано выше, но с изменением:
<path
d="
M cx cy
m -r, 0
a r,r 0 1,1 (r * 2),0
a r,r 0 1,1 -(r * 2),0
"
/>
В отношении решения Anthonys, вот функция для получения пути:
function circlePath(cx, cy, r){
return 'M '+cx+' '+cy+' m -'+r+', 0 a '+r+','+r+' 0 1,0 '+(r*2)+',0 a '+r+','+r+' 0 1,0 -'+(r*2)+',0';
}
Совершенно другой подход:
Вместо того, чтобы возиться с путями для указания дуги в svg, вы также можете взять элемент окружности и указать штрих-dasharray в псевдокоде:
with $score between 0..1, and pi = 3.141592653589793238
$length = $score * 2 * pi * $r
$max = 7 * $r (i.e. well above 2*pi*r)
<circle r="$r" stroke-dasharray="$length $max" />
Его простота является основным преимуществом по сравнению с методом с несколькими дугами (например, при написании сценариев вы включаете только одно значение, и вы делаете это для любой длины дуги)
Дуга начинается в самой правой точке и может быть сдвинута с помощью поворотного преобразования.
Примечание. В Firefox есть странная ошибка, в которой игнорируются вращения более 90 градусов и более. Чтобы начать дугу сверху, используйте:
<circle r="$r" transform="rotate(-89.9)" stroke-dasharray="$length $max" />
Adobe Illustrator использует кривые Безье, такие как SVG, а для кругов создает четыре точки. Вы можете создать круг с помощью двух команд эллиптической дуги... но тогда для круга в SVG я бы использовал <circle/>
:)
Это хорошая идея, что использование двух команд дуги для рисования полного круга.
обычно, я использую элемент эллипса или круга, чтобы нарисовать полный круг.
Написанная как функция, она выглядит так:
function getPath(cx,cy,r){
return "M" + cx + "," + cy + "m" + (-r) + ",0a" + r + "," + r + " 0 1,0 " + (r * 2) + ",0a" + r + "," + r + " 0 1,0 " + (-r * 2) + ",0";
}
Основываясь на ответах Энтони и Антона, я включил способность поворачивать созданный круг, не затрагивая его общий вид. Это полезно, если вы используете путь для анимации, и вам нужно контролировать, где он начинается.
function(cx, cy, r, deg){
var theta = deg*Math.PI/180,
dx = r*Math.cos(theta),
dy = -r*Math.sin(theta);
return "M "+cx+" "+cy+"m "+dx+","+dy+"a "+r+","+r+" 0 1,0 "+-2*dx+","+-2*dy+"a "+r+","+r+" 0 1,0 "+2*dx+","+2*dy;
}
Для таких, как я, которые искали атрибуты эллипса для преобразования пути:
const ellipseAttrsToPath = (rx,cx,ry,cy) =>
`M${cx-rx},${cy}a${rx},${ry} 0 1,0 ${rx*2},0a${rx},${ry} 0 1,0 -${rx*2},0`
Эти ответы слишком сложны.
Более простой способ сделать это без создания двух дуг или преобразования в разные системы координат.
Это предполагает, что ваша область холста имеет ширину w
и высоту h
.
'M${w*0.5 + radius},${h*0.5}
A${radius} ${radius} 0 1 0 ${w*0.5 + radius} ${h*0.5001}'
Просто используйте флаг "длинная дуга", чтобы заполнить полный флаг. Затем сделайте дуги на 99,9999% полным кругом. Визуально это то же самое. Избегайте флага развертки, просто начав окружность с крайней правой точки окружности (один радиус прямо горизонтально от центра).
Другой способ - использовать два кубических кривых Безье. Это для пользователей iOS, использующих pocketSVG, который не распознает параметр svg arc.
C x1 y1, x2 y2, x y (или c dx1 dy1, dx2 dy2, dx dy)
Последний набор координат здесь (x, y) - это место, где вы хотите, чтобы линия заканчивалась. Остальные два являются контрольными точками. (x1, y1) - контрольная точка для начала вашей кривой и (x2, y2) для конечной точки вашей кривой.
<path d="M25,0 C60,0, 60,50, 25,50 C-10,50, -10,0, 25,0" />
я сделал jsfiddle, чтобы сделать это здесь:
function polarToCartesian(centerX, centerY, radius, angleInDegrees) {
var angleInRadians = (angleInDegrees-90) * Math.PI / 180.0;
return {
x: centerX + (radius * Math.cos(angleInRadians)),
y: centerY + (radius * Math.sin(angleInRadians))
};
}
function describeArc(x, y, radius, startAngle, endAngle){
var start = polarToCartesian(x, y, radius, endAngle);
var end = polarToCartesian(x, y, radius, startAngle);
var largeArcFlag = endAngle - startAngle <= 180 ? "0" : "1";
var d = [
"M", start.x, start.y,
"A", radius, radius, 0, largeArcFlag, 0, end.x, end.y
].join(" ");
return d;
}
console.log(describeArc(255,255,220,134,136))
все, что вам нужно сделать, это изменить ввод console.log и получить результат в консоли
Эти примеры слишком сложны !!!
Просто сделайте это с литералами шаблона es6.
Более простой способ сделать это без создания двух дуг..
Это предполагает, что ваша область холста имеет ширину w и высоту h.
'M${w*0.5 + radius},${h*0.5}
A${radius} ${radius} 0 1 0 ${w*0.5 + radius} ${h*0.5001}'
Просто используйте флаг "длинная дуга", чтобы заполнить полный флаг. Затем сделайте дуги на 99,9999% полным кругом. Визуально это то же самое. Избегайте флага развертки, просто начав окружность с крайней правой точки окружности (один радиус прямо горизонтально от центра).