2015-05-17 19:02:57 -04:00
|
|
|
var FFZ = window.FrankerFaceZ,
|
|
|
|
utils = require('../utils'),
|
|
|
|
constants = require('../constants');
|
|
|
|
|
|
|
|
|
|
|
|
// --------------------
|
|
|
|
// Initialization
|
|
|
|
// --------------------
|
|
|
|
|
|
|
|
FFZ.prototype.setup_channel = function() {
|
2015-07-04 17:06:36 -04:00
|
|
|
// Style Stuff!
|
|
|
|
this.log("Creating channel style element.");
|
|
|
|
var s = this._channel_style = document.createElement("style");
|
|
|
|
s.id = "ffz-channel-css";
|
|
|
|
document.head.appendChild(s);
|
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
// Settings stuff!
|
|
|
|
document.body.classList.toggle("ffz-hide-view-count", !this.settings.channel_views);
|
2015-05-17 19:02:57 -04:00
|
|
|
|
|
|
|
this.log("Creating channel style element.");
|
|
|
|
var s = this._channel_style = document.createElement('style');
|
|
|
|
s.id = "ffz-channel-css";
|
|
|
|
document.head.appendChild(s);
|
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
this.log("Hooking the Ember Channel Index view.");
|
|
|
|
var Channel = App.__container__.resolve('view:channel/index'),
|
2015-05-17 19:02:57 -04:00
|
|
|
f = this;
|
|
|
|
|
|
|
|
if ( ! Channel )
|
|
|
|
return;
|
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
this._modify_cindex(Channel);
|
|
|
|
|
|
|
|
// The Stupid View Fix. Is this necessary still?
|
|
|
|
try {
|
|
|
|
Channel.create().destroy();
|
|
|
|
} catch(err) { }
|
|
|
|
|
|
|
|
// Update Existing
|
|
|
|
for(var key in Ember.View.views) {
|
|
|
|
if ( ! Ember.View.views.hasOwnProperty(key) )
|
|
|
|
continue;
|
|
|
|
|
|
|
|
var view = Ember.View.views[key];
|
|
|
|
if ( !(view instanceof Channel) )
|
|
|
|
continue;
|
|
|
|
|
|
|
|
this.log("Manually updating Channel Index view.", view);
|
|
|
|
this._modify_cindex(view);
|
|
|
|
view.ffzInit();
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
|
|
this.log("Hooking the Ember Channel controller.");
|
|
|
|
|
|
|
|
Channel = App.__container__.lookup('controller:channel');
|
|
|
|
if ( ! Channel )
|
|
|
|
return;
|
|
|
|
|
2015-05-17 19:02:57 -04:00
|
|
|
Channel.reopen({
|
|
|
|
ffzUpdateUptime: function() {
|
2015-06-05 03:59:28 -04:00
|
|
|
if ( f._cindex )
|
|
|
|
f._cindex.ffzUpdateUptime();
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
}.observes("isLive", "content.id"),
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
ffzUpdateTitle: function() {
|
|
|
|
var name = this.get('content.name'),
|
|
|
|
display_name = this.get('content.display_name');
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
if ( display_name )
|
|
|
|
FFZ.capitalization[name] = [display_name, Date.now()];
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
if ( f._cindex )
|
|
|
|
f._cindex.ffzFixTitle();
|
2015-06-10 18:46:04 -04:00
|
|
|
}.observes("content.status", "content.id"),
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-06-10 18:46:04 -04:00
|
|
|
ffzHostTarget: function() {
|
2015-06-05 03:59:28 -04:00
|
|
|
var target = this.get('content.hostModeTarget'),
|
|
|
|
name = target && target.get('name'),
|
2015-07-04 17:06:36 -04:00
|
|
|
id = target && target.get('id'),
|
2015-06-05 03:59:28 -04:00
|
|
|
display_name = target && target.get('display_name');
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-07-04 17:06:36 -04:00
|
|
|
if ( id !== f.__old_host_target ) {
|
|
|
|
if ( f.__old_host_target )
|
|
|
|
f.ws_send("unsub_channel", f.__old_host_target);
|
|
|
|
|
|
|
|
if ( id ) {
|
|
|
|
f.ws_send("sub_channel", id);
|
|
|
|
f.__old_host_target = id;
|
|
|
|
} else
|
|
|
|
delete f.__old_host_target;
|
|
|
|
}
|
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
if ( display_name )
|
|
|
|
FFZ.capitalization[name] = [display_name, Date.now()];
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
if ( f.settings.group_tabs && f._chatv )
|
|
|
|
f._chatv.ffzRebuildTabs();
|
2015-07-04 17:06:36 -04:00
|
|
|
|
|
|
|
if ( f.settings.follow_buttons )
|
|
|
|
f.rebuild_following_ui();
|
|
|
|
|
|
|
|
if ( f.settings.srl_races )
|
|
|
|
f.rebuild_race_ui();
|
|
|
|
|
2015-06-10 18:46:04 -04:00
|
|
|
}.observes("content.hostModeTarget")
|
2015-06-05 03:59:28 -04:00
|
|
|
});
|
|
|
|
}
|
2015-05-17 19:02:57 -04:00
|
|
|
|
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
FFZ.prototype._modify_cindex = function(view) {
|
|
|
|
var f = this;
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
view.reopen({
|
|
|
|
didInsertElement: function() {
|
|
|
|
this._super();
|
|
|
|
try {
|
|
|
|
this.ffzInit();
|
|
|
|
} catch(err) {
|
|
|
|
f.error("CIndex didInsertElement: " + err);
|
|
|
|
}
|
|
|
|
},
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
willClearRender: function() {
|
|
|
|
try {
|
|
|
|
this.ffzTeardown();
|
|
|
|
} catch(err) {
|
|
|
|
f.error("CIndex willClearRender: " + err);
|
|
|
|
}
|
|
|
|
return this._super();
|
|
|
|
},
|
|
|
|
|
|
|
|
ffzInit: function() {
|
2015-07-04 17:06:36 -04:00
|
|
|
var id = this.get('controller.id'),
|
|
|
|
el = this.get('element');
|
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
f._cindex = this;
|
2015-07-04 17:06:36 -04:00
|
|
|
f.ws_send("sub_channel", id);
|
|
|
|
|
|
|
|
el.setAttribute('data-channel', id);
|
|
|
|
el.classList.add('ffz-channel');
|
|
|
|
|
2015-07-06 00:09:21 -04:00
|
|
|
// Try changing the theater mode tooltip.
|
|
|
|
this.$('.theatre-button a').attr('title', 'Theater Mode (Alt+T)');
|
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
this.ffzFixTitle();
|
|
|
|
this.ffzUpdateUptime();
|
|
|
|
this.ffzUpdateChatters();
|
|
|
|
|
2015-07-04 17:06:36 -04:00
|
|
|
var views = this.get('element').querySelector('.svg-glyph_views:not(.ffz-svg)')
|
|
|
|
if ( views )
|
|
|
|
views.parentNode.classList.add('twitch-channel-views');
|
|
|
|
|
|
|
|
if ( f.settings.follow_buttons )
|
|
|
|
f.rebuild_following_ui();
|
|
|
|
|
|
|
|
if ( f.settings.srl_races )
|
|
|
|
f.rebuild_race_ui();
|
2015-06-05 03:59:28 -04:00
|
|
|
},
|
|
|
|
|
|
|
|
ffzFixTitle: function() {
|
|
|
|
if ( f.has_bttv || ! f.settings.stream_title )
|
|
|
|
return;
|
|
|
|
|
|
|
|
var status = this.get("controller.status"),
|
|
|
|
channel = this.get("controller.id");
|
|
|
|
|
|
|
|
status = f.render_tokens(f.tokenize_line(channel, channel, status, true));
|
|
|
|
|
|
|
|
this.$(".title span").each(function(i, el) {
|
|
|
|
var scripts = el.querySelectorAll("script");
|
2015-07-04 17:06:36 -04:00
|
|
|
if ( ! scripts.length )
|
|
|
|
el.innerHTML = status;
|
|
|
|
else
|
|
|
|
el.innerHTML = scripts[0].outerHTML + status + scripts[1].outerHTML;
|
2015-06-05 03:59:28 -04:00
|
|
|
});
|
|
|
|
},
|
2015-05-17 19:02:57 -04:00
|
|
|
|
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
ffzUpdateChatters: function() {
|
|
|
|
// Get the counts.
|
|
|
|
var room_id = this.get('controller.id'),
|
|
|
|
room = f.rooms && f.rooms[room_id];
|
|
|
|
|
|
|
|
if ( ! room || ! f.settings.chatter_count ) {
|
|
|
|
var el = this.get('element').querySelector('#ffz-chatter-display');
|
|
|
|
el && el.parentElement.removeChild(el);
|
|
|
|
el = this.get('element').querySelector('#ffz-ffzchatter-display');
|
|
|
|
el && el.parentElement.removeChild(el);
|
2015-05-17 19:02:57 -04:00
|
|
|
return;
|
2015-06-05 03:59:28 -04:00
|
|
|
}
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
var chatter_count = Object.keys(room.room.get('ffz_chatters') || {}).length,
|
2015-07-04 17:06:36 -04:00
|
|
|
ffz_chatters = room.ffz_chatters || 0,
|
|
|
|
ffz_viewers = room.ffz_viewers || 0;
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
var el = this.get('element').querySelector('#ffz-chatter-display span');
|
|
|
|
if ( ! el ) {
|
|
|
|
var cont = this.get('element').querySelector('.stats-and-actions .channel-stats');
|
|
|
|
if ( ! cont )
|
|
|
|
return;
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
var stat = document.createElement('span');
|
|
|
|
stat.className = 'ffz stat';
|
|
|
|
stat.id = 'ffz-chatter-display';
|
2015-07-04 17:06:36 -04:00
|
|
|
stat.title = "Currently in Chat";
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
stat.innerHTML = constants.ROOMS + " ";
|
|
|
|
el = document.createElement("span");
|
|
|
|
stat.appendChild(el);
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
var other = cont.querySelector("#ffz-ffzchatter-display");
|
|
|
|
if ( other )
|
|
|
|
cont.insertBefore(stat, other);
|
|
|
|
else
|
|
|
|
cont.appendChild(stat);
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
jQuery(stat).tipsy();
|
|
|
|
}
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
el.innerHTML = utils.number_commas(chatter_count);
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-07-04 17:06:36 -04:00
|
|
|
if ( ! ffz_chatters && ! ffz_viewers ) {
|
2015-06-05 03:59:28 -04:00
|
|
|
el = this.get('element').querySelector('#ffz-ffzchatter-display');
|
|
|
|
el && el.parentNode.removeChild(el);
|
|
|
|
return;
|
|
|
|
}
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
el = this.get('element').querySelector('#ffz-ffzchatter-display span');
|
|
|
|
if ( ! el ) {
|
|
|
|
var cont = this.get('element').querySelector('.stats-and-actions .channel-stats');
|
|
|
|
if ( ! cont )
|
|
|
|
return;
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
var stat = document.createElement('span');
|
|
|
|
stat.className = 'ffz stat';
|
|
|
|
stat.id = 'ffz-ffzchatter-display';
|
2015-07-04 17:06:36 -04:00
|
|
|
stat.title = "Viewers (In Chat) with FrankerFaceZ";
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
stat.innerHTML = constants.ZREKNARF + " ";
|
|
|
|
el = document.createElement("span");
|
|
|
|
stat.appendChild(el);
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
var other = cont.querySelector("#ffz-chatter-display");
|
|
|
|
if ( other )
|
|
|
|
cont.insertBefore(stat, other.nextSibling);
|
|
|
|
else
|
|
|
|
cont.appendChild(stat);
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
jQuery(stat).tipsy();
|
|
|
|
}
|
2015-05-17 19:02:57 -04:00
|
|
|
|
2015-07-04 17:06:36 -04:00
|
|
|
el.innerHTML = utils.number_commas(ffz_viewers) + " (" + utils.number_commas(ffz_chatters) + ")";
|
2015-06-05 03:59:28 -04:00
|
|
|
},
|
2015-05-17 19:02:57 -04:00
|
|
|
|
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
ffzUpdateUptime: function() {
|
|
|
|
if ( this._ffz_update_uptime ) {
|
|
|
|
clearTimeout(this._ffz_update_uptime);
|
|
|
|
delete this._ffz_update_uptime;
|
|
|
|
}
|
|
|
|
|
|
|
|
if ( ! f.settings.stream_uptime || ! this.get("controller.isLiveAccordingToKraken") ) {
|
|
|
|
var el = this.get('element').querySelector('#ffz-uptime-display');
|
|
|
|
if ( el )
|
|
|
|
el.parentElement.removeChild(el);
|
|
|
|
return;
|
2015-05-17 19:02:57 -04:00
|
|
|
}
|
2015-06-05 03:59:28 -04:00
|
|
|
|
|
|
|
// Schedule an update.
|
|
|
|
this._ffz_update_uptime = setTimeout(this.ffzUpdateUptime.bind(this), 1000);
|
|
|
|
|
|
|
|
// Determine when the channel last went live.
|
|
|
|
var online = this.get("controller.content.stream.created_at");
|
|
|
|
if ( ! online )
|
|
|
|
return;
|
|
|
|
|
|
|
|
online = utils.parse_date(online);
|
|
|
|
if ( ! online )
|
|
|
|
return;
|
|
|
|
|
|
|
|
var uptime = Math.floor((Date.now() - online.getTime()) / 1000);
|
|
|
|
if ( uptime < 0 )
|
|
|
|
return;
|
|
|
|
|
|
|
|
var el = this.get('element').querySelector('#ffz-uptime-display span');
|
|
|
|
if ( ! el ) {
|
|
|
|
var cont = this.get('element').querySelector('.stats-and-actions .channel-stats');
|
|
|
|
if ( ! cont )
|
|
|
|
return;
|
|
|
|
|
|
|
|
var stat = document.createElement('span');
|
|
|
|
stat.className = 'ffz stat';
|
|
|
|
stat.id = 'ffz-uptime-display';
|
|
|
|
stat.title = "Stream Uptime <nobr>(since " + online.toLocaleString() + ")</nobr>";
|
|
|
|
|
|
|
|
stat.innerHTML = constants.CLOCK + " ";
|
|
|
|
el = document.createElement("span");
|
|
|
|
stat.appendChild(el);
|
|
|
|
|
|
|
|
var viewers = cont.querySelector(".live-count");
|
|
|
|
if ( viewers )
|
|
|
|
cont.insertBefore(stat, viewers.nextSibling);
|
|
|
|
else {
|
|
|
|
try {
|
|
|
|
viewers = cont.querySelector("script:nth-child(0n+2)");
|
|
|
|
cont.insertBefore(stat, viewers.nextSibling);
|
|
|
|
} catch(err) {
|
|
|
|
cont.insertBefore(stat, cont.childNodes[0]);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
jQuery(stat).tipsy({html: true});
|
|
|
|
}
|
|
|
|
|
|
|
|
el.innerHTML = utils.time_to_string(uptime);
|
|
|
|
},
|
|
|
|
|
|
|
|
ffzTeardown: function() {
|
2015-07-04 17:06:36 -04:00
|
|
|
var id = this.get('controller.id');
|
|
|
|
if ( id )
|
|
|
|
f.ws_send("unsub_channel", id);
|
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
this.get('element').setAttribute('data-channel', '');
|
|
|
|
f._cindex = undefined;
|
|
|
|
if ( this._ffz_update_uptime )
|
|
|
|
clearTimeout(this._ffz_update_uptime);
|
2015-07-04 17:06:36 -04:00
|
|
|
|
|
|
|
utils.update_css(f._channel_style, id, null);
|
2015-05-17 19:02:57 -04:00
|
|
|
}
|
2015-06-05 03:59:28 -04:00
|
|
|
});
|
|
|
|
}
|
2015-05-17 19:02:57 -04:00
|
|
|
|
|
|
|
|
2015-06-05 03:59:28 -04:00
|
|
|
// ---------------
|
|
|
|
// Settings
|
|
|
|
// ---------------
|
|
|
|
|
|
|
|
FFZ.settings_info.chatter_count = {
|
|
|
|
type: "boolean",
|
|
|
|
value: false,
|
|
|
|
|
|
|
|
category: "Channel Metadata",
|
|
|
|
|
|
|
|
name: "Chatter Count",
|
|
|
|
help: "Display the current number of users connected to chat beneath the channel.",
|
|
|
|
|
|
|
|
on_update: function(val) {
|
|
|
|
if ( this._cindex )
|
|
|
|
this._cindex.ffzUpdateChatters();
|
|
|
|
|
|
|
|
if ( ! val || ! this.rooms )
|
|
|
|
return;
|
|
|
|
|
|
|
|
// Refresh the data.
|
|
|
|
for(var room_id in this.rooms)
|
|
|
|
this.rooms.hasOwnProperty(room_id) && this.rooms[room_id].room && this.rooms[room_id].room.ffzInitChatterCount();
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
|
|
FFZ.settings_info.channel_views = {
|
|
|
|
type: "boolean",
|
|
|
|
value: true,
|
|
|
|
|
|
|
|
category: "Channel Metadata",
|
|
|
|
name: "Channel Views",
|
|
|
|
help: 'Display the number of times the channel has been viewed beneath the stream.',
|
|
|
|
on_update: function(val) {
|
|
|
|
document.body.classList.toggle("ffz-hide-view-count", !val);
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
|
|
FFZ.settings_info.stream_uptime = {
|
|
|
|
type: "boolean",
|
|
|
|
value: false,
|
|
|
|
|
|
|
|
category: "Channel Metadata",
|
|
|
|
name: "Stream Uptime",
|
|
|
|
help: 'Display the stream uptime under a channel by the viewer count.',
|
|
|
|
on_update: function(val) {
|
|
|
|
if ( this._cindex )
|
|
|
|
this._cindex.ffzUpdateUptime();
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
|
|
FFZ.settings_info.stream_title = {
|
|
|
|
type: "boolean",
|
|
|
|
value: true,
|
|
|
|
no_bttv: true,
|
|
|
|
|
|
|
|
category: "Channel Metadata",
|
|
|
|
name: "Title Links",
|
|
|
|
help: "Make links in stream titles clickable.",
|
|
|
|
on_update: function(val) {
|
|
|
|
if ( this._cindex )
|
|
|
|
this._cindex.ffzFixTitle();
|
|
|
|
}
|
|
|
|
};
|