Skip to content

Instantly share code, notes, and snippets.

@eesur
Last active December 3, 2017 16:42
Show Gist options
  • Save eesur/ecdaf255a05402eb74c46d13145601a1 to your computer and use it in GitHub Desktop.
Save eesur/ecdaf255a05402eb74c46d13145601a1 to your computer and use it in GitHub Desktop.
d3 | ratio bar chart
var render = (function () {
var svg = d3.select('svg')
var vis = svg.select('#vis')
var width = +svg.attr('width')
var height = +svg.attr('height')
var xScale = d3.scaleLinear()
.domain([0, 100])
.range([0, width])
// append wrap
var wrap = vis.append('g')
.attr('class', 'ratio-wrap')
// append first rect
var firstRect = wrap.append('rect')
.attr('height', 88)
.attr('x', 0)
.attr('y', height / 2 - 50)
.style('fill', '#fbae17')
// append second rect
var scndRect = wrap.append('rect')
.attr('height', 88)
.attr('x', 0)
.attr('y', height / 2 - 50)
.style('fill', '#0095a3')
// append values
var label = vis.append('text')
.attr('class', 'ratio-label')
.attr('y', height / 2 + 5)
.style('text-anchor', 'middle')
// .style('dominant-baseline', 'central')
.style('font-size', '36px')
.style('fill', '#dddddd')
function update (data) {
// update the first rect
firstRect.attr('width', xScale(data[0]))
// update the second rect
scndRect.attr('width', xScale(data[1]))
// start the first rect after the first ends
.attr('x', xScale(data[0]))
// append the label
label
.attr('x', function () {
// ensure there is enough space to display numbers
console.log('xScale(data[0])', xScale(data[0]))
if (xScale(data[0]) < 90 || xScale(data[0]) > (width - 90)) {
return width / 2
} else {
return xScale(data[0])
}
})
.text(data[0] + ' : ' + data[1])
}
// expose the update
return update
})()

sketch of bar chart for displaying ratios (as percentage)

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<style>
html, body { height: 100%; }
body {
font-family: Consolas, monaco, monospace;
background: #dddddd;
width: 900px;
margin: 0 auto;
}
section {
padding-top: 30vh;
}
h3 {
margin: 0;
color: #fe9f97;
}
</style>
</head>
<body>
<section class="stats">
<h3>Ratio1 : Ratio2</h3>
<svg width="900" height="100">
<g id="vis"></g>
</svg>
</section>
<script src="https://d3js.org/d3.v4.min.js"></script>
<!-- d3 code -->
<script src=".script-compiled.js" charset="utf-8"></script>
<!-- render code -->
<script>
// render an update
render([57, 43])
d3.interval(function() {
let v1 = Math.floor(d3.randomUniform(5, 100)())
let v2 = 100 - v1
return render([v1, v2]);
}, 2000);
</script>
</body>
</html>
const render = (function () {
const svg = d3.select('svg')
const vis = svg.select('#vis')
const width = +svg.attr('width')
const height = +svg.attr('height')
const xScale = d3.scaleLinear()
.domain([0, 100])
.range([0, width])
// append wrap
const wrap = vis.append('g')
.attr('class', 'ratio-wrap')
// append first rect
const firstRect = wrap.append('rect')
.attr('height', 88)
.attr('x', 0)
.attr('y', height / 2 - 50)
.style('fill', '#fbae17')
// append second rect
const scndRect = wrap.append('rect')
.attr('height', 88)
.attr('x', 0)
.attr('y', height / 2 - 50)
.style('fill', '#0095a3')
// append values
const label = vis.append('text')
.attr('class', 'ratio-label')
.attr('y', height / 2 + 5)
.style('text-anchor', 'middle')
// .style('dominant-baseline', 'central')
.style('font-size', '36px')
.style('fill', '#dddddd')
function update (data) {
// update the first rect
firstRect.attr('width', xScale(data[0]))
// update the second rect
scndRect.attr('width', xScale(data[1]))
// start the first rect after the first ends
.attr('x', xScale(data[0]))
// append the label
label
.attr('x', function () {
// ensure there is enough space to display numbers
console.log('xScale(data[0])', xScale(data[0]))
if (xScale(data[0]) < 90 || xScale(data[0]) > (width - 90)) {
return width / 2
} else {
return xScale(data[0])
}
})
.text(data[0] + ' : ' + data[1])
}
// expose the update
return update
})()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment