Using the Twitch API to display the status of various channels.
New things I experimented with:
- Jade
- Sass
Other technologies used:
- jQuery
- bootstrap
A Pen by Charlotte Tan on CodePen.
Using the Twitch API to display the status of various channels.
New things I experimented with:
Other technologies used:
A Pen by Charlotte Tan on CodePen.
#result | |
.container-fluid | |
.row | |
.col-xs-10.col-xs-offset-1.col-md-8.col-md-offset-2.col-lg-6.col-lg-offset-3 | |
h1.text-center GLHF | |
table#resultTable.table.table-hover.table-responsive | |
tbody | |
tr.success | |
td | |
img(src="https://placeholdit.imgix.net/~text?txtsize=16&txt=%3F&w=40&h=40&txttrack=0") | |
td. | |
Live Streamer! | |
td. | |
Loading streams... | |
tr.info | |
td | |
img(src="https://placeholdit.imgix.net/~text?txtsize=16&txt=%3F&w=40&h=40&txttrack=0") | |
td. | |
Offline Streamer | |
td. | |
Loading streams... | |
tr.disabled | |
td | |
img(src="https://placeholdit.imgix.net/~text?txtsize=16&txt=%3F&w=40&h=40&txttrack=0") | |
td. | |
404 Streamer | |
td. | |
Loading streams... |
var STREAMERS = ['freecodecamp', 'ESL_CSGO', 'summit1g', 'DizzyKitten', 'noobs2ninjas', 'brunofin', 'comster40', 'TheBlackHokage', 'lirik', 'TehBeardedGamer', 'legendarylea', 'CrReaM', 'aimzatchu', 'jena_urf_lord_legacy']; | |
var streamersData = []; | |
var oldSortedCachedData = [{"mature":true,"status":"[PC-Ultra] Insane Campaign Co-op - Uitt.tv w/ @CrReaM","broadcaster_language":"en","display_name":"CrReaM","game":"Gears of War 4","language":"en","_id":2261919,"name":"CrReaM","created_at":"2008-10-24T01:34:09Z","updated_at":"2016-10-10T05:33:15Z","delay":null,"logo":"https://static-cdn.jtvnw.net/jtv_user_pictures/crream-profile_image-c1f570819b02f6f4-300x300.png","banner":null,"video_banner":"https://static-cdn.jtvnw.net/jtv_user_pictures/crream-channel_offline_image-45ca55ad950614d5-1920x1080.png","background":null,"profile_banner":"https://static-cdn.jtvnw.net/jtv_user_pictures/crream-profile_banner-6af7029714a2c2e6-480.png","profile_banner_background_color":"#000000","partner":true,"url":"https://www.twitch.tv/crream","views":9760534,"followers":101086,"_links":{"self":"http://api.twitch.tv/kraken/channels/crream","follows":"http://api.twitch.tv/kraken/channels/crream/follows","commercial":"http://api.twitch.tv/kraken/channels/crream/commercial","stream_key":"http://api.twitch.tv/kraken/channels/crream/stream_key","chat":"http://api.twitch.tv/kraken/chat/crream","subscriptions":"http://api.twitch.tv/kraken/channels/crream/subscriptions","editors":"http://api.twitch.tv/kraken/channels/crream/editors","teams":"http://api.twitch.tv/kraken/channels/crream/teams","videos":"http://api.twitch.tv/kraken/channels/crream/videos"},"title":"Gears of War 4: [PC-Ultra] Insane Campaign Co-op - Uitt.tv w/ @CrReaM","trClass":"success"},{"mature":false,"status":"New Stardew Update!","broadcaster_language":"en","display_name":"DizzyKitten","game":"Stardew Valley","language":"en","_id":47474524,"name":"DizzyKitten","created_at":"2013-08-12T00:11:45Z","updated_at":"2016-10-10T05:33:20Z","delay":null,"logo":"https://static-cdn.jtvnw.net/jtv_user_pictures/dizzykitten-profile_image-ca899752a83f72a6-300x300.png","banner":null,"video_banner":"https://static-cdn.jtvnw.net/jtv_user_pictures/dizzykitten-channel_offline_image-b2c2cae356a3a362-1920x1080.jpeg","background":null,"profile_banner":"https://static-cdn.jtvnw.net/jtv_user_pictures/dizzykitten-profile_banner-73e7d2a6bef94741-480.png","profile_banner_background_color":null,"partner":true,"url":"https://www.twitch.tv/dizzykitten","views":9334965,"followers":439749,"_links":{"self":"http://api.twitch.tv/kraken/channels/dizzykitten","follows":"http://api.twitch.tv/kraken/channels/dizzykitten/follows","commercial":"http://api.twitch.tv/kraken/channels/dizzykitten/commercial","stream_key":"http://api.twitch.tv/kraken/channels/dizzykitten/stream_key","chat":"http://api.twitch.tv/kraken/chat/dizzykitten","subscriptions":"http://api.twitch.tv/kraken/channels/dizzykitten/subscriptions","editors":"http://api.twitch.tv/kraken/channels/dizzykitten/editors","teams":"http://api.twitch.tv/kraken/channels/dizzykitten/teams","videos":"http://api.twitch.tv/kraken/channels/dizzykitten/videos"},"title":"Stardew Valley: New Stardew Update!","trClass":"success"},{"mature":false,"status":"RERUN: OpTiC vs. Virtus.Pro [Cobblestone] - ESL One New York 2016 - Round 5","broadcaster_language":"en","display_name":"ESL_CSGO","game":"Counter-Strike: Global Offensive","language":"de","_id":31239503,"name":"ESL_CSGO","created_at":"2012-06-11T13:36:21Z","updated_at":"2016-10-10T05:33:17Z","delay":null,"logo":"https://static-cdn.jtvnw.net/jtv_user_pictures/esl_csgo-profile_image-546a0c1883798a41-300x300.jpeg","banner":null,"video_banner":"https://static-cdn.jtvnw.net/jtv_user_pictures/esl_csgo-channel_offline_image-c9f885982daa1c83-1920x1080.png","background":null,"profile_banner":"https://static-cdn.jtvnw.net/jtv_user_pictures/esl_csgo-profile_banner-0d10712c29995dc2-480.jpeg","profile_banner_background_color":"#000000","partner":true,"url":"https://www.twitch.tv/esl_csgo","views":202745454,"followers":1764634,"_links":{"self":"http://api.twitch.tv/kraken/channels/esl_csgo","follows":"http://api.twitch.tv/kraken/channels/esl_csgo/follows","commercial":"http://api.twitch.tv/kraken/channels/esl_csgo/commercial","stream_key":"http://api.twitch.tv/kraken/channels/esl_csgo/stream_key","chat":"http://api.twitch.tv/kraken/chat/esl_csgo","subscriptions":"http://api.twitch.tv/kraken/channels/esl_csgo/subscriptions","editors":"http://api.twitch.tv/kraken/channels/esl_csgo/editors","teams":"http://api.twitch.tv/kraken/channels/esl_csgo/teams","videos":"http://api.twitch.tv/kraken/channels/esl_csgo/videos"},"title":"Counter-Strike: Global Offensive: RERUN: OpTiC vs. Virtus.Pro [Cobblestone] - ESL One New York 2016 - Round 5","trClass":"success"},{"logo":"https://static-cdn.jtvnw.net/jtv_user_pictures/aimzatchu-profile_image-7a815f29b890951a-300x300.jpeg","title":"Offline","name":"AimzAtchu","url":"https://www.twitch.tv/aimzatchu","trClass":"info"},{"logo":"https://static-cdn.jtvnw.net/jtv_user_pictures/freecodecamp-profile_image-d9514f2df0962329-300x300.png","title":"Offline","name":"FreeCodeCamp","url":"https://www.twitch.tv/freecodecamp","trClass":"info"},{"logo":"https://static-cdn.jtvnw.net/jtv_user_pictures/jena_urf_lord_legacy-profile_image-0d4c5dc6da966b9f-300x300.jpeg","title":"Offline","name":"jena_urf_lord_legacy","url":"https://www.twitch.tv/jena_urf_lord_legacy","trClass":"info"},{"logo":"https://static-cdn.jtvnw.net/jtv_user_pictures/legendarylea-profile_image-d0f3a63980113816-300x300.jpeg","title":"Offline","name":"LegendaryLea","url":"https://www.twitch.tv/legendarylea","trClass":"info"},{"logo":"https://static-cdn.jtvnw.net/jtv_user_pictures/lirik-profile_image-476e7a592cdfed74-300x300.png","title":"Offline","name":"LIRIK","url":"https://www.twitch.tv/lirik","trClass":"info"},{"logo":"https://static-cdn.jtvnw.net/jtv_user_pictures/noobs2ninjas-profile_image-34707f847a73d934-300x300.png","title":"Offline","name":"noobs2ninjas","url":"https://www.twitch.tv/noobs2ninjas","trClass":"info"},{"logo":"https://static-cdn.jtvnw.net/jtv_user_pictures/summit1g-profile_image-1cf38b42b1545fd7-300x300.jpeg","title":"Offline","name":"summit1g","url":"https://www.twitch.tv/summit1g","trClass":"info"},{"logo":"https://static-cdn.jtvnw.net/jtv_user_pictures/tehbeardedgamer-profile_image-1d39f2eb8520689a-300x300.png","title":"Offline","name":"TehBeardedGamer","url":"https://www.twitch.tv/tehbeardedgamer","trClass":"info"},{"logo":"https://static-cdn.jtvnw.net/jtv_user_pictures/theblackhokage-profile_image-9616087188bc0779-300x300.png","title":"Offline","name":"TheBlackHokage","url":"https://www.twitch.tv/theblackhokage","trClass":"info"},{"logo":"https://placeholdit.imgix.net/~text?txtsize=16&txt=%3F&w=40&h=40&txttrack=0","name":"brunofin","title":"Account Closed","trClass":"disabled"},{"logo":"https://placeholdit.imgix.net/~text?txtsize=16&txt=%3F&w=40&h=40&txttrack=0","name":"comster40","title":"Account Closed","trClass":"disabled"}]; | |
$(function() { | |
var GET_STREAMS_API = 'https://api.twitch.tv/kraken/streams/'; | |
var GET_CHANNELS_API = 'https://api.twitch.tv/kraken/channels/'; | |
var STREAMER_URL = 'https://secure.twitch.tv/'; | |
var TWITCH_CLIENT_ID = '6cox4qxxmaeazxlf5kmxmo1lyz7c9eq'; | |
function loadStreams(streamer) { | |
$.ajax({ | |
type: 'GET', | |
url: GET_STREAMS_API + streamer,// + '?callback=?', | |
headers: { | |
'Client-ID': TWITCH_CLIENT_ID | |
}, | |
success: parseStreamsData, | |
error: parseStreamsData | |
}); | |
} | |
function loadChannels(streamer) { | |
$.ajax({ | |
type: 'GET', | |
url: GET_CHANNELS_API + streamer,// + '?callback=?' | |
headers: { | |
'Client-ID': TWITCH_CLIENT_ID | |
}, | |
success: parseChannelsData | |
}); | |
} | |
function addToStreamersData(data) { | |
if (streamersData.length === 0) { | |
// clear cached data | |
$('#resultTable tbody').empty(); | |
} | |
streamersData.push(data); | |
if (streamersData.length === STREAMERS.length) { | |
streamersData.sort(function(a, b) { | |
if (a.trClass === 'success') { | |
if (b.trClass === a.trClass) { | |
return a.name.toLowerCase().localeCompare(b.name.toLowerCase()); | |
} else { | |
return -1; | |
} | |
} else if (a.trClass === 'info') { | |
if (b.trClass === 'success') { | |
return 1; | |
} else if (b.trClass === a.trClass) { | |
return a.name.toLowerCase().localeCompare(b.name.toLowerCase()); | |
} else { | |
return -1; | |
} | |
} else if (a.trClass === 'disabled') { | |
if (b.trClass === a.trClass) { | |
return a.name.toLowerCase().localeCompare(b.name.toLowerCase()); | |
} else { | |
return 1; | |
} | |
} | |
// a must be equal to b | |
return 0; | |
}); | |
streamersData.forEach(addToResults); | |
} | |
} | |
function addToResults(data) { | |
var tr = $('<tr>'); | |
if (data.trClass) { | |
tr.addClass(data.trClass); | |
} | |
// logo | |
var logo = $('<img>', { | |
src: data.logo | |
}); | |
var tdLogo = $('<td>').append(logo); | |
tr.append(tdLogo); | |
// name + link | |
var link = data.name; | |
if (data.url) { | |
link = $('<a>', { | |
href: data.url | |
}).text(data.name); | |
} | |
var tdName = $('<td>').append(link); | |
tr.append(tdName); | |
// what they're streaming | |
var tdTitle = $('<td>').text(data.title); | |
tr.append(tdTitle); | |
$('#resultTable tbody').append(tr); | |
} | |
function parseChannelsData(data) { | |
var resultsData = {}; | |
resultsData.logo = data.logo; | |
resultsData.title = 'Offline'; | |
resultsData.name = data.display_name; | |
resultsData.url = data.url; | |
resultsData.trClass = 'info'; | |
addToStreamersData(resultsData); | |
} | |
function parseStreamsData(data, txtStatus, jqXHR) { | |
var resultsData = {}; | |
var streamerName = this.url.replace(GET_STREAMS_API, '').split('?')[0]; | |
if (data.error) { | |
resultsData.logo = 'https://placeholdit.imgix.net/~text?txtsize=16&txt=%3F&w=40&h=40&txttrack=0'; | |
resultsData.name = streamerName; | |
resultsData.title = 'Account Closed'; | |
resultsData.trClass = 'disabled'; | |
} else if (!data.stream) { | |
loadChannels(streamerName); | |
return; | |
} else { | |
resultsData = data.stream.channel; | |
resultsData.title = data.stream.game + ': ' + data.stream.channel.status; | |
resultsData.name = data.stream.channel.display_name; | |
resultsData.trClass = 'success'; | |
} | |
addToStreamersData(resultsData); | |
} | |
STREAMERS.forEach(loadStreams); | |
}); |
<script src="//cdnjs.cloudflare.com/ajax/libs/jquery/2.2.2/jquery.min.js"></script> |
#resultTable | |
img | |
width: 40px | |
height: 40px | |
border-radius: 20px | |
tr.disabled | |
background-color: lightgrey | |
color: grey | |
&:hover | |
background-color: darken(lightgrey, 5%) | |
tr | |
td | |
vertical-align: middle |
<link href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.5/css/bootstrap.min.css" rel="stylesheet" /> |