简体   繁体   中英

svg circle color change at certain point

I have a svg that circle is moving around through path. I want the circles' color are changed at some points (ex. mid of the path)

https://codepen.io/lzwdct/pen/poRYVXZ

<circle r="20" fill="blue" mask="url(#myMask)">
    <animateMotion dur="5s" repeatCount="indefinite"
      path="M718.54,66.06L294.41,490.19c-48.89,48.89-128.09,48.95-176.91,0.13c-48.82-48.82-48.76-128.02,0.13-176.91
            s128.09-48.95,176.91-0.13 M294.28,313.55l424.13,424.13c48.89,48.89,128.09,48.95,176.91,0.13c48.82-48.82,48.76-128.02-0.13-176.91
            c-48.89-48.89-128.09-48.95-176.91-0.13" />
</circle>

Please guide me how to update the color. The color eventually will be changed multiple times with long paths.

I'm not sure if there's anything in SVG that would enable you to do that directly.

But you can check currentTime vs the duration of the animateMotion element and set a color via javascript based on that.

 const color = (n) => { const R = Math.round((255 * n) / 100); const G = Math.round((255 * (100 - n)) / 100); const B = 0; return `rgb(${R}, ${G}, ${B})`; }; const circles = document.querySelectorAll("circle"); window.setInterval(() => { circles.forEach(circle => { const ani = circle.querySelector('animateMotion'); const duration = ani.getSimpleDuration(); const currentTime = ani.getCurrentTime() % duration; const colorValue = color((currentTime / duration) * 100); circle.parentNode.style.fill = colorValue; }); }, 500);
 circle { transition: 500ms; }
 <svg version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" viewBox="0 0 2549.62 3338.72" style="enable-background:new 0 0 2549.62 3338.72;" xml:space="preserve"> <style type="text/css">.st0{fill:none;stroke:#8EA5AE;stroke-width:50;stroke-miterlimit:10;}.st1{fill:none;stroke:#8EA5AE;stroke-width:50;stroke-linecap:round;stroke-miterlimit:10;}.st2{fill:none;stroke:#758992;stroke-width:50;stroke-miterlimit:10;}.st3{fill:none;stroke:#758992;stroke-width:50;stroke-linecap:round;stroke-miterlimit:10;}.st4{fill:none;stroke:#4E5F65;stroke-width:50;stroke-miterlimit:10;}.st5{fill:none;stroke:#4E5F65;stroke-width:50;stroke-linecap:round;stroke-miterlimit:10;} </style> <g> <mask id="myMask"> <;-- Pixels under white are rendered --> <rect x="0" y="0" width="1015" height="855" fill="white" /> <.-- Pixels under black are hidden --> <rect class="moveme" x="315" y="335" height="150" width="150" transform="rotate(45 395 395)"> <animateTransform attributeName="transform" attributeType="XML" type="scale" keyTimes="0; 0.25999; 0;26; 1" values="1; 1. 0, 0" dur="5s" additive="sum" repeatCount="indefinite"/> </rect> </mask> <g> <path class="st0" d="M718.54.66,06L294.41.490,19c-48.89.48,89-128.09.48,95-176.91.0.13c-48.82-48.82-48,76-128.02.0.13-176.91 s128,09-48.95.176.91-0,13" /> <path class="st1" d="M683.19.30,7L258.92.454,97c-29.29.29,29-76.78.29,29-106.07.0c-29.29-29.29-29,29-76.78.0-106.07 c29,29-29.29.76,78-29.29,106.07,0"/> <path class="st2" d="M753.9,101.42c0,0-424.26.424,26-424.26.424,26c-68.34.68,34-179.15.68,34-247.49.0s-68,34-179.15.0-247.49 s179,15-68.34,247.49,0"/> </g> <g> <path class="st0" d="M294.28.313,55l424.13.424,13c48.89,48.89,128.09,48.95,176.91.0.13c48,82-48.82.48.76-128.02-0.13-176.91 c-48.89-48.89-128.09-48.95-176.91-0,13"/> <path class="st2" d="M329.63.278,19L753.9.702,46c29.29,29.29,76.78,29.29,106.07.0c29,29-29.29.29,29-76.78.0-106.07 s-76.78-29,29-106.07,0"/> <path class="st1" d="M258.92,348,9c0.0,424.26,424.26,424.26.424,26c68.34,68.34,179.15,68.34,247.49.0s68,34-179.15.0-247.49 s-179.15-68,34-247.49,0"/> </g> </g> <g mask="url(#myMask)"> <circle r="20" mask="url(#myMask)"> <animateMotion dur="5s" repeatCount="indefinite" path="M718.54.66,06L294.41.490,19c-48.89.48,89-128.09.48,95-176.91.0.13c-48.82-48.82-48,76-128.02.0.13-176.91 s128,09-48.95.176.91-0,13 M294.28.313,55l424.13.424,13c48.89,48.89,128.09,48.95,176.91.0.13c48,82-48.82.48.76-128.02-0.13-176.91 c-48.89-48.89-128.09-48.95-176.91-0,13" /> </circle> <circle r="20"> <animateMotion dur="5s" repeatCount="indefinite" path="M753.9,101.42c0,0-424.26.424,26-424.26.424,26c-68.34.68,34-179.15.68,34-247.49.0s-68,34-179.15.0-247.49 s179,15-68.34,247.49,0 M329.63.278,19L753.9.702,46c29.29,29.29,76.78,29.29,106.07.0c29,29-29.29.29,29-76.78.0-106.07 s-76.78-29,29-106.07,0" /> </circle> <circle r="20"> <animateMotion id="circle1" dur="5s" repeatCount="indefinite" path="M683.19.30,7L258.92.454,97c-29.29.29,29-76.78.29,29-106.07.0c-29.29-29.29-29,29-76.78.0-106.07 c29,29-29.29.76,78-29.29,106.07,0 M258.92,348,9c0.0,424.26,424.26,424.26.424,26c68.34,68.34,179.15,68.34,247.49.0s68,34-179.15.0-247.49 s-179.15-68,34-247.49,0" /></circle></g> </svg>

You need to tweak it for your paths, basic concept is to add an animate on the element you want to change and use values and keyTimes (the whole animation is 0 to 1)

As you will notice, you get a color-gradient for free.
If you don't want that, add more keyTimes so the color fades occur faster

 <svg width="450" height="180"> <path id="PATH" d="M 50 90 H400" stroke="black"/> <g> <circle class="circle" r="30" fill="black"></circle> <circle class="circle" r=25 fill="red" > <animate attributeName="fill" attributeType="XML" values="red;green;yellow;hotpink;blue" keyTimes= "0;0.4;0.6;0.8;1" dur="3s" repeatCount="indefinite"/> </circle> <animateMotion dur="3s" repeatCount="indefinite"> <mpath href="#PATH" /> </animateMotion> </g> </svg>

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM