Circular barplot in d3.js

This post describes how to build a very basic circular barplot with d3.js. You can see many other examples in the circular barplot section of the gallery. Learn more about this type of chart in

Circular barplot section


  • The X scale is defined using a scaleBand as for a normal barplot. However then range usually goes between 0 and 2Pi for a complete circle.

  • The Y scale takes advantage of the scaleRadial() function. A scaleLinear() would work as well, but would visually inflate the importance of high values as explained here and here.

  • Bars are then added using a path and not a rect. The d3.arc() is a life saver here, learn more about how it works here.

  • This chart is still useless: let's add labels.
<!DOCTYPE html>
<meta charset="utf-8">

<!-- Load d3.js -->
<script src=""></script>

<!-- Function for radial charts -->
<script src=""></script>

<!-- Create a div where the graph will take place -->
<div id="my_dataviz"></div>


// set the dimensions and margins of the graph
var margin = {top: 10, right: 10, bottom: 10, left: 10},
    width = 460 - margin.left - margin.right,
    height = 460 - - margin.bottom,
    innerRadius = 80,
    outerRadius = Math.min(width, height) / 2;   // the outerRadius goes from the middle of the SVG area to the border

// append the svg object to the body of the page
var svg ="#my_dataviz")
    .attr("width", width + margin.left + margin.right)
    .attr("height", height + + margin.bottom)
    .attr("transform", "translate(" + width / 2 + "," + ( height/2+100 )+ ")"); // Add 100 on Y translation, cause upper bars are longer

d3.csv("", function(data) {

  // X scale
  var x = d3.scaleBand()
      .range([0, 2 * Math.PI])    // X axis goes from 0 to 2pi = all around the circle. If I stop at 1Pi, it will be around a half circle
      .align(0)                  // This does nothing ?
      .domain( { return d.Country; }) ); // The domain of the X axis is the list of states.

  // Y scale
  var y = d3.scaleRadial()
      .range([innerRadius, outerRadius])   // Domain will be define later.
      .domain([0, 10000]); // Domain of Y is from 0 to the max seen in the data

  // Add bars
      .attr("fill", "#69b3a2")
      .attr("d", d3.arc()     // imagine your doing a part of a donut plot
          .outerRadius(function(d) { return y(d['Value']); })
          .startAngle(function(d) { return x(d.Country); })
          .endAngle(function(d) { return x(d.Country) + x.bandwidth(); })



Related blocks →