viewof date = {
var count = 0;
const svg = d3.select(DOM.svg(width, height))
.style("-webkit-tap-highlight-color", "transparent");
const lines = svg.append("g")
.selectAll("g")
.data(series)
.join("g")
.append("line")
.attr("transform", d => "translate(0,"+ (y(1) - y(d.values[0].value / d.values[0].value)) + y(d.values[0].value)+")")
.attr("x1", margin.left)
.attr("x2", width - margin.right)
.attr("stroke", d => z(d.key))
.attr("stroke-width", "1")
.style("opacity", "0.5");
const ruleanchor = svg.append("g");
const rule = ruleanchor.append("g")
.append("line")
.attr("y1", height)
.attr("y2", 0)
.attr("stroke", "black")
.attr("stroke-width", "2");
const rulehorizontal = ruleanchor.append("g")
.append("line")
.attr("x1", 0)
.attr("x2", width)
.attr("stroke", "grey")
.attr("stroke-width", "2");
const serie = svg.append("g")
.style("font", "arial 13px sans-serif")
.selectAll("g")
.data(series)
.join("g");
const path = serie.append("path")
.attr("fill", "none")
.attr("stroke-width", 5)
.attr("stroke-linejoin", "round")
.attr("stroke-linecap", "round")
.attr("stroke", d => z(d.key))
.attr("d", d => line(d.values));
svg.append("g")
.call(xAxis);
svg.append("g")
.call(yAxis);
const box = serie.append("g")
.attr("display", "none");
box.append("rect")
.attr("x", -45)
.attr("y", -30)
.attr("width", 90)
.attr("height", 20)
.attr("fill", "white")
.style("opacity", "0.66");
const dot = box.append("g");
dot.append("circle")
.attr("r", 5);
dot.append("text")
.style("font", "bold 14px sans-serif")
.attr("text-anchor", "middle")
.attr("x", 0)
.attr("y", -15);
const increasenumbers = serie.append("text")
.attr("x", x.range()[1] + 3)
.attr("y", d => y(d.values[d.values.length - 1].value)*1.2)
.attr("dy", "0.35em")
.text(d => d.values[d.values.length - 1].valueabs)
.attr("fill", d => z(d.key));
const yeartext = serie.append("text")
.attr("x", x.range()[1] - 330)
.attr("y", 135)
.attr("dy", "0.35em")
.attr("width", 100)
.attr("fill", "grey")
.text("Since 1960 we saw an increase in");
const increasetext = serie.append("text")
.attr("x", x.range()[1] + 97)
.attr("y", d => y(d.values[d.values.length - 1].value)*1.2)
.attr("dy", "0.35em")
.attr("width", 100)
.attr("fill", "grey")
.attr("text-anchor", "end")
.text(d => d.key +":")
.attr("fill", d => z(d.key));
var legendHeight = 12,
interLegend = 4,
colorWidth = legendHeight*3;
var legendContainer = svg.append("g")
.classed("legend", true)
.attr("transform", "translate("+[width-136, height-50]+")");
var legends = legendContainer.selectAll(".legend")
.data(series)
.enter();
var legend = legends.append("g")
.classed("legend", true)
.attr("transform", function(d,i){
return "translate("+[0, -i*(legendHeight+interLegend)]+")";
})
legend.append("rect")
.classed("legend-color", true)
.attr("y", -legendHeight)
.attr("width", colorWidth)
.attr("height", legendHeight)
.style("fill", d=> z(d.key));
legend.append("text")
.style("font-size", "11px")
.attr("transform", "translate("+[-5, -2]+")")
.attr("text-anchor", "end")
.text(d => d.values[0].seriesname);
d3.transition()
.ease(d3.easeLinear)
.duration(4000)
.tween("date", () => {
const i = d3.interpolateDate(x.domain()[1], x.domain()[0]);
return t => update(i(t));
});
function update(date) {
date = d3.timeDay.round(date);
const i = bisect(series[0].values, date, 0, series[0].values.length - 1);
var toplineposition = 1000;
series.forEach(function(element) {
const i = bisect(element.values, date, 0, element.values.length - 1);
const lineposition = (y(1) - y(element.values[i].value / element.values[0].value)) + y(element.values[element.values.length-1].value);
if (lineposition < toplineposition) toplineposition = lineposition;
});
ruleanchor.attr("transform", `translate(${x(date) + 0.5},${toplineposition})`);
serie.attr("transform", ({values}) => {
const i = bisect(values, date, 0, values.length - 1);
return `translate(0,${y(1) - y(values[i].value / values[0].value)})`;
});
box.attr("transform", ({values}) => {
const i = bisect(values, date, 0, values.length - 1);
return `translate(${x(date) + 0.5},${y(values[i].value)})`;
});
dot.attr("fill",d=>z(d.key));
dot.select("text").text(d=>d.values[i].valueabs+" "+d.values[i].unit);
yeartext.attr("transform", ({values}) => {
const i = bisect(values, date, 0, values.length - 1);
return `translate(-100,${-(y(1) - y(values[i].value / values[0].value))+toplineposition-148})`;
});
yeartext.text(({values}) => {
return "Compared to "+date.getFullYear()+" we saw an increase in";
});
increasetext.attr("transform", ({values}) => {
const i = bisect(values, date, 0, values.length - 1);
return `translate(-100,${-(y(1) - y(values[i].value / values[0].value))+toplineposition-186})`;
});
increasenumbers.attr("transform", ({values}) => {
const i = bisect(values, date, 0, values.length - 1);
return `translate(0,${-(y(1) - y(values[i].value / values[0].value))+toplineposition-186})`;
});
increasenumbers.text(({values}) => {
const i = bisect(values, date, 0, values.length - 1);
return "+"+(values.slice(-1)[0].valueabs-values[i].valueabs).toFixed(1)+" "+ values[0].unit;
});
svg.property("value", date).dispatch("input");
}
function moved() {
update(x.invert(d3.mouse(this)[0]));
/*
const ym = y.invert(d3.mouse(this)[1]);
const date = d3.timeDay.round(x.invert(d3.mouse(this)[0]));
const i = bisect(series[0].values, date, 0, series[0].values.length - 1);
//const s = series.reduce((a, b) => Math.abs((y(1) - y(a.values[i].value / a.values[0].value)) + y(a.values[i].value)) - y(ym) < Math.abs((y(1) - y(b.values[i].value / b.values[0].value)) + y(b.values[i].value) - y(ym)) ? a : b);
const s = series.reduce((a, b) => Math.abs((y(1) - y(a.values[i].value / a.values[0].value)) + y(a.values[i].value)-y(ym)) < Math.abs((y(1) - y(b.values[i].value / b.values[0].value)) + y(b.values[i].value)-y(ym)) ? a : b);
//path.attr("stroke", d => d === s ? null : "#ddd").filter(d => d === s).raise();
//dot.attr("transform", `translate(${x(date) + 0.5},${(y(1) - y(s.values[i].value / s.values[0].value)) + y(s.values[i].value)})`);
//box.attr("transform", `translate(${x(date) + 0.5},${(y(1) - y(s.values[i].value / s.values[0].value)) + y(s.values[i].value)})`);
box.attr("transform", d=>`translate(${x(date) + 0.5},0)`);
dot.attr("fill",d=>z(d.key));
dot.select("text").text(d=>d.values[i].valueabs+" "+d.values[i].unit);
*/
d3.event.preventDefault();
}
update(x.domain()[0]);
function entered() {
//path.style("mix-blend-mode", null).attr("stroke", "#ddd");
box.attr("display", null);
}
function left() {
//path.style("mix-blend-mode", "multiply").attr("stroke", null);
box.attr("display", "none");
}
if ("ontouchstart" in document) svg
.style("-webkit-tap-highlight-color", "transparent")
.on("touchmove", moved)
.on("touchstart", entered)
.on("touchend", left)
else svg
.on("mousemove", moved)
.on("mouseenter", entered)
.on("mouseleave", left);
return svg.node();
}