I'm trying to restart SVG animation sequence from Javascript. Restart-button below will broke SVG animation sequence. How to restart/reset entire sequence?
document.getElementById("button").addEventListener("click", function() {
document.getElementById("fore").beginElement();
});
<svg version="1.1" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 1000 150">
<path id="track" fill="none" stroke="#000000" stroke-width="1" stroke-dasharray="10,10" d="M 50 100 L 950 50"/>
<path id="plane" d="M-10 -10 L10 0L-10 10z" fill="red" />
<animateMotion xlink:href="#plane"
id="fore"
begin="0s;back.end"
dur="2s"
fill="freeze"
repeatCount="1"
rotate="auto"
keyPoints="0;1"
keyTimes="0;1"
><mpath xlink:href="#track" /></animateMotion>
<animateMotion xlink:href="#plane"
id="back"
begin="fore.end"
dur="2s"
fill="freeze"
repeatCount="1"
rotate="auto-reverse"
keyPoints="1;0"
keyTimes="0;1"
><mpath xlink:href="#track" /></animateMotion>
</svg>
<button id="button">RESTART</button>
You can use setCurrentTime on the entire svg element. I added an id of svgEl to the svg node and then when rest is clicked we do:
document.getElementById('svgEl').setCurrentTime(0);
Have a look at this:
document.getElementById("button").addEventListener("click", function() {
document.getElementById('svgEl').setCurrentTime(0);
});
<svg id="svgEl" version="1.1" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 1000 150">
<path id="track" fill="none" stroke="#000000" stroke-width="1" stroke-dasharray="10,10" d="M 50 100 L 950 50"/>
<path id="plane" d="M-10 -10 L10 0L-10 10z" fill="red" />
<animateMotion xlink:href="#plane"
id="fore"
begin="0s;back.end"
dur="2s"
fill="freeze"
repeatCount="1"
rotate="auto"
keyPoints="0;1"
keyTimes="0;1"
restart="always"
><mpath xlink:href="#track" /></animateMotion>
<animateMotion xlink:href="#plane"
id="back"
begin="fore.end"
dur="2s"
fill="freeze"
repeatCount="1"
rotate="auto-reverse"
keyPoints="1;0"
keyTimes="0;1"
restart="always"
><mpath xlink:href="#track" /></animateMotion>
</svg>
<button id="button">RESTART</button>
I have the following transformations
<svg height="205" width="365" xmlns="http://www.w3.org/2000/svg"> <!-- Created with Method Draw - http://github.com/duopixel/Method-Draw/ --> <g>
<title></title>
<rect fill="none" height="207" id="canvas_background" width="367" x="-1" y="-1"></rect> </g> <g>
<title></title>
<g id="svg_3"> <path class="hinh1" d="m22,88.5a67.5,67.5 0 0 1 135,0l-135,0z" fill="none" id="svg_1" stroke="#000" stroke-width="1.5" style="fill: rgb(92, 188, 214);stroke-linejoin: round;/* x: 100; *//* y: 100px; */"></path> <g transform="translate(-132.281 0)"><path class="hinh2" d="m207.0027,88.5a67.5,67.5 0 0 1 135,0l-135,0z" fill="none" id="svg_2" stroke="#000" stroke-width="1.5" transform="rotate(180 274.503 54.7665) translate(0 70.8138) translate(0 -82.7702)" style="fill: rgb(214, 92, 188); stroke-linejoin: round;">
</path>
<animateTransform attributeName="transform" attributeType="XML" type="translate" from="0 0" to="0 56" begin="0s" dur="5s" repeatCount="indefinite" id="one">
</animateTransform>
<animateTransform attributeName="transform" attributeType="XML" type="translate" from="0 0" to="-185 0" begin="one.end" dur="5s" repeatCount="indefinite">
</animateTransform>
</g> </g> </g> </svg>
I want the right semicircle to go down THEN go left (not simultaneously) to snap to the left semicircle.
I found that, the following code does not work as I expect, only the second one is triggered. Isn't it the case that one.end has no meaning here?
<animateTransform attributeName="transform" attributeType="XML" type="translate" from="0 0" to="0 56" begin="0s" dur="5s" repeatCount="indefinite" id="one">
</animateTransform>
<animateTransform attributeName="transform" attributeType="XML" type="translate" from="0 0" to="-185 0" begin="one.end" dur="5s" repeatCount="indefinite">
</animateTransform>
In addition, at the end of the animations, I want the right to stop for about 3s before repeating, how to do so?
Instead of using the to and for attributes you can animate between several values by using the values attribute where the values for the transformation are separates by semicolons:
<svg height="205" width="365" xmlns="http://www.w3.org/2000/svg">
<g>
<rect fill="none" height="207" id="canvas_background" width="367" x="-1" y="-1"></rect>
</g>
<g id="svg_3">
<path class="hinh1" d="m22,88.5a67.5,67.5 0 0 1 135,0l-135,0z" fill="none" id="svg_1" stroke="#000" stroke-width="1.5" style="fill: rgb(92, 188, 214);stroke-linejoin: round;"></path>
<g>
<path class="hinh2" d="m207.0027,88.5a67.5,67.5 0 0 1 135,0l-135,0z" fill="none" id="svg_2" stroke="#000" stroke-width="1.5" transform="rotate(180 274.503 54.7665) translate(0 70.8138) translate(0 -82.7702)" style="fill: rgb(214, 92, 188); stroke-linejoin: round;">
</path>
<animateTransform attributeName="transform" attributeType="XML" type="translate" values="0 0;0 56;-185,56" begin="0s" dur="5s" repeatCount="1" fill="freeze" id="one">
</animateTransform>
</g>
</g>
</svg>
I have a path which represent half of the circle, I want it to render in a circular way.
as it is only path I tried of svg but it couldn't work.
<svg version="1.1" x="0px"
y="0px" width="131.45px" height="131.451px" viewBox="0 0 131.45 131.451" enable-background="new 0 0 131.45 131.451"
xml:space="preserve">
<g id="Group_952" transform="translate(0 0)">
<g id="Path_211">
<path fill="#0088CE" d="M86.692,128.579l-6.314-20.938c17.843-5.735,29.832-22.563,29.832-41.875
c0-23.389-17.711-42.625-40.314-43.793l1.059-21.9c33.925,1.752,60.5,30.606,60.5,65.69
C131.452,94.733,113.463,119.974,86.692,128.579z"/>
</g>
<svg>
Your semicircle is drawn using a double path see image below
Therefore, you can animate figure drawing only with the help of filter ormask
I suggest using the technique of drawing a figure from the top point to a semicircle, by changing the 'stroke-dasharray' of the middle line of the figure.
The middle line turned out - a circle with the center of (70.70) and a radius of 50
Next, set stroke-width ="20" and stroke-dasharray = "157 157" to get half the circle
Turn the semicircle counterclockwise 90 degrees so that its beginning is at the top
<svg version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink"
width="131.45px" height="131.451px" viewBox="0 0 131.45 131.451" >
<circle transform="rotate(-90 70 70)" cx="70" cy="70" r="50" fill="none" stroke="#0088CE"
stroke-width="20" stroke-dasharray="157 157">
</circle>
</svg>
To animate the drawing from the top point to half the circle, change the stroke-dasharray from ="0 314" to ="157 157"
<svg version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink"
width="131.45px" height="131.451px" viewBox="0 0 131.45 131.451" >
<circle transform="rotate(-90 70 70)" cx="70" cy="70" r="50" fill="none" stroke="#0088CE"
stroke-width="20" stroke-dasharray="157 157">
<animate
attributeName="stroke-dasharray"
values="0 314;157 157"
dur="5s"
fill="freeze" />
</circle>
</svg>
CSS animation
.crc1 {
fill:none;
stroke:#0088CE;
stroke-width:20;
stroke-dasharray:157.07;
animation: dash 4s ;
}
#keyframes dash {
0% {stroke-dasharray: 0 314}
100% {stroke-dasharray: 157 157}
}
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink"
width="131.45px" height="131.451px" viewBox="0 0 131.45 131.451" >
<circle class="crc1" transform="rotate(-90 70 70)" cx="70" cy="70" r="50"> </circle>
</svg>
Semicircle rotation animation
For animation the change of attribute stroke-dashoffset is used:
<svg version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink"
width="131.45px" height="131.451px" viewBox="0 0 131.45 131.451" >
<circle cx="70" cy="70" r="50" fill="none" stroke="#EDEDED"
stroke-width="20" />
<circle transform="rotate(-90 70 70)" cx="70" cy="70" r="50" fill="none" stroke="#0088CE"
stroke-width="20" stroke-dasharray="157.07" stroke-dashoffset="-314">
<animate
attributeName="stroke-dashoffset"
values="0;-314"
dur="2s"
repeatCount="indefinite" />
</circle>
</svg>
Complex animation of drawing and rotation
<svg version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink"
width="131.45px" height="131.451px" viewBox="0 0 131.45 131.451" >
<circle cx="70" cy="70" r="50" fill="none" stroke="#EDEDED"
stroke-width="20" />
<circle transform="rotate(-90 70 70)" cx="70" cy="70" r="50" fill="none" stroke="#0088CE"
stroke-width="20" stroke-dasharray="157.07" stroke-dashoffset="-314">
<animate id="an_dasharray"
attributeName="stroke-dasharray"
values="0 314;157 157"
begin="0s;an_dashoffset.end+0.5s"
dur="2s"
fill="freeze" />
<animate id="an_dashoffset"
attributeName="stroke-dashoffset"
values="0;-314"
begin="an_dasharray.end"
dur="2s"
repeatCount="2" />
</circle>
</svg>
I'm considering putting an SVG spinner animation behind some images I'm loading and then having the image stacked on top of the spinner so that the spinner is obscured when the image is loaded. Planning to apply this to a list view with potentially hundreds of items.
First question is, will the obscured SVG spinner (once its respective image loads) continue to cause the browser to repaint? (that sounds expensive)
If yes, the next question would be, if I hide (display: none) the spinner when the image loads, will the hidden spinner continue to cause repainting?
Any other performance thoughts are very welcome.
FWIW, this is an Electron app, so Chromium (a relatively up to date version) is the only browser we're concerned with.
This got me interested... using an example SVG I whipped together this test (excuse how scrummy the code is):
document.onclick = function() {
output.innerHTML += (mySVG.innerHTML + output.innerHTML).replace(/<circle /g,"<circle style='opacity: 0' ");
preview.innerHTML += mySVG.innerHTML;
}
<div id="mySVG">
<svg width="30px" height="30px" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 100 100" preserveAspectRatio="xMidYMid" class="lds-dual-ring">
<circle cx="50" cy="50" fill="none" stroke-linecap="round" r="40" stroke-width="4" stroke="#facd9e" stroke-dasharray="62.83185307179586 62.83185307179586" transform="rotate(115.488 50 50)">
<animateTransform attributeName="transform" type="rotate" calcMode="linear" values="0 50 50;360 50 50" keyTimes="0;1" dur="1s" begin="0s" repeatCount="indefinite"></animateTransform>
</circle>
<circle cx="50" cy="50" fill="none" stroke-linecap="round" r="35" stroke-width="4" stroke="#389798" stroke-dasharray="54.97787143782138 54.97787143782138" stroke-dashoffset="54.97787143782138" transform="rotate(-115.488 50 50)">
<animateTransform attributeName="transform" type="rotate" calcMode="linear" values="0 50 50;-360 50 50" keyTimes="0;1" dur="1s" begin="0s" repeatCount="indefinite"></animateTransform>
</circle>
</svg>
</div>
<div id="output"></div>
<div id="preview"></div>
As you can see, when you click lots on the document, all the fully transparent spinning circles start to slow down the browser rendering. Looks like the animations do still trigger.
In this example with display: none; we get the same result, the div#preview is noticeably slower:
document.onclick = function() {
output.innerHTML += (mySVG.innerHTML + output.innerHTML).replace(/<circle /g,"<circle style='display: none' ");
preview.innerHTML += mySVG.innerHTML;
}
<div id="mySVG">
<svg width="30px" height="30px" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 100 100" preserveAspectRatio="xMidYMid" class="lds-dual-ring">
<circle cx="50" cy="50" fill="none" stroke-linecap="round" r="40" stroke-width="4" stroke="#facd9e" stroke-dasharray="62.83185307179586 62.83185307179586" transform="rotate(115.488 50 50)">
<animateTransform attributeName="transform" type="rotate" calcMode="linear" values="0 50 50;360 50 50" keyTimes="0;1" dur="1s" begin="0s" repeatCount="indefinite"></animateTransform>
</circle>
<circle cx="50" cy="50" fill="none" stroke-linecap="round" r="35" stroke-width="4" stroke="#389798" stroke-dasharray="54.97787143782138 54.97787143782138" stroke-dashoffset="54.97787143782138" transform="rotate(-115.488 50 50)">
<animateTransform attributeName="transform" type="rotate" calcMode="linear" values="0 50 50;-360 50 50" keyTimes="0;1" dur="1s" begin="0s" repeatCount="indefinite"></animateTransform>
</circle>
</svg>
</div>
<div id="output"></div>
<div id="preview"></div>
I'm currently testing different options to animate SVG Files directly in the .svg File. RIght now I'm testing animation with includet javascript. The Problem is, i don't get a proper rotation around the origin working.
My Code is currently looking like that:
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 18.1.0, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="Ebene_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
width="64px" height="64px" viewBox="0 0 64 64" enable-background="new 0 0 64 64" xml:space="preserve">
<g>
<g>
<path class="bag" fill="#016D49" d="M42.1,45.6c-6.7,0-13.5,0-20.2,0c-0.2,0-0.3-0.1-0.3-0.3c0.4-6.9,0.9-13.8,1.3-20.7c0-0.2,0.2-0.3,0.3-0.3
c5.9,0,11.7,0,17.6,0c0.2,0,0.3,0.1,0.3,0.3c0.4,6.9,0.9,13.8,1.3,20.7C42.4,45.5,42.3,45.6,42.1,45.6z"/>
</g>
<g>
<path fill="#016D49" d="M27.8,23.1c0-0.2,0.1-0.5,0.1-0.8c0.9-5.3,4.1-5,4.2-5c0,0,3-0.3,4,5c0,0.3,0.1,0.6,0.2,0.8H38
c0-0.2-0.1-0.5-0.2-0.8c-0.2-0.7-0.4-1.3-0.6-2.1c-1.2-3.1-3-4.7-5.4-4.6c-3.6,0.2-5.1,3.8-5.6,6.6c0,0.3-0.1,0.6-0.1,0.8
L27.8,23.1L27.8,23.1z"/>
</g>
</g>
<g id="loadingRing">
<circle fill="none" stroke="#016D49" stroke-width="0.75" stroke-miterlimit="10" stroke-dasharray="7.0201,7.0201" cx="32" cy="32" r="26.8">
</circle>
<script language="JavaScript" type="text/javascript">
var zpos=0;
function turnAround(){
zpos++;
if(zpos>359)zpos=0;
var dz=document.getElementById("loadingRing");
dz.style.transform = "rotate("+zpos+"deg) translate(1%,1%)";
window.setTimeout("turnAround()", 14);
}
turnAround();
</script>
</g>
</svg>
So what am I missing, or does there a better solution exist? Maybe it is possible to include jquery in the svg File?
Thanks in advance
Maybe you should stick to normal SVG tools and not over complicate things for something as trivial as a rotation.
It wasn't clear to me what you want to spin, so I made them both spin:
<svg version="1.1" id="Ebene_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
width="64px" height="64px" viewBox="0 0 64 64" enable-background="new 0 0 64 64" xml:space="preserve">
<g>
<g>
<path class="bag" fill="#016D49" d="M42.1,45.6c-6.7,0-13.5,0-20.2,0c-0.2,0-0.3-0.1-0.3-0.3c0.4-6.9,0.9-13.8,1.3-20.7c0-0.2,0.2-0.3,0.3-0.3
c5.9,0,11.7,0,17.6,0c0.2,0,0.3,0.1,0.3,0.3c0.4,6.9,0.9,13.8,1.3,20.7C42.4,45.5,42.3,45.6,42.1,45.6z"/>
</g>
<g>
<path fill="#016D49" d="M27.8,23.1c0-0.2,0.1-0.5,0.1-0.8c0.9-5.3,4.1-5,4.2-5c0,0,3-0.3,4,5c0,0.3,0.1,0.6,0.2,0.8H38
c0-0.2-0.1-0.5-0.2-0.8c-0.2-0.7-0.4-1.3-0.6-2.1c-1.2-3.1-3-4.7-5.4-4.6c-3.6,0.2-5.1,3.8-5.6,6.6c0,0.3-0.1,0.6-0.1,0.8
L27.8,23.1L27.8,23.1z"/>
</g>
<animateTransform attributeName="transform"
attributeType="XML"
type="rotate"
from="360 32 32"
to="0 32 32"
dur="10s"
repeatCount="indefinite"/>
</g>
<g id="loadingRing">
<circle fill="none" stroke="#016D49" stroke-width="0.75" stroke-miterlimit="10" stroke-dasharray="7.0201,7.0201" cx="32" cy="32" r="26.8">
</circle>
<animateTransform attributeName="transform"
attributeType="XML"
type="rotate"
from="0 32 32"
to="360 32 32"
dur="5s"
repeatCount="indefinite"/>
</g>
</svg>
Here you go, a version with scripting, impractical, but since you wanted it...
dz.setAttribute("transform", "rotate(" + zpos + " 32 32)");
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 18.1.0, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="Ebene_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
width="64px" height="64px" viewBox="0 0 64 64" enable-background="new 0 0 64 64" xml:space="preserve">
<g>
<g>
<path class="bag" fill="#016D49" d="M42.1,45.6c-6.7,0-13.5,0-20.2,0c-0.2,0-0.3-0.1-0.3-0.3c0.4-6.9,0.9-13.8,1.3-20.7c0-0.2,0.2-0.3,0.3-0.3
c5.9,0,11.7,0,17.6,0c0.2,0,0.3,0.1,0.3,0.3c0.4,6.9,0.9,13.8,1.3,20.7C42.4,45.5,42.3,45.6,42.1,45.6z"/>
</g>
<g>
<path fill="#016D49" d="M27.8,23.1c0-0.2,0.1-0.5,0.1-0.8c0.9-5.3,4.1-5,4.2-5c0,0,3-0.3,4,5c0,0.3,0.1,0.6,0.2,0.8H38
c0-0.2-0.1-0.5-0.2-0.8c-0.2-0.7-0.4-1.3-0.6-2.1c-1.2-3.1-3-4.7-5.4-4.6c-3.6,0.2-5.1,3.8-5.6,6.6c0,0.3-0.1,0.6-0.1,0.8
L27.8,23.1L27.8,23.1z"/>
</g>
</g>
<g id="loadingRing">
<circle fill="none" stroke="#016D49" stroke-width="0.75" stroke-miterlimit="10" stroke-dasharray="7.0201,7.0201" cx="32" cy="32" r="26.8">
</circle>
<script language="JavaScript" type="text/javascript">
var zpos=0;
function turnAround(){
zpos++;
//if(zpos>359)zpos=0;
var dz=document.getElementById("loadingRing");
//dz.style.transform = "rotate("+zpos+"deg 32 32)";
dz.setAttribute("transform", "rotate(" + zpos + " 32 32)");
window.setTimeout("turnAround()", 14);
}
turnAround();
</script>
</g>
</svg>
Notes:
I couldn't make it work with changing the style property. Not sure why.
You don't need to reset from 359 to 0. Degrees are anyway computed mod 360.