У меня встроенный SVG в HTML-документе. Круг (SVG) анимируется с использованием <animate>
. Я пытался найти способ разместить какой-то прослушиватель событий на этом круге только тогда, когда он перемещается горизонтально.Поймать изменения в круге элементов SVG и изменить атрибуты в другом месте через js
При перемещении (по горизонтали), я хотел бы найти x-координаты формы круга и установить третью (внешнюю) ширину прямоугольной формы в относительное положение круга. Этот третий прямоугольник будет похож на индикатор выполнения, отслеживающий горизонтальный ход круга.
Либо SVG-круг (кстати, круг внутри SVG-группы), перемещаемый триггером какого-либо события, я могу установить прослушиватель, чтобы затем я мог изменить атрибут width своего рода прогресса бар?
Я думал, что если либо <animate>
, либо элемент перемещен/изменен, инициирует какое-то событие, которое я мог бы попытаться поймать, а затем изменить ширину на панели.
Я обнаружил, что не очень хорошо использовать «независимый» анимированный на пряме, поскольку темп роста очень отличается, когда круг перемещается вверх. Я не использую элемент canvas, потому что я пытаюсь сохранить масштабируемость и семантику форм. (Я предпочел бы использовать javascript-решение, но я был бы благодарен за другие подходы.)
ИЗМЕНИТЬ после ответа: Ансер очень полезен для piint и (я думаю) полезен. Я очень новичок в SVG, и я, возможно, неправильно истолковал. Вот почему я включаю код.
Я попытался выполнить ваши рекомендации, и я, похоже, не увенчался успехом. .cx.animVal.value, примененное к кругу, похоже, не дает мне то, что мне нужно. Я буду включать исправленную версию моего кода, которая должна перемещать мяч по пути, который сам перемещается горизонтально; два прямоугольника (inBar и outBar) должны отслеживать горизонтальное перемещение, растущее горизонтально более или менее с той же скоростью, что и мяч. Чтобы убедиться, что setInterval работает, и позиция правильно собрана, строка была добавлена в список oBall..animVal и oball..baseVal. В FF 21.0 нет изменений для animVal по смещению. Правильно ли я понял ваши предложения? Отсюда следуют код (включая заголовки и т.д., как я нуб в SVG, в частности):
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en" dir="ltr">
<head><title>Motion</title>
<script>function beginAnim(anim,sPos){anim.beginElement();}</script>
</head>
<body>
<div id="here">
<button onclick="beginAnim(document.getElementById('anim'),'out');">START</button>
</div>
<div style="height:350px;">
<svg width="100%" height="100%" version="1.1" xmlns="http://www.w3.org/2000/svg">
<script type="text/ecmascript">
<![CDATA[
function trckngBars(){
oDiv=document.getElementById('here');
var oBall=document.getElementById('ball');
var oBar=[document.getElementById('inBar'),document.getElementById('outBar')];
idTimer=self.setInterval(function(){updtBars(oBall,oBar);},100);
}
function updtBars(oBall,oBar){
var xCoor=String(oBall.cx.animVal.value);
oDiv.innerHTML+='==>'+oBall.cx.animVal.value+'..'+oBall.cx.baseVal.value;
oBar[0].setAttribute("width",xCoor);
oBar[1].setAttribute("width",xCoor);
}
// ]]>
</script>
<defs>
<path id="throw" d="M0,0 q 80,-55 200,20" style="fill: none; stroke: blue;" />
</defs>
<g>
<g>
<rect x="2" y="50" width="400" height="110" style="fill: yellow; stroke: black;"></rect>
</g>
<g>
<!-- show the path along which the circle will move -->
<use id="throw_path" visibility="hidden" xlink:href="#throw" x="50" y="130" />
<circle id="ball" cx="50" cy="130" r="10" style="fill: red; stroke: black;">
<animateMotion id="ball_anim" begin="anim.begin+1s" dur="6s" fill="freeze" onbegin="trckngBars();" onend="window.clearInterval(idTimer);">
<mpath xlink:href="#throw" />
</animateMotion>
</circle>
<rect id="inBar" x="50" y="205" width="20" height="30" style="fill: purple;stroke-linecap: butt;">
<!-- <animate attributeType="XML" attributeName="width" from="0" to="200" begin="ball_anim.begin" dur="6s" fill="freeze" /> -->
</rect>
</g>
<animateTransform id="anim" attributeType="XML" attributeName="transform" type="translate" from="0" to="200" begin="indefinite" dur="10s" fill="freeze" />
</g>
<rect id="outBar" x="50" y="235" width="10" height="30" style="fill: orange;stroke-linecap: butt;">
<!-- <animate attributeType="XML" attributeName="width" from="0" to="400" begin="anim.begin+1s" dur="10s" fill="freeze" /> -->
</rect>
</svg>
</div>
</body>
</html>
Если код запускается, кажется, что animVal для движущейся #ball остается на том же х coordinat (50), хотя он явно движется.
Благодарим за быстрый ответ. При поиске более элегантного решения я попытался установить интервал таймера, связанный с началом и завершением событий, поскольку это можно сделать из вашего ответа. Хотя мне удалось установить интервал и изменить бары, я обнаружил, что не могу получить текущую позицию круга myCircle.getAttribute ('cx') всегда возвращает исходную позицию. Знаете ли вы, что происходит с элементом SVG при перемещении? – user1938578
Нашел то, что происходит (например) [ссылка] (http://edutechwiki.unige.ch/en/SVG/SMIL_animation_tutorial#Overview_of_SMIL_animation_markup) [чуть выше названия]. Похоже, что значения атрибута элемента в DOM не изменяются до конца анимации, и, если мое понимание верное, замораживание - это код для этого.Любые указатели от кого-либо на то, как получить доступ к текущей позиции в данный момент или определить позицию (x-) в данный момент в анимации SVG с SMIL? – user1938578
Еще раз спасибо за то, что вы продолжаете улучшать ответ. Тант звучит так, как мне нужно. Я попробую немного с моим кодом. – user1938578