chart = {
const height = width * 0.6;
const theSvg = d3.select(DOM.svg(width, height)).attr("id", "the-chart");
const g = theSvg.append("g");
g.append("g").attr("class", "slices");
g.append("g").attr("class", "labels");
g.append("g").attr("class", "lines");
const radius = Math.min(width, height) / 2;
const pie = d3
.pie()
.sort(null)
.value(function(d) {
return d.value;
});
const arc = d3
.arc()
.outerRadius(radius * 0.8)
.innerRadius(radius * 0.4);
const outerArc = d3
.arc()
.innerRadius(radius * 0.9)
.outerRadius(radius * 0.9);
g.attr("transform", "translate(" + width / 2 + "," + height / 2 + ")");
const key = function(d) {
return d.data.label;
};
change(randomData());
function change(data) {
console.log(data);
/* ------- PIE SLICES -------*/
const pieData = pie(data);
const slice = g
.select(".slices")
.selectAll("path.slice")
.data(pieData, key);
slice
.enter()
.insert("path")
.style("fill", function(d) {
return color(d.data.label);
})
.attr("class", "slice")
.merge(slice)
.transition()
.duration(1000)
.attrTween("d", function(d) {
console.log("i");
this._current = this._current || d;
const interpolate = d3.interpolate(this._current, d);
this._current = interpolate(0);
return function(t) {
return arc(interpolate(t));
};
});
slice.exit().remove();
/* ------- TEXT LABELS -------*/
const text = g
.select(".labels")
.selectAll("text")
.data(pie(data), key);
function midAngle(d) {
return d.startAngle + (d.endAngle - d.startAngle) / 2;
}
text
.enter()
.append("text")
.attr("dy", ".35em")
.text(function(d) {
return d.data.label;
})
.merge(text)
.transition()
.duration(1000)
.attrTween("transform", function(d) {
this._current = this._current || d;
const interpolate = d3.interpolate(this._current, d);
this._current = interpolate(0);
return function(t) {
const d2 = interpolate(t);
const pos = outerArc.centroid(d2);
pos[0] = radius * (midAngle(d2) < Math.PI ? 1 : -1);
return "translate(" + pos + ")";
};
})
.styleTween("text-anchor", function(d) {
this._current = this._current || d;
const interpolate = d3.interpolate(this._current, d);
this._current = interpolate(0);
return function(t) {
const d2 = interpolate(t);
return midAngle(d2) < Math.PI ? "start" : "end";
};
});
text.exit().remove();
/* ------- SLICE TO TEXT POLYLINES -------*/
const polyline = g
.select(".lines")
.selectAll("polyline")
.data(pie(data), key);
polyline
.join("polyline")
.transition()
.duration(1000)
.attrTween("points", function(d) {
this._current = this._current || d;
const interpolate = d3.interpolate(this._current, d);
this._current = interpolate(0);
return function(t) {
const d2 = interpolate(t);
const pos = outerArc.centroid(d2);
pos[0] = radius * 0.95 * (midAngle(d2) < Math.PI ? 1 : -1);
return [arc.centroid(d2), outerArc.centroid(d2), pos];
};
});
polyline.exit().remove();
}
return Object.assign(theSvg.node(), {
update() {
change(randomData());
}
});
}