<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>SVG Animation</title>
    <style>
        svg, input {
          display: block;
          margin: 2px;
        }

        svg {
          width: 200px;
          height: 200px;
          /*
          stroke: #FFFFFF;
          stroke-width: 2px;
          */
          fill: transparent;
        }
    </style>
</head>
<body>
    <input id="inputSec" type="number" placeholder="sec" value="10"/>
    <button onclick="run()">Run</button>
    <svg>
        <circle id="crclBg" cx="100" cy="100" r="50" fill="#333333" stroke="#EEEEEE" stroke-width="9" stroke-dashoffset="0" stroke-dasharray="0"/>
        <circle id="crclDp" cx="100" cy="100" r="50" fill="" stroke="#00cc44" stroke-width="9" stroke-dashoffset="0" stroke-dasharray="0"/>
        <text id="txtSec" x="100" y="100" fill="#FFFFFF" stroke="#FFFFFF" stroke-width="2" font-size="30" text-anchor="middle" dominant-baseline="central"></text>
    </svg>

    <script>
        // Simpler alternative to using SVG arcs: http://xahlee.info/js/svg_circle_arc.html
        // More about dash arrays: https://developer.mozilla.org/en-US/docs/Web/SVG/Attribute/stroke-dasharray
        
        const input     = document.querySelector("#inputSec");
        const circle    = document.querySelector("#crclDp");
        const text      = document.querySelector("#txtSec");

        // 1. Radius of SVG circle.
        const radius = parseFloat(circle.getAttribute("r"));
        const circumference = 2 * Math.PI * radius;   // Circle's circumference

        // 2. First, 1/4 of circumfence of 90 degrees. To start from top of the view,
        //    we must rotate it by 90 degrees. By default circle will start on the right.
        //    Stroke offset effectively rotates the circle.
        const strokeOffset = (1 / 4) * circumference; // need to know 1/4 of the circumference

        // 3. Rotate circle to start from the top.
        circle.setAttribute("stroke-dashoffset", strokeOffset);

        // 4. The length of visible dash, default 0.
        let strokeDasharray = 0;
        let angle = 0;
        
        const draw = (arc) =>
        {
            angle = (angle >= 360) ? 0 : angle + arc;

            // 4. Second, calculate dash array. We need dash array containing only two parts -
            //    visible dash, and invisible dash.
            //    Visible dash should have length of the chosen angle. Full circle is 360 degrees,
            //    and this 360 degrees does also equal the entire circumference. We want just a part of
            //    this entire circle to be visible - (angle / 360 degrees) returns a percentage value
            //    (between 0.0 and 1.0) of how much circumference should be visible.
            //    Hence, we then multiply (angle / 360) times the entire circumference.
            strokeDasharray = (angle / 360) * circumference;

            // 5. Create dash array of two elements (combined they must equal the entire circumference).
            //    First has the length of visible portion. Second, the remaining part.
            circle.setAttribute("stroke-dasharray", [strokeDasharray, circumference - strokeDasharray]);

            //console.log(angle);
        }

        const initCircle = () =>
        {
            angle = 360;
            draw(0);
            angle = 0;
        }

        let _sec = 0;
        let _itvlTime;
        let _loopCnt = 100;                 // loop time per 1 sec
        let _itvlUnit = 1000 / _loopCnt;    // 10/1000 milliseconds == 1/100 sec

        const run = () => 
        {
            if (_itvlTime == null)
            {
                // initialize
                initCircle();

                let _accLoopCnt = 0;

                _sec = parseInt(input.value);
                text.textContent = _sec;
                
                // loop (100 time per 1 sec)
                _itvlTime = setInterval(() =>
                {
                    ++_accLoopCnt;

                    let _arc =  360 / (_sec * _loopCnt);
                    draw(_arc);
                    
                    let _remainSec = parseInt(text.textContent);

                    if (_loopCnt ==  _accLoopCnt)
                    {
                        _accLoopCnt = 0;
                        --_remainSec;
                        text.textContent = _remainSec;

                        if (_remainSec <= 0)
                        {
                            clearInterval(_itvlTime);
                            _itvlTime = null;
                        }

                        //console.log(`${_accLoopCnt} : ${_remainSec}`);
                    }
                }, _itvlUnit);
            }
        }

        window.onload = function()
        {
            // initialize
            initCircle();
        }
    </script>
</body>
</html>