In the second lab of the Metis data visualization course my group (group 1) was to visualize the 1st example of Anscombe's Quartet. Creating a scatter plot is all well and good, but why not make things a little bit more interesting.
What's more interesting than a scatter plot, you might ask. Well, how about rainbow colors transitioning? No, this does not conform to data visualization best practices, but that's not what I was going for in this example.
You must know the rules, before you can break them.
xxxxxxxxxx
<head>
<meta charset="utf-8">
<style type="text/css">
.axis text {
font: 10px sans-serif;
}
.axis line,
.axis path {
fill: none;
stroke: #000;
shape-rendering: crispEdges;
}
</style>
</head>
<body>
</body>
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/3.5.5/d3.min.js" charset="utf-8"></script>
<script>
var data = [
[10,8.04],
[8,6.95],
[13,7.58],
[9,8.81],
[11,8.33],
[14,9.96],
[6,7.24],
[4,4.26],
[12,10.84],
[7,4.82],
[5,5.68]
];
// D3 margin convention bl.ock https://bl.ocks.org/mbostock/3019563
// define the margin object, clockwise starting from the top
var margin = {top: 20, right: 10, bottom: 20, left: 25};
// define width and height as inner dimensions of the chart
var width = 720 - margin.left - margin.right,
height = 400 - margin.top - margin.bottom;
// define svg as a G element that translates the origin to the top-left corner of the chart area
var svgContainer = d3.select("body")
.append("svg")
.attr("width", width + margin.left + margin.right)
.attr("height", height + margin.top + margin.bottom)
// .style("border", "1px solid #f0f") // make the svg pop in pink!
.append("g")
.attr("transform", "translate(" + margin.left + "," + margin.top +")");
var max = d3.max(function(data) { return data[0]; });
console.log(max);
// build our utilities for this scatter plot
var xScale = d3.scale.linear()
.domain([0, 14])
.range([0, width]);
var yScale = d3.scale.linear()
.domain([0, 10.84])
.range([height, 0]);
var xAxis = d3.svg.axis()
.scale(xScale)
.orient("bottom");
var yAxis = d3.svg.axis()
.scale(yScale)
.orient("left");
var groups = svgContainer.selectAll("g")
.data(data)
.enter()
.append("g");
var circleAttributes = groups
.append("circle")
.attr("class", "anscombe-circle")
.attr("cx", function(d) { return xScale(d[0]); })
.attr("cy", function(d) { return yScale(d[1]); })
.attr("r", "5")
.attr("fill", "#fff");
var circleLabels = groups
.append("text");
var labelAttributes = circleLabels
.attr("x", function(d) { return xScale(d[0]); })
.attr("y", function(d) { return yScale(d[1]); })
.text(function(d) {
return "(X:" + xScale(d[0]).toFixed(1) + ", Y:" + yScale(d[1]).toFixed(1) + ")";
})
.attr("font-family", "Arial")
.attr("font-size", "8px")
.attr("fill", "gray");
// finaly give the scatter plot axises
svgContainer.append("g")
.attr("class", "x axis")
.attr("transform", "translate(0," + height + ")")
.call(xAxis)
.selectAll("text");
svgContainer.append("g")
.attr("class", "y axis")
.attr("transform", "translate(0,0)" )
.call(yAxis)
.selectAll("text");
// To get the circles to change color we need create a function that can
// be called repeatedly to update the current color values.
var begR = Math.random() * 255,
begG = Math.random() * 255,
begB = Math.random() * 255;
var rainbow = [
"#FF0200",
"#FF8000",
"#FFED00",
"#00FF3F",
"#00FF78",
"#00FCFF",
"#5800FF",
"#0028FF",
"#FF0078",
"#FF00B7"],
i = 0;
setInterval(function () {
console.log(i);
circleAttributes
.attr("fill", "#fff")
.transition()
.duration(500)
.attr("r", "25")
.attr("fill", rainbow[i]);
i++;
i = i % 10;
}, 500);
</script>
https://cdnjs.cloudflare.com/ajax/libs/d3/3.5.5/d3.min.js