plotName = async ({ name, sex, caption }) => {
const nameData = await getNameData({name, sex})
return Plot.plot({
caption,
style: "overflow: visible;",
width: 800,
tip: true,
height: sex ? 350 : 700,
facet: {
data: nameData,
y: "sex"
},
color: {
domain: ["M", "F"],
scheme: "BuRd"
},
x: {
domain: xDomain
},
y: {
label: "↑ count"
},
grid: true,
marks: [
Plot.ruleY([0]),
Plot.line(nameData, {
clip: true,
x: "date",
y: "born",
tip: true,
title: tooltip
}),
Plot.areaY(nameData, {
x: "date",
y: "alive",
fill: "sex",
fillOpacity: 0.6
}),
Plot.text(
nameData,
Plot.selectMaxY({
x: "date",
frameAnchor: "middle",
y: "born",
stroke: "white",
fill: "black",
text: (d) => `Number of ${EXPANDED_SEX[d.sex]} ${name}s
born each year`
})
),
Plot.ruleX(
nameData,
Plot.select(
{
y: (I, V) => {
const sum = d3.sum(I, (i) => V[i]);
const i = d3
.cumsum(I, (i) => V[i])
.findIndex((d) => d >= sum / 2);
return [I[i]];
}
},
{
x: "date",
y: "alive",
stroke: "sex",
strokeWidth: 4
}
)
),
Plot.text(
nameData,
Plot.selectMaxY({
x: "date",
frameAnchor: "bottom",
y: (d) => d.alive * 0.1,
stroke: "white",
fill: "sex",
opacity: 0.9,
text: (d) => `Number of ${EXPANDED_SEX[d.sex]} ${name}s born each year
estimated to be alive on Jan 1 ${DATA_YEAR_END + 1}`
})
),
Plot.text(
nameData,
Plot.select(
{
y: (I, V) => {
const sum = d3.sum(I, (i) => V[i]);
const i = d3
.cumsum(I, (i) => V[i])
.findIndex((d) => d >= sum / 2);
return [I[i]];
}
},
{
x: "date",
frameAnchor: "top-right",
y: "alive",
stroke: "white",
fill: "sex",
text: (d) =>
`The median living ${EXPANDED_SEX[d.sex]} ${name}
in ${DATA_YEAR_END} was ${DATA_YEAR_END - d.date.getFullYear()}`
}
)
)
]
});
}