var SavedPlaylist = Class.create ();
SavedPlaylist.prototype = {
	type: 'saved_playlist',
	url_visible: false,
	initialize: function (container, jsonObj) {
		this.container = container;
		this.jsonObj = jsonObj;
		Object.extend(this, TemplatedElement);
		this._buildFromTemplate('template_playlists_list_item');

		this.elementName.innerHTML = jsonObj.name;
		this.elementURL.value = 'http://' + CHOST + '/?watch_pl=' + jsonObj.hash;
		this.elementVideosCount.innerHTML = jsonObj.videos.length + ' videos';
		if (jsonObj.description)
			this.elementDescription.innerHTML = jsonObj.description;
		else
			this.elementDescription.style.display = 'none';
		this.thumbnail.src = this.jsonObj.videos[0].thumbnail_url;
		this.appended = false;
		if (this.container.listOpened) {
			this.container.listContainer.appendChild(this.element);
			this.appended = true;
		}
		this.buildHintText();
	},
	delayedAppend: function () {
		this.appended = true;
		this.container.listContainer.appendChild(this.element);
	},

	setNumber: function (number) {
		if (number%2 == 0) Element.addClassName (this.element, 'even');
		this.elementOrd.innerHTML = number;
	},

	/*startDrag: function(event) {
		dnd.startDragging(event, this);
		if (this.jsonObj.videos.length > 0)
			dnd.setImage(this.jsonObj.videos[0].thumbnail_url);
	},*/

	buildHintText: function() {
		this.hintText = '';
		for (var i = 0; i < this.jsonObj.videos.length; i ++)
			this.hintText += (i+1) + '. ' + this.jsonObj.videos[i].title + '<br />';
	},

	remove: function () { // called from the container
		if (this.appended)
			this.container.listContainer.removeChild (this.element);
		this.element = null;
	},
/*
	dragHover: function (event, draggedObject) {
		this.element_hover(event);
		dnd.setText('append to this saved playlist');
	},

	dragUnhover: function() {
		this.element_unhover();
	},

	recieveDrag: function (draggedObject) {
		// the array is in reversed order (don't ask)
		this.jsonObj.videos.splice(0,0,draggedObject.jsonObj);
		// send append request
		var params = $H({id:this.jsonObj.id, action:'append'});
		new Ajax.Request ('save_playlist.php', {
			method:"post",
			parameters: params.toQueryString() +
				'&videos[0]=' + encodeURIComponent(ObjectToJsonString(draggedObject.jsonObj))
		});
		this.buildHintText();
	},
*/
	// jsonArr is array of videos jsonObj-ects
	appendVideos: function (jsonArr, onAppended) {
		this.onAppended = onAppended;
		if (jsonArr.length == 0) {
			if (this.onAppended) this.onAppended();
			return;
		}
		var params = $H({id:this.jsonObj.id, action:'append'});
		var qs = '';
		// remove duplicate videos in the playlist and the appended videos
		var cleanJsonArr = new Array ();
		for (var i = 0, n = jsonArr.length; i < n; i ++) {
			var found = false;
			for (var j = 0, k = this.jsonObj.videos.length; j < k; j ++)
				if (jsonArr[i].id == this.jsonObj.videos[j].id) {
					found = true;
					break;
				}
			if (!found)
				cleanJsonArr.push (jsonArr[i]);
		}
		jsonArr = cleanJsonArr;
		if (jsonArr.length == 0) {
			if (this.onAppended) this.onAppended();
			return;
		}
		var ids = '', ispr = '';
		for (var i = 0, n = jsonArr.length; i < n; i ++) {

			this.jsonObj.videos.push(jsonArr[i]);
			qs += '&videos[' + i + ']=' + encodeURIComponent(ObjectToJsonString(jsonArr[i]));
			ids += '&ids[' + i + ']=' + jsonArr[i].id;
			ispr += '&ispr[' + i + ']=' + (jsonArr[i].isprivate?'1':'0');
		}
		new Ajax.Request ('save_playlist.php', {
			method:"post",
			parameters: params.toQueryString() + qs + ids + ispr,
			onSuccess: this.appendVideos_handler.bind(this)
		});
		this.buildHintText();
		this.elementVideosCount.innerHTML = this.jsonObj.videos.length + ' videos';
	},
	appendVideos_handler: function () {
		if (this.onAppended)
			this.onAppended();
		this.onAppended = null;
		return;
	},
	update: function (jsonObj) {
		this.jsonObj = jsonObj;
		this.elementName.innerHTML = this.jsonObj.name;
		this.elementDescription.innerHTML = this.jsonObj.description;
		this.buildHintText();
	},

	switchNameURL: function (event) {
		Event.stop(event);
		this.input_URL.style.display = this.element_name.style.display;
		if (this.element_name.style.display == "block")
			this.element_name.style.display = "none";
		else
			this.element_name.style.display = "block";
	},

	onURLClick: function (event) {
		this.elementURL.select();
	},
	share: function (event) {
		this.container.closeList();
		send_recommendation_playlist(this.jsonObj.hash, this.jsonObj.name, this.container.openList.bind(this.container));
	},
	createPlayer: function (event) {
		this.container.closeList();
		EmbedPlayer.open(EmbedPlayer.EMBED_SAVED_LIST, this.jsonObj, null);
	},
	removeFromDB: function () {
		if (!this.element) return;
		var cp = EmbedPlayer.getPlayersWithPlaylist(this.jsonObj.id);
		var message = '';
		if (cp.length > 0) {
			message = "Hold on, this playlist is used in the following players:\n\n";
			for (var pi = 0; pi < 3 && pi < cp.length; pi ++)
				message += cp[pi].player_name + "\n";
			message += "\n";
			if (cp.length > 3)
				message += "and " + (cp.length - 3) + " more\n";
			message += "Deleting this playlist will cause all of the above players to break and not work properly.\n" +
				"Do you really want to delete it?";
		} else {
			message = "Are you sure you want to delete this playlist?";
		}
		if (!confirm(message)) return;
		if (!this.element) return;
		var params = $H({action:'delete', id:this.jsonObj.id });
		new Ajax.Request('save_playlist.php', {
			method:"post",
			parameters: params.toQueryString(), onSuccess: this.removeFromDB_handler.bind(this) });
		this.container.showLoading();
	},
	removeFromDB_handler: function () {
		this.container.hideLoading();
		this.remove();
		this.container.removePlaylist(this);
	},
	edit: function (){
		bc.openSavedPlaylist(this.jsonObj, 'none');
		this.container.closeList();
	},
	play: function () {
		bc.openSavedPlaylist(this.jsonObj);
		this.container.closeList();
	},
	rename: function () {
		this.container.renamePlaylist(this);
	},
	showURL: function () {
		if (this.url_visible) {
			Element.removeClassName (this.element, 'url_visible');
		}else{
			Element.addClassName (this.element, 'url_visible')
		}
		this.url_visible = !this.url_visible;
	},
	showHint: function (event) {
		var p = Position.cumulativeOffset(this.infoBtn);
		var e = {pageX: p[0] + this.infoBtn.offsetWidth - 5, pageY: p[1] + 20 - this.container.listContainer.scrollTop};
		Hint.show(e, this.jsonObj.name, this.hintText, "left");
	},
	hideHint: function () {
		Hint.hide();
	},

	filter: function (keywords) {
		var matches = true;
		var haystack = this.jsonObj.name.toLowerCase() + ' ' + this.jsonObj.description.toLowerCase();
		for (var i = 0, n = keywords.length; i < n; i ++) {
			var kw = keywords[i];
			if (haystack.indexOf(kw) == -1) {
				matches = false;
				break;
			}
		}
		this.filtered = !matches;
		this.element.style.display = this.filtered?'none':'block';
	}
}


