What are the steps to ensure the equalizer start button functions properly?

I have created an application that mimics the functionality of an equalizer by displaying changes in audio frequencies.

https://i.sstatic.net/W7Fzi.png

Issues with animation arise when you click the "Start" button again.
The animation resets and begins from the start.
This can be prevented by implementing protection against repeated clicks while the animation is active
restart ="whenNotactive"

However, this solution only partially addresses the problem.

I attempted to trigger a begin = "start.click" event on the "Start" button and
an end = "pause.click" event on the "Pause" button.

Below is my code:

<svg version="1.1" xmlns="http://www.w3.org/2000/svg" 
    xmlns:xlink="http://www.w3.org/1999/xlink"
       width="100%" height="100%" viewBox="0 0 400 150" preserveAspectRatio="xMinYMin meet" >  

 <defs>  
     <!-- Mask for forming the display of a part of the active line (with stroke = "white") -->
   <mask id="msk">
      <rect width="100%" height="100%" fill="black" /> 
     <rect x="15" y="0" width="60" height="160" fill="white" stroke="white" /> 
</mask> 
 </defs>  
       <!-- Black background -->
      <rect width="22%" height="100%" fill="black" /> 
   <!-- Colored line markers to show equalizer frequency levels  -->
 <polyline  points="10,0 10,139" stroke="#4C4C50" />     
     <polyline  points="80,0 80,139" stroke="#4C4C50" />       
  <polyline id="grey" points="20,0 20,139" stroke="#2A2A2C" /> 
    <use xlink:href="#grey" x="10" />
     <use xlink:href="#grey" x="20" />
      <use xlink:href="#grey" x="30" />
        <use xlink:href="#grey" x="40" />
          <use xlink:href="#grey" x="50" />
   <polyline points="15,2 74,2" stroke-width="2" stroke="#2A2A2C" />     

    <!-- Code continues -->

    

However, this approach does not achieve the desired outcome. The animation restarts from the beginning when you press the Start button.
I am seeking a solution where pressing the Pause button stops the animation, and subsequently pressing the Start button resumes the animation from where it was paused.

Question:

How can I make the animation resume from where it left off when the Start button is pressed again?

It seems like achieving this purely in SVG may not be feasible. Therefore, CSS and JavaScript solutions would be greatly beneficial.

Answer №1

Dynamic SVG Animation

This solution utilizes Javascript methods:

SVGRoot.animationsPaused()
SVGRoot.unpauseAnimations()

function Initialize(evt)
  {  
     SVGDoc = evt.target.ownerDocument;
     RootSVG = SVGDoc.getElementById('SVGRoot');

     pauseBtn = SVGDoc.getElementById('pause1');
     playBtn = SVGDoc.getElementById('start1');
     eq = SVGDoc.getElementById('equalizer');
  };

  function PauseAnimation()
  {  
     RootSVG.pauseAnimations();
  };

  function StartAnimation()
  {
     if(RootSVG.animationsPaused()){
        RootSVG.unpauseAnimations();
     }
     else{
         eq.beginElement();
         
     }
  };
text.yellow {
fill:yellow;
font-size:6px;
}
g#gr1 {
stroke-linecap:round;
stroke-linejoin:round;
 mask:url(#msk);
 transform:translate(348, 0);  
}
#trace{
fill:none;
stroke:cyan;
stroke-width:1.5;
}
<svg version="1.1" xmlns="http://www.w3.org/2000/svg" 
    xmlns:xlink="http://www.w3.org/1999/xlink"
       width="100%" height="100%" viewBox="0 0 400 150" preserveAspectRatio="xMinYMin meet" 
       onload='Initialize(evt)' id = "SVGRoot" >  

 <defs>  
     <!-- Mask for forming the display of a part of the active line (with stroke = "white") -->
   <mask id="msk">
      <rect width="100%" height="100%" fill="black" /> 
     <rect x="15" y="0" width="60" height="160" fill="white" stroke="white" /> 
</mask> 
 </defs>  
       <!-- Black background -->
      <rect width="22%" height="100%" fill="black" /> 
   <!-- Colored line markers to show equalizer frequency levels  -->
 <polyline  points="10,0 10,139" stroke="#4C4C50" />     
     <polyline  points="80,0 80,139" stroke="#4C4C50" />       
  <polyline id="grey" points="20,0 20,139" stroke="#2A2A2C" /> 
    <use xlink:href="#grey" x="10" />
     <use xlink:href="#grey" x="20" />
      <use xlink:href="#grey" x="30" />
        <use xlink:href="#grey" x="40" />
          <use xlink:href="#grey" x="50" />
   <polyline points="15,2 74,2" stroke-width="2" stroke="#2A2A2C" />          
    <polyline points="15,19 74,19" stroke="red" />    
     <polyline points="15,44 74,44" stroke="green" />     
      <polyline points="15,69 74,69" stroke="dodgerblue" />
       <polyline points="15,94 74,94" stroke="green" /> 
        <polyline points="15,119 74,119" stroke="gold" /> 
         <polyline points="15,139 74,139" stroke-width="2" stroke="#2A2A2C" />
       <!-- Frequency labeling text -->
    
    <text class="yellow" x="12" y="15"  >16K</text>     
     <text class="yellow" x="12" y="40" >6K</text>  
      <text class="yellow" x="12" y="67"  >1K</text>  
        <text class="yellow" x="12" y="92"  >310</text> 
          <text class="yellow" x="12" y="117"  >170</text> 
           <!-- Button to start animation -->
        <g id="start1" transform="translate(60,0)" cursor="pointer" onclick='StartAnimation()'>
          <text x="2" y="147" font-size="8px" fill="yellow">Start</text> 
          <circle cx="23" cy="145" r="3" fill="greenyellow" />
        </g>   
            <g id="pause1" transform="translate(10,0)" cursor="pointer" onclick='PauseAnimation()'>
          <text x="2" y="147" font-size="8px" fill="yellow">Pause</text> 
          <circle cx="25" cy="145" r="3" fill="red" />
        </g>
        <!-- Trajectory of line movement showing audio frequency -->
 <g id="gr1"> 
 <path id="trace" transform="translate(348, 0)"  
     fill="none" stroke="cyan" stroke-width="1.5" d="m-246 68.4c0 0 32.6 0 47.8 0 9.2 0 12.9-30.8 16.4-22.3 4.8 11.5 6 43.3 6 43.3l7.9-26.6 5 35.9 8.9-63.5 3.7 80.9 5.2-93.7 4.8 108.2 6.6-125.2 2.6 84 4.8-31.8 5 23.3 2-18.1 5.5 12.1 4-12.1 2.8 26.6 3.3-31.8 3.6 43.1 5.5-55.5 2.2 70.8 6.5-80.9 3.2 95.4 6-112.9 2.7 125.7 7-131.5 2.6 131.5 5.9-131.6 5.1 118.8 8.7-108.2 5 93.7 10.1-87.9 3.4 76.1 11.8-69.2 3.1 54.3L-5.6 44.1 0 74.9 4 57.7 8.6 74.9 13.7 51l4.3 23.9 4.7-35.2 8.2 53.5 6.3-58.1 5.7 54.3 9-54.3 5.9 54.3 6.2-54.3 8.6 54.3 5.9-67.1 8.6 81.9 7.3-89.6 5.5 95.4 6.6-100.6 6.2 115.5 6.9-115.1 4.1 128.6 7.3-127.6 2.8 132.4 8.3-133.8 4.1 121 4.8-108.2 4.8 101.7 4.8-96.5 5.9 94.4 2.8-86.8 4.8 73 4.1-62.9 6.9 59.1 2.8-50.1 4.8 42.2 2.4-37.7 4.1 27 2.1-22.8 2.4 20.4 1.7-24.9 2.4 22.5 2.4-21.4 1.7 15.6 3.1-12.1 2.8 67.8 3.8-95.4 2.8 89.9 9.7-102.7 4.1 102 6.2-102 4.1 93.7 4.8-80.9 4.8 69.2 4.5-61.2 3.8 53.9 4.1-41.1 3.8 27.7 3.1-20.7 4.1 12.1 2.8-12.1 3.5 12.1 2.4-12.1 4.5 26.6 2.4-42.1 6.6 57 4.8-69.2 7.3 80.9 5.5-93.7 10.4 108.2 2.1-114.5 8 127.2 2.8-130.7 8 122.4 4.8-124.5 8 114.5 3.5-98.2 7.3 83 5.5-79.5 4.8 68.8 6.9-53.1V80.8l4.5-18 5.2 17.2 3-22.4 3.4 27 5.1-27 2.4 46.7 7.5-69.2 2.9 76.5c0 0 2.8-66.4 7.3-84.8 5.3-21.4 6.6 103.7 6.6 103.7l7-116.8 10 129.6 3.2-112.6 8.8 112.6 2.8-94.6 8 48.3 1.9-44 2.9 29.7 3.6-25 4.7 21.5 3.6-16.3 3.1 14.8 6.5-64.2 5.2 102.7 7.5-101.1 5.6 101.1 6.2-97.9 5.9 92.8 5.5-82.9 5.2 80.7 4.3-70.7 2.7 66.3 6-54.4 4.1 46 6.2-83.1 6.9 117.8 4.6-116.1 10 101.6 0.4-78.3 8 60.5c0 0 3.1-34.2 6.8-51 2.7-12.1 2 16.9 8.2 21.1 4.2 2.9 15.4 0.1 15.4 0.1h19.7" > 
         <!-- Equalizer line animation -->
       <animateTransform
        id="equalizer"
        attributeName="transform"
        type="translate"
        dur="22s"
        values="250 0;-650 0"
        fill="freeze"
        repeatCount="indefinite"
        restart="whenNotActive"
        />
 </path> 
  </g>   
</svg>  

NEW VERSION AVAILABLE

VIEW LIVE DEMO

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Is it possible to show more than five buttons in an Amazon Lex-v2 response display?

