Skip to content

Instantly share code, notes, and snippets.

@Guerino1
Created March 27, 2012 03:14
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save Guerino1/2212156 to your computer and use it in GitHub Desktop.
Save Guerino1/2212156 to your computer and use it in GitHub Desktop.
Multiple D3 Pie Charts Mixed In With Common HTML Layout Constructs
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
xml:lang="en-US"
lang="en-US">
<head profile="http://www.w3.org/2005/10/profile">
<title>IF4IT Sample Charts Web Page</title>
<meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1" />
<meta name="Description" content="This page tries to mix charts with html formatting and layout constructs." />
<meta http-equiv="pragma" content="no-cache" />
<meta http-equiv="cache-control" content="no-cache" />
<meta http-equiv="expires" content="-l" />
<script type="text/javascript" src="http://mbostock.github.com/d3/d3.js?2.4.5"></script>
<script type="text/javascript">
// This example lays out multiple interactive pie charts on a page with multiple HTML layout constructs.
// Created by Frank Guerino : "http://www.guerino.net"
// Data Used for this example...
var dataSet1 = [
{legendLabel: "Legend String 1", magnitude: 51, link: "http://www.if4it.com"},
{legendLabel: "Legend String 2", magnitude: 21, link: "http://www.if4it.com/glossary.html"},
{legendLabel: "Legend String 3", magnitude: 31, link: "http://www.if4it.com/resources.html"},
{legendLabel: "Legend String 4", magnitude: 14, link: "http://www.if4it.com/taxonomy.html"},
{legendLabel: "Legend String 5", magnitude: 19, link: "http://www.if4it.com/disciplines.html"},
{legendLabel: "Legend String 6", magnitude: 47, link: "http://www.if4it.com"},
{legendLabel: "Legend String 7", magnitude: 27, link: "http://www.if4it.com/glossary.html"}];
var dataSet2 = [
{legendLabel: "Legend String 8", magnitude: 31, link: "http://www.if4it.com/glossary.html"},
{legendLabel: "Legend String 9", magnitude: 54, link: "http://www.if4it.com/resources.html"},
{legendLabel: "Legend String 10", magnitude: 21, link: "http://www.if4it.com"},
{legendLabel: "Legend String 11", magnitude: 31, link: "http://www.if4it.com/taxonomy.html"},
{legendLabel: "Legend String 12", magnitude: 54, link: "http://www.if4it.com/glossary.html"},
{legendLabel: "Legend String 13", magnitude: 14, link: "http://www.if4it.com/resources.html"},
{legendLabel: "Legend String 14", magnitude: 14, link: "http://www.if4it.com/disciplines.html"},
{legendLabel: "Legend String 15", magnitude: 27, link: "http://www.if4it.com/glossary.html"}];
var dataSet3 = [
{legendLabel: "Legend String 16", magnitude: 21, link: "http://www.if4it.com"},
{legendLabel: "Legend String 17", magnitude: 41, link: "http://www.if4it.com/resources.html"},
{legendLabel: "Legend String 18", magnitude: 34, link: "http://www.if4it.com/glossary.html"},
{legendLabel: "Legend String 19", magnitude: 9, link: "http://www.if4it.com/taxonomy.html"},
{legendLabel: "Legend String 20", magnitude: 47, link: "http://www.if4it.com/glossary.html"},
{legendLabel: "Legend String 21", magnitude: 17, link: "http://www.if4it.com/resources.html"},
{legendLabel: "Legend String 22", magnitude: 47, link: "http://www.if4it.com/glossary.html"},
{legendLabel: "Legend String 23", magnitude: 37, link: "http://www.if4it.com/disciplines.html"},
{legendLabel: "Legend String 24", magnitude: 47, link: "http://www.if4it.com/resources.html"},
{legendLabel: "Legend String 25", magnitude: 4, link: "http://www.if4it.com/glossary.html"},
{legendLabel: "Legend String 26", magnitude: 18, link: "http://www.if4it.com"},
{legendLabel: "Legend String 27", magnitude: 41, link: "http://www.if4it.com/resources.html"},
{legendLabel: "Legend String 28", magnitude: 37, link: "http://www.if4it.com/glossary.html"},
{legendLabel: "Legend String 29", magnitude: 27, link: "http://www.if4it.com"}];
function drawPie( pieName, dataSet, selectString, colors, margin, outerRadius, innerRadius, sortArcs ) {
// pieName => A unique drawing identifier that has no spaces, no "." and no "#" characters.
// dataSet => Input Data for the chart, itself.
// selectString => String that allows you to pass in
// a D3 select string.
// colors => String to set color scale. Values can be...
// => "colorScale10"
// => "colorScale20"
// => "colorScale20b"
// => "colorScale20c"
// margin => Integer margin offset value.
// outerRadius => Integer outer radius value.
// innerRadius => Integer inner radius value.
// sortArcs => Controls sorting of Arcs by value.
// 0 = No Sort. Maintain original order.
// 1 = Sort by arc value size.
// Color Scale Handling...
var colorScale = d3.scale.category20c();
switch (colors)
{
case "colorScale10":
colorScale = d3.scale.category10();
break;
case "colorScale20":
colorScale = d3.scale.category20();
break;
case "colorScale20b":
colorScale = d3.scale.category20b();
break;
case "colorScale20c":
colorScale = d3.scale.category20c();
break;
default:
colorScale = d3.scale.category20c();
};
var canvasWidth = 700;
var pieWidthTotal = outerRadius * 2;;
var pieCenterX = outerRadius + margin/2;
var pieCenterY = outerRadius + margin/2;
var legendBulletOffset = 30;
var legendVerticalOffset = outerRadius - margin;
var legendTextOffset = 20;
var textVerticalSpace = 20;
var canvasHeight = 0;
var pieDrivenHeight = outerRadius*2 + margin*2;
var legendTextDrivenHeight = (dataSet.length * textVerticalSpace) + margin*2;
// Autoadjust Canvas Height
if (pieDrivenHeight >= legendTextDrivenHeight)
{
canvasHeight = pieDrivenHeight;
}
else
{
canvasHeight = legendTextDrivenHeight;
}
var x = d3.scale.linear().domain([0, d3.max(dataSet, function(d) { return d.magnitude; })]).rangeRound([0, pieWidthTotal]);
var y = d3.scale.linear().domain([0, dataSet.length]).range([0, (dataSet.length * 20)]);
var synchronizedMouseOver = function() {
var arc = d3.select(this);
var indexValue = arc.attr("index_value");
var arcSelector = "." + "pie-" + pieName + "-arc-" + indexValue;
var selectedArc = d3.selectAll(arcSelector);
selectedArc.style("fill", "Maroon");
var bulletSelector = "." + "pie-" + pieName + "-legendBullet-" + indexValue;
var selectedLegendBullet = d3.selectAll(bulletSelector);
selectedLegendBullet.style("fill", "Maroon");
var textSelector = "." + "pie-" + pieName + "-legendText-" + indexValue;
var selectedLegendText = d3.selectAll(textSelector);
selectedLegendText.style("fill", "Maroon");
};
var synchronizedMouseOut = function() {
var arc = d3.select(this);
var indexValue = arc.attr("index_value");
var arcSelector = "." + "pie-" + pieName + "-arc-" + indexValue;
var selectedArc = d3.selectAll(arcSelector);
var colorValue = selectedArc.attr("color_value");
selectedArc.style("fill", colorValue);
var bulletSelector = "." + "pie-" + pieName + "-legendBullet-" + indexValue;
var selectedLegendBullet = d3.selectAll(bulletSelector);
var colorValue = selectedLegendBullet.attr("color_value");
selectedLegendBullet.style("fill", colorValue);
var textSelector = "." + "pie-" + pieName + "-legendText-" + indexValue;
var selectedLegendText = d3.selectAll(textSelector);
selectedLegendText.style("fill", "Blue");
};
var tweenPie = function (b) {
b.innerRadius = 0;
var i = d3.interpolate({startAngle: 0, endAngle: 0}, b);
return function(t) {
return arc(i(t));
};
}
// Create a drawing canvas...
var canvas = d3.select(selectString)
.append("svg:svg") //create the SVG element inside the <body>
.data([dataSet]) //associate our data with the document
.attr("width", canvasWidth) //set the width of the canvas
.attr("height", canvasHeight) //set the height of the canvas
.append("svg:g") //make a group to hold our pie chart
.attr("transform", "translate(" + pieCenterX + "," + pieCenterY + ")") // Set center of pie
// Define an arc generator. This will create <path> elements for using arc data.
var arc = d3.svg.arc()
.innerRadius(innerRadius) // Causes center of pie to be hollow
.outerRadius(outerRadius);
// Define a pie layout: the pie angle encodes the value of dataSet.
// Since our data is in the form of a post-parsed CSV string, the
// values are Strings which we coerce to Numbers.
var pie = d3.layout.pie()
.value(function(d) { return d.magnitude; })
.sort(function(a, b) {if (sortArcs==1) { return b.magnitude - a.magnitude; } else { return null; } });
// Select all <g> elements with class slice (there aren't any yet)
var arcs = canvas.selectAll("g.slice")
// Associate the generated pie data (an array of arcs, each having startAngle,
// endAngle and value properties)
.data(pie)
// This will create <g> elements for every "extra" data element that should be associated
// with a selection. The result is creating a <g> for every object in the data array
// Create a group to hold each slice (we will have a <path> and a <text> // element associated with each slice)
.enter().append("svg:a")
.attr("xlink:href", function(d) { return d.data.link; })
.append("svg:g")
.attr("class", "slice") //allow us to style things in the slices (like text)
// Set the color for each slice to be chosen from the color function defined above
// This creates the actual SVG path using the associated data (pie) with the arc drawing function
.style("stroke", "White" )
.attr("d", arc);
arcs.append("svg:path")
// Set the color for each slice to be chosen from the color function defined above
// This creates the actual SVG path using the associated data (pie) with the arc drawing function
.attr("fill", function(d, i) { return colorScale(i); } )
.attr("color_value", function(d, i) { return colorScale(i); }) // Bar fill color...
.attr("index_value", function(d, i) { return "index-" + i; })
.attr("class", function(d, i) { return "pie-" + pieName + "-arc-index-" + i; })
.style("stroke", "White" )
.attr("d", arc)
.on('mouseover', synchronizedMouseOver)
.on("mouseout", synchronizedMouseOut)
.transition()
.ease("bounce")
.duration(2000)
.delay(function(d, i) { return i * 50; })
.attrTween("d", tweenPie);
// Add a magnitude value to the larger arcs, translated to the arc centroid and rotated.
arcs.filter(function(d) { return d.endAngle - d.startAngle > .2; }).append("svg:text")
.attr("dy", ".35em")
.attr("text-anchor", "middle")
//.attr("transform", function(d) { return "translate(" + arc.centroid(d) + ")rotate(" + angle(d) + ")"; })
.attr("transform", function(d) { //set the label's origin to the center of the arc
//we have to make sure to set these before calling arc.centroid
d.outerRadius = outerRadius; // Set Outer Coordinate
d.innerRadius = innerRadius; // Set Inner Coordinate
return "translate(" + arc.centroid(d) + ")rotate(" + angle(d) + ")";
})
.style("fill", "White")
.style("font", "normal 12px Arial")
.text(function(d) { return d.data.magnitude; });
// Computes the angle of an arc, converting from radians to degrees.
function angle(d) {
var a = (d.startAngle + d.endAngle) * 90 / Math.PI - 90;
return a > 90 ? a - 180 : a;
}
// Plot the bullet circles...
canvas.selectAll("circle")
.data(dataSet).enter().append("svg:circle") // Append circle elements
.attr("cx", pieWidthTotal + legendBulletOffset)
.attr("cy", function(d, i) { return i*textVerticalSpace - legendVerticalOffset; } )
.attr("stroke-width", ".5")
.style("fill", function(d, i) { return colorScale(i); }) // Bullet fill color
.attr("r", 5)
.attr("color_value", function(d, i) { return colorScale(i); }) // Bar fill color...
.attr("index_value", function(d, i) { return "index-" + i; })
.attr("class", function(d, i) { return "pie-" + pieName + "-legendBullet-index-" + i; })
.on('mouseover', synchronizedMouseOver)
.on("mouseout", synchronizedMouseOut);
// Create hyper linked text at right that acts as label key...
canvas.selectAll("a.legend_link")
.data(dataSet) // Instruct to bind dataSet to text elements
.enter().append("svg:a") // Append legend elements
.attr("xlink:href", function(d) { return d.link; })
.append("text")
.attr("text-anchor", "center")
.attr("x", pieWidthTotal + legendBulletOffset + legendTextOffset)
//.attr("y", function(d, i) { return legendOffset + i*20 - 10; })
//.attr("cy", function(d, i) { return i*textVerticalSpace - legendVerticalOffset; } )
.attr("y", function(d, i) { return i*textVerticalSpace - legendVerticalOffset; } )
.attr("dx", 0)
.attr("dy", "5px") // Controls padding to place text in alignment with bullets
.text(function(d) { return d.legendLabel;})
.attr("color_value", function(d, i) { return colorScale(i); }) // Bar fill color...
.attr("index_value", function(d, i) { return "index-" + i; })
.attr("class", function(d, i) { return "pie-" + pieName + "-legendText-index-" + i; })
.style("fill", "Blue")
.style("font", "normal 1.5em Arial")
.on('mouseover', synchronizedMouseOver)
.on("mouseout", synchronizedMouseOut);
};
</script>
<style type="text/css">
svg {
font: 10px sans-serif;
display: block;
}
</style>
<STYLE type="text/css">
div.div_Header {
width: 100%;
border:2px solid White;
border-radius:7px;
background: WhiteSmoke;
font: bold 14px Arial;
font-family:Arial, Helvetica, sans-serif;
color:WhiteSmoke;
text-align:center;
}
h1.h1_BodyHeader {
text-align:center;
font: bold 1.5em Arial;
}
h2.h2_LeftMenuHeader {
text-align:center;
font: bold 1.2em Arial;
}
h3.h3_Body {
text-align:center;
}
p.p_Red {
color:Red;
}
table.table_Header {
width: 100%;
text-align:center;
}
td.td_HeaderLeft {
text-align:left;
}
td.td_HeaderRight {
text-align:right;
}
div.div_Menu {
width: 100%;
border:2px solid White;
border-radius:7px;
background: MidnightBlue;
font: bold 14px Arial;
font-family:Arial, Helvetica, sans-serif;
color:White;
text-align:center;
}
p.p_Left {
font-family:Arial, Helvetica, sans-serif;
color:Black;
text-align:left;
padding-left: 5px;
font: normal 14px Arial;
}
table.table_Body {
width: 100%;
height: 100%;
padding: 0;
}
td.td_BodyLeft {
width: 250px;
height: 100%;
padding: 0;
}
li.li_LeftMenu {
text-align:left;
font: normal 14px Arial;
}
a.a_LeftMenuNoUnderLine {
text-decoration: none;
}
div.div_Body {
height: 100%;
width: 100%;
position: relative;
border:2px solid White;
border-radius:7px;
background: WhiteSmoke;
font: bold 14px Arial;
font-family:Arial, Helvetica, sans-serif;
color:Black;
text-align:center;
}
div.div_Footer {
width: 100%;
border:2px solid White;
border-radius:7px;
background: MidnightBlue;
font: bold 14px Arial;
font-family:Arial, Helvetica, sans-serif;
color:White;
text-align:center;
}
p.p_if4itMessage {
width: 100%;
background: White;
font: bold .75em Arial;
font-family:Arial, Helvetica, sans-serif;
color:GoldenRod;
text-align:center;
}
.menuButton{
background-color: MidnightBlue;
}
.menuButton li{
height: 100%;
list-style: none;
display: inline;
}
.menuButton li a{
height: 100%;
padding: 3px 0.5em;
text-decoration: none;
color: White;
background-color: MidnightBlue;
border: 2px solid MidnightBlue;
}
.menuButton li a:hover{
height: 100%;
color: MidnightBlue;
background-color: White;
border-style: outset;
background-color: White;
}
.menuButton li a:active{
height: 100%;
border-style: inset;
color: MidnightBlue;
background-color: White;
}
.menuButton li a.disabled{
height: 100%;
padding: 3px 0.5em;
text-decoration: none;
color: MidnightBlue;
background-color: White;
border: 2px solid MidnightBlue;
border-style: inset;
border-color: White;
}
</STYLE>
<STYLE type="text/css">
div.div_RootBody {
position: relative;
border:2px solid White;
border-radius:7px;
background: WhiteSmoke;
font: normal 14px Arial;
font-family:Arial, Helvetica, sans-serif;
color:Black;
padding: 0px 1em;
text-align:left;
}
</STYLE>
<!--[if gt IE 7]>
<style>body { overflow-y:scroll; } </style>
<![endif]-->
</head>
<body>
<div>
<h1 style="text-align:center; font: bold 1.7em Arial;"><a href="http://www.if4it.com">The International Foundation for Information Technology (IF4IT)</a></h1>
</div>
<div class="div_Menu">
<ul class="menuButton">
<li><a href="http://www.if4it.com">HOME</a></li>
<li><a href="http://www.if4it.com/resources.html">RESOURCES</a></li>
<li><a href="http://www.if4it.com">PRODUCTS</a></li>
<li><a href="http://www.if4it.com">SERVICES</a></li>
<li><a href="http://www.if4it.com">SUPPORT</a></li>
<li><a href="http://www.if4it.com">HELP</a></li>
</ul>
</div>
<table class="table_Body">
<tr>
<td class="td_BodyLeft">
<div class="div_Body">
<h2 class="h2_LeftMenuHeader">Sample Left Menu Links</h2>
<ul>
<li class="li_LeftMenu"><a class="a_LeftMenuNoUnderLine" href="http://www.if4it.com">IF4IT Home</a></li>
<li class="li_LeftMenu"><a class="a_LeftMenuNoUnderLine" href="http://www.if4it.com/disciplines.html">IF4IT Disciplines</a></li>
<li class="li_LeftMenu"><a class="a_LeftMenuNoUnderLine" href="http://www.if4it.com/glossary.html">IF4IT Glossary</a></li>
<li class="li_LeftMenu"><a class="a_LeftMenuNoUnderLine" href="http://www.if4it.com/taxonomy.html">IF4IT Taxonomies</a></li>
</ul>
<p class="p_Left">This is dummy paragraph 1 text that would go in this section of the page.</p>
<p class="p_Left">This is dummy paragraph 2 text that would go in this section of the page.</p>
<p class="p_Left">This is dummy paragraph 3 text that would go in this section of the page.</p>
<p class="p_Left">This is dummy paragraph 4 text that would go in this section of the page.</p>
<p class="p_Left">This is dummy paragraph 5 text that would go in this section of the page.</p>
<ul>
<li class="li_LeftMenu"><a class="a_LeftMenuNoUnderLine" href="http://www.if4it.com">IF4IT Home</a></li>
<li class="li_LeftMenu"><a class="a_LeftMenuNoUnderLine" href="http://www.if4it.com/disciplines.html">IF4IT Disciplines</a></li>
<li class="li_LeftMenu"><a class="a_LeftMenuNoUnderLine" href="http://www.if4it.com/glossary.html">IF4IT Glossary</a></li>
<li class="li_LeftMenu"><a class="a_LeftMenuNoUnderLine" href="http://www.if4it.com/taxonomy.html">IF4IT Taxonomies</a></li>
</ul>
<p class="p_Left">This is dummy paragraph 1 text that would go in this section of the page.</p>
<p class="p_Left">This is dummy paragraph 2 text that would go in this section of the page.</p>
<p class="p_Left">This is dummy paragraph 3 text that would go in this section of the page.</p>
<p class="p_Left">This is dummy paragraph 4 text that would go in this section of the page.</p>
<p class="p_Left">This is dummy paragraph 5 text that would go in this section of the page.</p>
</div>
</td>
<td>
<div class="div_RootBody">
<h1 style="text-align:center; font: bold 1.5em Arial;">Multiple Interactive D3 Pie Charts on an HTML Page</h1>
</div>
<div class="div_RootBody">
<h3 class="h3_Body">Example Description</h3>
<p class="p_Red">This example shows how to mix multiple interactive D3 based Pie Charts with multiple common HTML page layout constructs. Cut, paste, and run the code into your own index.html file to see the multiple charts.</p>
</div>
<div class="div_RootBody" id="pie_chart_1">
<h3 class="h3_Body">Pie Chart Number 1</h3>
<div class="chart"></div>
</div>
<div class="div_RootBody" id="pie_chart_2">
<h3 class="h3_Body">Pie Chart Number 2</h3>
<div class="chart"></div>
</div>
<div class="div_RootBody">
<h3 class="h3_Body">Content Section: No Charts Here</h3>
<p>This is dummy paragraph 1 text that would go in this section of the page.</p>
<p>This is dummy paragraph 2 text that would go in this section of the page.</p>
</div>
<div class="div_RootBody" id="pie_chart_3">
<h3 class="h3_Body">Pie Chart Number 3</h3>
<div class="chart"></div>
</div>
</td>
</tr>
</table>
<div class="div_Footer"><p><p>This is the IF4IT Footer Message for this web page.</p></p></div>
<div><p class="p_if4itMessage">This Site Has Been Created and Published by The International Foundation for Information Technology (IF4IT).</p></div>
<script type="text/javascript">
drawPie("Pie1", dataSet1, "#pie_chart_1 .chart", "colorScale20", 10, 100, 5, 0);
drawPie("Pie2", dataSet2, "#pie_chart_2 .chart", "colorScale20b", 10, 100, 5, 0);
drawPie("Pie3", dataSet3, "#pie_chart_3 .chart", "colorScale20c", 10, 100, 5, 0);
</script>
</body>
</html>
@nutlessNeo
Copy link

This is awesome! I just have a couple of questions. How can you take out the legend and/or put the legend underneath the charts?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment