//
// KeyboardShortcuts.js
//
// Copyright 2008-2009 Palm, Inc.. All rights reserved.
//
// Keyboard shortcuts are contructed in the following way
// shortcuts = new KeyboardShorts();
// shortcuts.addShortcut({altKey:  true, which: Mojo.Char.b, command: callback0},
// shortcuts.addShortcut({ctrlKey: true, altKey: true, which: keyCode, command: callback1});
//
KeyboardShortcuts = Class.create({
   
	initialize: function() {
	
		// We manager the shortcuts as a simple hash.
		this.shortcuts = new Hash();
	},

	addShortcut: function(shortcut) {
	
		// Keep the shortcuts simple
		var nullShortcut = {
			ctrlKey: false,
			altKey:  false,
			metaKey: false,
			shift:   false,
			keyCode:   undefined,
			command: undefined};
	
		var newShortcut = Object.extend(nullShortcut, shortcut);
		var newHashKey = this._makeShortcutHashKey(newShortcut);
		if (!newHashKey.empty()) {
			Mojo.Log.info("Adding shortcut: " + newHashKey);
			this.shortcuts.set(newHashKey, newShortcut.command);
		}
	},

	isAShortcut: function(event) {
		return (this._findShortcutCommandForEvent(event) ? true : false);
	},
    
	_findShortcutCommandForEvent: function(event) {
	
		// Construct the shortcut in a predefined order by checking the 
		// event objects modifier flags
		var nullShortcut = {
			ctrlKey: false,
			altKey:  false,
			metaKey: false,
			shift:   false,
			keyCode:   undefined,
			command: undefined};
	
		var shortcut  = Object.extend(nullShortcut, {ctrlKey: event.ctrlKey,
			altKey: event.altKey,
			metaKey: event.metaKey,
			shift: event.shift,
			keyCode: event.keyCode});
		var key = this._makeShortcutHashKey(shortcut);
		var command = null;
		if (!key.empty()) {
			//Mojo.Log.info("SHORTCUTS: %o", this.shortcuts);
			command = this.shortcuts.get(key);
			if (typeof command !== 'function') {
				command = null;
			}
		}
	
		return command;        
	},

	// To execute on the command associated with the given event we contruct the
	// property name in a predefined way and look for the command value.
	invoke: function(event) {
	
		var command = this._findShortcutCommandForEvent(event);
		if (command) {
			// invoke the command
			Mojo.Log.info("Invoking shortcut!");
			command();
		}
	},
    
	_makeShortcutHashKey: function(shortcut) {
	
		//Mojo.Log.info("Making shortcut: %o", shortcut);
		var key = "";
		
		// We also check if at least one modifier is pressed.
		if ((!shortcut.ctrlKey) && 
			(!shortcut.altKey) &&  
			(!shortcut.metaKey)) {
			return "";
		}
		
		// Construct in a predefined order.
		if (shortcut.ctrlKey) {
			key += "CTRL+";
		}
		if (shortcut.altKey) {
			key += "ALT+";
		}
		if (shortcut.shiftKey) {
			key += "SHIFT+";
		}
		if (shortcut.metaKey) {
			key += "META+";
		}
		
		// Add the keycode (capitalize it by default.)
		key += String.fromCharCode(shortcut.keyCode).capitalize();
		
		return key;
	}    
});