Here is the sessionState object I am working with: { "sessionAttributes": {}, "dialogAction": { "type": "ElicitSlot", "slotToElicit": "flowName" }, "intent": { "name": &q ...

What is the best way to generate an extensive table with HTML and AngularJS?

I am looking to implement an expandable table feature where a single header with a plus icon can be clicked to reveal the child rows beneath it. Currently, I have been able to achieve this functionality. However, I am facing an issue where the child rows ...

Using CSS to remove the background of a dropdown button in a <select> element

I need to style a <select> element so that it appears like plain text until clicked, revealing the pulldown choices. Ideally, I would like to include small arrows to indicate multiple options, but I can add those as image overlays if necessary. My p ...

Reorganize a list based on another list without generating a new list

Among the elements in my HTML list, there are items with text, input fields, and tables. I also have a specific order list like [3,1,2,0]. Is it feasible to rearrange the items in the HTML list on the page based on this order list without generating a new ...

The view of the Google map is filled with numerous rounded tiles

Map divided into 3x3 tiles I am looking to customize the appearance of my map and remove all spaces and rounded corners to create a seamless, undivided visual. Is there a way to modify a map tile attribute to achieve this effect? Below is the code snippet ...

Arranging card images in a row using semantic cards for optimal alignment

Trying to create a row of semantic-ui cards with images at the top, I ran into an issue with varying image heights causing different card title positions. The goal is to have all images be the same height while still adapting to larger screens. Although I ...

The CSS div mysteriously vanishes right before I can trigger the click event

My CSS code looks like this: #searchbar-wrapper input#header-searchbar:focus + #search-dropdown-wrapper { display: block; } The purpose of this code is to make a dropdown visible when a user focuses on a textbox. The default behavior should be th ...

I have encountered a problem with ejs-mate where I am experiencing an issue with the <%- layout("path") %> command. Even though the path is accurate, it is not functioning correctly

Error Message: Unable to locate file at 'D:\Web Projects\major\views\listings\layouts\boilerplate.ejs' I have made numerous attempts to resolve this issue, but unfortunately, I keep encountering the same error. I ha ...

Using Node's Express bodyParser() to access a JSON string that has been parsed

Question: How can I retrieve the parsed JSON object from the server side? I have successfully sent a JSON string to the server, but I am having trouble accessing the object once it is parsed. The client-side script for sending the JSON data is as follows ...

Remove webpack functions from the bundle

After following a comprehensive tutorial on bundling files with webpack and some additional online research, I successfully created a configuration file that organizes the modules in my library into the specified structure: dist/node/weather.min.js dist/we ...

Creating an overloaded callable interface using TypeScript

The thread on implementing a callable interface provides some helpful information, but it doesn't fully address my specific query. interface lol { (a: number): (b: number) => string // (a: string): (b: string) => string // overloaded wi ...

Generating a Transform stream with ExcelJS to produce xlsx files

Currently, I am utilizing the ExcelJS module and creating a wrapper to suit my specific needs. This wrapper implements the Transform Stream API, and surprisingly, the node version being used is 0.10.40. The ExcelJS module offers a stream API, and based on ...

Encountering this issue despite confirming the presence of data on the line before! What could be the missing piece here? Error: Unable to access property 'includes' of undefined

Here is the situation.. I'm retrieving data from a database and storing it in an array of objects. These objects represent articles. I am working on implementing a filter system based on categories. The objective is to apply a filter that checks for a ...

Swap out the current image for a different one

When a user clicks on different image or color options, I want to change the main image displayed. Below are the links to the alternative images: https://i.sstatic.net/DxJEb.jpg This is the HTML code: <div class="container"> <p class="img-main" ...

Is there a way to make divs expand on top of existing content when hovering over them, in order to avoid needing to scroll through overflow content? I am currently working with

I am working with 9 boxes contained within divs, each box includes data that exceeds the size of the box itself (represented by Some Text repeated for demonstration purposes). I am seeking a solution where hovering over any box will cause it to enlarge and ...

Using a structural directive in Angular 2 that accepts a String as an input

I am attempting to develop a custom structural directive using the example provided here When trying to pass a string as an input with a slight modification, I encountered an issue where the input value was returning 'undefined' when calling th ...

What is the process for updating a particular index in a list?

Currently, I am delving into React by working on a task master app. The concept is simple - each user input becomes a new task in an array of tasks. The app features Add, Delete, and Update buttons for managing these tasks. Everything is functioning smoot ...

Is your toggleclass button suffering from technical difficulties?

Why am I having trouble toggling the box with the button? I want it to maintain its current functionality and also toggle the box as well. Check out my JS fiddle for reference. Here's my code snippet: $(function timelinetiles() { $('.timeline ...

Ways to center items within a column using Bootstrap

I'm working on a React project with Bootstrap and I'm trying to align the contents of my second column to the bottom. However, everything I've tried so far hasn't been successful. I've seen others achieve this layout but for some r ...

Utilizing the $set method to capture a jQuery variable and append it to a Vue array object

Currently, I am retrieving data from an API using jQuery's getJson method to extract the information. After successfully obtaining the data, my aim is to assign it to a Vue array object by making use of app.$set. Although I have managed to extract an ...