Skip to content

Instantly share code, notes, and snippets.

@jm3
Last active August 25, 2023 06:14
Show Gist options
  • Save jm3/9870108 to your computer and use it in GitHub Desktop.
Save jm3/9870108 to your computer and use it in GitHub Desktop.
d3.audio.waveforms
d3 audio waveforms block
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="description" content="">
<meta name="author" content="jm3">
<title>d3 audio waveforms</title>
<!-- build:css stylesheets/app.min.css-->
<link rel="stylesheet" type="text/css" href="http://fonts.googleapis.com/css?family=Roboto:400,100|Raleway:400,200|Amatic+SC">
<link rel="stylesheet" type="text/css" href="waveform.css">
<!-- endbuild-->
</head>
<body>
<div class="page">
<h1>d3 audio waveforms &middot;<a href="http://www.jm3.net/">john manoogian III</a></h1>
<div class="waveform">
<h2>divs:</h2>
<div></div>
<h2>SVG:</h2>
<div class="svg">
<!-- h2 Audio:-->
</div>
</div>
<iframe width="100%" height="166" scrolling="no" frameborder="no" src="https://w.soundcloud.com/player/?url=https%3A//api.soundcloud.com/tracks/141102884&amp;amp;color=ff5500&amp;amp;auto_play=false&amp;amp;hide_related=false&amp;amp;show_artwork=true" class="soundcloud_embed"></iframe>
</div>
<script src="http://d3js.org/d3.v3.min.js" charset="utf-8"></script>
<script src="waveform.js"></script>
<!-- endbuild-->
</body>
</html>
* {
margin: 0;
font-family: 'Amatic SC', cursive;
}
html {
margin: 1.0em;
}
h1 {
font-size: 48px;
font-weight: bold;
}
h1 a,
h1 a:visited {
text-decoration: none;
font-weight: normal;
font-size: 90%;
color: #000;
border-bottom: 1px dashed #bbb;
}
h1 a:hover {
color: red;
}
.waveform > svg,
.waveform > div {
border: 2px solid #ddd;
height: 140px;
margin-left: 40px;
padding: 2px;
position: relative;
width: 880px;
}
.waveform h2 {
margin-left: 40px;
font-size: 36px;
}
.waveform > div div.bar {
background-color: red;
position: absolute;
}
.waveform .svg g rect {
fill: red;
opacity: 0.5;
}
.soundcloud_embed {
display: none;
opacity: 0.5;
margin-left: 40px;
width: 968px;
/* weird padding offset; SC embed is slightly too short? */
}
.axis {
position: absolute;
top: 4px;
left: -40px;
}
.axis g path.domain {
display: none;
}
.axis g text {
font-family: 'Roboto', sans-serif;
opacity: 0.5;
font-size: 10px;
}
var wave_json;
var wave_uri = "http://public.jm3.net/d3/geiger.json";
var max_points = 1024;
var width = 880,
height = 140;
d3.json( wave_uri, function(error, json) {
wave_json = json.data.slice(1, max_points);
div_render( wave_json, ".waveform > div" );
svg_render( wave_json, ".waveform > .svg" );
});
function div_render( data, div ) {
var y = d3.scale.linear().range([height, -height]);
var x = d3.scale.linear().domain([0, data.length]);
var max_val = d3.max(data, function(d) { return d; });
y.domain([-max_val, max_val]);
var bar_width = width/data.length;
d3.select( div ).selectAll("div")
.data(wave_json)
.enter()
.append("div")
.attr("class", "bar")
.style("width", bar_width + "px" )
.style("height", function(d,i) {
return y(d) + "px";
})
.style("bottom", function(d) {
// 2px slide up because 2px padding
var bottom = height - Math.abs(y(d)/2) - height/2 + 2;
return bottom + "px";
})
.style("left", function(d,i) {
var left = x(i)*width; // could also do: i * bar_width;
return left + "px";
});
var axis = d3.svg.axis()
.scale(y)
.ticks(12)
.orient("left");
d3.select(".waveform > div").append("svg")
.attr("class", "axis")
.attr("width", 60)
.attr("height", height)
.append("g")
.attr("transform", "translate(40," + (height/2) + ")" )
.call(axis);
}
function svg_render( data, svg ) {
var node = d3.select(svg).append("svg")
.attr("class","chart")
.attr("width", width)
.attr("height", height);
var y = d3.scale.linear().range([height, -height]);
var max_val = d3.max(data, function(d) { return d; });
y.domain([-max_val, max_val]);
var x = d3.scale.linear().domain([0, data.length]);
var bar_width = width / data.length;
var chart = node.attr("width", width).attr("height", height);
var bar = chart.selectAll("g")
.data(data)
.enter().append("g") // svg "group"
.attr("transform", function(d, i) {
return "translate(" + i * bar_width + ",0)";
});
bar.append("rect")
.attr("y", function(d) {
var yv = height - Math.abs(y(d)/2) - height/2 + 2;
return yv;
})
.attr("height", function(d) {
return Math.abs(y(d)); })
.attr("width", bar_width );
var axis = d3.svg.axis()
.scale(y)
.ticks(12)
.orient("left");
d3.select(".svg").append("svg")
.attr("class", "axis")
.attr("width", 60)
.attr("height", height)
.append("g")
.attr("transform", "translate(40," + (height/2) + ")" )
.call(axis);
}
function d( s ) {
console.log( "log: " + s );
}
@bot5am
Copy link

bot5am commented Apr 10, 2023

Thanks! worked like a breeze.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment