javascript - 基于 HTML 和 JS 的音频波形

标签 javascript html css

我试图通过这篇文章制作音频波形可视化

Play a moving waveform for wav audio file in html

这是代码

<html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Audio Visualizer</title>
        <script type="text/javascript" src="visualization.js"></script>
        <link rel="stylesheet" href="style.css">
    </head>
    <body>
        <audio id="audioElement" src="bensound-perception.mp3"></audio>
        <canvas id="wave"></canvas>
        <div>
          <button onclick="audioElement.play()">Play the Audio</button>
          <button onclick="audioElement.pause()">Pause the Audio</button>
          <button onclick="audioElement.volume+=0.1">Increase Volume</button>
          <button onclick="audioElement.volume-=0.1">Decrease Volume</button>
        </div>

        <figure>
            <figcaption>Listen to the Track:</figcaption>
            <audio
                controls
                src="bensound-perception.mp3">
                    Your browser does not support the
                    <code>audio</code> element.
            </audio>
        </figure>
    </body>
</html>

这是JS代码

audioElement = document.getElementById('audioElement');
var audioCtx = new (window.AudioContext || window.webkitAudioContext)();
var audioSrc = audioCtx.createMediaElementSource(audioElement);
var analyser = audioCtx.createAnalyser();

// Bind our analyser to the media element source.
audioSrc.connect(analyser);
audioSrc.connect(audioCtx.destination);

//Get frequency data (800 = max frequency)
var frequencyData = new Uint8Array(400);
//Use below to show all frequencies
//var frequencyData = new Uint8Array(analyser.frequencyBinCount);

//Create canvas
var canvas = document.getElementById("wave");
canvas.style.width = "1000px";
canvas.style.height = "100px";

//High dpi stuff
canvas.width = parseInt(canvas.style.width) * 2;
canvas.height = parseInt(canvas.style.height) * 2;

//Get canvas context
var ctx = canvas.getContext("2d");

//Set stroke color to yellow
ctx.strokeStyle = "#ffff00";

//Draw twice as thick lines due to high dpi scaling
ctx.lineWidth = 2;

//Save x and y from the previous drawing
var drawX = 0;
var drawY = 0;

//Total duration (Seconds)
var duration;

//The animation reference
var animation;

//Audio is loaded
audioElement.oncanplaythrough = function() {

    //Get duration
    duration = audioElement.duration;

    //On play
    audioElement.onplay = function() {
        //Start drawing
        drawWave();
    };

    //On pause
    audioElement.onpause = function() {
        //Stop drawing
        cancelAnimationFrame(animation);
    };

    //On ended
    audioElement.onended = function() {
        //Stop drawing
        cancelAnimationFrame(animation);

        //Clear previous drawing
        ctx.clearRect(0, 0, canvas.width, canvas.height);

        //Clear previous x and y values
        drawX = 0;
        drawY = 0;

        //Prevent audio from looping (you can remove this if you want it to loop)
        audioElement.pause();
    };
};

//Our drawing method
function drawWave() {

    //Current time (seconds)
    var currentTime = audioElement.currentTime;

    // Copy frequency data to frequencyData array.
    analyser.getByteFrequencyData(frequencyData);

    //Total loudness of all frequencies in frequencyData
    var totalLoudness = 0;
    for(var i = 0; i < frequencyData.length; i++) {
        totalLoudness += frequencyData[i];
    }

    //Average loudness of all frequencies in frequencyData
    var averageLoudness = totalLoudness / frequencyData.length;

    //Get the previous x axis value
    var previousDrawX = drawX;

    //Scale of progress in song (from 0 to 1)
    drawX =  currentTime / duration;
    //Multiply with canvas width to get x axis value
    drawX *= canvas.width;

    //Get the previous y axis value
    var previousDrawY = drawY;

    //Scale of average loudness from (0 to 1), frequency loudness scale is (0 to 255)
    drawY = averageLoudness / 255;
    //Multiply with canvas height to get scale from (0 to canvas height)
    drawY *= canvas.height;
    //Since a canvas y axis is inverted from a normal y axis we have to flip it to get a normal y axis value
    drawY = canvas.height - drawY;

    //Draw line
    ctx.beginPath();
    ctx.moveTo(previousDrawX, previousDrawY);
    ctx.lineTo(drawX, drawY);
    ctx.stroke();

    //Animate
    animation = requestAnimationFrame(drawWave);
}

这是CSS

figure {
    margin: 0;
}

但它对我不起作用,并且在页面上也在控制台上显示一些错误它只显示按钮但不显示音频可视化和音频工作完美这就是为什么我使用图形 block 来测试它......

请看我附上的截图。

Console Error and Output

我还尝试了其他已经在 Stackoverflow 上讨论过的帖子,但没有发现任何像上面那样相关和简单的帖子。

如果有人能帮我解决这个问题,我将不胜感激。

提前致谢

最佳答案

错误表明你的JS代码找不到<audio />元素。确保页面上有此元素并在 document.getElementById(...) 中引用它使用实际元素的 ID。

关于javascript - 基于 HTML 和 JS 的音频波形,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57891964/

相关文章:

html - 在 tumblr 主题上定位 flash 对象

html - 将 CSS Badge 并排 float 我想我想 float

javascript - 从表中获取所有第一个子元素

html - 在一个盒子里得到 2 个 Div?

jQuery:如何将出现在 "hover"上的按钮更改为移动设备点击时出现的按钮?

html - 即使页面很长或很短,如何将文本移动到页面底部?

javascript - 在页面加载时水平和垂直居中 DIV

javascript - jsonp comet 挂起请求导致浏览器上出现丑陋的 "loading"状态

c# - 从 JavaScript 触发对 C# asp.net 代码的回调

javascript - jquery 创建双重验证错误