Merge pull request #342 from zoff-music/feature/soundcloud-player

Feature/soundcloud player
This commit is contained in:
Kasper Rynning-Tønnesen
2018-05-04 21:55:57 +02:00
committed by GitHub
36 changed files with 1246 additions and 594 deletions

View File

@@ -1,7 +1,7 @@
Zoff
====
Zoff (pronounced __søff__) is a shared (free) YouTube based radio service, built upon the YouTube API, with integrated casting with Chromecast.
Zoff (pronounced __søff__) is a shared (free) YouTube and SoundCloud based radio service, built upon the YouTube API, and SoundCloud API, with integrated casting with Chromecast.
## Install

View File

@@ -5,11 +5,11 @@ var gulp = require('gulp'),
gulp.task('js', function () {
gulp.src(['server/VERSION.js', 'server/config/api_key.js', 'server/public/assets/js/*.js', '!server/public/assets/js/embed*', '!server/public/assets/js/token*', '!server/public/assets/js/remotecontroller.js', '!server/public/assets/js/callback.js'])
.pipe(uglify({
/*.pipe(uglify({
mangle: true,
compress: true,
enclose: true
}))
}))*/
.pipe(concat('main.min.js'))
.pipe(gulp.dest('server/public/assets/dist'));
});

View File

@@ -26,6 +26,8 @@ POST /api/list/:channel_name/:video_id
"start_time": START_TIME,
"adminpass": PASSWORD, (leave this blank if there is no password/you don't know the password)
"userpass": USER_PASSWORD
"source": Either "youtube" or "soundcloud"
("thumbnail": thumbnail url for soundcloud elements (only used when source == "soundcloud"))
}
Returns 400 for bad request

View File

@@ -1,4 +1,4 @@
VERSION = 5;
VERSION = 6;
try {
module.exports = VERSION;

View File

@@ -17,15 +17,24 @@ function frontpage_lists(msg, socket) {
});
}
function update_frontpage(coll, id, title, callback) {
function update_frontpage(coll, id, title, thumbnail, callback) {
coll = coll.replace(/ /g,'');
db.collection("frontpage_lists").update({_id: coll}, {$set: {
db.collection("frontpage_lists").find({_id: coll}, function(e, doc) {
var updateObject = {
id: id,
title: title,
accessed: Functions.get_time()}
accessed: Functions.get_time()
};
if(doc.length > 0 && (doc[0].thumbnail == "" || doc[0].thumbnail == undefined || doc[0].thumbnail.indexOf("ttps://i1.sndcdn.com") > -1)) {
updateObject.thumbnail = thumbnail;
if(thumbnail == undefined) updateObject.thumbnail = "";
}
db.collection("frontpage_lists").update({_id: coll}, {$set: updateObject
},{upsert: true}, function(err, returnDocs){
if(typeof(callback) == "function") callback();
});
});
}
module.exports.frontpage_lists = frontpage_lists;

View File

@@ -19,6 +19,24 @@ function remove_name_from_db(guid, name) {
});
}
function isUrl(str) {
var pattern = new RegExp("\\b(((ht|f)tp(s?)\\:\\/\\/|~\\/|\\/)|www.)" +
"(\\w+:\\w+@)?(([-\\w]+\\.)+(com|org|net|gov" +
"|mil|biz|info|mobi|name|aero|jobs|museum" +
"|travel|[a-z]{2}))(:[\\d]{1,5})?" +
"(((\\/([-\\w~!$+|.,=]|%[a-f\\d]{2})+)+|\\/)+|\\?|#)?" +
"((\\?([-\\w~!$+|.,*:]|%[a-f\\d{2}])+=?" +
"([-\\w~!$+|.,*:=]|%[a-f\\d]{2})*)" +
"(&(?:[-\\w~!$+|.,*:]|%[a-f\\d{2}])+=?" +
"([-\\w~!$+|.,*:=]|%[a-f\\d]{2})*)*)*" +
"(#([-\\w~!$+|.,*:=]|%[a-f\\d]{2})*)?\\b");
if(!pattern.test(str)) {
return false;
} else {
return true;
}
}
function getSession(socket) {
try {
/*var cookieParser = require("cookie-parser");
@@ -273,6 +291,7 @@ function removeSessionAdminPass(id, channel, callback) {
});
}
module.exports.isUrl = isUrl;
module.exports.removeEmojis = removeEmojis;
module.exports.getSessionChatPass = getSessionChatPass;
module.exports.setSessionChatPass = setSessionChatPass;

View File

@@ -471,6 +471,7 @@ module.exports = function() {
socket.on('change_channel', function(obj)
{
if(obj == undefined && coll != undefined) {
obj = {};
obj.channel = coll;
} else if(obj.hasOwnProperty("channel") && obj.channel.indexOf("?") > -1){
var _list = obj.channel.substring(0, obj.channel.indexOf("?"));

View File

@@ -84,7 +84,8 @@ function list(msg, guid, coll, offline, socket) {
db.collection(coll + "_settings").insert(configs, function(err, docs){
socket.join(coll);
List.send_list(coll, socket, true, false, true);
db.collection("frontpage_lists").insert({"_id": coll, "count" : 0, "frontpage": true, "accessed": Functions.get_time(), "viewers": 1});
db.collection("frontpage_lists").insert({"_id": coll, "count" : 0, "frontpage": true, "accessed": Functions.get_time(), "viewers": 1}, function(e,d){
});
Functions.check_inlist(coll, guid, socket, offline);
});
});
@@ -380,7 +381,7 @@ function change_song_post(coll, next_song, callback, socket) {
List.send_play(coll, socket, true);
callback();
}
Frontpage.update_frontpage(coll, docs[0].id, docs[0].title);
Frontpage.update_frontpage(coll, docs[0].id, docs[0].title, docs[0].thumbnail);
});
});
});
@@ -438,7 +439,7 @@ function send_list(coll, socket, send, list_send, configs, shuffled)
skips:[]
}
}, function(err, returnDocs){
Frontpage.update_frontpage(coll, now_playing_doc[0].id, now_playing_doc[0].title);
Frontpage.update_frontpage(coll, now_playing_doc[0].id, now_playing_doc[0].title, now_playing_doc[0].thumbnail);
List.send_list(coll, socket, send, list_send, configs, shuffled);
});
});
@@ -680,7 +681,13 @@ function getNextSong(coll, callback) {
$limit:1
}], function(err, doc) {
if(doc.length == 1) {
io.to(coll).emit("next_song", {videoId: doc[0].id, title: doc[0].title});
var thumbnail = "";
var source = "youtube";
if(doc[0].source && doc[0].source == "soundcloud") {
source = "soundcloud";
thumbnail = doc[0].thumbnail;
}
io.to(coll).emit("next_song", {videoId: doc[0].id, title: doc[0].title, source: source, thumbnail: thumbnail});
}
if(typeof(callback) == "function") callback();
});

View File

@@ -88,6 +88,11 @@ function addFromOtherList(arr, guid, offline, socket) {
db.collection(channel).find({now_playing: true}, function(e, np_docs) {
to_change.id = np_docs[0].id;
to_change.title = np_docs[0].title;
db.collection("frontpage_lists").find({_id: coll}, function(e, doc) {
if(doc.length > 0 && doc[0].thumbnail != "" && doc[0].thumbnail != undefined) {
to_change.thumbnail = np_docs[0].thumbnail;
}
db.collection("frontpage_lists").update({_id: channel}, {$set: to_change}, function(e, d) {
List.send_list(channel, undefined, false, true, false);
List.send_play(channel, undefined);
@@ -95,6 +100,7 @@ function addFromOtherList(arr, guid, offline, socket) {
_db.close();
});
});
});
} else {
db.collection("frontpage_lists").update({_id: channel}, {$inc: {count: res.nInserted != undefined ? res.nInserted : res.insertedCount}}, function(e, d) {
List.send_list(channel, undefined, false, true, false);
@@ -218,6 +224,11 @@ function addPlaylist(arr, guid, offline, socket) {
db.collection(channel).find({now_playing: true}, function(e, np_docs) {
to_change.id = np_docs[0].id;
to_change.title = np_docs[0].title;
db.collection("frontpage_lists").find({_id: coll}, function(e, doc) {
if(doc.length > 0 && doc[0].thumbnail != "" && doc[0].thumbnail != undefined) {
to_change.thumbnail = np_docs[0].thumbnail;
}
db.collection("frontpage_lists").update({_id: channel}, {$set: to_change}, function(e, d) {
List.send_list(channel, undefined, false, true, false);
List.send_play(channel, undefined);
@@ -225,6 +236,7 @@ function addPlaylist(arr, guid, offline, socket) {
_db.close();
});
});
});
} else {
db.collection("frontpage_lists").update({_id: channel}, {$inc: {count: results.nInserted != undefined ? results.nInserted : results.insertedCount}}, function(e, d) {
List.send_list(channel, undefined, false, true, false);
@@ -298,7 +310,9 @@ function add_function(arr, coll, guid, offline, socket) {
if(typeof(arr.id) != "string" || typeof(arr.start) != "number" ||
typeof(arr.end) != "number" || typeof(arr.title) != "string" ||
typeof(arr.list) != "string" || typeof(arr.duration) != "number") {
typeof(arr.list) != "string" || typeof(arr.duration) != "number" ||
typeof(arr.source) != "string" ||
(arr.source == "soundcloud" && (!arr.hasOwnProperty("thumbnail") || !Functions.isUrl(arr.thumbnail)))) {
var result = {
start: {
expected: "number or string that can be cast to int",
@@ -327,6 +341,14 @@ function add_function(arr, coll, guid, offline, socket) {
adminpass: {
expected: "string",
got: arr.hasOwnProperty("adminpass") ? typeof(arr.adminpass) : undefined
},
source: {
expected: "string (youtube or soundcloud)",
got: arr.hasOwnProperty("source") ? typeof(arr.source) : undefined
},
thumbnail: {
expected: "url if source == soundcloud",
got: arr.hasOwnProperty("thumbnail") ? typeof(arr.thumbnail) : undefined
}
};
socket.emit('update_required', result);
@@ -350,6 +372,7 @@ function add_function(arr, coll, guid, offline, socket) {
var title = arr.title;
var hash = Functions.hash_pass(Functions.hash_pass(Functions.decrypt_string(arr.adminpass), true));
var duration = parseInt(arr.duration);
var source = arr.source;
/*db.collection(coll + "_settings").find(function(err, docs)
{*/
conf = docs;
@@ -366,18 +389,20 @@ function add_function(arr, coll, guid, offline, socket) {
} else {
np = false;
}
var new_song = {"added": added,"guids":guids,"id":id,"now_playing":np,"title":title,"votes":votes, "duration":duration, "start": parseInt(start), "end": parseInt(end), "type": "video"};
var new_song = {"added": added,"guids":guids,"id":id,"now_playing":np,"title":title,"votes":votes, "duration":duration, "start": parseInt(start), "end": parseInt(end), "type": "video", "source": source};
if(source == "soundcloud") new_song.thumbnail = arr.thumbnail;
db.collection(coll).update({id: id}, new_song, {upsert: true}, function(err, docs){
new_song._id = "asd";
if(np) {
List.send_list(coll, undefined, false, true, false);
db.collection(coll + "_settings").update({ id: "config" }, {$set:{startTime: Functions.get_time()}});
List.send_play(coll, undefined);
Frontpage.update_frontpage(coll, id, title);
Search.get_correct_info(new_song, coll, false);
var thumbnail = arr.thumbnail != undefined ? arr.thumbnail : undefined;
Frontpage.update_frontpage(coll, id, title, thumbnail);
if(source != "soundcloud") Search.get_correct_info(new_song, coll, false);
} else {
io.to(coll).emit("channel", {type: "added", value: new_song});
Search.get_correct_info(new_song, coll, true);
if(source != "soundcloud") Search.get_correct_info(new_song, coll, true);
}
db.collection("frontpage_lists").update({_id:coll}, {$inc:{count:1}, $set:{accessed: Functions.get_time()}}, {upsert:true}, function(err, docs){});
List.getNextSong(coll);

View File

@@ -82,6 +82,7 @@ function check_error_video(msg, channel) {
};
return;
}
if(msg.source == "soundcloud") return;
channel = channel.replace(/ /g,'');
request({
type: "GET",

View File

@@ -1,23 +1,7 @@
function isUrl(str) {
var pattern = new RegExp("\\b(((ht|f)tp(s?)\\:\\/\\/|~\\/|\\/)|www.)" +
"(\\w+:\\w+@)?(([-\\w]+\\.)+(com|org|net|gov" +
"|mil|biz|info|mobi|name|aero|jobs|museum" +
"|travel|[a-z]{2}))(:[\\d]{1,5})?" +
"(((\\/([-\\w~!$+|.,=]|%[a-f\\d]{2})+)+|\\/)+|\\?|#)?" +
"((\\?([-\\w~!$+|.,*:]|%[a-f\\d{2}])+=?" +
"([-\\w~!$+|.,*:=]|%[a-f\\d]{2})*)" +
"(&(?:[-\\w~!$+|.,*:]|%[a-f\\d{2}])+=?" +
"([-\\w~!$+|.,*:=]|%[a-f\\d]{2})*)*)*" +
"(#([-\\w~!$+|.,*:=]|%[a-f\\d]{2})*)?\\b");
if(!pattern.test(str)) {
return false;
} else {
return true;
}
}
function thumbnail(msg, coll, guid, offline, socket) {
if(msg.thumbnail != undefined && msg.channel && msg.channel != undefined && isUrl(msg.thumbnail)){
if(msg.thumbnail != undefined && msg.channel && msg.channel != undefined && Functions.isUrl(msg.thumbnail)){
if(typeof(msg.channel) != "string" || typeof(msg.thumbnail) != "string")
{
var result = {

View File

@@ -13,6 +13,28 @@
transition: all .3s !important;
}
#player_overlay {
position: absolute;
height: calc(100% - 32px);
top: 0px;
left: 0px;
width: 50vw;
}
.soundcloud_info_container {
position: absolute;
bottom: 20px;
right: 0px;
padding-left: 20px;
display: flex;
align-items: center;
background: rgba(0,0,0,.7);
}
.soundcloud_info_container a {
margin: 0 10px;
}
.card {
cursor:pointer;
background-color: rgba(255, 255, 255, 0.04) !important;

View File

@@ -123,6 +123,34 @@ a {
margin: auto;
}
.soundcloud_info_container {
position: absolute;
bottom: 20px;
right: 0px;
padding-left: 20px;
display: flex;
align-items: center;
background: rgba(0,0,0,.7);
}
.soundcloud_info_container a {
margin: 0 10px;
}
#player_loader_container {
height: 100%;
width: 100%;
background: rgba(0,0,0,.5);
}
#player_loader {
position: absolute;
left: 0;
right: 0;
margin: auto;
}
#send-loader {
position: absolute;
top: 0px;
@@ -1480,7 +1508,7 @@ margin:-1px;
}
#inner-results {
height: calc(100vh - 64px - 76px);
height: calc(100vh - 64px - 76px - 64px);
overflow-y: scroll;
overflow-x: hidden;
}
@@ -1602,6 +1630,38 @@ ul #chat-log{
align-items: center;
}
.search_results {
background: black;
position: absolute;
width: 100vw;
top: 64px;
/* height: 100vh; */
}
.results-tabs li {
width: 50%;
text-align: center;
}
.results-tabs .indicator {
height: 2px;
z-index: 9;
position: absolute;
margin-left: -16px;
margin-top: 64px;
width: 50%;
}
#results_soundcloud {
padding: 0;
}
#results_soundcloud #inner-results {
height: calc(100vh - 64px - 64px);
}
#search_loader_inner{
display: flex;
}
@@ -2011,11 +2071,15 @@ nav ul li:hover, nav ul li.active {
position: absolute;
width: 100%;
top: 64px;
max-height: calc(100vh - 64px);
max-height: calc(100vh - 128px);
overflow: overlay;
overflow-x: hidden;
/* z-index: 99999999; */
}
#results_soundcloud {
max-height: calc(100vh - 64px - 64px);
}
.result:hover, .hoverResults {
background-color: rgba(0,0,0,0.4);
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 9.7 KiB

View File

@@ -15,6 +15,8 @@ var Channel = {
Helper.addClass("#results", "client-results-height");
Helper.addClass(".pagination-results", "client-pagination-height");
Helper.addClass(".control-list", "client-control-list");
} else {
//Player.soundcloud_player = document.querySelector("#soundcloud_player");
}
if(!Admin.logged_in) Admin.display_logged_out();
number_suggested = 0;
@@ -77,6 +79,7 @@ var Channel = {
}
Helper.tabs('.chatTabs');
Helper.tabs('.results-tabs');
}
var sidenavElem = document.getElementsByClassName("sidenav")[0];
M.Sidenav.init(sidenavElem, {
@@ -165,6 +168,7 @@ var Channel = {
Playercontrols.initSlider();
if(player_ready) {
Player.player.setVolume(Crypt.get_volume());
Player.soundcloud_player.setVolume(embed ? 1 : Crypt.get_volume() / 100);
}
Helper.removeClass(".video-container", "no-opacity");
var codeURL = "https://remote."+window.location.hostname+"/"+id;

View File

@@ -8,6 +8,11 @@ var startTime = 0;
var socket_connected = false;
var dynamicListeners = {};
var player_ready = false;
var empty_clear = false;
var fix_too_far = false;
var beginning = false;
var soundcloud_loading = false;
var firstLoad = "";
var list_html = document.getElementById("list-song-html").innerHTML;
var w_p = true;
var lazy_load = false;
@@ -85,6 +90,7 @@ window.addEventListener("DOMContentLoaded", function() {
});
color = "#" + hash[1];
add = "https://zoff.me";
if(window.location.hostname == "localhost") add = "localhost";
//add = "localhost";
socket = io.connect(''+add+':8080', connection_options);
@@ -299,6 +305,10 @@ addListener("click", ".prev_page", function(e) {
List.dynamicContentPage(-1);
});
addListener("click", "#player_overlay", function(event) {
if(videoSource == "soundcloud") Playercontrols.play_pause();
});
addListener("click", ".next_page", function(e) {
event.preventDefault();
List.dynamicContentPage(1);

View File

@@ -77,8 +77,9 @@ var Frontpage = {
var id = lists[x].id;
var viewers = lists[x].viewers;
var description = lists[x].description;
var img = "background-image:url('https://img.youtube.com/vi/"+id+"/hqdefault.jpg');";
if(lists[x].thumbnail) {
var img;
img = "background-image:url('https://img.youtube.com/vi/"+id+"/hqdefault.jpg');";
if(lists[x].thumbnail && lists[x].thumbnail != "") {
img = "background-image:url('" + lists[x].thumbnail + "');";
}
@@ -86,7 +87,7 @@ var Frontpage = {
var card = document.createElement("div");
card.innerHTML += pre_card;
//card.innerHTML = card.children[0];
if(song_count > 4) {
if(song_count > 3) {
if(lists[x].pinned == 1) {
card.querySelector(".pin").setAttribute("style", "display:block;");
//card.find(".card").attr("title", "Featured list");

View File

@@ -84,6 +84,7 @@ function hide_native(way) {
Helper.setHtml("#chromecast_text", "Playing on<br>" + castSession.La.friendlyName);
}
Player.player.setVolume(100);
Player.soundcloud_player.setVolume(1);
Helper.toggleClass("#player_overlay_text", "hide");
} else if(way == 0){
@@ -108,6 +109,7 @@ function hide_native(way) {
if(!Helper.mobilecheck()){
Player.player.setVolume(Crypt.get_volume());
Playercontrols.visualVolume(Crypt.get_volume());
Player.soundcloud_player.setVolume(embed ? 1 : Crypt.get_volume() / 100);
}
Helper.addClass("#player_overlay", "hide");
Helper.toggleClass("#player_overlay_text", "hide");
@@ -199,7 +201,6 @@ function get_list_ajax() {
}
},
error: function(response) {
console.log(response);
response = JSON.parse(response);
if(response.status == 403) {
start_auth();
@@ -235,6 +236,11 @@ function contextListener(that, event) {
} else if(top < 0) {
top = 15;
}
if(parent.getAttribute("data-video-source") == "soundcloud") {
Helper.addClass(".find-context-menu", "context-menu-disabled");
} else {
Helper.removeClass(".find-context-menu", "context-menu-disabled");
}
Helper.css(".context-menu-root", "left", left + "px");
Helper.css(".context-menu-root", "top", top + "px");
Helper.removeClass(".context-menu-root","hide");
@@ -318,7 +324,7 @@ function del_ajax(id) {
})
}
function add_ajax(id, title, duration, playlist, num, full_num, start, end) {
function add_ajax(id, title, duration, playlist, num, full_num, start, end, source, thumbnail) {
/*var a = Crypt.get_pass(chan.toLowerCase());
var u = Crypt.get_userpass(chan.toLowerCase());
if(a == undefined) a = "";
@@ -332,6 +338,8 @@ function add_ajax(id, title, duration, playlist, num, full_num, start, end) {
duration: duration,
end_time: end,
start_time: start,
thumbnail: thumbnail,
source: source,
token: zoff_api_token
},
headers: {"Content-Type": "application/json;charset=UTF-8"},
@@ -901,9 +909,11 @@ function searchTimeout(event) {
}
if(code == 13){
Search.search(search_input);
Search.soundcloudSearch(search_input);
}else{
timeout_search = setTimeout(function(){
Search.search(search_input);
Search.soundcloudSearch(search_input);
}, 1000);
}
}

View File

@@ -38,6 +38,7 @@ var Hostcontroller = {
if(arr.type == "volume") {
Playercontrols.visualVolume(arr.value);
Player.setVolume(arr.value);
Player.soundcloud_player.setVolume(arr.value / 100);
localStorage.setItem("volume", arr.value);
Playercontrols.choose_button(arr.value, false);
} else if(arr.type == "channel") {

View File

@@ -245,7 +245,7 @@ var List = {
check_error_videos: function(i) {
//Helper.log("Empty-checker at " + i);
if(full_playlist.length == 0) return;
if(full_playlist.length == 0 || full_playlist[i].source == "soundcloud") return;
Helper.ajax({
method: "get",
url: 'https://www.googleapis.com/youtube/v3/videos?id=' + full_playlist[i].id
@@ -255,7 +255,7 @@ var List = {
//Helper.log("Empty-checker items " + data.items.length);
if (data.items.length == 0) {
Helper.log(["Emtpy-checker error at " + full_playlist[i].id + " " + full_playlist[i].title]);
socket.emit("error_video", {channel: chan.toLowerCase(), id: full_playlist[i].id, title: full_playlist[i].title});
socket.emit("error_video", {channel: chan.toLowerCase(), id: full_playlist[i].id, title: full_playlist[i].title, source: full_playlist[i].source});
}
if(full_playlist.length > i + 1 && window.location.pathname != "/") {
List.check_error_videos(i + 1);
@@ -356,7 +356,7 @@ var List = {
full_playlist.push(now_playing);
}
if(document.querySelectorAll("#suggested-"+added.id).length > 0) {
if(added.source != "soundcloud" && document.querySelectorAll("#suggested-"+added.id).length > 0) {
number_suggested = number_suggested - 1;
if(number_suggested < 0) number_suggested = 0;
@@ -366,9 +366,9 @@ var List = {
}
document.querySelector(".suggested-link span.badge.new.white").innerText = to_display;
Helper.removeElement("#suggested-"+added.id);
}
Helper.removeElement("#suggested-"+added.id);
if(List.empty){
List.empty = false;
}
@@ -798,7 +798,7 @@ var List = {
exportToYoutube: function() {
ga('send', 'event', "export", "youtube");
var request_url = "https://www.googleapis.com/youtube/v3/playlists?part=snippet";
var request_url = "https://www.googleapis.com/youtube/v3/playlists?part=snippet&key=" + api_key;
Helper.removeClass(".exported-list-container", "hide");
Helper.removeClass("#playlist_loader_export", "hide");
Helper.ajax({
@@ -818,10 +818,11 @@ var List = {
response = JSON.parse(response);
var number_added = 0;
var playlist_id = response.id;
var request_url = "https://www.googleapis.com/youtube/v3/playlistItems?part=snippet";
var request_url = "https://www.googleapis.com/youtube/v3/playlistItems?part=snippet&key=" + api_key;
List.addToYoutubePlaylist(playlist_id, full_playlist, number_added, request_url)
},
error: function(response){
console.log(response);
response = response.responseText;
Helper.log([
"export to youtube response",
@@ -831,13 +832,13 @@ var List = {
});
},
addToYoutubePlaylist: function(playlist_id, full_playlist, num, request_url) {
insertInYouTubePlaylist: function(playlist_id, _videoId, num, request_url) {
var _data = JSON.stringify({
'snippet': {
'playlistId': playlist_id,
'resourceId': {
'kind': 'youtube#video',
'videoId': full_playlist[num].id
'videoId': _videoId
}
}
});
@@ -863,14 +864,162 @@ var List = {
//setTimeout(function(){
Helper.removeClass(".current_number", "hide");
document.querySelector(".current_number").innerText = (num + 1) + " of " + (full_playlist.length);
List.addToYoutubePlaylist(playlist_id, full_playlist, num + 1, request_url)
List.addToYoutubePlaylist(playlist_id, full_playlist, num + 1, request_url);
//}, 50);
}
}, error: function(response) {
console.log(response);
}
});
},
addToYoutubePlaylist: function(playlist_id, full_playlist, num, request_url) {
console.log(full_playlist[num], num);
if(num == full_playlist.length - 1){
Helper.log(["All videoes added!"]);
Helper.log(["url: https://www.youtube.com/playlist?list=" + playlist_id]);
document.querySelector(".exported-list").insertAdjacentHTML("beforeend", "<a target='_blank' class='btn light exported-playlist' href='https://www.youtube.com/playlist?list=" + playlist_id + "'>" + chan + "</a>");
Helper.addClass("#playlist_loader_export", "hide");
Helper.addClass(".current_number", "hide");
return;
//$(".youtube_export_button").removeClass("hide");
}
if(full_playlist[num].hasOwnProperty("source") && full_playlist[num].source != "soundcloud") {
List.insertInYouTubePlaylist(playlist_id, full_playlist[num].id, num, request_url)
} else {
var yt_url = "https://www.googleapis.com/youtube/v3/search?key="+api_key+"&videoEmbeddable=true&part=id,snippet&fields=items(id,snippet)&type=video&order=relevance&safeSearch=none&maxResults=10&videoCategoryId=10";
yt_url+="&q="+full_playlist[num].title;
var title = full_playlist[num].title;
var temptitle = title.split("-");
temptitle = temptitle.join(" ").split(" ");
var vid_url = "https://www.googleapis.com/youtube/v3/videos?part=contentDetails,snippet,id&key="+api_key+"&id=";
Helper.ajax({
type: "GET",
url: yt_url,
dataType:"jsonp",
success: function(response){
response = JSON.parse(response);
//Helper.log(response);
if(response.items.length === 0){
Helper.log([
"NO MATCH FOR:",
"Spotify title: " + title,
"Spotify length: " + length
]);
var not_added_song = document.createElement("div");
not_added_song.innerHTML = not_export_html;
not_added_song.querySelector(".extra-add-text").innerText = title;
not_added_song.querySelector(".extra-add-text").setAttribute("title", title);
not_added_song.querySelector(".extra-button-search").setAttribute("data-text", title);
document.querySelector(".not-exported-container").insertAdjacentHTML("beforeend", not_added_song.innerHTML);
Helper.removeClass(".not-exported", "hide");
if(num == full_playlist.length - 1){
Helper.log(["All videoes added!"]);
Helper.log(["url: https://www.youtube.com/playlist?list=" + playlist_id]);
document.querySelector(".exported-list").insertAdjacentHTML("beforeend", "<a target='_blank' class='btn light exported-playlist' href='https://www.youtube.com/playlist?list=" + playlist_id + "'>" + chan + "</a>");
Helper.addClass("#playlist_loader_export", "hide");
Helper.addClass(".current_number", "hide");
//$(".youtube_export_button").removeClass("hide");
} else {
//setTimeout(function(){
Helper.removeClass(".current_number", "hide");
document.querySelector(".current_number").innerText = (num + 1) + " of " + (full_playlist.length);
List.addToYoutubePlaylist(playlist_id, full_playlist, num + 1, request_url);
//}, 50);
}
} else if(response.items.length > 0) {
for(var i = 0; i < response.items.length; i++) {
var data = response.items[i];
vid_url += data.id.videoId+",";
}
Helper.ajax({
type: "GET",
url: vid_url,
dataType:"jsonp",
success: function(response){
response = JSON.parse(response);
if(response.items.length > 0) {
var matched = false;
for(var y = 0; y < response.items.length; y++) {
var data = response.items[y];
//Helper.log(data);
//var title = data.snippet.title;
var duration = Search.durationToSeconds(data.contentDetails.duration);
var not_matched = false;
if(similarity(data.snippet.title,title) > 0.75) {
not_matched = false;
} else {
for(var i = 0; i < temptitle.length; i++) {
var data_title = temptitle[i];
if(data.snippet.title.toLowerCase().indexOf(data_title.toLowerCase()) == -1 || !(
data.snippet.title.toLowerCase().indexOf("cover") == -1 &&
title.toLowerCase().indexOf("cover") == -1 &&
((data.snippet.title.toLowerCase().indexOf("remix") == -1 &&
title.toLowerCase().indexOf("remix") == -1) ||
(data.snippet.title.toLowerCase().indexOf("remix") != -1 &&
title.toLowerCase().indexOf("remix") != -1) || !(data.snippet.title.toLowerCase().indexOf(artist[0].toLowerCase()) == -1 &&
data.snippet.channelTitle.toLowerCase().indexOf("vevo") == -1)))
)
not_matched = true;
else if(duration > 1800) not_matched = true;
}
}
if((!not_matched)){
matched = true;
List.insertInYouTubePlaylist(playlist_id, data.id, num, request_url);
break;
}
}
if(!matched){
if(num == full_playlist.length - 1){
Helper.log(["All videoes added!"]);
Helper.log(["url: https://www.youtube.com/playlist?list=" + playlist_id]);
document.querySelector(".exported-list").insertAdjacentHTML("beforeend", "<a target='_blank' class='btn light exported-playlist' href='https://www.youtube.com/playlist?list=" + playlist_id + "'>" + chan + "</a>");
Helper.addClass("#playlist_loader_export", "hide");
Helper.addClass(".current_number", "hide");
//$(".youtube_export_button").removeClass("hide");
} else {
//setTimeout(function(){
Helper.removeClass(".current_number", "hide");
document.querySelector(".current_number").innerText = (num + 1) + " of " + (full_playlist.length);
//}, 50);
}
Helper.log([
"NO MATCH FOR:",
"Spotify title: " + title,
"Spotify length: " + length
]);
var not_added_song = document.createElement("div");
not_added_song.innerHTML = not_export_html;
not_added_song.querySelector(".extra-add-text").innerText = title;
not_added_song.querySelector(".extra-add-text").setAttribute("title", title);
not_added_song.querySelector(".extra-button-search").setAttribute("data-text", title);
document.querySelector(".not-exported-container").insertAdjacentHTML("beforeend", not_added_song.innerHTML);
Helper.removeClass(".not-exported", "hide");
List.addToYoutubePlaylist(playlist_id, full_playlist, num + 1, request_url);
}
}
},
error: function(e) {
console.log(e);
}
});
}
}, error: function(e) {
console.log(e);
}
});
}
},
sortList: function() {
full_playlist.sort(Helper.predicate({
name: 'votes',
@@ -899,6 +1048,9 @@ var List = {
var video_title = _song_info.title;
var video_votes = _song_info.votes;
var video_thumb_url = "//img.youtube.com/vi/"+video_id+"/mqdefault.jpg";
if(_song_info.source == "soundcloud") {
video_thumb_url = _song_info.thumbnail;
}
var video_thumb = "background-image:url('" + video_thumb_url + "');";
var song = document.createElement("div");
song.innerHTML = list_html;
@@ -924,9 +1076,11 @@ var List = {
song.querySelector(".list-image").setAttribute(image_attr,video_thumb);
if(list){
song.querySelector("#list-song")
song.querySelector(".list-votes").innerText = video_votes;
song.querySelector("#list-song").setAttribute("data-video-id", video_id);
song.querySelector("#list-song").setAttribute("data-video-type", "song");
song.querySelector("#list-song").setAttribute("data-video-source", _song_info.source);
song.querySelector("#list-song").setAttribute("id", video_id);
song.classList.remove("hide");
song.querySelector(".vote-container").setAttribute("title", video_title);

View File

@@ -5,9 +5,14 @@ var client = false;
if(domain.length > 0 && domain[0] == "client") {
client = true;
}
var SC;
var _SC2;
var firstLoad = "";
var videoSource;
var dynamicListeners = {};
var socket_connected = false;
var hasadmin = 0;
var soundcloud_loading = false;
var list_html = document.querySelectorAll("#list-song-html").length > 0 ? document.querySelector("#list-song-html").innerHTML : undefined;
var unseen = false;
var searching = false;
@@ -183,6 +188,31 @@ window.addEventListener("DOMContentLoaded", function() {
else if(!fromChannel && window.location.pathname == "/"){
Frontpage.init();
}
if(window.location.pathname == "/" && !client) {
tag = document.createElement('script');
tag.src = "https://www.youtube.com/iframe_api";
firstScriptTag = document.getElementsByTagName('script')[0];
firstScriptTag.parentNode.insertBefore(tag, firstScriptTag);
tag.onload = function() {
if(document.querySelectorAll("script[src='https://w.soundcloud.com/player/api.js']").length == 1) {
} else {
tagSearch = document.createElement('script');
tagSearch.setAttribute("async", true);
tagSearch.src = "https://connect.soundcloud.com/sdk/sdk-3.3.0.js";
firstScriptTag = document.getElementsByTagName('script')[0];
firstScriptTag.parentNode.insertBefore(tagSearch, firstScriptTag);
tagSearch.onload = function() {
SC.initialize({
client_id: 'ed53fc01f248f15becddf8eb52cc91ef'
}, function() {
});
}
}
}
}
if(Helper.mobilecheck()) {
socket.on("guid", function(msg) {
@@ -262,8 +292,8 @@ initializeCastApi = function() {
} catch(event){
_seekTo = seekTo;
}
castSession.sendMessage("urn:x-cast:zoff.me", {type: "loadVideo", start: Player.np.start, end: Player.np.end, videoId: video_id, seekTo: _seekTo, channel: chan.toLowerCase()})
castSession.sendMessage("urn:x-cast:zoff.me", {type: "nextVideo", videoId: full_playlist[0].id, title: full_playlist[0].title})
castSession.sendMessage("urn:x-cast:zoff.me", {type: "loadVideo", start: Player.np.start, end: Player.np.end, videoId: video_id, seekTo: _seekTo, channel: chan.toLowerCase(), source: videoSource})
castSession.sendMessage("urn:x-cast:zoff.me", {type: "nextVideo", videoId: full_playlist[0].id, title: full_playlist[0].title, source: full_playlist[0].source})
if(Helper.mobilecheck() && !chromecast_specs_sent) {
socket.emit("get_id");
@@ -291,8 +321,8 @@ initializeCastApi = function() {
} catch(event){
_seekTo = seekTo;
}
castSession.sendMessage("urn:x-cast:zoff.me", {type: "loadVideo", start: Player.np.start, end: Player.np.end, videoId: video_id, seekTo: _seekTo, channel: chan.toLowerCase()})
castSession.sendMessage("urn:x-cast:zoff.me", {type: "nextVideo", videoId: full_playlist[0].id, title: full_playlist[0].title})
castSession.sendMessage("urn:x-cast:zoff.me", {type: "loadVideo", start: Player.np.start, end: Player.np.end, videoId: video_id, seekTo: _seekTo, channel: chan.toLowerCase(), source: videoSource})
castSession.sendMessage("urn:x-cast:zoff.me", {type: "nextVideo", videoId: full_playlist[0].id, title: full_playlist[0].title, source: full_playlist[0].source})
hide_native(1);
Helper.css("#channel-load", "display", "none");
Helper.addClass('.castButton', 'castButton-white-active');
@@ -488,6 +518,9 @@ addListener("click", ".copy-context-menu", function(e) {
addListener("click", ".find-context-menu", function(e) {
this.preventDefault();
var that = e;
if(that.classList.contains("context-menu-disabled")) {
return;
}
var parent = that.parentElement;
var id = parent.getAttribute("data-id");
Search.search(id, false, true);
@@ -541,6 +574,7 @@ addListener("click", "#closePlayer", function(event){
socket.removeEventListener("np");
socket.removeEventListener("id");
socket.removeEventListener(id);
Helper.removeElement("#soundcloud_container");
Helper.removeElement("#alreadychannel");
Player.player = "";
document.title = "Zoff - the shared YouTube based radio";
@@ -580,6 +614,11 @@ document.addEventListener("keydown", function(event) {
document.querySelector("#import") != document.activeElement &&
document.querySelector("#find_input") != document.activeElement &&
document.querySelector("#import_spotify") != document.activeElement) {
if(videoSource == "soundcloud") {
event.preventDefault();
Playercontrols.play_pause();
return false;
}
if(Player.player.getPlayerState() == 1) {
event.preventDefault();
Player.player.pauseVideo();
@@ -636,6 +675,7 @@ document.addEventListener("keyup", function(event) {
}
});*/
document.querySelector("#results").innerHTML = "";
document.querySelector("#results_soundcloud").innerHTML = "";
document.getElementsByTagName("body")[0].setAttribute("style", "overflow-y:auto")
document.querySelector("#search-btn i").innerText = "search";
document.querySelector(".search_input").value = "";
@@ -741,6 +781,10 @@ addListener("click", ".modal-close", function(event){
this.preventDefault();
});
addListener("click", "#player_overlay", function(event) {
if(videoSource == "soundcloud") Playercontrols.play_pause();
});
/*
addListener("change", ".password_protected", function(event) {
this.preventDefault();
@@ -1213,6 +1257,7 @@ addListener("click", "#closeSettings", function(event)
Admin.hide_settings();
});
window.addEventListener("focus", function(event) {
document.getElementById("favicon").setAttribute("href", "/assets/images/favicon.png");
unseen = false;
@@ -1254,6 +1299,12 @@ addListener("click", ".result-object", function(e){
var original_length = e.getAttribute("data-video-length");
var start = parseInt(e.querySelector(".result-start").value);
var end = parseInt(e.querySelector(".result-end").value);
var source = "youtube";
var thumbnail;
if(e.getAttribute("data-type-source") != undefined) {
source = "soundcloud";
thumbnail = e.getAttribute("data-type-thumbnail");
}
if(end > original_length) {
end = original_length;
}
@@ -1264,7 +1315,7 @@ addListener("click", ".result-object", function(e){
} else {
try {
var length = parseInt(end) - parseInt(start);
Search.submitAndClose(id, title, length, start, end);
Search.submitAndClose(id, title, length, start, end, source, thumbnail);
} catch(err) {
M.toast({html: "Only numbers are accepted as song start and end parameters..", displayLength: 3000, classes: "red lighten"});
}
@@ -1349,6 +1400,13 @@ addListener("click", "#add-many", function(e){
if(end > original_length) {
end = original_length;
}
var source = "youtube";
var thumbnail;
if(e.getAttribute("data-type-source") != undefined) {
source = "soundcloud";
thumbnail = e.getAttribute("data-type-thumbnail");
}
if(start > end) {
M.toast({html: "Start can't be before the end..", displayLength: 3000, classes: "red lighten"});
} else if(start < 0) {
@@ -1356,8 +1414,9 @@ addListener("click", "#add-many", function(e){
} else {
try {
var length = parseInt(end) - parseInt(start);
e.parentElement.parentElement.parentElement.remove();
Search.submit(id, title, length, false, 0, 1, start, end);
Search.submit(id, title, length, false, 0, 1, start, end, source, thumbnail);
} catch(event) {
M.toast({html: "Only numbers are accepted as song start and end parameters..", displayLength: 3000, classes: "red lighten"});
}
@@ -1380,7 +1439,7 @@ addListener("click", ".add-suggested", function(e){
var title = e.getAttribute("data-video-title");
var length = e.getAttribute("data-video-length");
var added_by = e.getAttribute("data-added-by");
Search.submit(id, title, parseInt(length), false, 0, 1, 0, parseInt(length));
Search.submit(id, title, parseInt(length), false, 0, 1, 0, parseInt(length), "youtube");
if(added_by == "user") {
number_suggested = number_suggested - 1;
if(number_suggested < 0) number_suggested = 0;

View File

@@ -7,23 +7,12 @@ var Player = {
stopInterval: false,
fireplace: "",
np: {},
soundcloud_player: {
setVolume: function(val) {}
},
youtube_listener: function(obj) {
Helper.log(["object", obj]);
var state;
fix_too_far = false;
if(embed && !autoplay && obj && obj.np.length > 0) {
if(Object.keys(obj).length == 0) {
paused = false;
empty_clear = true;
} else {
empty_clear = false;
}
Player.getTitle(obj.np[0].title, viewers);
//Player.setBGimage(video_id);
if(!Helper.mobilecheck()) {
Player.notifyUser(obj.np[0].id, obj.np[0].title);
}
if(obj.np != undefined) {
video_id = obj.np[0].id;
Player.np = {
id: video_id,
@@ -31,56 +20,25 @@ var Player = {
end: obj.np[0].end,
duration: obj.np[0].duration,
};
if(!obj.np[0].hasOwnProperty("start")) {
Player.np.start = 0;
}
if(!obj.np[0].hasOwnProperty("end")) {
Player.np.end = Player.np.duration;
}
conf = obj.conf[0];
time = obj.time;
seekTo = (time - conf.startTime) + Player.np.start;
startTime = time - conf.startTime;
song_title = obj.np[0].title;
duration = obj.np[0].duration;
if(player_ready) {
Player.cueVideoById(video_id, duration);
Player.stopVideo();
}
return;
}
if(embed && obj.np) {
if(window.parentWindow && window.parentOrigin) {
window.parentWindow.postMessage({type: "np", title: obj.np[0].title}, window.parentOrigin);
if(full_playlist.length > 0) {
Player.sendNext({title: full_playlist[0].title, videoId: full_playlist[0].id});
}
}
}
try {
state = Player.player.getPlayerState();
} catch(e) {
state = null;
}
if(!paused) {
gotten_np = true;
}
if((((!offline && (state != null || from_frontpage)) || (offline && (!(state != null) || from_frontpage))|| (!offline && (!(state != null) || from_frontpage)) || (offline && state == -1)) && !(offline && prev_chan_player == chan)) || (offline && video_id == undefined)){
prev_chan_player = chan;
from_frontpage = false;
Player.loaded = false;
Helper.log([
"youtube_listener",
"Received: ",
obj,
"paused variable: " + paused,
"mobile_beginning variable: " + mobile_beginning]);
try{
Helper.log(["getVideoUrl(): " + Player.player.getVideoUrl().split('v=')[1]]);
} catch(e){}
Helper.log(["video_id variable: " + video_id]);
if(!obj.np){
videoSource = obj.np[0].hasOwnProperty("source") ? obj.np[0].source : "youtube";
} else {
Player.np = {
id: "",
start: 0,
end: 0,
duration: 0,
};
document.getElementById('song-title').innerText = "Empty channel. Add some songs!";
document.title = "Zoff - the shared YouTube based radio";
Helper.css("#channel-load", "display", "none");
@@ -95,164 +53,38 @@ var Player = {
}catch(e){
}
//List.importOldList(channel.toLowerCase());
} else if(paused || was_stopped){
Player.getTitle(obj.np[0].title, viewers);
//Player.setBGimage(video_id);
if(!Helper.mobilecheck()) {
Player.notifyUser(obj.np[0].id, obj.np[0].title);
}
if(!chromecastAvailable) {
Player.stopVideo();
}
video_id = obj.np[0].id;
Player.np = {
id: video_id,
start: obj.np[0].start,
end: obj.np[0].end,
duration: obj.np[0].duration,
};
if(!obj.np[0].hasOwnProperty("start")) {
Player.np.start = 0;
}
if(!obj.np[0].hasOwnProperty("end")) {
Player.np.end = Player.np.duration;
}
if(obj.conf != undefined) {
conf = obj.conf[0];
}
time = obj.time;
seekTo = (time - conf.startTime) + Player.np.start;
startTime = time - conf.startTime;
song_title = obj.np[0].title;
duration = obj.np[0].duration;
Player.setThumbnail(conf, video_id);
Player.cueVideoById(video_id, duration);
//Player.setBGimage(video_id);
} else if(!paused){
//Helper.log("gotten new song");
if(previous_video_id === undefined) {
previous_video_id = obj.np[0].id;
} else if(previous_video_id != video_id) {
previous_video_id = video_id;
}
video_id = obj.np[0].id;
Player.np = {
id: video_id,
start: obj.np[0].start,
end: obj.np[0].end,
duration: obj.np[0].duration,
};
if(!obj.np[0].hasOwnProperty("start")) {
Player.np.start = 0;
}
if(!obj.np[0].hasOwnProperty("end")) {
Player.np.end = Player.np.duration;
}
conf = obj.conf[0];
time = obj.time;
seekTo = (time - conf.startTime) + Player.np.start;
startTime = time - conf.startTime;
song_title = obj.np[0].title;
duration = obj.np[0].duration;
Player.setThumbnail(conf, video_id);
if(mobile_beginning && Helper.mobilecheck() && seekTo === 0 && !chromecastAvailable) {
seekTo = 1 + Player.np.start;
}
try{
if(full_playlist[0].id == video_id && !mobile_beginning){
List.song_change(full_playlist[0].added);
}
if(!client) Suggestions.fetchYoutubeSuggests(video_id);
}catch(e){}
// Play video/autoplay video
if(obj.np != undefined) {
Player.getTitle(song_title, viewers);
if(player_ready && !window.MSStream) {
try {
var compared;
var prev_state = state;
try {
compared = Player.player.getVideoUrl().split('v=')[1] != video_id;
} catch(e) {
compared = true;
}
if(prev_state == 2 && !chromecastAvailable) {
Player.stopVideo();
was_stopped = true;
Player.cueVideoById(video_id, duration);
if(!durationBegun) {
Player.durationSetter();
}
if(((embed && autoplay) || !embed ) && !offline && !was_stopped) {
Helper.log(["loadVideoById \nwas_stopped="+was_stopped+"\noffline="+offline])
Player.loadVideoById(Player.np.id, duration, Player.np.start, Player.np.end);
} else {
if(compared || chromecastAvailable){
if(paused && !chromecastAvailable){
Player.cueVideoById(video_id, duration);
} else {
Player.loadVideoById(video_id, duration);
Player.seekTo(seekTo);
Helper.log(["cueVideoById \nwas_stopped="+was_stopped+"\noffline="+offline])
Player.cueVideoById(Player.np.id, duration, Player.np.start, Player.np.end);
}
if(!Helper.mobilecheck()) {
Player.notifyUser(video_id, song_title);
}
}
if(!paused){
if(((!mobile_beginning || chromecastAvailable) && prev_state != 2) && autoplay) {
Player.playVideo();
}
if(!durationBegun) {
Player.durationSetter();
}
}
if(Player.player.getDuration() > seekTo || Player.player.getDuration() === 0 || chromecastAvailable || Player.player.getCurrentTime() != seekTo) {
Player.seekTo(seekTo);
}
Player.after_load = video_id;
if(!Player.loaded) {
setTimeout(function(){Player.loaded = true;},500);
}
}
}catch(e) {
if(chromecastAvailable && !paused) {
Player.loadVideoById(video_id, duration);
Player.seekTo(seekTo);
}
if(!durationBegun && !chromecastAvailable) {
Player.durationSetter();
}
}
} else {
if(!autoplay) {
Player.stopVideo();
} else if(player_ready){
Player.seekTo(seekTo);
}
Player.getTitle(song_title, viewers);
}
}
} else {
if(!durationBegun) {
Player.durationSetter();
}
duration = Player.player.getDuration();
}
if(Object.keys(obj).length == 0) {
paused = false;
empty_clear = true;
} else {
empty_clear = false;
}
},
setThumbnail: function(conf, video_id) {
if(embed) return;
if(!conf.hasOwnProperty("thumbnail") || conf.thumbnail == "") {
if(videoSource == "soundcloud") {
document.getElementById("thumbnail_image").innerHTML = "<img id='thumbnail_image_channel' src='" + full_playlist[full_playlist.length - 1].thumbnail + "' alt='thumbnail' />";
} else {
document.getElementById("thumbnail_image").innerHTML = "<img id='thumbnail_image_channel' src='https://img.youtube.com/vi/"+video_id+"/mqdefault.jpg' alt='thumbnail' />";
}
}
},
onPlayerStateChange: function(newState) {
@@ -271,13 +103,14 @@ var Player = {
Helper.log(["getVideoUrl(): " + Player.player.getVideoUrl().split('v=')[1]]);
} catch(e){}
Helper.log(["video_id variable: " + video_id]);
switch(newState.data) {
case YT.PlayerState.UNSTARTED:
break;
case YT.PlayerState.ENDED:
playing = false;
paused = false;
was_stopped = false;
if(!offline) {
/*var u = Crypt.crypt_pass(Crypt.get_userpass(chan.toLowerCase()), true);
if(u == undefined) u = "";*/
@@ -287,6 +120,11 @@ var Player = {
}
break;
case YT.PlayerState.PLAYING:
if(videoSource == "soundcloud") {
Player.player.stopVideo();
//was_stopped = false;
return;
}
if(embed) {
Helper.css("#player", "visibility", "visible");
}
@@ -329,6 +167,7 @@ var Player = {
end_programmatically = false;
} else {
if(!chromecastAvailable){
was_stopped = true;
if(beginning && mobile_beginning) {
Helper.css("#playpause", "visibility", "visible");
Helper.css("#playpause", "pointer-events", "all");
@@ -365,9 +204,14 @@ var Player = {
Helper.toggleClass("#pause", "hide");
}
//Playercontrols.play_pause();
} else {
if(videoSource == "soundcloud") {
Player.soundcloud_player.play();
//SC.Widget(document.querySelector("#soundcloud_player")).play();
} else {
Player.player.playVideo();
}
}
},
pauseVideo: function(){
@@ -380,8 +224,13 @@ var Player = {
//Playercontrols.play_pause();
} else {
paused = true;
if(videoSource == "soundcloud") {
Player.soundcloud_player.pause();
//SC.Widget(document.querySelector("#soundcloud_player")).pause();
} else {
Player.player.pauseVideo();
}
}
},
seekTo: function(_seekTo){
@@ -394,7 +243,66 @@ var Player = {
}
},
loadSoundCloud: function(id, this_duration, start, end, _autoplay) {
try {
if(SC == null) return;
} catch(e) {
return;
}
Player.stopVideo();
if(_autoplay) was_stopped = false;
Helper.removeClass(document.getElementById("player_overlay"), "hide");
Helper.css(document.getElementById("player_overlay"), "background-color", "#2d2d2d");
if(start == undefined) start = 0;
if(seekTo == undefined) seekTo = 0;
soundcloud_loading = false;
var _autoAdd = "false";
if(_autoplay) {
_autoAdd = "true";
Helper.removeClass("#player_loader_container", "hide");
}
try {
if(SC == null || !SC.stream) return;
} catch(e) {
return;
}
SC.stream("/tracks/" + id).then(function(player){
Player.soundcloud_player = player;
Player.soundcloud_player.bind("finish", Player.soundcloudFinish);
Player.soundcloud_player.bind("pause", Player.soundcloudPause);
Player.soundcloud_player.bind("play", Player.soundcloudPlay);
window.player = player;
SC.get('/tracks', {
ids: id
}).then(function(tracks) {
var sound = tracks[0];
Helper.removeClass(".soundcloud_info_container", "hide");
document.querySelector("#soundcloud_listen_link").href = sound.permalink_url;
document.querySelector(".soundcloud_info_container .green").href = sound.user.permalink_url;
//document.querySelector(".soundcloud_info_container .red").href = sound.user.permalink_url;
});
if(_autoplay) {
player.play().then(function(){
Player.soundcloud_player.setVolume(embed ? 1 : Crypt.get_volume() / 100);
Player.soundcloud_player.seek((seekTo) * 1000);
}).catch(function(e){
});
}
});
soundcloud_loading = true;
if(start == undefined) start = 0;
if(seekTo == undefined) seekTo = 0;
if(_autoplay) was_stopped = false;
Helper.css(document.getElementById("player_overlay"), "background", "url('" + full_playlist[full_playlist.length - 1].thumbnail + "')");
Helper.css(document.getElementById("player_overlay"), "background-size", "auto");
Helper.css(document.getElementById("player_overlay"), "background-position", "20%");
Helper.css(document.getElementById("player_overlay"), "background-color", "#2d2d2d");
Helper.addClass("#player_overlay_text", "hide");
},
loadVideoById: function(id, this_duration, start, end){
if(id == undefined) return;
var s;
var e;
if(start) s = start;
@@ -402,13 +310,41 @@ var Player = {
if(end) e = end;
else e = Player.np.end;
if(chromecastAvailable){
castSession.sendMessage("urn:x-cast:zoff.me", {start: s, end: e, type: "loadVideo", videoId: id, channel: chan.toLowerCase()});
castSession.sendMessage("urn:x-cast:zoff.me", {start: s, end: e, type: "loadVideo", videoId: id, channel: chan.toLowerCase(), source: videoSource});
chrome.cast.media.GenericMediaMetadata({metadataType: 0, title:song_title, image: 'https://img.youtube.com/vi/'+id+'/mqdefault.jpg', images: ['https://img.youtube.com/vi/'+id+'/mqdefault.jpg']});
chrome.cast.Image('https://img.youtube.com/vi/'+id+'/mqdefault.jpg');
} else {
if(videoSource == "soundcloud") {
try {
Player.player.stopVideo();
} catch(e) {
}
was_stopped = false;
Player.loadSoundCloud(id, this_duration, start, end, true);
//SC.Widget(Player.soundcloud_player).play();
} else {
//window.player = Player.player;
try {
Player.soundcloud_player.pause();
} catch(e) {
}
Helper.addClass(".soundcloud_info_container", "hide");
Helper.addClass(document.getElementById("player_overlay"), "hide");
Helper.css(document.getElementById("player_overlay"), "background", "none");
Helper.addClass("#player_overlay_text", "hide");
Helper.addClass(document.getElementById("player_overlay"), "hide");
try {
if(Player.player.getVideoUrl().indexOf(id) > -1) {
Player.player.seekTo(seekTo);
} else {
Player.player.loadVideoById({'videoId': id, 'startSeconds': s, 'endSeconds': e});
}
} catch(e) {
}
was_stopped = false;
}
}
if(offline) {
getColor(id);
//socket.emit("color", {id: id});
@@ -423,8 +359,28 @@ var Player = {
if(end) e = end;
else e = Player.np.end;
Player.player.cueVideoById({'videoId': id, 'startSeconds': s, 'endSeconds': e});
if(videoSource == "soundcloud") {
try {
Player.player.stopVideo();
} catch(e) {
}
Player.loadSoundCloud(id, this_duration, start, end, false);
//SC.Widget(Player.soundcloud_player).play();
} else {
try {
Player.soundcloud_player.pause();
} catch(e) {
}
Helper.addClass(document.getElementById("player_overlay"), "hide");
Helper.css(document.getElementById("player_overlay"), "background", "none");
Helper.addClass("#player_overlay_text", "hide");
Helper.addClass(document.getElementById("player_overlay"), "hide");
try {
Player.player.cueVideoById({'videoId': id, 'startSeconds': s, 'endSeconds': e});
} catch(e) {
}
}
},
stopVideo: function(){
@@ -442,6 +398,7 @@ var Player = {
castSession.setVolume(vol/100);
} else {
Player.player.setVolume(vol);
Player.soundcloud_player.setVolume(vol / 100);
}
},
@@ -469,7 +426,7 @@ var Player = {
Player.getTitle(song_title, viewers);
//Player.setBGimage(video_id);
if(chromecastAvailable){
castSession.sendMessage("urn:x-cast:zoff.me", {type: "loadVideo", videoId: video_id, channel: chan.toLowerCase(), start: start, end:end});
castSession.sendMessage("urn:x-cast:zoff.me", {type: "loadVideo", videoId: video_id, channel: chan.toLowerCase(), start: start, end:end, source: videoSource});
chrome.cast.media.GenericMediaMetadata({metadataType: 0, title:song_title, image: 'https://img.youtube.com/vi/'+video_id+'/mqdefault.jpg', images: ['https://img.youtube.com/vi/'+video_id+'/mqdefault.jpg']});
chrome.cast.Image('https://img.youtube.com/vi/'+video_id+'/mqdefault.jpg');
} else {
@@ -506,7 +463,7 @@ var Player = {
//Player.setBGimage(video_id);
if(chromecastAvailable){
castSession.sendMessage("urn:x-cast:zoff.me", {type: "loadVideo", videoId: video_id, channel: chan.toLowerCase(), start: start, end: end});
castSession.sendMessage("urn:x-cast:zoff.me", {type: "loadVideo", videoId: video_id, channel: chan.toLowerCase(), start: start, end: end, source: videoSource});
chrome.cast.media.GenericMediaMetadata({metadataType: 0, title:song_title, image: 'https://img.youtube.com/vi/'+video_id+'/mqdefault.jpg', images: ['https://img.youtube.com/vi/'+video_id+'/mqdefault.jpg']});
chrome.cast.Image('https://img.youtube.com/vi/'+video_id+'/mqdefault.jpg');
} else {
@@ -518,7 +475,7 @@ var Player = {
sendNext: function(obj){
if(chromecastAvailable){
castSession.sendMessage("urn:x-cast:zoff.me", {type: "nextVideo", title: obj.title, videoId: obj.videoId});
castSession.sendMessage("urn:x-cast:zoff.me", {type: "nextVideo", title: obj.title, videoId: obj.videoId, source: obj.source});
}
if(embed) {
@@ -571,6 +528,97 @@ var Player = {
}
},
soundcloudFinish: function() {
playing = false;
paused = false;
end_programmatically = true;
if(!offline) {
/*var u = Crypt.crypt_pass(Crypt.get_userpass(chan.toLowerCase()), true);
if(u == undefined) u = "";*/
socket.emit("end", {id: video_id, channel: chan.toLowerCase()});
} else {
Player.playNext();
}
},
soundcloudPause: function() {
if(end_programmatically) {
paused = false;
playing = false;
end_programmatically = false;
} else {
was_stopped = true;
if(!chromecastAvailable){
if(Helper.mobilecheck()) {
Helper.css("#playpause", "visibility", "visible");
Helper.css("#playpause", "pointer-events", "all");
Helper.css("#channel-load", "display", "none");
}
if(!empty_clear && !gotten_np) {
paused = true;
}
if(gotten_np) gotten_np = false;
if(window.location.pathname != "/") Playercontrols.play_pause_show();
mobile_beginning = true;
}
Helper.removeClass("#play", "hide");
Helper.addClass("#pause", "hide");
}
},
soundcloudPlay: function() {
Helper.addClass("#player_loader_container", "hide");
if(videoSource == "youtube") {
Player.soundcloud_player.pause();
} else if(soundcloud_loading){
Player.soundcloud_player.seek((seekTo) * 1000);
Player.soundcloud_player.setVolume(embed ? 1 : Crypt.get_volume() / 100);
soundcloud_loading = false;
}
if(embed) {
Helper.css("#player", "visibility", "visible");
}
if(embed && !autoplay) autoplay = true;
if(!window.MSStream) {
Helper.css("#player", "opacity", "1");
//if(!Helper.mobilecheck()) {
Helper.css("#channel-load", "display", "none");
//}
}
Helper.css("#playpause", "visibility", "visible");
Helper.css("#playpause", "pointer-events", "all");
playing = true;
if(beginning && Helper.mobilecheck() && !chromecastAvailable){
//Player.pauseVideo();
beginning = false;
mobile_beginning = false;
}
//if(!embed && window.location.pathname != "/" && !chromecastAvailable) Helper.addClass("#player_overlay", "hide");
if(window.location.pathname != "/"){
Helper.addClass("#play", "hide");
Helper.removeClass("#pause", "hide");
}
if((was_stopped) && !offline) {
/*var u = Crypt.crypt_pass(Crypt.get_userpass(chan.toLowerCase()), true);
if(u == undefined) u = "";*/
paused = false;
was_stopped = false;
socket.emit('pos', {channel: chan.toLowerCase()});
} else {
paused = false;
was_stopped = false;
}
},
soundcloudReady: function() {
beginning = true;
player_ready = true;
if(videoSource == "soundcloud" && videoId != undefined) Player.loadVideoById(videoId, Player.np.duration, Player.np.start, Player.np.end);
},
onPlayerReady: function(event) {
try{
beginning = true;
@@ -669,7 +717,9 @@ var Player = {
notifyUser: function(id, title) {
title = title.replace(/\\\'/g, "'").replace(/&quot;/g,"'").replace(/&amp;/g,"&");
if (Notification.permission === "granted" && document.hidden && !embed) {
var notification = new Notification("Now Playing", {body: title, icon: "https://img.youtube.com/vi/"+id+"/mqdefault.jpg", iconUrl: "http://img.youtube.com/vi/"+id+"/mqdefault.jpg"});
var icon = "https://img.youtube.com/vi/"+id+"/mqdefault.jpg";
if(videoSource) icon = full_playlist[full_playlist.length - 1].thumbnail;
var notification = new Notification("Now Playing", {body: title, icon: icon, iconUrl: icon});
notification.onclick = function(x) { window.focus(); this.cancel(); };
setTimeout(function(){
notification.close();
@@ -734,7 +784,12 @@ var Player = {
dMinutes = Math.floor(duration / 60);
dSeconds = duration - dMinutes * 60;
if(videoSource == "soundcloud") {
currDurr = Math.floor(Player.soundcloud_player.currentTime()) / 1000;
} else {
currDurr = Player.player.getCurrentTime() !== undefined ? Math.floor(Player.player.getCurrentTime()) : seekTo;
}
if(currDurr - Player.np.start > duration && !offline) {
currDurr = duration - Player.np.start;
}
@@ -761,20 +816,31 @@ var Player = {
if(!dragging) {
document.getElementById("bar").style.width = per+"%";
}
if(videoSource == "soundcloud") {
if(Math.ceil(currDurr) + 1 > Player.np.end && Player.soundcloud_player.isPlaying()) {
end_programmatically = true;
if(!offline) {
Player.soundcloud_player.pause();
was_stopped = false;
socket.emit("end", {id: video_id, channel: chan.toLowerCase()});
} else {
Player.playNext();
}
}
} else {
if(Player.player.getCurrentTime() > Player.np.end && Player.player.getPlayerState() == YT.PlayerState.PLAYING) {
end_programmatically = true;
if(!offline) {
Player.player.pauseVideo();
/*var u = Crypt.crypt_pass(Crypt.get_userpass(chan.toLowerCase()), true);
if(u == undefined) u = "";*/
was_stopped = false;
socket.emit("end", {id: video_id, channel: chan.toLowerCase()});
} else {
Player.playNext();
}
}
}
}
}catch(e){}
if(!Player.stopInterval) {
setTimeout(Player.durationSetter, 1000);
@@ -785,6 +851,8 @@ var Player = {
if(document.querySelectorAll("script[src='https://www.youtube.com/iframe_api']").length == 1){
try{
Player.onYouTubeIframeAPIReady();
//SC.Widget(Player.soundcloud_player).bind("ready", Player.soundcloudReady);
Player.soundcloudReady();
} catch(error){
console.error("Seems YouTube iFrame script isn't correctly loaded. Please reload the page.");
}
@@ -793,6 +861,27 @@ var Player = {
tag.src = "https://www.youtube.com/iframe_api";
firstScriptTag = document.getElementsByTagName('script')[0];
firstScriptTag.parentNode.insertBefore(tag, firstScriptTag);
tag.onload = function() {
if(document.querySelectorAll("script[src='https://w.soundcloud.com/player/api.js']").length == 1) {
//SC.Widget(Player.soundcloud_player);
//SC.Widget(Player.soundcloud_player).bind(SC.Widget.Events.READY, Player.soundcloudReady);
} else {
tagSearch = document.createElement('script');
tagSearch.setAttribute("async", true);
tagSearch.src = "https://connect.soundcloud.com/sdk/sdk-3.3.0.js";
firstScriptTag = document.getElementsByTagName('script')[0];
firstScriptTag.parentNode.insertBefore(tagSearch, firstScriptTag);
tagSearch.onload = function() {
SC.initialize({
client_id: 'ed53fc01f248f15becddf8eb52cc91ef'
}, function() {
});
}
}
}
}
}

View File

@@ -190,6 +190,13 @@ var Playercontrols = {
play_pause: function() {
if(!chromecastAvailable){
if(videoSource == "soundcloud") {
if(!Player.soundcloud_player.isPlaying()) {
Player.playVideo();
} else {
Player.pauseVideo();
}
} else {
if(Player.player.getPlayerState() == YT.PlayerState.PLAYING)
{
Player.pauseVideo();
@@ -210,6 +217,7 @@ var Playercontrols = {
Helper.toggleClass(".page-footer", "padding-bottom-extra");
}
}
}
} else {
Playercontrols.play_pause_show();
}
@@ -265,6 +273,7 @@ var Playercontrols = {
setVolume: function(vol) {
Player.setVolume(vol);
Player.soundcloud_player.setVolume(vol / 1000);
Playercontrols.choose_button(vol, false);
if(Player.player.isMuted())
Player.player.unMute();
@@ -345,6 +354,17 @@ var Playercontrols = {
},
playPause: function() {
if(videoSource == "soundcloud") {
if(!Player.soundcloud_player.isPlaying()) {
Helper.addClass("#play", "hide");
Helper.removeClass("#pause", "hide");
Player.soundcloud_player.play();
} else {
Helper.removeClass("#play", "hide");
Helper.addClass("#pause", "hide");
Player.soundcloud_player.pause();
}
} else {
state = Player.player.getPlayerState();
button = document.getElementById("playpause");
if(state == YT.PlayerState.PLAYING) {
@@ -352,6 +372,7 @@ var Playercontrols = {
} else if(state == YT.PlayerState.PAUSED) {
Player.playVideo();
}
}
},
visualVolume: function(val) {

View File

@@ -17,28 +17,30 @@ var Search = {
//$("#results").empty();
if(document.querySelector("#search-btn i").innerText == "close") {
document.querySelector("body").setAttribute("style", "overflow-y:auto")
/*$("#results").slideUp({
complete: function() {
$("#results").empty();
}
});*/
document.getElementById("results").innerHTML = "";
document.getElementById("results_soundcloud").innerHTML = "";
Helper.css(".search_results", "display", "none");
//Helper.css(".results-tabs", "display", "none");
document.querySelector(".search_input").value = "";
document.querySelector("#search-btn i").innerText = "search";
//Helper.css(document.querySelector(".search_results .col.s12"), "display", "none");
} else {
document.querySelector("#search-btn i").innerText = "close";
//Helper.css(".search_results", "display", "block");
}
document.querySelector("#search").focus();
},
search: function(search_input, retried, related, pagination){
if(result_html === undefined || empty_results_html === undefined) {
result_html = document.getElementById("temp-results-container");
empty_results_html = Helper.html("#empty-results-container");
}
if(!pagination && document.querySelectorAll("#inner-results").length == 0) {
Helper.setHtml(".search_results", '');
Helper.setHtml("#results", '');
}
if(search_input !== ""){
searching = true;
@@ -55,7 +57,8 @@ var Search = {
Helper.addClass(".search_loader_spinner", "active");
Helper.removeClass("#results", "hide");
//Helper.removeClass(".search_results", "hide");
//Helper.css(".results-tabs", "display", "none");
Helper.ajax({
type: "GET",
@@ -63,11 +66,14 @@ var Search = {
dataType: "jsonp",
success: function(response){
response = JSON.parse(response);
var output = "";
var nextPageToken = response.nextPageToken;
var prevPageToken = response.prevPageToken;
//Helper.css(document.querySelector(".search_results .col.s12"), "display", "block");
if(response.items.length === 0) {
document.getElementById("results").innerHTML = "";
Helper.css("#results", "display", "block");
//Helper.css(".results-tabs", "display", "block");
//$("<div style='display:none;' id='inner-results' class='empty-inner-results'>"+empty_results_html+"</div>").appendTo($("#results")).show("blind", 83.33);
document.getElementById("results").insertAdjacentHTML("beforeend", "<div style='display:block;' id='inner-results' style='height:calc(100vh - 64px);' class='empty-inner-results'>"+empty_results_html+"</div>");
Helper.removeClass(".search_loader_spinner", "active");
@@ -88,18 +94,17 @@ var Search = {
pre_result.innerHTML = result_html.outerHTML;
//$("#results").append(result_html);
for(var i = 0; i < response.items.length; i++) {
var song = response.items[i];
var duration=song.contentDetails.duration;
secs=Search.durationToSeconds(duration);
var secs=Search.durationToSeconds(duration);
var _temp_duration = Helper.secondsToOther(secs);
if(!longsongs || secs<720){
title=song.snippet.title;
enc_title=title;//encodeURIComponent(title).replace(/'/g, "\\\'");
id=song.id;
if((longsongs != undefined && !longsongs) || secs<720){
var title=song.snippet.title;
var enc_title=title;//encodeURIComponent(title).replace(/'/g, "\\\'");
var id=song.id;
duration = duration.replace("PT","").replace("H","h ").replace("M","m ").replace("S","s");
thumb=song.snippet.thumbnails.medium.url;
var thumb=song.snippet.thumbnails.medium.url;
//$("#results").append(result_html);
var songs = pre_result.cloneNode(true);
@@ -127,7 +132,7 @@ var Search = {
if(document.querySelectorAll("#inner-results").length == 0) {
fresh = true;
}
document.getElementsByClassName("search_results")[0].innerHTML = "";
document.getElementById("results").innerHTML = "";
if(output.length > 0) {
//$(window).scrollTop(0);
if(!pagination && fresh) {
@@ -157,7 +162,10 @@ var Search = {
//setTimeout(function(){$(".thumb").lazyload({container: $("#results")});}, 250);
Helper.removeClass(".search_loader_spinner", "active");
if(document.querySelector("#results_soundcloud").innerHTML.length > 0) {
Helper.css(".search_results", "display", "block");
}
Helper.css(".results-tabs", "display", "block");
} else if(!retried){
Search.search(search_input, true);
@@ -165,6 +173,9 @@ var Search = {
//$("<div style='display:none;' id='inner-results'>"+empty_results_html+"</div>").appendTo($("#results")).show("blind", 83.33);
document.getElementById("results").insertAdjacentHTML("beforeend", "<div style='display:block;' id='inner-results' style='height:calc(100vh - 64px);'>"+empty_results_html+"</div>");
Helper.css("#results", "display", "block");
if(document.querySelector("#results_soundcloud").innerHTML.length > 0) {
Helper.css(".search_results", "display", "block");
}
Helper.removeClass(".search_loader_spinner", "active");
}
}
@@ -179,6 +190,111 @@ var Search = {
}
},
soundcloudSearch: function(keyword) {
SC.get('/tracks', {
q: keyword
}).then(function(tracks) {
var pre_result = document.createElement("div");
pre_result.innerHTML = result_html.outerHTML;
//$("#results").append(result_html);
//Helper.css(document.querySelector(".search_results .col.s12"), "display", "block");
var output = "";
for(var i = 0; i < tracks.length; i++) {
var song = tracks[i];
if(!song.streamable) continue;
var duration=Math.floor(song.duration / 1000);
//var secs=Search.durationToSeconds(duration);
var secs = duration;
var _temp_duration = Helper.secondsToOther(secs);
if((longsongs != undefined && !longsongs) || secs<720){
var title=song.title;
if(title.indexOf(song.user.username) == -1) {
title = song.user.username + " - " + title;
}
var enc_title=title;//encodeURIComponent(title).replace(/'/g, "\\\'");
var id=song.id;
//duration = duration.replace("PT","").replace("H","h ").replace("M","m ").replace("S","s");
var thumb=song.artwork_url;
//var thumb = null;
if(thumb == null) thumb = song.waveform_url;
else thumb = thumb.replace("-large.jpg", "-t500x500.jpg");
//$("#results").append(result_html);
var songs = pre_result.cloneNode(true);
songs.querySelector(".search-title").innerText = title;
songs.querySelector(".result_info").innerText = Helper.pad(_temp_duration[0]) + ":" + Helper.pad(_temp_duration[1]);
songs.querySelector(".thumb").setAttribute("src", thumb);
//songs.querySelector(".add-many").attr("onclick", "submit('"+id+"','"+enc_title+"',"+secs+");");
songs.querySelector("#add-many").setAttribute("data-type-source", "soundcloud");
songs.querySelector("#add-many").setAttribute("data-type-thumbnail", thumb);
songs.querySelector("#add-many").setAttribute("data-video-id", id);
songs.querySelector("#add-many").setAttribute("data-video-title", enc_title);
songs.querySelector("#add-many").setAttribute("data-video-length", secs);
//$($(songs).querySelector("div")[0]).setAttribute("onclick", "submitAndClose('"+id+"','"+enc_title+"',"+secs+");");
songs.querySelector("#temp-results").setAttribute("data-video-id", id);
songs.querySelector("#temp-results").setAttribute("data-video-title", enc_title);
songs.querySelector("#temp-results").setAttribute("data-video-length", secs);
songs.querySelector(".open-externally").setAttribute("href", song.permalink_url);
songs.querySelector(".result-end").setAttribute("value", secs);
songs.querySelector("#temp-results").setAttribute("data-type-source", "soundcloud");
songs.querySelector("#temp-results").setAttribute("data-type-thumbnail", thumb);
//$($(songs).querySelector("div")[0]).setAttribute("id", id)
//output += undefined;
if(songs.innerHTML != undefined && songs.innerHTML != "") {
output += songs.innerHTML;
}
}
}
var fresh = false;
if(document.querySelectorAll("#inner-results").length == 0) {
fresh = true;
}
document.getElementById("results_soundcloud").innerHTML = "";
if(output.length > 0) {
if(document.querySelector("#results").innerHTML.length > 0) {
Helper.css(".search_results", "display", "block");
}
//$(window).scrollTop(0);
/*if(!pagination && fresh) {
//Helper.css(".search_results", "display", "none");
}*/
//document.getElementById("results_soundcloud").insertAdjacentHTML("beforeend", pagination_buttons_html);
//$("<div id='inner-results'>"+output+"</div>").prependTo($("#results"));
document.getElementById("results_soundcloud").insertAdjacentHTML("afterbegin", "<div id='inner-results'>"+output+"</div>");
if(!pagination && fresh) {
//$(".search_results").slideDown();
}
document.getElementsByTagName("body")[0].setAttribute("style", "overflow-y:hidden !important")
/*if(nextPageToken) {
document.querySelector(".next-results-button").setAttribute("data-pagination", nextPageToken);
} else {
Helper.addClass(".next-results-button", "disabled");
}
if(prevPageToken) {
document.querySelector(".prev-results-button").setAttribute("data-pagination", prevPageToken);
} else {
Helper.addClass(".prev-results-button", "disabled");
}
document.querySelector(".pagination-results a").setAttribute("data-original-search", search_input);
*/
//setTimeout(function(){$(".thumb").lazyload({container: $("#results")});}, 250);
/*Helper.removeClass(".search_loader_spinner", "active");
Helper.css(".search_results", "display", "block");*/
} /*else if(!retried){
Search.search(search_input, true);
} else {
//$("<div style='display:none;' id='inner-results'>"+empty_results_html+"</div>").appendTo($("#results_soundcloud")).show("blind", 83.33);
document.getElementById("results_soundcloud").insertAdjacentHTML("beforeend", "<div style='display:block;' id='inner-results' style='height:calc(100vh - 64px);'>"+empty_results_html+"</div>");
Helper.css("#results_soundcloud", "display", "block");
Helper.removeClass(".search_loader_spinner", "active");
}*/
});
},
backgroundSearch: function(title, artist, length, totalNumber, current){
var keyword= encodeURIComponent(title + " " + artist);
var yt_url = "https://www.googleapis.com/youtube/v3/search?key="+api_key+"&videoEmbeddable=true&part=id,snippet&fields=items(id,snippet)&type=video&order=relevance&safeSearch=none&maxResults=10&videoCategoryId=10";
@@ -247,8 +363,6 @@ var Search = {
))
not_matched = true;
else if(duration > 1800) not_matched = true;
}
}
@@ -276,13 +390,13 @@ var Search = {
}
},
error: function(e) {
console.log(e);
console.error(e);
}
});
}
}, error: function(e) {
console.log(e);
console.error(e);
}
});
},
@@ -309,16 +423,18 @@ var Search = {
}
},
submitAndClose: function(id,title,duration, start, end){
Search.submit(id,title, duration, false, 0, 1, start, end);
submitAndClose: function(id,title,duration, start, end, source, thumbnail){
Search.submit(id,title, duration, false, 0, 1, start, end, source, thumbnail);
Helper.setHtml("#results", '');
Search.showSearch();
document.getElementById("search").value = "";
document.getElementsByTagName("body")[0].setAttribute("style", "overflow-y:auto")
Helper.setHtml("#results","");
Helper.setHtml("#results-soundcloud", "");
Helper.removeClass(".main", "blurT");
Helper.removeClass("#controls", "blurT");
Helper.removeClass(".main", "clickthrough");
Helper.css(".search_results", "display", "none");
},
importPlaylist: function(pId,pageToken){
@@ -491,7 +607,7 @@ var Search = {
for(var i = 0; i < response.items.length; i++) {
var song = response.items[i];
var duration=Search.durationToSeconds(song.contentDetails.duration);
if(!longsongs || duration<720){
if((longsongs != undefined && !longsongs) || duration<720){
enc_title= song.snippet.title;//encodeURIComponent(song.snippet.title);
//Search.submit(song.id, enc_title, duration, playlist, i);
x += 1;
@@ -506,14 +622,14 @@ var Search = {
}
},
error: function(e) {
console.log(e);
console.error(e);
}
});
},
submit: function(id,title,duration, playlist, num, full_num, start, end){
submit: function(id,title,duration, playlist, num, full_num, start, end, source, thumbnail){
if((client || Helper.mobilecheck()) && !socket_connected) {
add_ajax(id, title, duration, playlist, num, full_num, start, end);
add_ajax(id, title, duration, playlist, num, full_num, start, end, source, thumbnail);
return;
}
if(offline && document.getElementsByName("addsongs")[0].checked && document.getElementsByName("addsongs")[0].disabled){
@@ -529,7 +645,7 @@ var Search = {
} else {
/*var u = Crypt.crypt_pass(Crypt.get_userpass(chan.toLowerCase()), true);
if(u == undefined) u = "";*/
emit("add", {id: id, start: start, end: end, title: title, list: chan.toLowerCase(), duration: duration});
emit("add", {id: id, start: start, end: end, title: title, list: chan.toLowerCase(), duration: duration, source: source, thumbnail: thumbnail});
}//[id, decodeURIComponent(title), adminpass, duration, playlist]);
},

View File

@@ -37,6 +37,7 @@ var Suggestions = {
},
fetchYoutubeSuggests: function(id){
if(videoSource == "soundcloud") return;
var get_url = "https://www.googleapis.com/youtube/v3/search?part=snippet&relatedToVideoId="+id+"&type=video&key="+api_key;
var video_urls = "https://www.googleapis.com/youtube/v3/videos?part=contentDetails,snippet,id&key="+api_key+"&id=";

View File

@@ -191,9 +191,9 @@
<div class="row">
<div class="col l6 s12">
<h5 class="white-text">Zoff</h5>
<p class="grey-text text-lighten-4">The shared YouTube radio</p>
<p class="grey-text text-lighten-4">The shared YouTube and SoundCloud radio</p>
<p class="grey-text text-lighten-4">
Being built around the YouTube search and video API
Being built around the YouTube and SoundCloud API
it enables the creation of collaborative and shared live playlists,
with billions of videos and songs to choose from, all for free and without registration.
<br />

View File

@@ -10,6 +10,20 @@
<div id="container" style="display:inline-flex;">
<div id="player-container">
<div id="player"></div>
<div id="player_overlay" class="hide valign-wrapper">
<div class="soundcloud_info_container hide">
<a href="#!" id="soundcloud_listen_link" target="_blank">
<img src="https://developers.soundcloud.com/assets/powered_by_large_white-9c2af6a93ad2b1c541f423d9e9045980.png" />
</a>
<a href="#!" class="btn green waves-effect waves-light" target="_blank">Buy</a>
<a href="#!" class="btn red waves-effect waves-light" target="_blank">Artist</a>
</div>
<div id="player_loader_container" class="hide valign-wrapper">
<div id="player_loader" class="preloader-wrapper large active valign">
{{> spinner}}
</div>
</div>
</div>
<div id="zoffbutton" title="Visit the channel!"></div>
<div id="controls" class="noselect">
<div id="playpause">

View File

@@ -8,10 +8,10 @@
| Made by: Kasper Rynning-Tønnesen and Nicolas Almagro Tonne |
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -->
<title>Zoff - the shared YouTube based radio</title>
<title>Zoff - the shared YouTube and SoundCloud based radio</title>
<meta http-equiv="content-type" content="text/html; charset=UTF-8" />
<meta name="author" content="Nicolas 'Nixo' Almagro Tonne &amp; Kasper 'KasperRT' Rynning-Tønnesen"/>
<meta name="description" content="The shared (free) YouTube radio."/>
<meta name="description" content="The shared (free) YouTube and SoundCloud radio."/>
<meta name="viewport" content="width=device-width, initial-scale=1"/>
<meta name="apple-mobile-web-app-capable" content="yes">
<meta name="mobile-web-app-capable" content="yes">
@@ -19,7 +19,7 @@
<meta property="og:image" content="https://zoff.me/assets/images/favicon-32x32.png" />
<meta property="og:url" content="https://zoff.me" />
<meta property="og:title" content="Zoff"/>
<meta property="og:description" content="The Shared (free) YouTube radio."/>
<meta property="og:description" content="The Shared (free) YouTube and SoundCloud radio."/>
<meta property="og:type" content="website"/>
<meta property="fb:app_id" content="1581693815380949" />
<link rel="manifest" href="/assets/manifest.json">

View File

@@ -13,7 +13,7 @@
Loading...
</li>
<li class="search-container hide" id="search-wrapper">
<input id="search" class="search_input white-text" type="text" title="Search for songs..." placeholder="Find song on YouTube..." onsubmit="null;" autocomplete="off" />
<input id="search" class="search_input white-text" type="text" title="Search for songs..." placeholder="Find song on YouTube or SoundCloud..." onsubmit="null;" autocomplete="off" />
</li>
</ul>
<ul class="right control-list noselect">

View File

@@ -3,6 +3,7 @@
<div id="fireplace_player" class="ytplayer"></div>
{{/unless}}
<div id="player" class="ytplayer"></div>
<div id="main_components">
<div id="player_overlay" class="hide valign-wrapper">
<div id="playing_on">
@@ -11,9 +12,20 @@
</div>
<div id="chromecast_text"></div>
</div>
<div class="soundcloud_info_container hide">
<a href="#!" id="soundcloud_listen_link" target="_blank">
<img src="https://developers.soundcloud.com/assets/powered_by_large_white-9c2af6a93ad2b1c541f423d9e9045980.png" />
</a>
<a href="#!" class="btn green waves-effect waves-light" target="_blank">Artist</a>
</div>
<div id="player_overlay_text" class="valign center-align">
Waiting for Video
</div>
<div id="player_loader_container" class="hide valign-wrapper">
<div id="player_loader" class="preloader-wrapper large active valign">
{{> spinner}}
</div>
</div>
<div id="player_overlay_controls" class="hide valign-wrapper">
<div id="playpause-overlay" class="valign center-align">
<i id="play-overlay" class="material-icons hide">play_arrow</i>

View File

@@ -1,4 +1,11 @@
<div id="results" class="search_results hide">
<div class="row search_results" style="display:none;">
<div class="col s12">
<ul class="results-tabs">
<li class="tab col s6"><a class="active" href="#results">YouTube</a></li>
<li class="tab col s6"><a href="#results_soundcloud">SoundCloud</a></li>
</ul>
</div>
<div id="results" class="">
<div id="temp-results-container">
<div id="temp-results" class="result-object">
<div id="result" class="result">
@@ -41,3 +48,5 @@
<a href="#" class="btn waves-effect waves-light next-results-button orange">Next</a>
</div>
</div>
<div id="results_soundcloud" class="col s12">Test 2</div>
</div>

View File

@@ -8,7 +8,7 @@
<div class="row">
<div class="col s12 m6 center">
<div class="col s12 center">
<img src="https://en.bitcoin.it/w/images/en/c/cb/BC_Logotype.png" alt="bitcoin-image" class="col s6 center"/>
<img src="/assets/images/btcdonate.png" alt="bitcoin-image" class="col s6 center"/>
<input type="text" id="bitcoin-address" readonly value="18DxBV9ij9t1eSLC3rTrugJbzGtMVPEyNB" />
</div>
<div class="col s12 center">

View File

@@ -3,9 +3,9 @@
<div class="row">
<div class="col l6 s12">
<h5 class="white-text">Zoff</h5>
<p class="grey-text text-lighten-4">The shared YouTube radio</p>
<p class="grey-text text-lighten-4">The shared YouTube and SoundCloud radio</p>
<p class="grey-text text-lighten-4">
Being built around the YouTube search and video API
Being built around the YouTube and SoundCloud API
it enables the creation of collaborative and shared live playlists,
with billions of videos and songs to choose from, all for free and without registration.
<br />

View File

@@ -26,7 +26,7 @@
</div>
</form>
<div class="pitch outline">
<div>Live &amp; democratic playlists with YouTube Music</div>
<div>Live, free &amp; democratic playlists with YouTube and SoundCloud</div>
<div>Play everywhere — No login required</div>
</div>
</div>

View File

@@ -1,7 +1,7 @@
<div id="about" class="modal">
<div class="modal-content">
<h4>About</h4>
<p>Zoff (pronounced <b>søff</b>) is a shared (free) YouTube based radio service, built upon the YouTube API. <br><br>
<p>Zoff (pronounced <b>søff</b>) is a shared (free) YouTube and SoundCloud based radio service, built upon the YouTube and SoundCloud API. <br><br>
Zoff is mainly a web-based service. The website uses NodeJS with Socket.IO, MongoDB and express on the backend, with JavaScript and Materialize on the frontend.<br><br>
The team consists of Kasper Rynning-Tønnesen and Nicolas Almagro Tonne, and the project has been worked on since late 2014.<br><br>
</p>

View File

@@ -18,6 +18,8 @@ var toShowChannel = {
_id: 0,
now_playing: 1,
type: 1,
source: 1,
thumbnail: 1,
};
var toShowConfig = {
addsongs: 1,
@@ -622,7 +624,8 @@ router.route('/api/list/:channel_name/:video_id').post(function(req,res) {
if(!fetch_only && (!req.body.hasOwnProperty('adminpass') || !req.body.hasOwnProperty('userpass') ||
!req.params.hasOwnProperty('channel_name') || !req.params.hasOwnProperty('video_id') ||
!req.body.hasOwnProperty('duration') || !req.body.hasOwnProperty('start_time') ||
!req.body.hasOwnProperty('end_time') || !req.body.hasOwnProperty('title'))) {
!req.body.hasOwnProperty('end_time') || !req.body.hasOwnProperty('title') ||
!req.body.hasOwnProperty('source'))) {
throw "Wrong format";
}
@@ -637,10 +640,15 @@ router.route('/api/list/:channel_name/:video_id').post(function(req,res) {
var duration = parseInt(req.body.duration);
var start_time = parseInt(req.body.start_time);
var end_time = parseInt(req.body.end_time);
var source = req.body.source;
if(source == "soundcloud" && !req.body.hasOwnProperty("thumbnail")) {
throw "Wrong format";
}
if(duration != end_time - start_time) duration = end_time - start_time;
var title = req.body.title;
if(typeof(userpass) != "string" || typeof(adminpass) != "string" ||
typeof(title) != "string" || isNaN(duration) || isNaN(start_time) || isNaN(end_time)) {
console.log("this place crash");
throw "Wrong format";
}
}
@@ -704,6 +712,7 @@ router.route('/api/list/:channel_name/:video_id').post(function(req,res) {
var type = fetch_only ? "fetch_song" : "add";
validateLogin(adminpass, userpass, channel_name, type, res, function(exists, conf, authenticated) {
db.collection(channel_name).find({id: video_id}, function(err, result) {
console.log(result);
if(result.length == 0 || result[0].type == "suggested") {
var song_type = authenticated ? "video" : "suggested";
if(fetch_only && result.length == 0) {
@@ -715,8 +724,15 @@ router.route('/api/list/:channel_name/:video_id').post(function(req,res) {
if(now_playing.length == 0 && authenticated) {
set_np = true;
}
var new_song = {"added": Functions.get_time(),"guids":[guid],"id":video_id,"now_playing":set_np,"title":title,"votes":1, "duration":duration, "start": parseInt(start_time), "end": parseInt(end_time), "type": song_type};
Search.get_correct_info(new_song, channel_name, false, function(element, found) {
var new_song = {"added": Functions.get_time(),"guids":[guid],"id":video_id,"now_playing":set_np,"title":title,"votes":1, "duration":duration, "start": parseInt(start_time), "end": parseInt(end_time), "type": song_type, "source": source};
var runFunction = Search.get_correct_info;
if(source == "soundcloud") {
new_song.thumbnail = req.body.thumbnail;
runFunction = function(new_song, foo_2, foo_3, callback) {
callback(new_song, true);
}
}
runFunction(new_song, channel_name, false, function(element, found) {
if(!found) {
res.status(404).send(JSON.stringify(error.not_found.youtube));
return;
@@ -747,7 +763,8 @@ router.route('/api/list/:channel_name/:video_id').post(function(req,res) {
postEnd(channel_name, configs, new_song, guid, res, authenticated, authorized);
});
} else if(set_np) {
Frontpage.update_frontpage(channel_name, video_id, title, function() {
var thumbnail = req.body.thumbnail != undefined ? req.body.thumbnail : undefined;
Frontpage.update_frontpage(channel_name, video_id, title, thumbnail, function() {
io.to(channel_name).emit("np", {np: [new_song], conf: [conf]});
postEnd(channel_name, configs, new_song, guid, res, authenticated, authorized);
});