/*
 * Copyright 2008-2009 Palm, Inc. All rights reserved.
 */

/**
 * @name history-assistant.js
 * @fileOverview The assistant for the History scene.
 */

/**
 * Constructor.
 * @param {PageAssistant} pageAssistant
 */
function HistoryAssistant(webPreferences) {
	this._webPreferences = webPreferences;
	this.historyStore = new HistoryStore({
		database: Mojo.Controller.appController.assistant.getDatabase()
	});

	this._chunkSize = 50;
}

HistoryAssistant.Menu = {

	Clear: {
		label: $L('Clear History'),
		command: 'clear-history-command'
	}
};

HistoryAssistant.prototype.setup = function() {

	try {
		this.controller.setupWidget('historyList', {
			itemTemplate:'history/history-entry',
			listTemplate:'history/history-container',
			itemsCallback:this._itemsCallback.bind(this)
		});

		this._onListSelectionHandler = this._onListSelection.bindAsEventListener(this);
		this._historyListWidget = this.controller.get('historyList');

		var appMenuModel = {
			visible: true,
			items: [
				MenuData.ApplicationMenu.ShowBookmarks,
				MenuData.ApplicationMenu.ShowHistory,
				HistoryAssistant.Menu.Clear
			]
		};

		this.controller.setupWidget(Mojo.Menu.appMenu, undefined, appMenuModel);
	}
	catch (e) {
		Mojo.Log.logException(e, 'HistoryAssistant#setup');
	}
};

HistoryAssistant.prototype.cleanup = function() {

};

HistoryAssistant.prototype.activate = function() {

	this._historyListWidget.addEventListener(Mojo.Event.listTap, this._onListSelectionHandler);

	// On an activation for a re-render of the contents.
	var len = this._historyListWidget.mojo.getLength();	
	var lir = this._historyListWidget.mojo.setLengthAndInvalidate(len);
};

HistoryAssistant.prototype.deactivate = function() {

	Mojo.Event.stopListening(this._historyListWidget, Mojo.Event.listTap, this._onListSelectionHandler);
};

/**
 * Called by the HistoryStore when it has finished successfully reading the
 * history from the database
 *
 * @param {HistoryList} historyList
 * @private
 */
HistoryAssistant.prototype._onHistoryReadSuccess = function(historyList, offset, limit) {

	var model = $A();
	for (var d = 0; d < historyList.days.length; d++) {

		var day = historyList.days[d];
		for (var i = 0; i < day.items.length; i++ ) {

			var item = day.items[i];
			item.dispUrl = UrlUtil.cleanup(item.url);
			if (!item.title || item.title.empty()) {
				item.title = item.dispUrl;
				item.dispUrl = '&nbsp;';
			}
			else {
				item.title = item.title.escapeHTML();
			}

			model.push(item);
		}
	}

	// Update the list with the new model and if required
	// setup the list to callback and to load more data.
	this._historyListWidget.mojo.noticeUpdatedItems(offset, model);
	newlen = this._historyListWidget.mojo.getLength();

	if (limit !== model.length || model.length === 0) {
		// No more to load - We ran out of data.
		this._historyListWidget.mojo.setLength(offset + model.length);

	} else {
		// Don't go backward in length!
		if (newlen <= (model.length + offset)) {
			this._historyListWidget.mojo.setLength(newlen + this._chunkSize);
		}
	}
};

/**
 * This callback is called by the URL search list to retrieve model objects to be
 * displayed in the list.
 *
 * @param {Object} listWidget	The widget to add the items to.
 * @param {Number} offset	The zero based item offset
 * @param {Number} count	The number of items to retrieve.
 *
 * @private
 */
HistoryAssistant.prototype._itemsCallback = function(listWidget, offset, count) {

	this.historyStore.getHistory(new HistoryList(),
		undefined,
		this._onHistoryReadSuccess.bind(this),
		function(msg, e) {
			Mojo.Log.error("Error reading history: %s.", e.toString());
		},
		offset,
		count);
};

HistoryAssistant.prototype._onListSelection = function(event) {

	var url = event.item.url;
	this.controller.stageController.popScene({
		type: 'history',
		payload: url
	});
};

/**
 * handle a menu command.
 */
HistoryAssistant.prototype.handleCommand = function(event) {

	try {
		switch (event.type) {

			case Mojo.Event.command:

				switch (event.command) {

					case MenuData.ApplicationMenu.ShowBookmarks.command:
						this._openBookmarkView();
						break;

					case HistoryAssistant.Menu.Clear.command:
						this._clearHistory();
						break;

					case Mojo.Menu.prefsCmd:
						this._openPreferencesView();
						break;

					case Mojo.Menu.helpCmd:
						this._showHelpCommand();
						break;
				}
				break;

			case Mojo.Event.commandEnable:

				// Standard Application Menu commands.
				if (event.command === Mojo.Menu.prefsCmd ||
				    event.command === Mojo.Menu.helpCmd) {

					event.stopPropagation(); // Enable the chosen menuitems
					return;
				}

				if (event.command === MenuData.ApplicationMenu.ShowHistory.command) {
					event.preventDefault();
					return;
				}

				break;
		}
	}
	catch (e) {
		Mojo.Log.logException(e, 'handleCommand');
	}
};

HistoryAssistant.prototype._openPreferencesView = function() {

	this.controller.stageController.pushScene('preferences', this._webPreferences);
};

HistoryAssistant.prototype._openBookmarkView = function() {

	this.controller.stageController.swapScene({
			name: 'bookmarks',
			transition: Mojo.Transition.crossFade
		},
		this._webPreferences);
};

HistoryAssistant.prototype._clearHistory = function(){

	var self = this;
	this.controller.showAlertDialog({
		onChoose: function(value) {
			if (value === 'ok') {
				// We also now clear the local history list.
				self.historyStore.deleteHistoryBefore(new Date(),
					function(){
						var lir = self._historyListWidget.mojo.setLengthAndInvalidate(0);
						self._historyListWidget.mojo.noticeRemovedItems(0, 0);
			
						// Persist the request to clear the session history
						self._webPreferences.ClearHistory = true;
						self._webPreferences.save();	
					},
					function(msg, e) {
						Mojo.Log.error("History delete failed: %s", msg);
					});
			}
		},
		title:$L('Clear History'),
		message:$L('Your browsing history will be permanently deleted.'),
		cancelable:true,
		choices:[
			{label:$L('Clear History'), value:'ok'},
			{label:$L('Cancel'), value:'cancel'}
		]
	});
};

HistoryAssistant.prototype._showHelpCommand = function() {

	// Launch the help system.
	AppAssistant.launchHelp();
};

