Related
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>
Move.gif
I want to animate this path up and down (vertically). I use animationMotion for this, but my path is moving in different directions.
<svg width="698" height="745" viewBox="0 0 698 645" fill="none" xmlns="http://www.w3.org/2000/svg">
<path id="bottom-arrow" d="M404.767 578.541L414.523 592.852L397.251 594.146L404.767 578.541Z" stroke="#EEE8FB" stroke-width="2"
>
<animateMotion
path="M0,0 0 50 90 0 90 10"
begin="0s" dur="2s" repeatCount="indefinite"
/>
</path>
</svg>
Hope you got my point
You just need to give proper path for animateMotion. In your code it should be path="M0,0 0 90 0 0"
For more information, check this link
<svg width="698" height="745" viewBox="0 0 698 645" fill="none" xmlns="http://www.w3.org/2000/svg">
<path id="bottom-arrow" d="M404.767 578.541L414.523 592.852L397.251 594.146L404.767 578.541Z" stroke="#EEE8FB" stroke-width="2"
>
<animateMotion
path="M0,0 0 90 0 0"
begin="0s" dur="2s" repeatCount="indefinite"
/>
</path>
</svg>
I'm trying to achieve a svg path fill animation like the gif below, tried clipPath but no luck, any help, idea how to achieve that kind of animation (gif image below)? tried gsap or any svg animation library but none of them cater my needs.
<svg id="Layer_1" data-name="Layer 1" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 263.42 187.39">
<defs>
<clipPath id="clip1">
<path class="cls-1" fill="#c2a01e" d="M1889.36,77.11v3.47L1853,111.81q-10.32,2.86-21.35,7.09l-5.2,2c-8.68-2.49-17.65-5-26.73-7.37l90.6-109.08L1891.48,3V0H1737.59V4.49h0V51.65h2.23V48.17l50.94-43.68h44l-82.46,99.29-4,4.76c25.65,2.89,53.48,10.52,78.8,17.75l5.2-2c22.16-8.58,42.53-12.81,59.26-13.69V77.11Z" transform="translate(-1677.9)"/>
</clipPath>
<clipPath id="clip2">
<path class="cls-1" fill="#c2a01e" d="M1932.74,126.17c-13.82-10.71-52.11-11.68-98.2,6.14l-5.19,2c-53.78-15.35-118.75-32.47-150.47-2.43a3.15,3.15,0,0,0-1,2.51v0a2.32,2.32,0,0,0,3.67,1.69c24.48-17.77,57.75-16.76,132.38,4.48l-1.75.75c-8.06,3.49-21,9.57-34.68,15.79-20.34-9.54-48.19-17.44-66.13-6.65-26.21,15.75-19.06,51.2,38.47,30.66,8.47-3,48.84-21.17,83-35,2.93.89,5.92,1.79,9,2.73,16.51,5.06,38.3,8.93,57.55,10.6C1945.4,163.47,1948.48,138.37,1932.74,126.17ZM1712,157.37c15.48-11.94,39.91-5.59,58.83,2.82-6.94,3.12-13.89,6.17-20.3,8.84C1699.64,190.21,1697.33,168.67,1712,157.37Zm149.51-14c-4.11-1.09-8.38-2.27-12.78-3.51,9.34-3.58,17.56-6.5,23.64-8.22,29.63-8.41,58.5-3.24,61,6.19C1936.54,149.74,1912.3,156.79,1861.48,143.37Z" transform="translate(-1677.9)"/>
</clipPath>
</defs>
<path class="cls-1" fill="#FFF" clip-path="url(#clip1)" transform="translate(-1677.9)"/>
<path class="cls-1" fill="#FFF" clip-path="url(#clip2)" transform="translate(-1677.9)"/>
</svg>
The general idea is this: you draw the path you clip it as you need and next you animate the stroke-dashoffset of the clipped path. You make sure that the animation for the next path begins after the previous one ends: begin="a.end + .5s".
However in this case you will need to rewrite the paths. For example in the case of the lace I would use 2 paths and 2 different clip-paths or even 3. Otherwise you get an unaesthetic bleeding effect where the path overlaps.
<svg viewBox="0 0 500 500">
<defs>
<clipPath id="theZ">
<path d="M401.374,215.788v6.586l-69.015,59.278c-13.06,3.619-26.567,8.105-40.525,13.457l-9.869,3.797
c-16.477-4.727-33.502-9.49-50.737-13.989L403.196,77.872l2.202-2.752v-5.694h-292.1v8.522l0,0v89.515h4.232v-6.605l96.69-82.91
h83.517L141.219,266.41l-7.592,9.035c48.687,5.486,101.511,19.969,149.57,33.691l9.871-3.796
c42.062-16.286,80.727-24.315,112.481-25.985v-63.567H401.374z"/>
</clipPath>
<clipPath id="theLace">
<path d="M483.714,308.909c-26.231-20.329-98.91-22.17-186.394,11.654l-9.852,3.796
c-102.081-29.135-225.4-61.631-285.608-4.611c-1.316,1.222-2.013,2.971-1.898,4.764l0,0c0.201,2.424,2.328,4.227,4.751,4.025
c0.799-0.065,1.565-0.348,2.215-0.817c46.466-33.729,109.616-31.812,251.271,8.503l-3.321,1.424
c-15.298,6.625-39.86,18.165-65.826,29.971c-38.607-18.107-91.47-33.103-125.522-12.621c-49.75,29.895-36.178,97.183,73.02,58.195
c16.077-5.694,92.704-40.184,157.544-66.434c5.561,1.689,11.236,3.397,17.082,5.182c31.338,9.604,72.698,16.95,109.236,20.12C507.744,379.709,513.591,332.066,483.714,308.909z M64.726,368.131c29.383-22.664,75.753-10.611,111.666,5.352
c-13.173,5.923-26.365,11.712-38.531,16.779C41.265,430.464,36.88,389.579,64.726,368.131z M348.512,341.557
c-7.801-2.068-15.906-4.309-24.258-6.662c17.729-6.795,33.331-12.338,44.871-15.603c56.241-15.963,111.04-6.149,115.785,11.749
c6.017,22.607-39.993,35.988-136.455,10.516H348.512z"/>
</clipPath>
</defs>
<path fill="none" stroke="#C2A01E" clip-path="url(#theLace)" stroke-width="25" stroke-dasharray="1206" stroke-dashoffset="1206" d="M-0.038,324.512c0,0,49.523-27.071,69.538-27.012 c23.35,0.069,74.84,1.785,121.646,11.637C242.583,319.965,288.5,338.5,288.5,338.5s134.99,34.916,169,27s36.999-16.612,35-33.425
s-44.115-67.954-226,12.425s-172,69-172,69s-52.867,8.077-52-16s7.277-37.219,43.205-46.984c38.84-10.557,110.17,30.986,110.17,30.986" >
<animate id="a"
attributeName="stroke-dashoffset"
attributeType="XML"
from="1206" to="0"
dur="1s"
fill="freeze"
repeatCount="1"/>
</path>
<path fill="none" stroke="#C2A01E" d="M259.424,309.137V64.778" clip-path="url(#theZ)" stroke-width="300" stroke-dasharray="244.36" stroke-dashoffset="244.36">
<animate
attributeName="stroke-dashoffset"
attributeType="XML"
begin="a.end + .5s"
from="244.36" to="0"
dur="1s"
fill="freeze"
repeatCount="1"
/>
</path>
</svg>
I would like to have my svg animation run when clicking an html button. I thought I could make that work by setting begin="click in my animateTransform and then trigger a click event on the animateTransform (or the svg element containing the animateTransform, I tried both) using js.
Any advice would be a great help.
var needle = $('#needle'),
tape = $('#tape'),
btn = $('#muhBtn');
btn.on('click', function() {
needle.click();
tape.click();
});
#tape {
fill: #ED1C24;
}
#needle {
fill: #8DC63F;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<?xml version="1.0" encoding="utf-8"?>
<svg version="1.1" id="Layer_1" xmlns:x="&ns_extend;" xmlns:i="&ns_ai;" xmlns:graph="&ns_graphs;" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" width="200px" height="200px" viewBox="0 0 200 200" style="enable-background:new 0 0 200 200;"
xml:space="preserve">
<circle cx="100" cy="100" r="100" class="background"/>
<path class="st0" id="tape" d="M182.7,100c0,45.7-37,82.7-82.7,82.7V17.3C145.7,17.3,182.7,54.3,182.7,100z">
<animateTransform id="animateTape"
attributeName="transform"
attributeType="XML"
type="rotate"
from="0 100 100"
to="180 100 100"
dur="5s"
begin="click"
repeatCount="1"/>
</path>
<path d="M200,100c0,55.2-44.8,100-100,100V0C155.2,0,200,44.8,200,100z" class="mask"/>
<polygon class="st1" id="needle" points="96,100 104,100 104,192 100,200 96,192">
<animateTransform id="animateNeedle"
attributeName="transform"
attributeType="XML"
type="rotate"
from="0 100 100"
to="180 100 100"
dur="5s"
begin="click"
repeatCount="1"/>
</polygon>
</svg>
<button class="btn btn-warning" id="muhBtn">Begin!</button>
If you want to start the animations just do it directly via javascript and the beginElement method, no need for all that click event rigmarole. Note that I've changed the begin on the animation from click to indefinite to make it clearer what's happening.
var needle = $('#animateNeedle'),
tape = $('#animateTape');
btn = $('#muhBtn');
btn.on('click', function(){
needle[0].beginElement();
tape[0].beginElement();
});
#tape{
fill:#ED1C24;
}
#needle{
fill:#8DC63F;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<?xml version="1.0" encoding="utf-8"?>
<svg version="1.1" id="Layer_1" xmlns:x="&ns_extend;" xmlns:i="&ns_ai;" xmlns:graph="&ns_graphs;"
xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" width="200px" height="200px"
viewBox="0 0 200 200" style="enable-background:new 0 0 200 200;" xml:space="preserve">
<circle cx="100" cy="100" r="100" class="background"/>
<path class="st0" id="tape" d="M182.7,100c0,45.7-37,82.7-82.7,82.7V17.3C145.7,17.3,182.7,54.3,182.7,100z">
<animateTransform id="animateTape"
attributeName="transform"
attributeType="XML"
type="rotate"
from="0 100 100"
to="180 100 100"
dur="5s"
begin="indefinite"
repeatCount="1"/>
</path>
<path d="M200,100c0,55.2-44.8,100-100,100V0C155.2,0,200,44.8,200,100z" class="mask"/>
<polygon class="st1" id="needle" points="96,100 104,100 104,192 100,200 96,192">
<animateTransform id="animateNeedle"
attributeName="transform"
attributeType="XML"
type="rotate"
from="0 100 100"
to="180 100 100"
dur="5s"
begin="indefinite"
repeatCount="1"/>
</polygon>
</svg>
<button class="btn btn-warning" id="muhBtn">Begin!</button>
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.