var SavedPlaylists = {
	playlists: null,
	list_order_by: 'date',
	onLoadRecheckPlayers: [],

	initialize: function () {
		Object.extend(this, TemplatedElement);
		this._buildFromTemplate('playlists_list', false);

		this.scrollbar = new Scrollbar (this.listContainer, this.scrollbarContainer);

		this.playlists = new Array();

		/*var s = Cookies.getValue ('pll_box_s', '');
		if (s != '') {
			var ch = s.split(',');
			this.element.style.width = parseInt(ch[0]) + "px";
			var nh = parseInt(ch[1]);
			this.element.style.height = nh + "px";
			this.listContainer.style.height = this.scrollbarContainer.style.height = (nh-100) + "px";
			this.element.style.left = parseInt(ch[2]) + "px";
			this.element.style.top = parseInt(ch[3]) + "px";
		}*/
		this.appendOnNextOpen = true;
		this.sortList(Cookies.getValue('pllsb', 'date'), false);
		SavedPlaylistSelect.initialize();
	},

	openList: function () {
		showBackground();
		this.listOpened = true;
		this.element.style.display = 'block';
		if (this.appendOnNextOpen) {
			for (var i = 0; i < this.playlists.length; i ++)
				this.playlists[i].delayedAppend();
			this.appendOnNextOpen = false;
		}
		this.fixScrolls();
	},
	closeList: function () {
		hideBackground();
		this.listOpened = false;
		this.element.style.display = 'none';
	},
	sortList: function (order, load) {
		if (arguments.length == 1)
			var load = true;
		this.list_order_by = order;
		if (this.list_order_by == 'date') {
			Element.addClassName (this.soDate, 'current');
			Element.removeClassName (this.soName, 'current');
		} else {
			Element.addClassName (this.soName, 'current');
			Element.removeClassName (this.soDate, 'current');
		}
		Cookies.setValue ('pllsb', order);
		if (load)
			this.loadPlaylists();

	},
	showLoading: function () {
		this.boxLoadingImg.style.display = 'block';
	},
	hideLoading: function () {
		this.boxLoadingImg.style.display = 'none';
	},

	loadPlaylists: function () {
		this.showLoading();
		this.clearPlaylists();
		new Ajax.Request ('load_playlists.php', {
			method:"post",
			parameters:"order=" + this.list_order_by,
			onSuccess: this.loadPlaylists_handler.bind(this) });
	},

	loadPlaylists_handler: function (ajaxResponse) {
		var t = ajaxResponse.responseText;
		var jsonObj = null;
		this.hideLoading();
		eval ('jsonObj = ' + unescape(t));
		$('playlists_search').value = '';
		if (jsonObj && jsonObj.errorid == 0) {
			this.jsonObj = jsonObj;
			if (this.jsonObj.playlists.length > 0) {
				this.noPlaylists.style.display = 'none';
				for (var i = 0; i < this.jsonObj.playlists.length; i ++)
					this.addPlaylist(this.jsonObj.playlists[i]);
			} else {
				this.noPlaylists.style.display = 'block';
			}
			this.showCount();
			this.fixScrolls();
			SavedPlaylistSelect.loadLists();
			if (!this.listOpened)
				this.appendOnNextOpen = true;
			$('playlists_search_container').style.display = (this.playlists.length > 2?'':'none');

			// some players, that are linked with playlist may load before the playlists are loaded.
			// they are pushed to this array for later recheck of the playlist
			for (var i = 0; i < this.onLoadRecheckPlayers.length; i ++)
				this.onLoadRecheckPlayers[i].recheckPlaylist();
			this.onLoadRecheckPlayers = [];
		} else {	}
	},

	filter: function () {
		var kw = $('playlists_search').value;
		var kws = kw.replace(/\s+/g, ' ').replace(/^\s*/, '').replace(/\s*$/, '').toLowerCase().split(' ');
		var i = 0, n = this.playlists.length;
		for (i = 0; i < n; i ++) {
			this.playlists[i].filter(kws);
			Element.removeClassName(this.playlists[i].element, 'first');
		}
		// find the first NOT filtered!
		i = 0;
		while (i < n) {
			if (!this.playlists[i].filtered) {
				Element.addClassName(this.playlists[i].element, 'first');
				break;
			}
			i ++
		}
		if (i == n) { // all lists are filtered!
			/// then what?
		}
		this.fixScrolls();
	},

	openNewPlaylist: function () {
		bc.openEmptyPlayer();
		this.closeList();
	},

	renamePlaylist: function (playlist) {
		this.renamed_playlist = playlist;
		showBackground();
		if (this.listOpened)
			this.element.style.display = 'none';
		$('playlist_name_dialog').style.display = 'block';
		$('playlist_name').value = playlist.jsonObj.name;
		$('playlist_description').value = playlist.jsonObj.description;
	},

	saveFromPlayer: function (playlist_object, onListSaved) {
		if (!playlist_object.loadedPlaylistName)
			this.saveFromPlayerAs (playlist_object, '', onSave);
		else {
			this.playlist_to_save = playlist_object;
			$('playlist_name').value = playlist_object.loadedPlaylistName;
			$('playlist_description').value = playlist_object.loadedPlaylistDescription;
			this.resaved_playlist = playlist_object.loadedPlaylistId;
			this.savePlaylistFormOK();
		}
		if (onListSaved)
			this._onListSaved = onListSaved;
	},

	saveFromPlayerAs: function (playlist_object, onListSaved) { // when in the playlist of a player is pressed save
		this.playlist_to_save = playlist_object;
		showBackground();
		$('playlist_name_dialog').style.display = 'block';
		$('playlist_name').value = $('playlist_description').value = '';

		/*if (playlist_object.loadedPlaylistName) {
			$('playlist_name').value = playlist_object.loadedPlaylistName;
			$('playlist_description').value = playlist_object.loadedPlaylistDescription;
		}*/
		if (playlist_object.loadedPlaylistName) {
			$('playlist_name').value = playlist_object.loadedPlaylistName;
			$('playlist_description').value = playlist_object.loadedPlaylistDescription;
		}
		if (onListSaved)
			this._onListSaved = onListSaved;
	},

	savePlaylistFormOK: function () {
		if (!this.renamed_playlist) // renamed playlists do not get the entire list of items passed on
			if (!this.playlist_to_save.items) return;
		// check for dublicate name, before saving
		var new_name = $('playlist_name').value;
		var new_description = $('playlist_description').value;

		var i = 0;

		var action = '';
		var plid = -1;
		if (this.renamed_playlist) {
			action = 'rename';
			plid = this.renamed_playlist.jsonObj.id;
			while (i < this.playlists.length) {
				if (this.playlists[i].jsonObj.name != new_name) i ++;
				else if (this.playlists[i].jsonObj.id == this.renamed_playlist.jsonObj.id) i ++
					else break;
			}
			if (i < this.playlists.length) {
				alert ('There is another playlist with the same name!');
				return;
			}
		} else
		if (this.resaved_playlist) {
			action = 'edit';
			plid = this.resaved_playlist;
		} else {
			while (i < this.playlists.length && this.playlists[i].jsonObj.name != new_name)
				i ++;
			if (i < this.playlists.length) {
				if (!confirm ('There is already a playlist with that name. Do you want to overwrite it?'))
					return;
				else {
					action = 'edit';
					plid = this.playlists[i].jsonObj.id;
				}
			} else {
				action = 'new';
				plid = "NULL";
			}
		}

		$('saving_playlist').style.display = 'block';
		// prepare the parameters of the request
		this.req_params = {action: action, name: new_name, description: new_description,  id: plid};
		var params = $H(this.req_params);
		var v = '', ids = '', ispr = '';
		if (action != 'rename') {
			this.req_params.videos = new Array ();
			for (i = 0; i < this.playlist_to_save.items.length; i ++) {
				this.req_params.videos.push (this.playlist_to_save.items[i].jsonObj);
				v += '&videos[' + i + ']=' + escape(VideoToJSONString(this.req_params.videos[i]));
				ids += '&ids[' + i + ']=' + this.req_params.videos[i].id;
				ispr += '&ispr[' + i + ']=' + (this.req_params.videos[i].isprivate?'1':'0');
			}
		}
		new Ajax.Request ('save_playlist.php', {
			method: "post",
			onSuccess: this.savePlaylist_handler.bind(this),
			parameters: params.toQueryString() + v + ids + ispr });
		urchinTracker('saved_playlists/' + action);
		this.showCount();
	},

	savePlaylist_handler: function (ajaxResponse) {
		$('saving_playlist').style.display = 'none';
		$('playlist_name_dialog').style.display = 'none';
		if (this.listOpened) {
			this.element.style.display = 'block';
		}
		hideBackground();
		// check the result, update the playlist array according to this.req_params;
		var t = ajaxResponse.responseText;
		var jsonObj = null;
		eval ('jsonObj = ' + t);
		if (jsonObj != null && jsonObj.errorid == 0) {
			/*this.req_params.id = jsonObj.id;
			this.noPlaylists.style.display = 'none';
			if (jsonObj.hash)
				this.req_params.hash = jsonObj.hash;
			if (this.req_params.action == 'new')
				this.addPlaylist(this.req_params);
			else
				this.updatePlaylist(this.req_params);*/
		} else {
			// error handling
		}
		this.renamed_playlist = null;
		this.resaved_playlist = null;
		this.loadPlaylists();

		if (this._onListSaved)
			this._onListSaved (jsonObj.id, $('playlist_name').value, $('playlist_description').value);

		$('playlist_name').value = '';
		$('playlist_description').value = '';

		/*this.showCount();
		this.fixScrolls();*/
	},

	savePlaylistFormCancel: function () {
		this.playlist_to_save = null;
		if (this.listOpened) {
			this.element.style.display = 'block';
		}
		hideBackground();
		$('playlist_name_dialog').style.display = 'none';
	},

	//
	addPlaylist: function (jsonObj) {
		var p = new SavedPlaylist(this, jsonObj);
		this.playlists.push (p);
		if (this.playlists.length == 1) Element.addClassName(p.element, 'first');
		p.setNumber(this.playlists.length);
		this.showCount();
		//this.fixScrolls();
	},

	updatePlaylist: function (jsonObj) {
		var i = 0;
		while (i < this.playlists.length && this.playlists[i].jsonObj.id != jsonObj.id)
			i ++;
		if (i < this.playlists.length) {
			this.playlists[i].update(jsonObj);
		}
		this.fixScrolls();
	},

	clearPlaylists: function () { // does not delete them from DB
		for (var i = this.playlists.length - 1; i >= 0; i --)
			this.playlists[i].remove();
		this.playlists.clear();
		this.showCount();
		this.fixScrolls();
		SavedPlaylistSelect.clearLists();
	},

	removePlaylist: function (list) { // this is called by the playlist, when the user clicks "Delete"
		urchinTracker('saved_playlists/delete');
		this.playlists = this.playlists.without(list);
		this.loadPlaylists();
		/*this.showCount();
		this.fixScrolls();*/

	},

	userHasLoggedIn: function () {
		//this.loadPlaylists();
		this.sortList(this.list_order_by);
	},

	userHasLoggedOut: function () {
		this.clearPlaylists();
	},
	showCount: function () {
		$('playlists_count').innerHTML = this.playlists.length;
	},
	fixScrolls: function () {
		this.scrollbar.update();
	},

	getListObjectById: function (id) {
		for (var i = 0, n = this.playlists.length; i < n; i ++)
			if (this.playlists[i].jsonObj.id == id)
				return this.playlists[i];
		return null;
	},

	getListById : function (id) {
		for (var i = 0, n = this.playlists.length; i < n; i ++)
			if (this.playlists[i].jsonObj.id == id)
				return this.playlists[i].jsonObj;
	}
}

var SavedPlaylistSelect = {
	initialize: function () {
		this.box = $('select_playlist_dialog');
		this.selectBox = $ST ('playlist_select_box');
		this.waitingImg = $('select_playlist_waiting');
	},
	loadLists: function () {
		this.clearLists();
		for (var i = 0, n = SavedPlaylists.playlists.length; i < n; i ++) {
			var opt = document.createElement ('option');
			opt.innerHTML = SavedPlaylists.playlists[i].jsonObj.name;
			opt.value = SavedPlaylists.playlists[i].jsonObj.id;
			this.selectBox.appendChild(opt);
		}
	},
	clearLists: function () {
		this.selectBox.innerHTML = '';
	},
	openBox: function (onOKHandler, onCancelHandler) {
		this.hideLoading();
		if (!logged_in) {
			showLoginOrRegisterForm ();
			return false;
		}
		if (SavedPlaylists.playlists.length == 0) {
			alert ('You have to create some playlists first');
			return false;
		}
		this.selectBox.selectedIndex = 0;
		this.onOKHandler = onOKHandler;
		this.onCancelHandler = onCancelHandler;
		showBackground();
		this.box.style.display = 'block';
		if (this.selectBox.focus) this.selectBox.focus();
		return true;
	},
	closeBox: function () {
		this.onCancelHandler = null;
		this.onOKHandler = null;
		this.hideLoading();
		hideBackground();
		this.box.style.display = 'none';
	},
	showLoading: function () {
		this.waitingImg.style.display = 'block';
	},
	hideLoading: function () {
		this.waitingImg.style.display = 'none';
	},
	onClickOK: function () {
		var selID = this.selectBox.getSelected();
		if (!selID) {
			alert ('Please, select some playlist!');
			return false;
		}
		if (this.onOKHandler)
			this.onOKHandler (selID);
	},
	onClickCancel: function () {
		if (this.onCancelHandler)
			this.onCancelHandler();
		this.closeBox();
	}
}