Created
February 1, 2016 01:35
-
-
Save daluu/d43ec5e610dd5dedbbe1 to your computer and use it in GitHub Desktop.
d3 Pareto Chart Example
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<!DOCTYPE html> | |
<meta charset="utf-8"> | |
<style> | |
svg { | |
font: 10px sans-serif; | |
} | |
.bar rect { | |
fill: steelblue; | |
shape-rendering: crispEdges; | |
} | |
.axis path, .axis line { | |
fill: none; | |
stroke: #000; | |
shape-rendering: crispEdges; | |
} | |
.line { | |
fill: none; | |
stroke: purple; | |
stroke-width: 1.5px; | |
} | |
</style> | |
<body> | |
<script src="//d3js.org/d3.v3.min.js"></script> | |
<script> | |
//sample based upon: http://www.pryor.com/blog/creating-a-pareto-chart-in-excel/ | |
//TODO - perhaps add circle "points" on the line to match the reference sample | |
//Set dimensions | |
var m = {top: 50, right: 50, bottom: 50, left: 50} | |
, h = 500 - m.top - m.bottom | |
, w = 960 - m.left - m.right | |
, barWidth = 5; | |
var dataset = null; | |
d3.csv("pareto_data.csv",function(error,data){ | |
if (error) return console.log(error); | |
//typecast Amount to #, calculate total, and cumulative amounts | |
var totalAmount = 0; | |
for(var i = 0; i < data.length; i++){ | |
data[i].Amount = +data[i].Amount; | |
totalAmount += data[i].Amount; | |
if(i > 0){ | |
data[i]['CumulativeAmount'] = data[i].Amount + data[i-1].CumulativeAmount; | |
}else{ | |
data[i]['CumulativeAmount'] = data[i].Amount; | |
} | |
} | |
//now calculate cumulative % from the cumulative amounts & total, round % | |
for(var i = 0; i < data.length; i++){ | |
data[i]['CumulativePercentage'] = (data[i]['CumulativeAmount'] / totalAmount); | |
data[i]['CumulativePercentage'] = parseFloat(data[i]['CumulativePercentage'].toFixed(2)); | |
} | |
dataset = data; | |
//Axes and scales | |
var xScale = d3.scale.ordinal().rangeRoundBands([0, w], 0.1); | |
xScale.domain(data.map(function(d) { return d.Category; })); | |
var yhist = d3.scale.linear() | |
.domain([0, d3.max(data, function(d) { return d.Amount; })]) | |
.range([h, 0]); | |
var ycum = d3.scale.linear().domain([0, 1]).range([h, 0]); | |
var xAxis = d3.svg.axis() | |
.scale(xScale) | |
.orient('bottom'); | |
var yAxis = d3.svg.axis() | |
.scale(yhist) | |
.orient('left'); | |
var yAxis2 = d3.svg.axis() | |
.scale(ycum) | |
.orient('right'); | |
//Draw svg | |
var svg = d3.select("body").append("svg") | |
.attr("width", w + m.left + m.right) | |
.attr("height", h + m.top + m.bottom) | |
.append("g") | |
.attr("transform", "translate(" + m.left + "," + m.top + ")"); | |
//Draw histogram | |
var bar = svg.selectAll(".bar") | |
.data(data) | |
.enter().append("g") | |
.attr("class", "bar"); | |
bar.append("rect") | |
.attr("x", function(d) { return xScale(d.Category); }) | |
.attr("width", xScale.rangeBand()) | |
.attr("y", function(d) { return yhist(d.Amount); }) | |
.attr("height", function(d) { return h - yhist(d.Amount); }); | |
//Draw CDF line | |
var guide = d3.svg.line() | |
.x(function(d) { return xScale(d.Category); }) | |
.y(function(d){ return ycum(d.CumulativePercentage) }) | |
.interpolate('basis'); | |
var line = svg.append('path') | |
.datum(data) | |
.attr('d', guide) | |
.attr('class', 'line'); | |
//Draw axes | |
svg.append("g") | |
.attr("class", "x axis") | |
.attr("transform", "translate(0," + h + ")") | |
.call(xAxis); | |
svg.append("g") | |
.attr("class", "y axis") | |
.call(yAxis) | |
.append("text") | |
.attr("transform", "rotate(-90)") | |
.attr("y", 6) | |
.attr("dy", ".71em") | |
.style("text-anchor", "end") | |
.text("Amount"); | |
svg.append("g") | |
.attr("class", "y axis") | |
.attr("transform", "translate(" + [w, 0] + ")") | |
.call(yAxis2) | |
.append("text") | |
.attr("transform", "rotate(-90)") | |
.attr("y", 4) | |
.attr("dy", "-.71em") | |
.style("text-anchor", "end") | |
.text("Cumulative %"); | |
}); | |
</script> | |
</body> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Category | Amount | |
---|---|---|
Training Fees | 3750 | |
Hardware | 2980 | |
Office supplies | 2440 | |
Software | 1979 | |
Mileage | 841 | |
Other | 260 |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Sorry, I don't work with React at the moment. Forks and contributions (via comments or email contact) are welcome as you can't do PRs for gists here. You could perhap ask around and have a React expert convert this sample to React. The code logic should be same, just the UI presentation interface/layer changes per React.
This was meant to be a basic example showing how to render a pareto chart in D3 comparing against a non-D3 reference implementation.
You could probably try https://react-d3-library.github.io, or searching online for "react d3", etc. to find examples, to which you can then follow to adapt the code here. This might be a useful example: https://medium.com/codesphere-cloud/creating-data-visualizations-with-d3-and-reactjs-c288d7890390.