var probabilityByArticle = new Array();
var visibleArticleIds = new Array();
var targetProbabilityByArticle = new Object();
var probabilityModifyInterval = null;
var lastSelectedArticleId = 0;
var forcedSelectedArticleId = 0;
var readStatusController = new ReadStatusController();

function selectTopArticle()
{
	if (readStatusController.wantsFlush())
		readStatusController.flush();

	var pageScrollTop = document.documentElement.scrollTop;

	if (forcedSelectedArticleId > 0 && isArticleHeaderInView(forcedSelectedArticleId))
		return;
		
	forcedSelectedArticleId = 0;

	for(var i = 0; i < visibleArticleIds.length; i++) {
		var id = visibleArticleIds[i];
		var articleHeaderElement = document.getElementById('Article_' + id);

		if (articleHeaderElement == null)
			continue;

		var offsetFromScrollTop = articleHeaderElement.offsetTop - pageScrollTop;

		if (!readStatusController.isSet(id))
			readStatusController.setRead(id, true);

		if (offsetFromScrollTop > -10) {
			setSelectedArticle(id);
			break;
		}
	}
}

// Begin our interval immeditately without waiting for our body to completely load
setInterval('selectTopArticle()', 30);

function setReadUpToArticleIfUnset(articleId)
{
	if (readStatusController == null)
		return;
		
	for(var i = 0; i < visibleArticleIds.length; i++) {
		var id = visibleArticleIds[i];
		
		if (!readStatusController.isSet(id))
			readStatusController.setRead(id, true);

		if (id == articleId)
			break;
	}
}

function isArticleHeaderInView(id)
{
	var articleHeaderElement = document.getElementById('Article_' + id);
	if (articleHeaderElement == null)
		return false;
	
	var pageScrollTop = document.documentElement.scrollTop;
	var offsetFromScrollTop = articleHeaderElement.offsetTop - pageScrollTop;
	var usablePageHeight = document.documentElement.clientHeight;
	
	var inView = offsetFromScrollTop > 0 && offsetFromScrollTop < usablePageHeight;
	
	return inView;
}

function forceSelectedArticle(id)
{
	forcedSelectedArticleId = id;
	setSelectedArticle(id);
	setReadUpToArticleIfUnset(id);
}

function setSelectedArticle(id)
{
	var selectElement = document.getElementById('SelectedArticle_' + id);
	if (selectElement == null)
		return;
		
	selectElement.className = 'Selected';

	if (lastSelectedArticleId > 0 && lastSelectedArticleId != id) {
		var previousElement = document.getElementById('SelectedArticle_' + lastSelectedArticleId);
		if (previousElement == null)
			return;

		previousElement.className = '';
	}

	lastSelectedArticleId = id;
}

function setArticleRead(id, hasRead)
{
	if (readStatusController == null)
		return;

	readStatusController.setRead(id, hasRead);
}

function onReadStatusClick(id) 
{
	var readStatusButton = document.getElementById('ReadStatusButton_' + id);

	readStatusController.setRead(id, readStatusButton.className != 'Read');
}

function init(disableSuperScroll) {
	if(!disableSuperScroll && document.getElementsByClassName('Article').length > 0)
		initSuperScroll(); // assume that the presence of a div with class 'Article' means we're on a super-scroll page
		
	setTimeout(function() {
		var headers = document.getElementsByClassName('ArticleHeaders');
		for(var i=0; i<headers.length; i++)
			if(headers[i].getAttribute('rel').substr(0,'PreToggle|'.length) == 'PreToggle|')
				ToggleArticleMode(parseInt(headers[i].getAttribute('rel').split('|')[1]));
	}, 100);
}

function updateProbability()
{
	var processed = 0;
	for(var articleId in targetProbabilityByArticle) {
		if (targetProbabilityByArticle[articleId] == null)
			continue;
		stepProbability(articleId, targetProbabilityByArticle[articleId]);
		processed++;
	}
	
	if (processed <= 0) {
		clearInterval(probabilityModifyInterval);
		probabilityModifyInterval = null;
	} else {
		if (probabilityModifyInterval == null)
			probabilityModifyInterval = setInterval(updateProbability, 50);
	}
}

function stepProbability(id, targetProbability)
{
	var currentProbability = probabilityByArticle[id];
	
	if (currentProbability == undefined || currentProbability == targetProbability) {
		refreshStatusText(id, targetProbability);
		targetProbabilityByArticle[id] = null;
		return;
	}

	var increment = 0.05;
	
	// Move closer to our target probability from our
	// current probability in this tick by one increment step
	var delta = Math.abs(targetProbability - currentProbability);
	if (increment > delta)
		increment = delta;
		
	if(targetProbability < currentProbability)
		increment = -increment;

	var newProbability = currentProbability + increment;

	if (newProbability > 1)
		newProbability = 1;
	else if (newProbability < 0)
		newProbability = 0;

	probabilityByArticle[id] = newProbability;

	setProbability(id, newProbability);
}

function refreshStatusText(articleId, newProbability)
{
	var div = $('Article_' + articleId);
	var targetProbability = newProbability * 100;
	//bad or worse
	if (targetProbability >= GetBadThreshold()) {
		if (!div.manuallyExpandedOnce)
			SetArticleMode(articleId,ArticleMode.Minimal);
		if ($('HintText_Rerate_' + articleId))
			$('HintText_Rerate_' + articleId).innerHTML = "( We think you won't like this article. )";
		if ($('CollapseExplanation_' + articleId)) {
			$('CollapseExplanation_' + articleId).className = "FullCollapsedExplanation";
			$('CollapseExplanation_' + articleId).style.display = 'inline';
		}
	}
	//good or better
	else if (targetProbability <= GetGoodThreshold()) {
		if (!div.manuallyExpandedOnce)
			SetArticleMode(articleId,ArticleMode.Full);
		if ($('CollapseExplanation_' + articleId))
			$('CollapseExplanation_' + articleId).style.display = 'none';
	}
	//in between
	else {
		if (!div.manuallyExpandedOnce)
			SetArticleMode(articleId,ArticleMode.Partial);
		if ($('HintText_Rerate_' + articleId))
			$('HintText_Rerate_' + articleId).innerHTML = "( Unsure about whether or not you'll like this article. )";
		if ($('CollapseExplanation_' + articleId)) {
			$('CollapseExplanation_' + articleId).className = "PartCollapsedExplanation";
			$('CollapseExplanation_' + articleId).style.display = 'inline';
		}
	}
	
}

function setProbability(id, probability)
{
	var div = document.getElementById('PercentageBar_' + id);
	
	if (div == null)
		return;
	
	var containerDiv = document.getElementById('ProbabilityBar_' + id);
	var valueDiv = document.getElementById('ProbabilityValue_' + id);

	var red = 0, green = 0;

	var goodWidth = 100 - probability * 100;
	if (goodWidth == undefined || goodWidth < 0)
		goodWidth = 0;

	if (goodWidth >= 50) {
		green = 255;
		red = 255 * (100 - goodWidth) / 50;
		red = red - red % 1;
	} else {
		red = 255;
		green = 255 * goodWidth / 50;
		green = green - green % 1;
	}

	var resultProbability = goodWidth - goodWidth % 1;

	if (goodWidth < 1) {
		div.className = "PercentageBar_Empty";
		div.style.width = "100%";
		div.style.backgroundColor = "transparent";
	}
	else {
		div.className = "PercentageBar";
		div.style.width = goodWidth + "%";
		div.style.backgroundColor = "rgb(" + red + ", " + green + ", 0)";
	}
	containerDiv.title = "The probability that you will like this article is " + resultProbability + "%";
	valueDiv.innerHTML = resultProbability + "%";
}

function ratingResult(isGood,id) {
	$('RatingLoadingIndicator_'+id).style.display = 'none';
	
	$('RatingButton_Like_'+id).style.display = isGood ? 'none' : 'block';
	$('RatingButton_Like_NoSelection_'+id).style.display = 'none';
	$('RatingButton_LikeSelected_'+id).style.display = isGood ? 'block' : 'none';
	$('RatingButton_LikeDisabled_'+id).style.display = 'none';
	
	$('RatingButton_Dislike_'+id).style.display = isGood ? 'block' : 'none';
	$('RatingButton_Dislike_NoSelection_'+id).style.display = 'none';
	$('RatingButton_DislikeSelected_'+id).style.display = isGood ? 'none' : 'block';
	$('RatingButton_DislikeDisabled_'+id).style.display = 'none';
	
	var element = $('CollapseExplanation_'+id);
	if(element) {
		element.style.display = isGood ? 'none' : '';
		element.className = 'FullCollapsedExplanation';
	}
	
	if ($('HintText_Rerate_' + id))
		$('HintText_Rerate_' + id).innerHTML = "( You've indicated that you aren't interested in this article. )";
	
	SetArticleMode(id, isGood ? ArticleMode.Full: ArticleMode.Minimal);
	
	// Request the updated probabilities of our visible articles
	UpdateVisibleArticleProbabilities();
}

function onBeforeRating(id) {
	$('RatingLoadingIndicator_'+id).style.display = 'block';
	
	$('RatingButton_Like_'+id).style.display = 'none';
	$('RatingButton_Like_NoSelection_'+id).style.display = 'none';
	$('RatingButton_LikeSelected_'+id).style.display = 'none';
	$('RatingButton_LikeDisabled_'+id).style.display = 'block';
	
	$('RatingButton_Dislike_'+id).style.display = 'none';
	$('RatingButton_Dislike_NoSelection_'+id).style.display = 'none';
	$('RatingButton_DislikeSelected_'+id).style.display = 'none';
	$('RatingButton_DislikeDisabled_'+id).style.display = 'block';
	
	var bar = $('ProbabilityBar_'+id);
	if(bar) bar.style.display = 'none';
}

function RateArticle(articleId, isGood)
{
	var rating = isGood ? 5 : 1;
	
	forceSelectedArticle(articleId);
	
	onBeforeRating(articleId);

	ViewArticles.Rate(articleId, rating, function(data) {
		ratingResult(isGood, articleId);
	});
}

function UpdateVisibleArticleProbabilities()
{
	ViewArticles.GetUpdatedArticleProbabilities(visibleArticleIds, function(data) {
		targetProbabilityByArticle = new Object();

		for(var id in data)
			targetProbabilityByArticle[id] = data[id];

		updateProbability();
	});	
}

function queryString(arg) {
	var qn = location.href.indexOf('?');
	if(qn == -1 || qn == location.href.length - 1) return null;
	var qs = location.href.substring(qn+1);
	var arr = qs.split(/&/g);
	for(var i=0; i<arr.length; i++) {
		var nvp = arr[i].split(/=/);
		if(nvp.length == 2 && nvp[0] == arg)
			return unescape(nvp[1]);
	}
	return null;
}

var collapseArticles;

function getPage()
{
	var feedId = queryString('feedId');
	if(!feedId) feedId = queryString('FeedId');
	if(feedId != null && feedId != '')
		try { feedId = parseInt(feedId); }
		catch(e) { feedId = 0; }
	else
		feedId = 0;
	
	if (collapseArticles == undefined)
		collapseArticles = true;

	var page = {
		feedId: feedId,
		number: 1,
		size: 10,
		loading: false,
		searchText: queryString('searchText'),
		filter: queryString('filter'),
		collapseArticles: collapseArticles
		
	};
	
	return page;
}

function updateArticleDisplay(div)
{
	var page = getPage();
	
	// Assume that the presence of a div with id 'Search' means we're on a search page
	var isSearch = document.getElementById('Search'); 

	if (isSearch) {
		ViewArticles.GetArticles(page.searchText, page.filter, page.number, page.size, function(data) {
			var content = data["content"].strip();

			if(content.length == 0) {
				div.style.display = 'none';
				return;
			}
			
			div.className = '';
			div.innerHTML = content;
			page.loading = false;
			
			eval(data["javascript"]);

			// We did not have articles shown before, need to now initialize super scroll
			initSuperScroll();
		});
	} else {
		ViewArticles.GetFeeds(page.feedId, page.number, page.size, page.collapseArticles, function(data) {
			var content = data["content"].strip();
			
			if(content.length == 0) {
				div.style.display = 'none';
				return;
			}			
			
			div.className = '';
			div.innerHTML = content;

			eval(data["javascript"]);

			// We did not have articles shown before, need to now initialize super scroll
			initSuperScroll();
		});
	}
}


function initSuperScroll() {
	var getScrollPos, getWindowHeight;

	if (typeof(window.innerWidth) == 'number')
		getWindowHeight = function() { return window.innerHeight; }
	else if (document.documentElement && document.documentElement.clientHeight)
		getWindowHeight = function() { return document.documentElement.clientHeight; }
	else if (document.body && document.body.clientHeight)
		getWindowHeight = function() { return document.body.clientHeight; }
	else
		getWindowHeight = function() { return 10000; }

	if (window.pageYOffset != undefined)
		getScrollPos = function() { return window.pageYOffset; };
	else if (document.documentElement.scrollTop != undefined)
		getScrollPos = function() { return document.documentElement.scrollTop; };
	else if (document.body.pageYOffset != undefined)
		getScrollPos = function() { return document.body.pageYOffset; };
	else
		getScrollPos = function() { return 0; };
		
	var page = getPage();

	function addMore() {
		if(page.loading)
			return;

		page.loading = true;
		page.number++;
		var div = document.createElement('div');
		div.innerHTML = 'Loading more articles...';
		div.className = 'loading_more_articles';
		var divs = document.getElementsByClassName('Article');
		
		divs[divs.length-1].parentNode.appendChild(div);
		var isSearch = document.getElementById('Search'); // assume that the presence of a div with id 'Search' means we're on a search page
		if (isSearch) {
			ViewArticles.GetArticles(page.searchText, page.filter, page.number, page.size, function(data) {
				var content = data["content"].strip();
				
				if(content.length == 0) {
					div.style.display = 'none';
					return;
				}
				div.className = '';
				div.innerHTML = removeDuplicateArticles(content);
				page.loading = false;
				
				eval(data["javascript"]);
			});
		}
		else {
			ViewArticles.GetFeeds(page.feedId, page.number, page.size, page.collapseArticles, function(data) {
				var content = data["content"].strip();

				if(content.length == 0) {
					div.style.display = 'none';
					return;
				}
				div.className = '';
				div.innerHTML = removeDuplicateArticles(content);
				page.loading = false;
				
				eval(data["javascript"]);
			});
		}
	}
	
	setInterval(function() {
		var winheight = getWindowHeight();
		var threshold = document.body.offsetHeight - winheight - 900;
		if(getScrollPos() >= threshold)
			addMore();
	}, 20);
	
}

function removeDuplicateArticles(sourceHTML) {
	var innerdiv = document.createElement('div');
	innerdiv.innerHTML = sourceHTML;
	var removethese = [];
	for(var i=0; i<innerdiv.childNodes.length; i++) {
		var articleDiv = innerdiv.childNodes[i];
		if(document.getElementById(articleDiv.id) != null)
			removethese[removethese.length] = articleDiv;
	}
	for(var i=0; i<removethese.length; i++)
		innerdiv.removeChild(removethese[i]);
		
	return innerdiv.innerHTML;
}

ArticleMode = {
	Full: 2,
	Partial: 1,
	Minimal: 0,
	Hidden: -1
}

function SetArticleMode(articleId, mode) {
	var div = $('Article_' + articleId);
	var cssClass;
	switch(mode) {
		case ArticleMode.Minimal:
			div.isArticleExpanded = false;
			cssClass = 'ArticleCollapsed';
			setTimeout(function(){ $('ArticleInfo_'+articleId).style.display = 'inline'; $('ArticleInfo_'+articleId).style.display = 'block'; }, 10);
			break;
		case ArticleMode.Partial:
			div.isArticleExpanded = false;
			cssClass = 'ArticleNotSure';
			break;
		default:
			cssClass = 'ArticleGood';
			div.isArticleExpanded = true;
			setTimeout(function(){ $('ArticleInfo_'+articleId).style.display = 'inline'; $('ArticleInfo_'+articleId).style.display = 'block'; }, 10);
			break;
	}
	div.className = 'Article ' + cssClass;
}

function ToggleArticleMode(articleId) {
	var div = $('Article_' + articleId);
	var main = $('MainContent');
	
	div.manuallyExpandedOnce = true;
	if (div.hasClassName("ArticleCollapsed"))
		SetArticleMode(articleId, ArticleMode.Full);
	else if ((main.hasClassName("BadPresExpanded")) && (div.hasClassName("ArticleNotSure")))
		SetArticleMode(articleId, ArticleMode.Minimal);
	else if (div.hasClassName("ArticleNotSure"))
		SetArticleMode(articleId, ArticleMode.Full);
	else 
		SetArticleMode(articleId, ArticleMode.Minimal);
		
	forceSelectedArticle(articleId);
}

function ToggleArticleModeIfCollapsed(articleId, event) {
	var div = $('Article_' + articleId);
	if(div.hasClassName('ArticleBad') || div.hasClassName('ArticleNotSure') || div.hasClassName('ArticleCollapsed'))
		ToggleArticleMode(articleId);
}

function EnsureLinkFromExpanded(articleId)
{
	var div = $('Article_' + articleId);
	
	if (div.hasClassName("ArticleCollapsed"))
		return false;
		
	StopEventBubbling(window.event);
	return true;
}

function SetBadArticleDisplay()
{
	document.getElementById("BadArticleDisplaySaving").style.display = "inline";
	var option = 0;
	var i = 0;
	for (i = 0; i < $("BadArticleDisplayOptions").BadArticleDisplay.length; i++) {
		if ($("BadArticleDisplayOptions").BadArticleDisplay[i].checked) {
			option = $("BadArticleDisplayOptions").BadArticleDisplay[i].value;
			break;
		}
	}
	Customer.SetBadArticleDisplayOptions(option, function(data) {
		if (data != null) {
			document.getElementById("BadArticleDisplayOptionsBox").style.display = "none";
		}
	});	
}

function StopEventBubblingIfExpanded(articleId, e)
{
	var div = $('Article_' + articleId);
	
	if (!div || div.hasClassName("ArticleCollapsed"))
		return;

	StopEventBubbling(e);
}

function StopEventBubbling(e) {
	if(!e) e = window.event;
	if(e.stopPropogation)
		e.stopPropogation();
	else
		e.cancelBubble = true;
}

function GetBadThreshold()
{
	if (typeof(badThreshold) == "undefined")
		return 70;
	return badThreshold;
}

function GetGoodThreshold()
{
	if (typeof(goodThreshold) == "undefined")
		return 30;
	return goodThreshold;
}
