A simple example of using the layout in my d3 icon array plugin to render a hemicycle (typicaly for election results).
In this case for the results of the 2014 EU election.
xxxxxxxxxx
<html>
<head>
<title>Icon array hemicycle</title>
<script src="//d3js.org/d3.v4.0.0-alpha.18.min.js" charset="utf-8"></script>
<script type="text/javascript" src="d3-iconarray.js"></script>
<style type="text/css">
*{
font-family: sans-serif;
}
</style>
</head>
<body>
<div id="hemicycle"></div>
</body>
<script type="text/javascript">
var width = 750,
height = 500,
margin = {top:20,left:20,bottom:20,right:0}
dotRadius = 3.5;
d3.json('eu-results.json', function(data){
//make a group lookup
var groupInfo = {};
data.groups.forEach(function(d){
groupInfo[d.key] = d;
});
var resultsData = data.europeresults.reduce(function(value, d){
if(d.groupname[0]!=='TOTAL'){
for(var i=0;i<d.seats[0] ;i++){
value.push(d.groupname[0]);
}
}
return value;
}, []);
console.log(groupInfo)
//make a layout
var layout = d3_iconarray.layout()
.height(10)
.widthFirst(false); //we want the seats arranged by spokes, not like a rainbow
var iconArray = layout(resultsData);
//and some scales
var distanceScale = d3.scaleLinear()
.domain([0, layout.height()])
.range([200, 350]);
var angleScale = d3.scaleLinear()
.domain([0, layout.width() ])
.range([-180, 0]);
//draw the hemicycle
var svg = d3.select('#hemicycle')
.append('svg')
.attr('width', width)
.attr('height', height)
.append('g')
.attr('transform', 'translate('+width/2+','+(height - margin.bottom)+')')
svg.selectAll('circle')
.data(iconArray)
.enter()
.append('circle')
.attr('r', dotRadius)
.attr('fill', function(d){
return groupInfo[d.data].colour;
})
.attr('transform', function(d){
var rotation = angleScale(d.position.x);
var distance = distanceScale(d.position.y);
return 'rotate(' + rotation + ') translate(' + distance + ',0)'
});
d3.select('#hemicycle svg').selectAll('g.key-element')
.data(data.groups) //note, ideally this should be in the same order as the aprties appear in the hemicycle
.enter()
.append('g')
.attr('class','key-element')
.attr('transform',function(d,i){
return 'translate('+margin.left+','+(margin.top+i*20)+')';
})
.call(function(parent){
parent.append('circle')
.attr('r',dotRadius)
.attr('cy',-dotRadius*2)
.attr('cx',-dotRadius*2)
.attr('fill',function(d){
return d.colour;
});
parent.append('text')
.text(function(d){
console.log(d)
return d.name;
})
})
});
d3.select(self.frameElement).style("height", height + "px");
</script>
</html>
https://d3js.org/d3.v4.0.0-alpha.18.min.js