Hi all- I am new to this forum. I am creating a snowflake chart. I wasn’t to curve the labels (Metric 1, Metric 2 etc) around the outer circle. Right now it is horizontally aligned.
The code I used is:
{
// Sample data for radar chart
const data = [
{ axis: "Metric 1", value: 0.8 },
{ axis: "Metric 2", value: 0.6 },
{ axis: "Metric 3", value: 0.4 },
{ axis: "Metric 4", value: 0.7 },
{ axis: "Metric 5", value: 0.9 },
];
// Configurations
const width = 600;
const height = 500;
const levels = 5; // Number of concentric circles
const maxValue = 1; // Assuming data values are normalized between 0 and 1
const radius = 200;
// Angle for each axis
const angleSlice = (Math.PI * 2) / data.length;
// Scales
const radiusScale = d3.scaleLinear().range([0, radius]).domain([0, maxValue]);
// SVG container
const svg = d3.create("svg")
.attr("width", width)
.attr("height", height);
// Create a Chart withing the SVG
const chart = svg.append("g")
.attr("transform", `translate(${width / 2},${height / 2})`);
// Draw concentric circles for reference levels
for (let i = 1; i <= levels; i++) {
chart.append("circle")
.attr("r", (radius / levels) * i)
.style("fill", "none")
.style("stroke", "#CDCDCD")
.style("stroke-dasharray", "3 3");
}
// Axes
data.forEach((d, i) => {
// Calculate the end point for each axis line
const angle = angleSlice * i;
const lineEndX = radius * Math.cos(angle - Math.PI / 2);
const lineEndY = radius * Math.sin(angle - Math.PI / 2);
// Draw axis lines
chart.append("line")
.attr("x1", 0)
.attr("y1", 0)
.attr("x2", lineEndX)
.attr("y2", lineEndY)
.style("stroke", "gray")
.style("stroke-width", 1);
});
// Position labels between each axis line, at the line ends
data.forEach((d, i) => {
// Midpoint angle between the current axis and the next
const midAngle = angleSlice * (i + 0.5);
const labelX = (radius + 40) * Math.cos(midAngle - Math.PI / 2);
const labelY = (radius + 20) * Math.sin(midAngle - Math.PI / 2);
// Place label at the midpoint between current and next axis
chart.append("text")
.attr("x", labelX)
.attr("y", labelY)
.attr("text-anchor", "middle")
.attr("dy", "0.35em")
.text(d.axis);
});
// Line generator for the radar area
const radarLine = d3.line()
.x((d, i) => radiusScale(d.value) * Math.cos(angleSlice * i - Math.PI / 2))
.y((d, i) => radiusScale(d.value) * Math.sin(angleSlice * i - Math.PI / 2))
.curve(d3.curveCardinalClosed); // Ensures the path is closed
// Draw radar area (snowflake shape)
chart.append("path")
.datum(data)
.attr("d", radarLine)
.style("fill", "steelblue")
.style("fill-opacity", 0.5)
.style("stroke", "blue")
.style("stroke-width", 2);
return svg.node();
}