Flexbox table of most popular artist by genre (in skate videos). Click to a column to sort by it.
Last active
October 9, 2018 00:57
-
-
Save jwilber/219e9d40802c2a33a71958a5d6ab07b7 to your computer and use it in GitHub Desktop.
d3 flexbox table
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
license: mit |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
.table { | |
display: flex; | |
flex-flow: column nowrap; | |
flex: 1 1 auto; | |
font-size: .9rem; | |
margin: 0 -5px; | |
line-height: .5; | |
width: 50%; | |
font-family: Gill Sans; | |
font-weight: 10%; | |
} | |
.th { | |
display: none; | |
font-weight: bold; | |
/*background-color: #f2f2f2;*/ | |
border-bottom: 1px solid #d0d0d0; | |
color: #74a9cf; | |
} | |
.th > .td { | |
white-space: normal; | |
justify-content: center; | |
} | |
.tr { | |
width: 100%; | |
display: flex; | |
flex-flow: row nowrap; | |
/*border-bottom: .5px solid #d0d0d0;*/ | |
} | |
/* | |
.tr:nth-of-type(even) { | |
background-color: #e8eff9; | |
} | |
.tr:nth-of-type(odd) { | |
background-color: #ffffff; | |
}*/ | |
.td { | |
display: flex; | |
flex-flow: row nowrap; | |
flex-grow: 1; | |
flex-basis: 0; | |
padding: 0.3em; | |
word-break: break-word; | |
overflow: hidden; | |
text-overflow: ellipsis; | |
min-width: 0px; | |
white-space: nowrap; | |
margin: 0 5px; | |
} | |
/* Non-table styling */ | |
.title { | |
font-weight: bold; | |
font-size: 200%; | |
margin-bottom: 14px; | |
vertical-align: top; | |
font-family: Gill Sans; | |
color: #2b8cbe; | |
/*margin-left: 200px;*/ | |
} | |
.SearchBar { | |
font-weight: bold; | |
font-size: 90%; | |
margin-bottom: 10px; | |
font-family: Gill Sans; | |
color: #2b8cbe; | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
[{"genre2":"Indie Rock","artist":"Joy Division","art_count":32,"percent":0.1609},{"genre2":"Western Hip-Hop/Rap","artist":"Gang Starr","art_count":34,"percent":0.1579},{"genre2":"Punk","artist":"Bad Brains","art_count":19,"percent":0.0629},{"genre2":"70's Rock","artist":"Pink Floyd","art_count":40,"percent":0.0529},{"genre2":"Metal","artist":"Black Sabbath","art_count":47,"percent":0.0432},{"genre2":"Alternative","artist":"The Cure","art_count":15,"percent":0.0423},{"genre2":"60's Rock","artist":"The Beatles","art_count":54,"percent":0.0411},{"genre2":"Mainstream Rock","artist":"The Rolling Stones","art_count":40,"percent":0.0372},{"genre2":"Classic R&B/Soul","artist":"Curtis Mayfield","art_count":25,"percent":0.0349},{"genre2":"Western Pop","artist":"John Lennon","art_count":14,"percent":0.0325},{"genre2":"Downtempo, Lounge & Ambient","artist":"Tommy Guerrero","art_count":19,"percent":0.0226},{"genre2":"Electronica Mainstream","artist":"Moby","art_count":15,"percent":0.0178},{"genre2":"Hard Rock","artist":"David Bowie","art_count":40,"percent":0.0166},{"genre2":"Emo & Hardcore","artist":"Fugazi","art_count":45,"percent":0.0135},{"genre2":"Original Film/TV Music","artist":"Ennio Morricone","art_count":9,"percent":0.0124},{"genre2":"Contemporary R&B/Soul","artist":"Michael Jackson","art_count":9,"percent":0.0122},{"genre2":"Reggae","artist":"Bob Marley","art_count":14,"percent":0.0121},{"genre2":"Garage Rock Revival","artist":"The Greenhornes","art_count":8,"percent":0.0097},{"genre2":"Synth Pop","artist":"New Order","art_count":22,"percent":0.0085},{"genre2":"Alternative Folk","artist":"Devendra Banhart","art_count":12,"percent":0.0085},{"genre2":"Techno","artist":"Squarepusher","art_count":8,"percent":0.0085},{"genre2":"New Wave Pop","artist":"Devo","art_count":32,"percent":0.0078},{"genre2":"House","artist":"Justice","art_count":11,"percent":0.0075},{"genre2":"Bebop & Modern Jazz","artist":"John Coltrane","art_count":4,"percent":0.0074},{"genre2":"Folk","artist":"Donovan","art_count":14,"percent":0.007},{"genre2":"New Wave Rock","artist":"The Velvet Underground","art_count":16,"percent":0.0064},{"genre2":"Dance & Club","artist":"DJ Egadz","art_count":6,"percent":0.0064},{"genre2":"Country","artist":"The Sadies","art_count":4,"percent":0.0064},{"genre2":"Contemporary Jazz & Fusion","artist":"Shawn Lee's Ping Pong Orchestra","art_count":10,"percent":0.006},{"genre2":"Data & Other","artist":"Blvck Ceiling","art_count":5,"percent":0.006},{"genre2":"Folk Rock","artist":"Bob Dylan","art_count":26,"percent":0.0059},{"genre2":"European Pop","artist":"Edith Piaf","art_count":3,"percent":0.0054},{"genre2":"Alternative Roots","artist":"Radical Face","art_count":7,"percent":0.0047},{"genre2":"Brit Rock","artist":"Placebo","art_count":9,"percent":0.0045},{"genre2":"Electric Blues","artist":"Gibb Droll","art_count":3,"percent":0.0044},{"genre2":"Adult Alternative Rock","artist":"Ben Harper","art_count":9,"percent":0.0041},{"genre2":"Electronica Fusion","artist":"Bonobo","art_count":13,"percent":0.004},{"genre2":"Trance","artist":"Gorgeous","art_count":2,"percent":0.004},{"genre2":"Other Classical","artist":"Adeodat Warfield","art_count":2,"percent":0.0039},{"genre2":"Jam Bands","artist":"Sol","art_count":22,"percent":0.0037},{"genre2":"50's Rock","artist":"Elvis Presley","art_count":8,"percent":0.003},{"genre2":"Ska Revival","artist":"Dance Hall Crashers","art_count":6,"percent":0.003},{"genre2":"Brit Pop","artist":"Oasis","art_count":6,"percent":0.003},{"genre2":"Brazilian","artist":"Chorão & Charlie Brown Jr.","art_count":5,"percent":0.0028},{"genre2":"Japanese Pop","artist":"Cornelius","art_count":5,"percent":0.0028},{"genre2":"New Age","artist":"18 Carat Affair","art_count":2,"percent":0.0028},{"genre2":"Jazz Vocals","artist":"Nina Simone","art_count":19,"percent":0.0027},{"genre2":"Easy Listening","artist":"Frank Sinatra","art_count":5,"percent":0.0027},{"genre2":"Disco","artist":"Cheryl Lynn","art_count":2,"percent":0.0027},{"genre2":"Classic Country","artist":"Johnny Cash","art_count":12,"percent":0.0026},{"genre2":"Power Pop","artist":"Cheap Trick","art_count":3,"percent":0.0025},{"genre2":"Spoken Word","artist":"Justin Bates","art_count":2,"percent":0.0025},{"genre2":"Latin Rock","artist":"El Guincho","art_count":3,"percent":0.0024},{"genre2":"African Pop","artist":"The Budos Band","art_count":11,"percent":0.0023},{"genre2":"Latin Traditional","artist":"Buena Vista Social Club","art_count":3,"percent":0.0023},{"genre2":"Japanese Rock","artist":"Mr. E","art_count":4,"percent":0.0022},{"genre2":"New Romantic","artist":"A Flock Of Seagulls","art_count":5,"percent":0.0021},{"genre2":"Smooth Jazz","artist":"Bob James","art_count":3,"percent":0.0019},{"genre2":"Comedy","artist":"Bobby Pickett and The Crypt","art_count":2,"percent":0.0019},{"genre2":"Goth","artist":"HIM","art_count":5,"percent":0.0016},{"genre2":"Industrial","artist":"Lard","art_count":4,"percent":0.0016},{"genre2":"Stage Musicals","artist":"Baron","art_count":4,"percent":0.0015},{"genre2":"Jungle/Drum 'n' Bass","artist":"Hive","art_count":4,"percent":0.0015},{"genre2":"Rockabilly Revival","artist":"The Cramps","art_count":7,"percent":0.0013},{"genre2":"Big Band & Swing","artist":"Enoch","art_count":4,"percent":0.0013},{"genre2":"Latin Hip-Hop/Rap","artist":"Mala Rodriguez","art_count":3,"percent":0.0013},{"genre2":"Latin Pop","artist":"Bronx River Parkway","art_count":2,"percent":0.0013},{"genre2":"Early Jazz","artist":"Louis Armstrong","art_count":4,"percent":0.0012},{"genre2":"Classic Pop Vocals","artist":"456 Productions","art_count":3,"percent":0.0012},{"genre2":"Surf Revival","artist":"Los Tiki Phantoms","art_count":2,"percent":0.0012}] |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
function makeTable(data, columns) { | |
// columns MUST be the same length as the number of features in the dataset | |
var searchBar = d3.select('body').append("div").attr("class", "SearchBar") | |
var table = d3.select('body').append('div').attr('class', 'table'); | |
var thead = table.append('div').attr('class', 'tr th'); | |
var tbody = table.append('div').attr('class', 'tbody'); | |
// Save column names for column creation | |
var dataFeatures = d3.keys(data[0]); | |
// Create dictionary to track true column names for sorting later | |
// i.e.; {'columns[i] : dataFeatures[i]} | |
var colDict = {}; | |
for (var i=0; i<columns.length; i++) { | |
colDict[columns[i]] = dataFeatures[i]; | |
}; | |
// keep track of sort ordenr | |
var sortAscending = true; | |
var barScalePercent = d3.scale.linear() | |
.domain([0,.20]) | |
.range([5,100]); | |
var barScaleGenre = d3.scale.linear() | |
.domain([10,2060]) | |
.range([5,100]); | |
var barScaleArtist = d3.scale.linear() | |
.domain([0,70]) | |
.range([5,100]); | |
// append the header row | |
thead.selectAll('div') | |
.data(columns).enter() | |
.append('div') | |
.attr('class', 'td') | |
.attr('style', 'justify-content: left;') | |
.attr('featureName', function (column) { return column; }) | |
.text(function (column) { return column; }); | |
// create a row for each object in the data | |
var rows = tbody.selectAll('div') | |
.data(data) | |
.enter() | |
.append('div') | |
.attr('class', 'tr'); | |
// create a cell in each row for each column | |
var cells = rows.selectAll('div') | |
.data(function (row) { | |
return dataFeatures.map(function (columnName) { | |
return {col: columnName, value: row[columnName]}; | |
}); | |
}) | |
.enter() | |
.append('div') | |
.attr('class', 'td') | |
.attr('style', 'justify-content: left;') | |
.text(function (d) { return d.value; }) | |
.append('svg') | |
.attr('height', 10) | |
.attr('width', 100) | |
.append("rect") | |
.attr("height", 8) | |
.attr('width', function(d) { | |
if (isNaN(d.value)) { | |
return 0; | |
} else { | |
if (d.col == 'percent'){ | |
return barScalePercent(d.value); | |
} else if (d.col == 'art_count'){ | |
return barScaleArtist(d.value); | |
} else if (d.col == 'count') { | |
return barScaleGenre(d.value); | |
} else { | |
return 0; | |
}; | |
}; | |
}) | |
.attr('fill', 'coral'); | |
// Search | |
searchBar.append("p") | |
.attr("class", "SearchBar") | |
.text("Search By Title:"); | |
d3.select(".SearchBar") | |
.append("input") | |
.attr("class", "SearchBar") | |
.attr("id", "search") | |
.attr("type", "text") | |
.attr("placeholder", "Search..."); | |
d3.select("#search") | |
.on("keyup", function() { // filter according to key pressed | |
var searched_data = data, | |
text = this.value.trim(); | |
console.log(text); | |
var searchResults = searched_data.map(function(r) { | |
var regex = new RegExp("^" + text + ".*", "i"); | |
if (regex.test(r.artist)) { // if there are any results | |
return regex.exec(r.artist)[0]; // return them to searchResults | |
} ; | |
}); | |
// filter blank entries from searchResults | |
searchResults = searchResults.filter(function(r){ | |
return r != undefined; | |
}); | |
// filter dataset with searchResults | |
searched_data = searchResults.map(function(r) { | |
return data.filter(function(p) { | |
return p.artist.indexOf(r) != -1; | |
}); | |
}); | |
// flatten array | |
searched_data = [].concat.apply([], searched_data); | |
console.log(searched_data); | |
// data bind with new data | |
rows = rows.data(searched_data, function(d){ return d.genre2}); | |
console.log(rows); | |
// enter the rows | |
rows.enter() | |
.append('div') | |
.attr('class', 'tr'); | |
// enter td's in each row | |
var cells = rows.selectAll('div') | |
.data(function (row) { | |
return dataFeatures.map(function (columnName) { | |
return {col: columnName, value: row[columnName]}; | |
}); | |
}) | |
.enter() | |
.append('div') | |
.attr('class', 'td') | |
.attr('style', 'justify-content: left;') | |
.text(function (d) { return d.value; }) | |
.append('svg') | |
.attr('height', 10) | |
.attr('width', 100) | |
.append("rect") | |
.attr("height", 8) | |
.attr('width', function(d) { | |
if (isNaN(d.value)) { | |
return 0; | |
} else { | |
if (d.col == 'percent'){ | |
return barScalePercent(d.value); | |
} else if (d.col == 'art_count'){ | |
return barScaleArtist(d.value); | |
} else if (d.col == 'count') { | |
return barScaleGenre(d.value); | |
} else { | |
return 0; | |
}; | |
}; | |
}) | |
.attr('fill', 'coral'); | |
// exit | |
rows.exit().remove(); | |
// }) | |
}); | |
// highlight rows on hover | |
d3.selectAll('.tbody .tr') | |
.on('mouseover', function() { | |
d3.select(this) | |
// .style('background-color', '#e8eff9'); | |
.style('background-color', '#f1eef6'); | |
}) | |
.on('mouseout', function() { | |
d3.select(this) | |
.style('background-color', '#ffffff'); | |
}); | |
// Sort columns on click | |
d3.selectAll('.th .td') | |
.on("click", function() { | |
// Identify column header's true name | |
var colName = d3.select(this)[0][0]['__data__']; | |
var dataName = colDict[colName]; | |
if (sortAscending) { | |
rows.sort(function(a, b) { | |
if (!isNaN(a[dataName])) { // sort numeric columns | |
return b[dataName] - a[dataName]; | |
} else { // sort text columns | |
return d3.ascending(b[dataName], a[dataName]); | |
}; | |
}); | |
sortAscending = !sortAscending; | |
} else { | |
rows.sort(function(a, b) { | |
if (!isNaN(a[dataName])) { // sort numeric columns | |
return a[dataName] - b[dataName]; | |
} else { // sort text columns | |
return d3.ascending(a[dataName], b[dataName]); | |
}; | |
}); | |
sortAscending = !sortAscending; | |
}; | |
}); | |
return table; | |
} | |
// Throw data into function and create table | |
d3.json('genre_table_data.json', function (error,data) { | |
// create table | |
makeTable(data, ['Genre', 'Top Artist', 'Artist Count', 'Frequency']); | |
}); | |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<!DOCTYPE html> | |
<meta charset='utf-8'> | |
<html> | |
<head> | |
<script src="http://d3js.org/d3.v3.min.js" charset="utf-8"></script> | |
<link rel="stylesheet" href="flx.css"> | |
</head> | |
<body> | |
<h3 class="title"> Genre Distribution</h3> | |
<script type='text/javascript' src='genre_table_flex.js'></script> | |
</body> | |
</html> |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment