Unlisted
Edited
Nov 1, 2023
Insert cell
Insert cell
Plot.plot({
width,
height,
axis: null,
y: { reverse: true },
marks: [
Plot.rect(treemap.leaves(), {
x1: "x0",
y1: "y0",
x2: "x1",
y2: "y1",
fill: (d) => d.ancestors().slice(-2).shift().data.name,
title: (d) =>
d
.ancestors()
.map((d) => d.data.name)
.reverse()
.join(".")
}),

// clip rect for the top label
Plot.rect(treemap.leaves(), {
x1: "x0",
y1: "y0",
x2: "x1",
y2: "y1",
render(index, scales, values, dimensions, context, next) {
const g = d3.select(next(index, scales, values, dimensions, context));
const rect = g
.selectAll("rect")
.attr("x", -3) // -dx
.attr("y", -12) // -dy
.each(function (i, k, e) {
const a = d3
.create("svg:clipPath", context)
.attr("id", `clip1_${i}`)
.node();
e[k].replaceWith(a);
a.appendChild(e[k]);
});
return g.node();
}
}),

// clip rect for the bottom label
Plot.rect(treemap.leaves(), {
x1: "x0",
y1: "y0",
x2: "x1",
y2: "y1",
render(index, scales, values, dimensions, context, next) {
const g = d3.select(next(index, scales, values, dimensions, context));
const rect = g
.selectAll("rect")
.attr("x", -3)
.attr("y", -23)
.each(function (i, k, e) {
const a = d3
.create("svg:clipPath", context)
.attr("id", `clip2_${i}`)
.node();
e[k].replaceWith(a);
a.appendChild(e[k]);
});
return g.node();
}
}),
// top label
Plot.text(treemap.leaves(), {
x: "x0",
y: "y0",
text: (d) => d.data.name,
textAnchor: "start",
dx: 3,
dy: 12,
render(index, scales, values, dimensions, context, next) {
const g = next(index, scales, values, dimensions, context);
d3.select(g)
.selectAll("text")
.attr("clip-path", (i) => `url(#clip1_${i})`);
return g;
}
}),
// bottom label
Plot.text(treemap.leaves(), {
x: "x0",
y: "y0",
text: (d) => d.value.toLocaleString("en"),
textAnchor: "start",
fillOpacity: 0.7,
dx: 3,
dy: 23,
render(index, scales, values, dimensions, context, next) {
const g = next(index, scales, values, dimensions, context);
d3.select(g)
.selectAll("text")
.attr("clip-path", (i) => `url(#clip2_${i})`);
return g;
}
})
]
})
Insert cell
treemap = d3.treemap()
.tile(d3.treemapSquarify)
.size([width, height])
.padding(1)
.round(true)
(d3.hierarchy(flare)
.sum(d => d.size)
.sort((a, b) => b.value - a.value))
Insert cell
width = 928
Insert cell
height = width
Insert cell
flare = FileAttachment("flare.json").json()
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