I'm new in D3, so my question probably is pretty simple, but for me it's a big problem right now.
Question:
How to make Streamgraph vertically? my JSFiddle
I have this:
I should have this:
JS
var dataMetric = [
{
"id": 1,
"title": "Little Inc",
"metrics": {
"offers": 665,
"shares": 20,
"landings": 1124,
"leads": 1102,
"purchases": 88,
"friends": 74
}
},
{
"id": 2,
"title": "Marvin LLC",
"metrics": {
"offers": 20,
"shares": 2,
"landings": 20,
"leads": 25,
"purchases": 28,
"friends": 18
}
},
{
"id": 3,
"title": "Hodkiewicz, Jacobson and O'Conner",
"metrics": {
"offers": 834,
"shares": 8,
"landings": 759,
"leads": 683,
"purchases": 41,
"friends": 35
}
},
{
"id": 4,
"title": "Harber, Fahey and Berge",
"metrics": {
"offers": 233,
"shares": 5,
"landings": 352,
"leads": 348,
"purchases": 31,
"friends": 25
}
}
];
var metrics = ["offers", "shares", "landings", "leads", "purchases", "friends"];
var width = 500,
height = 200,
colors = {'0': '#6ff500', '1': '#ffad0a', '2': '#f90035', '3': '#6fD000'},
stack = d3.layout.stack().offset("expand");
var svg = d3.select("#timeline").append("svg")
.attr("width", width)
.attr("height", height);
var y = d3.scale.linear()
.domain([0, 1])
.range([height, 0]);
var color = d3.scale.linear()
.range(["#0D0", "#060"]);
streamed_history(dataMetric)
function streamed_history(data) {
var m = [];
data_array = metrics.forEach(function (f, metricIndex) {
for (var index in data) {
m[index] = m[index] || [];
m[index].push({x: metricIndex, y:data[index].metrics[f]});
}
})
layers = stack(m)
console.log(m)
layers = dataMetric.map(function (f, i) {
return {layer: layers[i], companyName: f.title, color: color(i/(dataMetric.length -1))}
})
var x = d3.scale.linear()
.domain([0, metrics.length - 1])
.range([0, width]);
var area = d3.svg.area()/*.interpolate("basis")*/
.x(function(d) { return x(d.x); })
.y0(function(d) { return y(null); })
.y1(function(d) { return y(d.y0 + d.y); });
function fixPath (path) {
var Lidx = path.indexOf('L');
var Cidx = path.slice(Lidx).indexOf('C');
var PCidx = path.slice(0,Lidx).lastIndexOf('C');
var lp = path.substr(PCidx, Lidx-PCidx);
var ss = path.substr(Lidx, Cidx);
return (path.slice(0,Lidx) + lp + ss + path.slice(Lidx));
}
//enter
svg.selectAll("path")
.data(layers.reverse())
.enter().append("path")
.attr("d", function (d) {
return fixPath(area(d.layer));
})
.style("fill", function(d) { return d.color; });
//update
d3.selectAll("path")
.data(layers)
.transition()
.duration(2000)
.attr("d", function (d) {return fixPath(area(d.layer));});
}
All you need to do is change the x to y and y to x in your area definition:
var area = d3.svg.area()/*.interpolate("basis")*/
.y(function(d) { return x(d.x); })
.x0(function(d) { return y(null); })
.x1(function(d) { return y(d.y0 + d.y); });
Complete example here.