Built with blockbuilder.org
forked from sxywu's block: d3.unconf 2016, v6
forked from sxywu's block: d3.unconf 2016, v7
forked from sxywu's block: d3.unconf 2016, v8
forked from sxywu's block: d3.unconf 2016, v9
| license: mit |
Built with blockbuilder.org
forked from sxywu's block: d3.unconf 2016, v6
forked from sxywu's block: d3.unconf 2016, v7
forked from sxywu's block: d3.unconf 2016, v8
forked from sxywu's block: d3.unconf 2016, v9
| First Name | Last Name | Ticket Type | version | first | favorite | |
|---|---|---|---|---|---|---|
| Alan | McLean | General Admission | v1 | Scatter plot | d3.timer | |
| alanna | scott | General Admission | v3 | Bar chart, Line chart | ||
| Alastair | Dant | General Admission | v1 | Treemap | d3.forceSimulation | |
| Alex | Macy | General Admission | v3 | Line chart | d3.transition | |
| Amit | Patel | General Admission | v1 | N/A | d3.behavior.zoom | |
| Andrew | Wong | Invited | v3 | Radial plot | d3.scale | |
| Angela | Pablo | Invited | v2 | Scatter plot | ||
| Anna | Smylie | General Admission | v3 | Bar chart | ||
| Anna | Vital | Invited | v2 | Tree | d3.line | |
| Anuja | Verma | Scholarship | v3 | Tree | d3.hierarchy | |
| Bo | Ericsson | General Admission | v3 | Line chart | selection.data | |
| Brad | Lyon | General Admission | v2 | Chord diagram | d3.selectAll | |
| Brent | Cohn | General Admission | v3 | Bar plot | d3.forceSimulation | |
| Brian | Bailey | Scholarship | v4 | Bar chart | d3.voronoi | |
| Casey | Haber | Scholarship | v3 | Bar chart | d3.force | |
| Chris | Polis | General Admission | v3 | Time series | d3.transition | |
| christophe | viau | Invited | v1 | Tooltip | d3.axis | |
| Daniel | Overstreet | General Admission | v3 | Scatter plot | d3.nest | |
| Daniel | Wolfe | General Admission | v3 | Map | d3.transition | |
| David | Richards | General Admission | v3 | Force | d3.interpolate | |
| David | Schnurr | General Admission | v3 | Charting library | d3.voronoi | |
| David | Lin | General Admission | v3 | Bar chart | selection.data | |
| Don | McCurdy | General Admission | v3 | Choropleth | d3.voronoi | |
| Eric | Socolofsky | General Admission | v3 | Map | d3.transition | |
| Erik | Cunningham | General Admission | v3 | Scatter plot | selection.data | |
| Erik | Hazzard | General Admission | v1 | Radar chart | d3.voronoi | |
| Francois | Chabbey | General Admission | v3 | Bar chart | d3.scale | |
| Marcos | Iglesias | General Admission | v3 | Bar chart | d3.selectAll | |
| Hourann | Bosci | General Admission | v3 | Map, Bubble chart | d3.scaleOrdinal | |
| Ian | Johnson | Invited | v1 | Bar chart | d3.scaleLinear | |
| Ivy | Wang | General Admission | v1 | Network graph | nest.rollup | |
| James | Womack | Invited | v3 | Scatter plot | d3.scale | |
| James | Wenzel | Scholarship | v3 | Line chart | nest.map | |
| Jamie | Popkin | General Admission | v2 | Map | transform | |
| Janine | Heiser | Invited | v3 | Bar chart | d3.selection | |
| Jay | Mahabal | General Admission | v3 | Bar chart | d3.scale | |
| Jeff | Zerger | Invited | v2 | Map | d3.geoProjection | |
| Jeffrey | Catania | General Admission | v2 | Line chart | d3.voronoi | |
| Jennifer | Lee | Invited | v3 | Bar chart | d3.transition | |
| Jeremy | Wong | General Admission | v3 | Line Chart | d3.geoProjection | |
| Jeremy | Wildfire | General Admission | v2 | Bar chart | d3.scale | |
| Jim | Vallandingham | General Admission | v2 | Bubble chart | d3.nest | |
| Jing | Lu | Scholarship | v4 | Scatter plot | d3.brush | |
| John | Schulz | General Admission | v2 | Area chart | d3.histogram | |
| John | Huynh | Scholarship | v3 | Scatter plot | d3.transition | |
| Jon | Sadka | Invited | v4 | Bar chart | d3.transition | |
| Jon | Nguyen | General Admission | v2 | Bar chart | d3.extent | |
| Jonathan | Nesci | General Admission | v2 | Bar chart | scale.invert | |
| Kai | Chang | Invited | v1 | Chord diagram | d3.interpolateMagma | |
| Ken | Penn | General Admission | v3 | Bar chart | d3.forceSimulation | |
| Kerry | Rodden | Invited | v1 | Chord diagram | d3.scale | |
| Krist | Wongsuphasawat | General Admission | v3 | Scatter plot | d3.selection, d3.scale | |
| Kristen | Judd | General Admission | v3 | Pie chart | d3.transition | |
| Kristin | Henry | Invited | v2 | Chloropleth | d3.scale | |
| Leland | Lee | Scholarship | v3 | Bar chart | arcTween | |
| Logan | Carter | General Admission | v4 | Pie chart, Donut chart | d3.pie | |
| Ludwig | Schubert | Scholarship | v3 | Tree | projection.fitSize | |
| Marie | Swarzenski | Scholarship | v3 | Line chart | d3.transition | |
| Mark | Vital | General Admission | v2 | Tree | d3.line | |
| Matthew | Isanuk | Invited | v4 | Scatter plot | d3.scale | |
| Mauro | Perez | Scholarship | v3 | Sunburst | selection.data | |
| Micah | Stubbs | Invited | v3 | Map | d3.request | |
| Michael | Freeman | General Admission | v2 | Bar chart | d3.pack | |
| Mike | Bostock | Invited | v1 | N/A | d3.pack | |
| Minwei | Xu | Scholarship | v4 | bar chart | d3.layout.force | |
| Naoya | Kanai | Scholarship | v3 | bar chart | d3.scale | |
| Noah | Veltman | Invited | v2 | Line chart | d3.transition | |
| Patrick | Sun | General Admission | v3 | Scatter Plot | selection.attr | |
| Paul | Rosenzweig | General Admission | v4 | Scatter plot | d3.selectAll | |
| Paul | Van slembrouck | Invited | v1 | Bar chart | d3.scale | |
| Philippe | Rivière | Invited | v3 | Map | d3.geoProjection | |
| Phillip | Mispagel | General Admission | v4 | Donut chart | d3.scale, d3.zoom | |
| Ramesh | Sampath | General Admission | v4 | Scatter plot | d3.scale | |
| Ric | Cheng | Scholarship | v3 | Line chart | d3.brush | |
| Robert | Crocker | Invited | v3 | Bar chart | d3.nest | |
| Robert | Harris | General Admission | v2 | Force | d3.scale | |
| Roger | Fischer | Invited | v3 | Map | d3.geo | |
| Rumman | Chowdhury | Invited | v3 | Line chart | d3.voronoi | |
| Saniya | Jesupaul | Scholarship | v3 | Scatter plot | d3.color | |
| Sara | Quigley | Invited | v2 | Circle pack | d3.nest | |
| Sara | Schnadt | General Admission | v3 | Scatter plot | ||
| Sarah | Kwak | Scholarship | v4 | Donut chart | d3.transition | |
| Seemant | Kulleen | Invited | v3 | Donut chart | d3.nest | |
| Shan | Carter | Invited | v2 | Bubble chart | d3.scaleLinear | |
| Shelby | Sturgis | Invited | v3 | Scatter plot | d3.scale | |
| Shirley | Wu | Invited | v2 | Tree | d3.forceSimulation | |
| Siu-Mei | Man | Invited | v4 | Bar chart | d3.voronoi | |
| Susie | Lu | Invited | v2 | Bar chart | d3.nest | |
| Tarek | Rached | General Admission | v2 | Bar chart | d3.layout.pack | |
| Tim Hyon | Hyon | General Admission | v3 | Parallel coordinates | d3.scale | |
| Tony | Chu | Invited | v3 | Bubble chart | d3.scale | |
| Toshiyuki | Hayashi | General Admission | v3 | Network graph | selection.enter, selection.exit | |
| Vasco | Asturiano | General Admission | v2 | Force | selection.data | |
| Victor | Powell | General Admission | v4 | Scatter plot | d3.geo.path | |
| Visnu | Pitiyanuvath | General Admission | v2 | Bar chart | d3.nest | |
| Xianlin | Hu | General Admission | v3 | Force | d3.transition | |
| Yukiko | Steineman | General Admission | v3 | Bar chart | d3.color | |
| Zack | DeSario | Invited | v2 | Bar chart | selection.enter |
| <!DOCTYPE html> | |
| <head> | |
| <meta charset="utf-8"> | |
| <script src="https://d3js.org/d3.v4.min.js"></script> | |
| <script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.15.0/lodash.min.js"></script> | |
| <script src="https://npmcdn.com/babel-core@5.8.34/browser.min.js"></script> | |
| <script type="text/javascript" src="http://gka.github.io/chroma.js/vendor/chroma-js/chroma.min.js"></script> | |
| <style> | |
| body { | |
| /* background-color: #000; */ | |
| font-family: courier; | |
| text-align: center; | |
| } | |
| h1 { | |
| font-size: 36px; | |
| width: 1000px; | |
| padding-top: 40px; | |
| } | |
| #header { | |
| width: 1000px; | |
| /* padding: 40px 0; */ | |
| position: relative; | |
| margin: auto; | |
| } | |
| #legend { | |
| width: 580px; | |
| height: 600px; | |
| margin: auto; | |
| } | |
| #annotation { | |
| width: 1000px; | |
| position: absolute; | |
| top: 0; | |
| font-size: 20px; | |
| } | |
| #content { | |
| position: relative; | |
| width: 1000px; | |
| padding-bottom: 100px; | |
| margin: auto; | |
| } | |
| #flowers { | |
| width: 800px; | |
| height: 1000px; | |
| margin: auto; | |
| } | |
| #hover { | |
| position: absolute; | |
| width: 250px; | |
| border: 1px solid #666; | |
| border-radius: 5px; | |
| box-shadow: 0 0 5px #666; | |
| text-align: center; | |
| background-color: #fff; | |
| padding: 10px; | |
| } | |
| </style> | |
| </head> | |
| <body> | |
| <div id='header'> | |
| <h1>d3.unconf 2016</h1> | |
| <p>(Hover for attendee info ✨)</p> | |
| <svg id='legend'></svg> | |
| <div id='annotation'></svg> | |
| </div> | |
| <div id='content'> | |
| <svg id='flowers'></svg> | |
| <div id='hover'></div> | |
| </div> | |
| <script> | |
| var midpoint = -2/3; | |
| var halfSide = Math.sqrt(1 / 3); | |
| var triangle = [ | |
| (-halfSide) + ',-1', | |
| (halfSide) + ',-1', | |
| '0,0' | |
| ]; | |
| var favoritesScale = d3.scaleLinear() | |
| .range([midpoint - .05, -.85]); | |
| var versionsScale = d3.scaleOrdinal() | |
| .range(_.rangeRight(3, 7)); | |
| var firstsScale = d3.scaleOrdinal(); | |
| var hexScale = 40; | |
| var hexSize = hexScale * 2 / Math.sqrt(3); | |
| d3.csv('data.csv', data => { | |
| /************************************** | |
| ** process data and add them to scales as domain | |
| **************************************/ | |
| var attendees = _.map(data, d => { | |
| return { | |
| name: d['First Name'], | |
| first: d.first.split(', ')[0], | |
| favorite: d.favorite.split(', ')[0], | |
| version: parseInt(d.version.replace('v', '')), | |
| }; | |
| }); | |
| var firsts = _.chain(attendees) | |
| .map('first').flatten() | |
| .countBy().toPairs() | |
| .sortBy(d => -d[1]) | |
| .map(0).value(); | |
| var favorites = _.chain(attendees) | |
| .map('favorite').flatten() | |
| .countBy().value(); | |
| var versions = _.chain(attendees) | |
| .map('version').flatten() | |
| .countBy().toPairs() | |
| .sortBy(d => -d[1]) | |
| .filter(d => d[1] > 1) | |
| .map(0).value(); | |
| // update colors with number of classes | |
| var colors = chroma.cubehelix() | |
| .start(280) | |
| // .rotations(-1 / firsts.length) | |
| .gamma(0.5) | |
| .lightness([0.3, 0.4]) | |
| .scale() // convert to chroma.scale | |
| // .correctLightness() | |
| .colors(firsts.length); | |
| firstsScale.domain(firsts).range(colors); | |
| versionsScale.domain(_.range(1, 5)); | |
| var maxFavorites = _.max(_.values(favorites)); | |
| favoritesScale.domain([1, maxFavorites]); | |
| /************************************** | |
| ** legend | |
| **************************************/ | |
| var baseLegendData = { | |
| version: 1, | |
| first: 'Bar chart', | |
| favorite: 'd3.scale', | |
| }; | |
| var legend = d3.select('#legend'); | |
| var annotation = d3.select('#annotation'); | |
| // first, the versions | |
| // annotation.append('div') | |
| // .style('position', 'absolute') | |
| // .style('width', '1000px') | |
| // .style('top', hexScale) | |
| // .html('Which version of d3 did you start with?'); | |
| var versionsData = _.times(4, i => { | |
| return Object.assign(_.clone(baseLegendData), { | |
| version: i + 1, | |
| legendText: 'd3 v' + (i + 1), | |
| }); | |
| }); | |
| legend.append('g') | |
| .attr('transform', 'translate(' + [0, 0] + ')') | |
| .call(drawHexagons, versionsData, 4); | |
| // first | |
| // annotation.append('div') | |
| // .style('position', 'absolute') | |
| // .style('width', '1000px') | |
| // .style('top', 5.5 * hexScale) | |
| // .html('Your first d3 project:<br />what type of visualization was it?'); | |
| var firstData1 = _.times(4, i => { | |
| var index = !i ? i : i * 4 - 1; | |
| return Object.assign(_.clone(baseLegendData), { | |
| first: firsts[index], | |
| legendText: firsts[index], | |
| }); | |
| }); | |
| var firstData2 = _.times(3, i => { | |
| var index = (!i ? i : i * 4 - 1) + 14; | |
| return Object.assign(_.clone(baseLegendData), { | |
| first: firsts[index], | |
| legendText: firsts[index], | |
| }); | |
| }); | |
| legend.append('g') | |
| .attr('transform', 'translate(' + [0, 4 * hexScale] + ')') | |
| .call(drawHexagons, firstData1, 4); | |
| legend.append('g') | |
| .attr('transform', 'translate(' + [1.9 * hexScale, 6.75 * hexScale] + ')') | |
| .call(drawHexagons, firstData2, 3); | |
| // favorites | |
| // annotation.append('div') | |
| // .style('position', 'absolute') | |
| // .style('width', '1000px') | |
| // .style('top', 13.5 * hexScale) | |
| // .html('What is your favorite d3 api function?'); | |
| var favoriteNames = ['d3.scale', 'd3.transition', 'd3.forceSimulation', 'd3.hierarchy']; | |
| var favoriteData = _.times(4, i => { | |
| return Object.assign(_.clone(baseLegendData), { | |
| favorite: favoriteNames[i], | |
| legendText: favoriteNames[i], | |
| }); | |
| }); | |
| legend.append('g') | |
| .attr('transform', 'translate(' + [0, 10.75 * hexScale] + ')') | |
| .call(drawHexagons, favoriteData, 4); | |
| /************************************** | |
| ** draw the hexagons | |
| **************************************/ | |
| var perRow = 5; | |
| var svg = d3.select('#flowers').append('g') | |
| .call(drawHexagons, attendees, perRow); | |
| function drawHexagons(selection, data, perRow) { | |
| var hex = selection.selectAll('.hex') | |
| .data(data).enter().append('g') | |
| .classed('hex', true) | |
| .attr('transform', (d, i) => { | |
| var row = Math.floor(i / perRow); | |
| var x = (i % perRow * 3.2 + 1.5) * hexSize; | |
| if (row % 2) { | |
| x += 1.6 * hexSize; | |
| } | |
| var y = (row * 1.05 + 2) * hexScale; | |
| d.x = x; | |
| d.y = y; | |
| return 'translate(' + [x, y] + ')scale(' + hexScale + ')'; | |
| }).on('mouseenter', mouseenter) | |
| .on('mouseleave', mouseleave); | |
| var triangles = hex.selectAll('triangle') | |
| .data((d, j) => { | |
| return _.times(versionsScale(d.version), i => { | |
| return { | |
| angle: i * 60, | |
| midpoint: favoritesScale(favorites[d.favorite]), | |
| color: firstsScale(d.first), | |
| // color: colors[j], | |
| }; | |
| }); | |
| }).enter().append('g') | |
| .classed('triangle', true) | |
| .attr('transform', d => 'rotate(' + d.angle + ')'); | |
| triangles.append('polygon') | |
| .attr('points', triangle.join(' ')) | |
| .attr('fill', d => chroma(d.color).darken(2.5)); | |
| // .attr('fill', '#fff'); | |
| triangles.selectAll('.subtri') | |
| .data(d => _.times(3, i => { | |
| return Object.assign({ | |
| subangle: i * 120, | |
| subcolor: chroma(d.color).saturate(1.5).brighten(i), | |
| }, d); | |
| })).enter().append('polygon') | |
| .classed('subtri', true) | |
| .attr('transform', d => 'rotate(' + d.subangle + ' 0 ' + midpoint + ')') | |
| .attr('points', d => { | |
| return [ | |
| (-halfSide) + ',-1', | |
| '0,' + d.midpoint, | |
| halfSide + ',-1' | |
| ].join(' '); | |
| }).attr('fill', d => d.subcolor); | |
| // add in text if it's for legend | |
| var fontSize = 14; | |
| hex.filter(d => d.legendText) | |
| .append('text') | |
| .attr('y', 1.25) | |
| .attr('font-size', fontSize / hexScale) | |
| .attr('text-anchor', 'middle') | |
| .attr('dy', '.35em') | |
| .text(d => d.legendText); | |
| } | |
| }); | |
| /************************************** | |
| ** hover interaction | |
| **************************************/ | |
| var hover = d3.select('#hover') | |
| .style('display', 'none'); | |
| function mouseenter(d) { | |
| if (!d.name) return; | |
| var html = '<h2>' + d.name + '</h2>'; | |
| html += '<p>started with d3.js v' + d.version; | |
| if (d.first) { | |
| html += ' and made a ' + d.first; | |
| } | |
| if (d.favorite) { | |
| html += '. Their favorite d3 function is ' + d.favorite; | |
| } | |
| html += '.'; | |
| var x = d.x + hexSize / 2; | |
| var y = d.y + hexSize / 2; | |
| hover.style('display', 'block') | |
| .style('top', y + 'px') | |
| .style('left', x + 'px') | |
| .html(html); | |
| } | |
| function mouseleave() { | |
| hover.style('display', 'none'); | |
| } | |
| </script> | |
| </body> |