/* ----------------------------------------------------------------

HotKeys.js

	- because I hate reaching for my mouse

Quietly keeps track of key combinations and allows interface
for event binding.

---------------------------------------------------------------- */

// TODO : hotkey enabler/disabler (CTRL+SHIFT+EH/DH...)
// TODO : be sure keypressed is passed to result function (maybe not...)
// TODO : Have "fragile" states, ie, activate on state, deactivate when state goes away

var HotKeys = Class.create({
    initialize:function() {
        this.ctrl   	= false;
        this.shift  	= false;
        this.opt    	= false;
        this.stack  	= "";

		this.clamp 		= false;
		this.extant 	= false;
		this.hardclear 	= false;
    },
    
    translations:{
        //Enter
        _13:"ENTER",
        
        //Numpad
        _96:"0",
        _97:"1",
        _98:"2",
        _99:"3",
        _100:"4",
        _101:"5",
        _102:"6",
        _103:"7",
        _104:"8",
        _105:"9",
        _107:"+",_61:"+",_187:"+", //unifies these actions
        _109:"-",_189:"-"
    },
    
	disable:function() {
		this.clamp = true;
	},

    enable:function(hardclear) {
        
		if(this.clamp) {
			this.clamp = false;
			return;
		}

		this.hardclear = (hardclear ? true : false);

		if(this.extant) return;
		
		this.extant = true;
		
		var pass = this;

        document.observe("keyup", function(e) {

	   		if(pass.clamp) return;

            if(e.keyCode == 17)         {pass.ctrl   = false;pass.stack = "";}
            else if(e.keyCode == 16)    {pass.shift  = false;pass.stack = "";}
            else if(e.keyCode == 18)    {pass.opt    = false;pass.stack = "";}
            else if(pass.hardclear)     {pass.stack  = "";}

            pass.state();
            return;
        });
        document.observe("keydown", function(e) {
	    
			if(pass.clamp) return;
	
            if(e.keyCode == 17)         pass.ctrl   = true;
            else if(e.keyCode == 16)    pass.shift  = true;
            else if(e.keyCode == 18)    pass.opt    = true;
            else {
                if(pass.translations["_" + e.keyCode]) {
                    pass.stack += pass.translations["_" + e.keyCode];                    
    	        } else {
    	            pass.stack += String.fromCharCode(e.keyCode).toUpperCase();
    	        }
            }
            pass.state();
            return;
        });
		document.observe("mousedown", function(){
			pass.ctrl = false;
			pass.state();
		});
    },

    state:function() {

        if(this.ctrl)   ctr_text = "CTRL+";
        else            ctr_text = "";
        
        if(this.shift)  sft_text = "SHIFT+";
        else            sft_text = "";

        if(this.opt)    opt_text = "OPT+";
        else            opt_text = "";

        if(this.stack)  act_text = this.stack;
        else            act_text = "";

        pressed = ctr_text + sft_text + opt_text + act_text;

        if(this[pressed]) {
			if(this[pressed].toggle) {
				if(!this[pressed].toggleState)
				{
					this[pressed].toggleState = true;
					this[pressed].toggle.on();
				} else {
					this[pressed].toggleState = false;
					this[pressed].toggle.off();
				}
			} else {
				this[pressed]();
			}
		}
        this.stack = '';
    }
});

var KeyCombos = new HotKeys();
