规范化堆叠条形图绘图问题。无论数据如何,所有矩形均等分
Normalized stacked bar chart plotting issue. All rect are equally divided irrespective of data
您好,我正在使用这个示例 here to construct a normalized stacked bar chart. My data structure is a bit different from what is normally used. I am able to plot the chart, but somewhere the calculation is getting messed up and I am having a hard time figuring it out. I have created a pen。如您所见,条形图被平均分配,我认为这不是应该发生的情况。我猜 y0, y1
计算没有正确发生。感谢解决此问题的任何努力。
代码片段
var normalizedStackedData = dataset;
var excludedYaxisKey = "sum(quantity)";
console.log(normalizedStackedData);
checkLength(normalizedStackedData);
function plotNormalizedStack(data) {
var x = d3.scale.ordinal()
.rangeRoundBands([0, WIDTH], .1);
var y = d3.scale.linear()
.rangeRound([HEIGHT, 0]);
var color = d3.scale.ordinal()
.range(["#98abc5", "#8a89a6", "#7b6888", "#6b486b", "#a05d56", "#d0743c", "#ff8c00"]);
var xAxis = d3.svg.axis()
.scale(x)
.orient("bottom")
.tickValues(_arr.map(function(d) {
return d[excludedYaxisKey];
}));
var yAxis = d3.svg.axis()
.scale(y)
.orient("left")
.tickFormat(d3.format(".0%"));
appendResponsiveSvg();
svg.append("g")
.attr("transform", "translate(" + MARGINS.left + "," + MARGINS.top + ")");
color.domain(d3.keys(data[0]).filter(function(key) { return key !== excludedYaxisKey; }));
var nested_data = d3.nest()
.key(function(d) { return d["state"]; })
.entries(normalizedStackedData);
var domain = [excludedYaxisKey]//Object.keys(d);
var y0;
nested_data.forEach(function(_data) {
_data.values.map(function(d, index){
y0 = 0;
_data.groupedItem = [];
for (var i = 0; i < (_data.values).length; i++) {
_data.groupedItem.push(domain.map(function(name) { return {label: "quantity"+(i+1) ,name: name, y0: y0, y1: y0 += +d[name]}; })[0]);
}
_data.groupedItem.forEach(function(d) {
d.y0 /= y0;
d.y1 /= y0;
});
});
});
data = nested_data;
data.sort(function(a, b) { return b.groupedItem[0].y1 - a.groupedItem[0].y1; });
x.domain(data.map(function(d) { return d["key"]; }));
svg.append("g")
.attr("class", "x axis")
.attr("transform", "translate(0," + HEIGHT + ")")
.call(xAxis);
svg.append("g")
.attr("class", "y axis")
.call(yAxis);
var state = svg.selectAll(".state")
.data(data)
.enter().append("g")
.attr("class", "state")
.attr("transform", function(d) { return "translate(" + x(d["key"]) + ",0)"; });
state.selectAll("rect")
.data(function(d) { return d.groupedItem; })
.enter().append("rect")
.attr("width", x.rangeBand())
.attr("y", function(d) {
return y(d.y1);
})
.attr("height", function(d) {
return y(d.y0) - y(d.y1);
})
.style("fill", function(d) { return color(d.label); });
}
plotNormalizedStack(normalizedStackedData);
我发现您的堆叠数据操作步骤很难阅读和调试。由于您没有变量 domain
(您正在为 运行 .map
创建一个数组),只需将其丢弃并为感兴趣的特定属性编写代码。考虑到这一点,它简化为更具可读性:
nested_data.forEach(function(d0) {
d0.groupedItem = [];
var y0 = 0;
d0.values.forEach(function(d1){
d0.groupedItem.push({
y0: y0,
y1: y0 += +d1["sum(quantity)"],
label: d1["zip"]
});
});
d0.groupedItem.forEach(function(d1){
d1.y0 /= y0;
d1.y1 /= y0;
});
});
完整运行宁码:
<!DOCTYPE html>
<html>
<head>
<script data-require="d3@3.5.3" data-semver="3.5.3" src="//cdnjs.cloudflare.com/ajax/libs/d3/3.5.3/d3.js"></script>
<style>
body {
font: 10px sans-serif;
}
.axis path,
.axis line {
fill: none;
stroke: #000;
shape-rendering: crispEdges;
}
.browser text {
text-anchor: end;
}
svg {
width: 100%;
height: 400px;
}
</style>
</head>
<body>
<svg width="100%" height="100%" preserveAspectRatio="xMinYMin meet" viewBox="-80 -10 1450 600" class="svg-content-responsive"></svg>
<script>
function getRes(data) {
var _len = data.length;
var offset = 20;
var _range = Math.round(_len / offset);
//console.log("myRange : ", _range);
var _arr = [];
var _res = [];
for (var i = 0; i < 20; i++) {
if (_range * i < data.length)
_res.push(data[_range * i]);
}
//console.log(_res);
return _res;
}
function checkLength(data) {
if (data.length >= 50) {
_arr = getRes(data);
} else {
_arr = data;
}
}
var WIDTH = 1250,
HEIGHT = 500,
MARGINS = {
top: 20,
right: 20,
bottom: 20,
left: 50
},
xoffset = 22,
svg = [],
tooltip = [];
var dataset = [{
"state": "AK",
"zip": "99546",
"sum(quantity)": "623.95"
}, {
"state": "AL",
"zip": "35440",
"sum(quantity)": "265.40"
}, {
"state": "CA",
"zip": "93510",
"sum(quantity)": "682.81"
}, {
"state": "CA",
"zip": "95220",
"sum(quantity)": "367.14"
}, {
"state": "GA",
"zip": "30102",
"sum(quantity)": "609.85"
}, {
"state": "GA",
"zip": "30103",
"sum(quantity)": "691.53"
}, {
"state": "IA",
"zip": "50001",
"sum(quantity)": "597.52"
}, {
"state": "IA",
"zip": "50601",
"sum(quantity)": "741.38"
}, {
"state": "IL",
"zip": "62214",
"sum(quantity)": "564.20"
}, {
"state": "LA",
"zip": "70420",
"sum(quantity)": "576.45"
}, {
"state": "LA",
"zip": "70511",
"sum(quantity)": "377.81"
}, {
"state": "LA",
"zip": "70710",
"sum(quantity)": "398.69"
}, {
"state": "MD",
"zip": "20606",
"sum(quantity)": "423.71"
}, {
"state": "MD",
"zip": "20607",
"sum(quantity)": "544.17"
}, {
"state": "MD",
"zip": "21005",
"sum(quantity)": "233.74"
}, {
"state": "MD",
"zip": "21520",
"sum(quantity)": "601.30"
}, {
"state": "ME",
"zip": "4406",
"sum(quantity)": "238.58"
}, {
"state": "ME",
"zip": "4606",
"sum(quantity)": "412.01"
}, {
"state": "MS",
"zip": "39735",
"sum(quantity)": "486.00"
}, {
"state": "MT",
"zip": "59001",
"sum(quantity)": "434.12"
}, {
"state": "ND",
"zip": "58001",
"sum(quantity)": "122.81"
}, {
"state": "ND",
"zip": "58002",
"sum(quantity)": "883.31"
}, {
"state": "NE",
"zip": "68001",
"sum(quantity)": "605.27"
}, {
"state": "NJ",
"zip": "8205",
"sum(quantity)": "630.63"
}, {
"state": "NM",
"zip": "87510",
"sum(quantity)": "1059.78"
}, {
"state": "NY",
"zip": "12404",
"sum(quantity)": "573.52"
}, {
"state": "NY",
"zip": "12405",
"sum(quantity)": "911.70"
}, {
"state": "NY",
"zip": "13606",
"sum(quantity)": "295.05"
}, {
"state": "NY",
"zip": "14410",
"sum(quantity)": "91.27"
}, {
"state": "OH",
"zip": "43802",
"sum(quantity)": "234.60"
}, {
"state": "OK",
"zip": "73520",
"sum(quantity)": "331.16"
}, {
"state": "OK",
"zip": "74330",
"sum(quantity)": "679.95"
}, {
"state": "OK",
"zip": "74720",
"sum(quantity)": "723.63"
}, {
"state": "OK",
"zip": "74821",
"sum(quantity)": "624.22"
}, {
"state": "OR",
"zip": "97810",
"sum(quantity)": "229.12"
}, {
"state": "PA",
"zip": "15410",
"sum(quantity)": "558.51"
}, {
"state": "PA",
"zip": "15520",
"sum(quantity)": "859.19"
}, {
"state": "PA",
"zip": "15610",
"sum(quantity)": "656.57"
}, {
"state": "PA",
"zip": "15611",
"sum(quantity)": "303.19"
}, {
"state": "PA",
"zip": "16820",
"sum(quantity)": "763.54"
}, {
"state": "PA",
"zip": "17301",
"sum(quantity)": "314.21"
}, {
"state": "PA",
"zip": "18010",
"sum(quantity)": "522.25"
}, {
"state": "PA",
"zip": "19001",
"sum(quantity)": "541.86"
}, {
"state": "PA",
"zip": "19501",
"sum(quantity)": "314.65"
}, {
"state": "SC",
"zip": "29426",
"sum(quantity)": "387.74"
}, {
"state": "TX",
"zip": "77326",
"sum(quantity)": "497.49"
}, {
"state": "TX",
"zip": "79311",
"sum(quantity)": "619.80"
}, {
"state": "TX",
"zip": "79699",
"sum(quantity)": "546.51"
}, {
"state": "TX",
"zip": "79713",
"sum(quantity)": "424.77"
}, {
"state": "VA",
"zip": "23001",
"sum(quantity)": "340.39"
}, {
"state": "VA",
"zip": "23301",
"sum(quantity)": "446.56"
}, {
"state": "VT",
"zip": "5640",
"sum(quantity)": "548.90"
}, {
"state": "WA",
"zip": "98520",
"sum(quantity)": "223.90"
}, {
"state": "WI",
"zip": "54101",
"sum(quantity)": "680.80"
}, {
"state": "WI",
"zip": "54405",
"sum(quantity)": "485.17"
}, {
"state": "WV",
"zip": "25606",
"sum(quantity)": "404.94"
}];
function appendResponsiveSvg() {
svg = d3.select("svg")
.attr("width", 100 + "%")
.attr("height", 100 + "%")
.attr("preserveAspectRatio", "xMinYMin meet")
.attr("viewBox", "-80 -10 " + (WIDTH + 200) + " " + (HEIGHT + 100))
.classed("svg-content-responsive", true);
return svg;
}
var normalizedStackedData = dataset;
var excludedYaxisKey = "sum(quantity)";
//console.log(normalizedStackedData);
checkLength(normalizedStackedData);
function plotNormalizedStack(data) {
var x = d3.scale.ordinal()
.rangeRoundBands([0, WIDTH], .1);
var y = d3.scale.linear()
.rangeRound([HEIGHT, 0]);
var color = d3.scale.ordinal()
.range(["#98abc5", "#8a89a6", "#7b6888", "#6b486b", "#a05d56", "#d0743c", "#ff8c00"]);
var xAxis = d3.svg.axis()
.scale(x)
.orient("bottom");
var yAxis = d3.svg.axis()
.scale(y)
.orient("left")
.tickFormat(d3.format(".0%"));
appendResponsiveSvg();
svg.append("g")
.attr("transform", "translate(" + MARGINS.left + "," + MARGINS.top + ")");
color.domain(d3.keys(data[0]).filter(function(key) {
return key !== excludedYaxisKey;
}));
var nested_data = d3.nest()
.key(function(d) {
return d["state"];
})
.entries(normalizedStackedData);
var domain = [excludedYaxisKey] //Object.keys(d);
var y0;
nested_data.forEach(function(d0) {
d0.groupedItem = [];
var y0 = 0;
d0.values.forEach(function(d1){
d0.groupedItem.push({
y0: y0,
y1: y0 += +d1["sum(quantity)"],
label: d1["zip"]
});
});
d0.groupedItem.forEach(function(d1){
d1.y0 /= y0;
d1.y1 /= y0;
});
});
data = nested_data;
data.sort(function(a, b) {
return b.groupedItem[0].y1 - a.groupedItem[0].y1;
});
x.domain(data.map(function(d) {
return d["key"];
}));
svg.append("g")
.attr("class", "x axis")
.attr("transform", "translate(0," + HEIGHT + ")")
.call(xAxis);
svg.append("g")
.attr("class", "y axis")
.call(yAxis);
var state = svg.selectAll(".state")
.data(data)
.enter().append("g")
.attr("class", "state")
.attr("transform", function(d) {
return "translate(" + x(d["key"]) + ",0)";
});
state.selectAll("rect")
.data(function(d) {
return d.groupedItem;
})
.enter().append("rect")
.attr("width", x.rangeBand())
.attr("y", function(d) {
return y(d.y1);
})
.attr("height", function(d) {
return y(d.y0) - y(d.y1);
})
.style("fill", function(d) {
return color(d.label);
});
}
plotNormalizedStack(normalizedStackedData);
</script>
</body>
</html>
您好,我正在使用这个示例 here to construct a normalized stacked bar chart. My data structure is a bit different from what is normally used. I am able to plot the chart, but somewhere the calculation is getting messed up and I am having a hard time figuring it out. I have created a pen。如您所见,条形图被平均分配,我认为这不是应该发生的情况。我猜 y0, y1
计算没有正确发生。感谢解决此问题的任何努力。
代码片段
var normalizedStackedData = dataset;
var excludedYaxisKey = "sum(quantity)";
console.log(normalizedStackedData);
checkLength(normalizedStackedData);
function plotNormalizedStack(data) {
var x = d3.scale.ordinal()
.rangeRoundBands([0, WIDTH], .1);
var y = d3.scale.linear()
.rangeRound([HEIGHT, 0]);
var color = d3.scale.ordinal()
.range(["#98abc5", "#8a89a6", "#7b6888", "#6b486b", "#a05d56", "#d0743c", "#ff8c00"]);
var xAxis = d3.svg.axis()
.scale(x)
.orient("bottom")
.tickValues(_arr.map(function(d) {
return d[excludedYaxisKey];
}));
var yAxis = d3.svg.axis()
.scale(y)
.orient("left")
.tickFormat(d3.format(".0%"));
appendResponsiveSvg();
svg.append("g")
.attr("transform", "translate(" + MARGINS.left + "," + MARGINS.top + ")");
color.domain(d3.keys(data[0]).filter(function(key) { return key !== excludedYaxisKey; }));
var nested_data = d3.nest()
.key(function(d) { return d["state"]; })
.entries(normalizedStackedData);
var domain = [excludedYaxisKey]//Object.keys(d);
var y0;
nested_data.forEach(function(_data) {
_data.values.map(function(d, index){
y0 = 0;
_data.groupedItem = [];
for (var i = 0; i < (_data.values).length; i++) {
_data.groupedItem.push(domain.map(function(name) { return {label: "quantity"+(i+1) ,name: name, y0: y0, y1: y0 += +d[name]}; })[0]);
}
_data.groupedItem.forEach(function(d) {
d.y0 /= y0;
d.y1 /= y0;
});
});
});
data = nested_data;
data.sort(function(a, b) { return b.groupedItem[0].y1 - a.groupedItem[0].y1; });
x.domain(data.map(function(d) { return d["key"]; }));
svg.append("g")
.attr("class", "x axis")
.attr("transform", "translate(0," + HEIGHT + ")")
.call(xAxis);
svg.append("g")
.attr("class", "y axis")
.call(yAxis);
var state = svg.selectAll(".state")
.data(data)
.enter().append("g")
.attr("class", "state")
.attr("transform", function(d) { return "translate(" + x(d["key"]) + ",0)"; });
state.selectAll("rect")
.data(function(d) { return d.groupedItem; })
.enter().append("rect")
.attr("width", x.rangeBand())
.attr("y", function(d) {
return y(d.y1);
})
.attr("height", function(d) {
return y(d.y0) - y(d.y1);
})
.style("fill", function(d) { return color(d.label); });
}
plotNormalizedStack(normalizedStackedData);
我发现您的堆叠数据操作步骤很难阅读和调试。由于您没有变量 domain
(您正在为 运行 .map
创建一个数组),只需将其丢弃并为感兴趣的特定属性编写代码。考虑到这一点,它简化为更具可读性:
nested_data.forEach(function(d0) {
d0.groupedItem = [];
var y0 = 0;
d0.values.forEach(function(d1){
d0.groupedItem.push({
y0: y0,
y1: y0 += +d1["sum(quantity)"],
label: d1["zip"]
});
});
d0.groupedItem.forEach(function(d1){
d1.y0 /= y0;
d1.y1 /= y0;
});
});
完整运行宁码:
<!DOCTYPE html>
<html>
<head>
<script data-require="d3@3.5.3" data-semver="3.5.3" src="//cdnjs.cloudflare.com/ajax/libs/d3/3.5.3/d3.js"></script>
<style>
body {
font: 10px sans-serif;
}
.axis path,
.axis line {
fill: none;
stroke: #000;
shape-rendering: crispEdges;
}
.browser text {
text-anchor: end;
}
svg {
width: 100%;
height: 400px;
}
</style>
</head>
<body>
<svg width="100%" height="100%" preserveAspectRatio="xMinYMin meet" viewBox="-80 -10 1450 600" class="svg-content-responsive"></svg>
<script>
function getRes(data) {
var _len = data.length;
var offset = 20;
var _range = Math.round(_len / offset);
//console.log("myRange : ", _range);
var _arr = [];
var _res = [];
for (var i = 0; i < 20; i++) {
if (_range * i < data.length)
_res.push(data[_range * i]);
}
//console.log(_res);
return _res;
}
function checkLength(data) {
if (data.length >= 50) {
_arr = getRes(data);
} else {
_arr = data;
}
}
var WIDTH = 1250,
HEIGHT = 500,
MARGINS = {
top: 20,
right: 20,
bottom: 20,
left: 50
},
xoffset = 22,
svg = [],
tooltip = [];
var dataset = [{
"state": "AK",
"zip": "99546",
"sum(quantity)": "623.95"
}, {
"state": "AL",
"zip": "35440",
"sum(quantity)": "265.40"
}, {
"state": "CA",
"zip": "93510",
"sum(quantity)": "682.81"
}, {
"state": "CA",
"zip": "95220",
"sum(quantity)": "367.14"
}, {
"state": "GA",
"zip": "30102",
"sum(quantity)": "609.85"
}, {
"state": "GA",
"zip": "30103",
"sum(quantity)": "691.53"
}, {
"state": "IA",
"zip": "50001",
"sum(quantity)": "597.52"
}, {
"state": "IA",
"zip": "50601",
"sum(quantity)": "741.38"
}, {
"state": "IL",
"zip": "62214",
"sum(quantity)": "564.20"
}, {
"state": "LA",
"zip": "70420",
"sum(quantity)": "576.45"
}, {
"state": "LA",
"zip": "70511",
"sum(quantity)": "377.81"
}, {
"state": "LA",
"zip": "70710",
"sum(quantity)": "398.69"
}, {
"state": "MD",
"zip": "20606",
"sum(quantity)": "423.71"
}, {
"state": "MD",
"zip": "20607",
"sum(quantity)": "544.17"
}, {
"state": "MD",
"zip": "21005",
"sum(quantity)": "233.74"
}, {
"state": "MD",
"zip": "21520",
"sum(quantity)": "601.30"
}, {
"state": "ME",
"zip": "4406",
"sum(quantity)": "238.58"
}, {
"state": "ME",
"zip": "4606",
"sum(quantity)": "412.01"
}, {
"state": "MS",
"zip": "39735",
"sum(quantity)": "486.00"
}, {
"state": "MT",
"zip": "59001",
"sum(quantity)": "434.12"
}, {
"state": "ND",
"zip": "58001",
"sum(quantity)": "122.81"
}, {
"state": "ND",
"zip": "58002",
"sum(quantity)": "883.31"
}, {
"state": "NE",
"zip": "68001",
"sum(quantity)": "605.27"
}, {
"state": "NJ",
"zip": "8205",
"sum(quantity)": "630.63"
}, {
"state": "NM",
"zip": "87510",
"sum(quantity)": "1059.78"
}, {
"state": "NY",
"zip": "12404",
"sum(quantity)": "573.52"
}, {
"state": "NY",
"zip": "12405",
"sum(quantity)": "911.70"
}, {
"state": "NY",
"zip": "13606",
"sum(quantity)": "295.05"
}, {
"state": "NY",
"zip": "14410",
"sum(quantity)": "91.27"
}, {
"state": "OH",
"zip": "43802",
"sum(quantity)": "234.60"
}, {
"state": "OK",
"zip": "73520",
"sum(quantity)": "331.16"
}, {
"state": "OK",
"zip": "74330",
"sum(quantity)": "679.95"
}, {
"state": "OK",
"zip": "74720",
"sum(quantity)": "723.63"
}, {
"state": "OK",
"zip": "74821",
"sum(quantity)": "624.22"
}, {
"state": "OR",
"zip": "97810",
"sum(quantity)": "229.12"
}, {
"state": "PA",
"zip": "15410",
"sum(quantity)": "558.51"
}, {
"state": "PA",
"zip": "15520",
"sum(quantity)": "859.19"
}, {
"state": "PA",
"zip": "15610",
"sum(quantity)": "656.57"
}, {
"state": "PA",
"zip": "15611",
"sum(quantity)": "303.19"
}, {
"state": "PA",
"zip": "16820",
"sum(quantity)": "763.54"
}, {
"state": "PA",
"zip": "17301",
"sum(quantity)": "314.21"
}, {
"state": "PA",
"zip": "18010",
"sum(quantity)": "522.25"
}, {
"state": "PA",
"zip": "19001",
"sum(quantity)": "541.86"
}, {
"state": "PA",
"zip": "19501",
"sum(quantity)": "314.65"
}, {
"state": "SC",
"zip": "29426",
"sum(quantity)": "387.74"
}, {
"state": "TX",
"zip": "77326",
"sum(quantity)": "497.49"
}, {
"state": "TX",
"zip": "79311",
"sum(quantity)": "619.80"
}, {
"state": "TX",
"zip": "79699",
"sum(quantity)": "546.51"
}, {
"state": "TX",
"zip": "79713",
"sum(quantity)": "424.77"
}, {
"state": "VA",
"zip": "23001",
"sum(quantity)": "340.39"
}, {
"state": "VA",
"zip": "23301",
"sum(quantity)": "446.56"
}, {
"state": "VT",
"zip": "5640",
"sum(quantity)": "548.90"
}, {
"state": "WA",
"zip": "98520",
"sum(quantity)": "223.90"
}, {
"state": "WI",
"zip": "54101",
"sum(quantity)": "680.80"
}, {
"state": "WI",
"zip": "54405",
"sum(quantity)": "485.17"
}, {
"state": "WV",
"zip": "25606",
"sum(quantity)": "404.94"
}];
function appendResponsiveSvg() {
svg = d3.select("svg")
.attr("width", 100 + "%")
.attr("height", 100 + "%")
.attr("preserveAspectRatio", "xMinYMin meet")
.attr("viewBox", "-80 -10 " + (WIDTH + 200) + " " + (HEIGHT + 100))
.classed("svg-content-responsive", true);
return svg;
}
var normalizedStackedData = dataset;
var excludedYaxisKey = "sum(quantity)";
//console.log(normalizedStackedData);
checkLength(normalizedStackedData);
function plotNormalizedStack(data) {
var x = d3.scale.ordinal()
.rangeRoundBands([0, WIDTH], .1);
var y = d3.scale.linear()
.rangeRound([HEIGHT, 0]);
var color = d3.scale.ordinal()
.range(["#98abc5", "#8a89a6", "#7b6888", "#6b486b", "#a05d56", "#d0743c", "#ff8c00"]);
var xAxis = d3.svg.axis()
.scale(x)
.orient("bottom");
var yAxis = d3.svg.axis()
.scale(y)
.orient("left")
.tickFormat(d3.format(".0%"));
appendResponsiveSvg();
svg.append("g")
.attr("transform", "translate(" + MARGINS.left + "," + MARGINS.top + ")");
color.domain(d3.keys(data[0]).filter(function(key) {
return key !== excludedYaxisKey;
}));
var nested_data = d3.nest()
.key(function(d) {
return d["state"];
})
.entries(normalizedStackedData);
var domain = [excludedYaxisKey] //Object.keys(d);
var y0;
nested_data.forEach(function(d0) {
d0.groupedItem = [];
var y0 = 0;
d0.values.forEach(function(d1){
d0.groupedItem.push({
y0: y0,
y1: y0 += +d1["sum(quantity)"],
label: d1["zip"]
});
});
d0.groupedItem.forEach(function(d1){
d1.y0 /= y0;
d1.y1 /= y0;
});
});
data = nested_data;
data.sort(function(a, b) {
return b.groupedItem[0].y1 - a.groupedItem[0].y1;
});
x.domain(data.map(function(d) {
return d["key"];
}));
svg.append("g")
.attr("class", "x axis")
.attr("transform", "translate(0," + HEIGHT + ")")
.call(xAxis);
svg.append("g")
.attr("class", "y axis")
.call(yAxis);
var state = svg.selectAll(".state")
.data(data)
.enter().append("g")
.attr("class", "state")
.attr("transform", function(d) {
return "translate(" + x(d["key"]) + ",0)";
});
state.selectAll("rect")
.data(function(d) {
return d.groupedItem;
})
.enter().append("rect")
.attr("width", x.rangeBand())
.attr("y", function(d) {
return y(d.y1);
})
.attr("height", function(d) {
return y(d.y0) - y(d.y1);
})
.style("fill", function(d) {
return color(d.label);
});
}
plotNormalizedStack(normalizedStackedData);
</script>
</body>
</html>