Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Using wavesurfer.js to animate a CSS property

wavesurfer.js is great for rendering a waveform from an audio file, but I'm wondering if it's possible to animate any CSS property to the amplitude/frequency of the waveform/spectrograph, being generated by wavesurfer.js? Is there a sort of variable I can assign to another parameter (for example: the opacity of an <img>)?

like image 955
Roland Avatar asked Nov 23 '16 10:11

Roland


1 Answers

Looking at wavesurfer.js, you can get AnalyserNode using wavesurfer.backend.analyser.

Note: you will have to check that analyser is an instance of AnalyserNode. It will only be this if the browser supports the Web Audio API.

From AnalyserNode you can get the AnalyserNode.frequencyBinCount property, you can then start creating a visualisation/animation.

I made a simple example (codepen) building on the wavesurfer.js examples on their site.

var wavesurfer = WaveSurfer.create({
  container: '#waveform',
  waveColor: '#5B88C8',
  progressColor: '#264E73'
});
wavesurfer.load('https://ia902606.us.archive.org/35/items/shortpoetry_047_librivox/song_cjrg_teasdale_64kb.mp3');

//get the AnalyserNode from wavesurfer
//@see https://developer.mozilla.org/en-US/docs/Web/API/AnalyserNode
var analyser = wavesurfer.backend.analyser,
  //array to store the frequency data
  //@see https://developer.mozilla.org/en-US/docs/Web/API/AnalyserNode/getByteFrequencyData
  frequencyData = new Uint8Array(analyser.frequencyBinCount),

  //div to animate and play/pause button
  box = document.getElementById('box'),
  play = document.getElementById('play');

//play button - play pause audio
play.addEventListener('click', function() {
  wavesurfer.playPause();
});

//wavesurfer 'audioprocess' event Fires continuously as the audio plays @see events on wave surfer http://wavesurfer-js.org/docs/events.html
wavesurfer.on('audioprocess', function(e) {

  analyser.getByteFrequencyData(frequencyData);
  //console.log(frequencyData);

  //simple example - get the first value in the array and set the width of the box
  var w = frequencyData[0] * 0.05;
  //apply a scale transform;
  box.style.transform = 'scale(' + w + ',1)';

});
/* add some transition */

.animation {
  margin: 50px auto;
  width: 50px;
  height: 50px;
  background-color: #71C2D0;
  transition: transform 0.1s ease-out;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/wavesurfer.js/1.2.3/wavesurfer.min.js"></script>
<div id="waveform"></div>
<div id="box" class="animation"></div>
<button id="play">Play</button>
like image 164
r8n5n Avatar answered Oct 15 '22 11:10

r8n5n