Waveform made for audiohackathon.com
Audio from Serial
Waveform made for audiohackathon.com
Audio from Serial
<!DOCTYPE html> | |
<meta charset="utf-8"> | |
<style> | |
body{ position: relative; background: black; } | |
canvas{ position: fixed; } | |
div { | |
position: absolute; | |
top: 20px; | |
right: 20px; | |
background: #fff; | |
padding: 10px; | |
font-family: monospace; | |
cursor: pointer; | |
} | |
</style> | |
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/3.5.5/d3.min.js"></script> | |
<div>Click to Play</div> | |
<audio id="myAudio" src="serial.m4a"></audio> | |
<script> | |
var width = innerWidth, | |
height = innerHeight, | |
audio = document.getElementById('myAudio') | |
d3.select('div').on('click', () => { | |
audio.play() | |
init() | |
d3.select('div').remove() | |
}) | |
function init(){ | |
ctx = new AudioContext() | |
audioSrc = ctx.createMediaElementSource(audio) | |
analyser = ctx.createAnalyser() | |
analyser.smoothingTimeConstant = .3 | |
var gainNode = ctx.createGain() | |
gainNode.gain.value = 1 | |
audioSrc.connect(gainNode) | |
gainNode.connect(ctx.destination) | |
audioSrc.connect(analyser) | |
frequencyData = new Uint8Array(analyser.frequencyBinCount) | |
analyser.fftSize = 32768 | |
var bufferLength = analyser.frequencyBinCount | |
dataArray = new Uint8Array(bufferLength); | |
var x = d3.scale.linear().domain([0, dataArray.length/2]).range([0, width]) | |
var y = d3.scale.linear().domain([0, 200]).range([height, 0]) | |
var canvasCtx1 = d3.select('body') | |
.append('canvas') | |
.attr({width: width, height: height}) | |
.node() | |
.getContext('2d') | |
var canvas2 = d3.select('body') | |
.append('canvas') | |
.attr({width: width, height: height}) | |
.node() | |
var canvasCtx2 = canvasCtx2 = canvas2.getContext('2d') | |
var lastSum = 0 | |
var lastChangeT = 0 | |
d3.timer(function(t){ | |
analyser.getByteFrequencyData(dataArray) | |
//fade clear | |
canvasCtx1.fillStyle = 'rgba(0, 0, 0, .01)' | |
canvasCtx1.fillRect(0, 0, width, height) | |
//clear all | |
canvas2.width = width | |
canvasCtx1.beginPath() | |
var curSum = d3.sum(dataArray) | |
if (curSum > 1.1*lastSum && t - lastChangeT > 800){ | |
curColorI += 31 | |
lastChangeT = t | |
} | |
lastSum = curSum | |
canvasCtx1.strokeStyle = color() | |
canvasCtx2.beginPath() | |
canvasCtx2.strokeStyle = inverseColor() | |
var ma = 0 | |
dataArray.forEach(function(d,i){ | |
canvasCtx1.rect(x(i), y(d), 2, 2) | |
ma += d | |
if ((i % 32) || !i) return | |
canvasCtx2.lineTo(x(i), y(ma/32)) | |
ma = 0 | |
}) | |
canvasCtx1.stroke() | |
canvasCtx2.stroke() | |
}) | |
} | |
var curColorI = 0 | |
function color(){ | |
return d3.hsl(10*curColorI/2/Math.PI, 1, .6) | |
} | |
function inverseColor(){ | |
return d3.hsl((120 - 10*curColorI)/2/Math.PI, 1, .35) | |
} | |
</script> |