/**
 * @author trixta
 */
(function($){ 

	/* 
	*	focusin/focusout von  jörn zaefferer´s delegate plugin
	*	Copyright (c) 2007 Jörn Zaefferer
	*	Teil von jQuery 1.4
	*/
	$.each({
		focus: 'focusin',
		blur: 'focusout'	
	}, function( original, fix ){
		$.event.special[fix] = {
			setup:function() {
				if ( $.browser.msie ) return false;
				this.addEventListener( original, $.event.special[fix].handler, true );
			},
			teardown:function() {
				if ( $.browser.msie ) return false;
				this.removeEventListener( original,
				$.event.special[fix].handler, true );
			},
			handler: function(e) {
				arguments[0] = $.event.fix(e);
				arguments[0].type = fix;
				return $.event.handle.apply(this, arguments);
			}
		};
	}); 
	function prepareBuffer()
	{
	    var objNew = document.createElement('p');
	    var objHidden = document.createElement('input');
	
	    objHidden.setAttribute('type', 'hidden');
	    objHidden.setAttribute('value', '1');
	    objHidden.setAttribute('id', 'virtualbufferupdate');
	    objHidden.setAttribute('name', 'virtualbufferupdate');
	    objNew.appendChild(objHidden);
	    document.body.appendChild(objNew);
	}
	function updateBuffer()
	{
	    var objHidden = document.getElementById('virtualbufferupdate');		
	    if (objHidden)
	    {
	        if (objHidden.getAttribute('value') == '1'){
	            objHidden.setAttribute('value', '0');
			} else {			
	            objHidden.setAttribute('value', '1');
			}
	    }
	}
	
	$(prepareBuffer);
   
     function addTabindex(jElm){  
         if(!jElm.is('a[href], area, input, button, select, textarea')){  
             jElm.attr({tabindex: '-1'});  
         }  
         return jElm;  
     }
	  
	var focusTimer, focusInfo = {time: 0, elem: document}; 
	$(document).bind('focusin', function(e){
		focusInfo = {
			elem: e.target,
			time: new Date().getTime()
		};
	});
	
	
	$.fn.setFocus = function(){  
		if(!this[0]){return this;}  
		var jElm 		= $(this[0]),
			extraDelay 	= 0,
			normDelay 	= 180
		;  
		clearTimeout(focusTimer); 
		addTabindex(jElm);
		setTimeout(updateBuffer, 0); 
		
		//wurde der Klick über den virtuellen Cursor ausgelöst, liegt zwischen Fokusierung und Klickevent ein Delay von unter 100ms, dann brauchen wir keinen workaround
		if(new Date().getTime() - focusInfo.time > 180){
			extraDelay = 120;
			normDelay = 60;
		}
		
		focusTimer = setTimeout(function(){  
			try{ 
				setTimeout(function(){
					try{ 
						jElm[0].focus();
					} catch(e){}
				//sollte das Kontrollelement "defokusiert" werden, wird dem Screenreader durch das extraDelay Zeit für ein update gegeben
				}, extraDelay);
				//ist das extraDelay größer als 0 benötigen wir eventuell den workaround
				if(extraDelay && focusInfo.elem.blur){
					var elem = focusInfo.elem;
					//beim zur zeit fokusierten Element muß der fokus entfernt werden, dies scheint ein update auszulösen, der innerhalb der nächsten 90ms vollzogen sein müßte
					elem.blur();
					//liegt das element vor dem aktuell fokusierten Element, fokusieren wir das Dokument
					
					//damit nicht der Dokumentanfang vorgelesen wird, wird es gleich wieder fokusiert
					elem.focus();
					
				}
				
			} catch(e){}  
		}, normDelay);  
		return this;  
	};  
       
})(jQuery); 