Public
Edited
Feb 6
2 forks
Insert cell
Insert cell
viewof noichart = {
const svg = d3.select(DOM.svg(width, height)).property("value", []);

const xAxis = (svg) =>
svg.attr("transform", `translate(0,${height - margin.bottom})`).call(
d3
.axisBottom(x)
.ticks(d3.timeMonth.every(12))
.tickFormat((d) => (d <= d3.timeYear(d) ? d.getFullYear() : null))
);

const yAxis = (svg) =>
svg
.attr("transform", `translate(${margin.left},0)`)
.call(
d3
.axisRight(y)
.tickSize(width - margin.left - margin.right)
.tickFormat(formatTick)
)
.call((g) => g.select(".domain").remove())
.call((g) =>
g.attr("stroke-opacity", 0.5).attr("stroke-dasharray", "2,2")
)
.call((g) => g.selectAll(".tick text").attr("x", -10).attr("dy", -4));

svg
.selectAll(".bar")
.data(data)
.enter()
.append("rect")
.attr("class", function (d) {
return "bar bar--" + (d.noi < 0 ? "negative" : "positive");
})
.attr("x", function (d) {
return x(d.year);
})
.attr("y", function (d) {
return y(Math.max(0, d.noi));
})
.attr("height", function (d) {
return Math.abs(y(d.noi) - y(0));
})
.attr("width", x.bandwidth());

svg.append("g").call(xAxis);

svg.append("g").attr("transform", `translate(${margin.left}, 0)`).call(yAxis);

return svg.node();
}
Insert cell
margin = ({ top: 40, right: 20, bottom: 20, left: 40 })
Insert cell
Insert cell
function formatTick(d) {
const s = (d / 1e6).toFixed(1);
return this.parentNode.nextSibling ? `\xa0${s}` : `$${s} million`;
}
Insert cell
x = {
const xExtent = d3.extent(data, d => d.year);
const x = d3
.scaleBand()
.domain(data.map(d => d.year))
.rangeRound([margin.left, width - margin.right])
.padding(0.1);
return x;
}
Insert cell
xScale = {
const xExtent = d3.extent(data, d => d.year);
const xScale = d3
.scaleOrdinal()
.domain(xExtent)
.range([margin.left, width - margin.right]);
return xScale;
}
Insert cell
y = {
const yMax = d3.max(data, d => d.noi);
const yMin = d3.min(data, d => d.noi);
const noiScale = d3
.scaleLinear()
.domain([yMin, yMax])
.range([height - margin.bottom, margin.top]);

return noiScale;
}
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell

Purpose-built for displays of data

Observable is your go-to platform for exploring data and creating expressive data visualizations. Use reactive JavaScript notebooks for prototyping and a collaborative canvas for visual data exploration and dashboard creation.
Learn more