|
<!DOCTYPE html> |
|
<title>Absolute -> Relative Judgment</title> |
|
<style type="text/css"> |
|
body { |
|
font-size: 12px; |
|
font-family: Arial; |
|
width: 940px; |
|
margin: 0 auto; |
|
text-align: center; |
|
} |
|
|
|
.header { |
|
font-size: 14px; |
|
font-weight: bold; |
|
} |
|
.description { |
|
font-size: 10px; |
|
fill: #888; |
|
display: none; |
|
} |
|
|
|
.data { |
|
shape-rendering: crispEdges; |
|
stroke: none; |
|
fill: gray; |
|
} |
|
|
|
.bounds, |
|
.ticks { |
|
shape-rendering: crispEdges; |
|
stroke: black; |
|
fill: none; |
|
} |
|
|
|
.grids { |
|
shape-rendering: crispEdges; |
|
stroke: gray; |
|
} |
|
|
|
</style> |
|
<body> |
|
<div id="chart"> |
|
</div> |
|
|
|
<script src="http://d3js.org/d3.v3.min.js" charset="utf-8"></script> |
|
<script> |
|
|
|
var margin = {top: 10, right: 10, bottom: 100, left: 60}, |
|
width = 940 - margin.left - margin.right, |
|
height = 500 - margin.top - margin.bottom, |
|
rowHeight = 40; |
|
|
|
var svg = d3.select("#chart").append("svg") |
|
.attr("width", width + margin.left + margin.right) |
|
.attr("height", height + margin.top + margin.bottom) |
|
.append("g") |
|
.attr("transform", "translate(" + margin.left + "," + margin.top + ")"); |
|
|
|
// generate random array of 10 numbers from 10 to 20 |
|
function genData() { |
|
return d3.shuffle(d3.range(10, 20)); |
|
} |
|
var sectionTitles = [ |
|
'Absolute Judgment', |
|
'Bounding Boxes', |
|
'Grid/Tick Marks', |
|
'Residuals', |
|
'Reorientation', |
|
]; |
|
var sectionScale = d3.scale.ordinal() |
|
.domain(sectionTitles) |
|
.rangeRoundBands([0, height], 0.1, 0.1); |
|
var xScale = d3.scale.ordinal() |
|
.domain(d3.range(0, 10)) |
|
.rangeRoundBands([0, width], 0.2, 0.1); |
|
var yScale = d3.scale.ordinal() |
|
.domain(d3.range(0, 10)) |
|
.rangeBands([10, 80], 0.1, 0.1); |
|
|
|
// create the sections and headers |
|
var sections = svg.selectAll('.section') |
|
.data(sectionTitles) |
|
.enter() |
|
.append("g") |
|
.attr('class', function (d) { return 'section ' + d.toLowerCase().replace('/', ' '); }) |
|
.attr('transform', function (d) { return 'translate(0,' + sectionScale(d) + ')'; }); |
|
sections |
|
.append('text') |
|
.attr('class', 'header') |
|
.text(function (d) { return d; }); |
|
|
|
// draw the initial boxes |
|
var boxContainers = sections.selectAll('.box') |
|
.data(genData) |
|
.enter() |
|
.append('g') |
|
.attr('class', 'box') |
|
.attr('transform', function (d, i) { return 'translate(' + xScale(i) + ',20)'; }); |
|
boxContainers |
|
.append('rect') |
|
.attr('class', 'data') |
|
.attr('width', function (d) { return d * xScale.rangeBand() / 20; }) |
|
.attr('height', 5); |
|
|
|
// Add a bounding box to that section |
|
svg.selectAll('.section.bounding .box') |
|
.append('rect') |
|
.attr('class', 'bounds') |
|
.attr('x', -2) |
|
.attr('y', -2) |
|
.attr('width', xScale.rangeBand()) |
|
.attr('height', 8); |
|
|
|
// Add tick marks to that section |
|
svg.selectAll('.section.tick.marks .box').selectAll('.ticks') |
|
.data([5, 10, 15]) |
|
.enter() |
|
.append('line') |
|
.attr('class', 'grids') |
|
.attr('x1', function (d) { return xScale.rangeBand() * d / 20; }) |
|
.attr('y1', -2) |
|
.attr('x2', function (d) { return xScale.rangeBand() * d / 20; }) |
|
.attr('y2', 7); |
|
svg.selectAll('.section.tick.marks .box') |
|
.append('line') |
|
.attr('class', 'ticks') |
|
.attr('x1', 0) |
|
.attr('y1', 6) |
|
.attr('x2', xScale.rangeBand()) |
|
.attr('y2', 6); |
|
var average = d3.sum(genData()) / 10; |
|
// Subtract average from residuals section |
|
svg.selectAll('.section.residuals .data') |
|
.attr('width', function (d) { return Math.abs(d - average) * xScale.rangeBand() / 5; }) |
|
svg.selectAll('.section.residuals .box') |
|
.append('line') |
|
.attr('class', 'ticks') |
|
.attr('x1', function (d) { return d > average ? 0 : (d - average) * xScale.rangeBand() / -5; }) |
|
.attr('y1', -2) |
|
.attr('x2', function (d) { return d > average ? 0 : (d - average) * xScale.rangeBand() / -5; }) |
|
.attr('y2', 7); |
|
|
|
// Re-orient the orientation section |
|
svg.selectAll('.section.reorientation .box') |
|
.attr('transform', function (d, i) { return 'translate(' + xScale(0) + ',' + yScale(i) + ')'; }) |
|
|
|
</script> |