Ext.ux.SpinTrigger = Ext.extend(Ext.form.TwinTriggerField, {
  trigger1Class: 'spinTrigUp',
  trigger2Class: 'spinTrigDown'
  
});
Ext.reg('spintrigger',Ext.ux.SpinTrigger);

Ext.ux.TimeSpinner = Ext.extend(Ext.Panel, {
  border: false,
  cls: 'timespinner',
  defaults: {width: 23, border:true, bodyStyle: 'border: none'},
  decNum : function(timeField){
    if(timeField.getValue() == timeField.minNumStr){
      timeField.setValue(timeField.maxNumStr);
    } else {
      timeField.setValue(this.numLeadZero(timeField.getValue()-1));
    }  
  },
  incNum : function(timeField){
      if(timeField.getValue() == timeField.maxNumStr){
        timeField.setValue(timeField.minNumStr);
      } else {
        num = parseInt(timeField.getValue(), 10)+1;
        timeField.setValue(this.numLeadZero(num));

      }
  },
  numLeadZero : function(num){
    if (num < 10){
      return ('0' + num);
    }
    return num;
  },
  updateValue : function(){
    this.hour = this.items.items[0].getValue();
    this.minute = this.items.items[2].getValue();
    if (this.seconds) {
      this.second = this.items.items[4].getValue();
      this.tod = this.items.items[5].getValue();
    } else {
      this.tod = this.items.items[3].getValue();
    }
    this.value = this.hour + ':' + this.minute + ((this.seconds)?':' +this.second:'') + ' ' + this.tod;
    this.items.last().setValue(this.value, true);
  },
  constructor: function(config){
        Ext.ux.TimeSpinner.superclass.constructor.apply(this, arguments);
        var fieldListeners = {
          keyup : function(timeField, e){
            if (timeField.getValue() > parseInt(timeField.maxNumStr,10)){
              timeField.setValue(timeField.maxNumStr);
            }
          },
          invalid : function(timeField){
            if (timeField.getValue().length == 1 && parseInt(timeField.getValue(),10) >= parseInt(timeField.minNumStr,10)){
              timeField.setValue('0' + timeField.getValue());
            } else {
              timeField.setValue(timeField.maxNumStr);
            }
          },      
          change : function(timeField){
            if (timeField.getValue().length == 1 && parseInt(timeField.getValue(),10) >= parseInt(timeField.minNumStr,10)){
              timeField.setValue('0' + timeField.getValue());
            } else if(parseInt(timeField.getValue(),10) < parseInt(timeField.minNumStr,10)) {
              timeField.setValue(timeField.maxNumStr);
            }
            this.ownerCt.updateValue();
          },
          focus : function(){
            this.ownerCt.curTarget = this;
          },
          render: function(){
            this.keyNav = new Ext.KeyNav(this.el, {
      			"up" : function(e){
      				e.preventDefault();
      				this.ownerCt.incNum(this);
      			},
      
      			"down" : function(e){
      				e.preventDefault();
      				this.ownerCt.decNum(this);
      			},
      
      			"pageUp" : function(e){
      				e.preventDefault();
      				this.ownerCt.incNum(this);
      			},
      
      			"pageDown" : function(e){
      				e.preventDefault();
      				this.ownerCt.decNum(this);
      			},
      
      			scope : this
      		});          
          }
        };
        this.add({xtype:'textfield', submitValue: false, cls: 'tsLeftInp', allowDecimals: false, allowNegative: false, maxNumStr: '12', minNumStr: '01', enableKeyEvents: true, regex: /[0-1][0-9]*/ ,value: '12', listeners: fieldListeners, autoCreate: {maxlength: '2', tag: "input", type: "text"}});
        this.items.items[0].addListener('render',function(){
          if (this.ownerCt.init != undefined && this.ownerCt.init.hour != undefined && parseInt(this.ownerCt.init.hour,10) >= parseInt(this.minNumStr,10) && parseInt(this.ownerCt.init.hour,10) <= parseInt(this.maxNumStr,10)){
            this.setValue(this.ownerCt.numLeadZero(this.ownerCt.init.hour));
          }
        });
        this.add({xtype: 'textfield', value: ':', width: 4, readOnly: true});
        this.add({xtype:'textfield', submitValue: false, cls: 'tsSec', allowDecimals: false, allowNegative: false, maxNumStr: '59', minNumStr: '00', enableKeyEvents: true, regex: /[0-5][0-9]*/ ,value: '00', listeners: fieldListeners, autoCreate: {maxlength: '2', tag: "input", type: "text"}});
        this.items.items[2].addListener('render',function(){
          if (this.ownerCt.init != undefined && this.ownerCt.init.minute != undefined && parseInt(this.ownerCt.init.minute,10) >= parseInt(this.minNumStr,10) && parseInt(this.ownerCt.init.minute,10) <= parseInt(this.maxNumStr,10)){
            this.setValue(this.ownerCt.numLeadZero(this.ownerCt.init.minute));
          }
        });
        if (this.seconds){
          this.add({xtype: 'textfield', value: ':', width: 4, readOnly: true});
          this.add({xtype:'textfield', submitValue: false, cls: 'tsSec', allowDecimals: false, allowNegative: false, maxNumStr: '59', minNumStr: '00', enableKeyEvents: true, regex: /[0-5][0-9]*/ ,value: '00', listeners: fieldListeners, autoCreate: {maxlength: '2', tag: "input", type: "text"}});                      
          this.items.items[4].addListener('render',function(){
          if (this.ownerCt.init != undefined && this.ownerCt.init.second != undefined && parseInt(this.ownerCt.init.second,10) >= parseInt(this.minNumStr,10) && parseInt(this.ownerCt.init.second,10) <= parseInt(this.maxNumStr,10)){
            this.setValue(this.ownerCt.numLeadZero(this.ownerCt.init.second));
          }
        });
        }
        TOD = new Ext.ux.SpinTrigger({xtype:'spintrigger', submitValue: false, autoWidth: false, cls: 'tsTod', isTimeOfDay: true,
        click1 : function() {
			if (!this.disabled) {
			  if (this.ownerCt.curTarget == undefined){
				this.ownerCt.curTarget = this.ownerCt.items.items[0];
			  }
			  if (!this.ownerCt.curTarget.isTimeOfDay){
				this.ownerCt.incNum(this.ownerCt.curTarget);
			  } else if (this.ownerCt.curTarget.isTimeOfDay){
				this.ownerCt.curTarget.switchTime(this.ownerCt.curTarget);
			  }
			  this.ownerCt.curTarget.focus();
			  this.ownerCt.updateValue();
			}
        },
        click2 : function() {
			if (!this.disabled) {
			  if (this.ownerCt.curTarget == undefined){
				this.ownerCt.curTarget = this.ownerCt.items.items[0];
			  }
			  if (!this.ownerCt.curTarget.isTimeOfDay){
				this.ownerCt.decNum(this.ownerCt.curTarget);
			  } else if (this.ownerCt.curTarget.isTimeOfDay){
				this.ownerCt.curTarget.switchTime(this.ownerCt.curTarget);
			  }
			  this.ownerCt.curTarget.focus();
			  this.ownerCt.updateValue();
			}
        },
        value: 'AM', maskRe: /[AM]/, enableKeyEvents: true, 
        listeners: {
          keypress : function(timeField,e){
            key = e.getKey();
            if (key == e.A || key == 97){
              timeField.setValue('AM');
            } else if (key == e.P || key == 112){
              timeField.setValue('PM');
            }
            this.ownerCt.updateValue();
          },
          focus : function(timeField){
            timeField.ownerCt.curTarget = timeField;
          },
          render : function(){
            if (this.ownerCt.init != undefined && this.ownerCt.init.tod && (this.ownerCt.init.tod.toUpperCase() == "AM" || this.ownerCt.init.tod.toUpperCase() == "PM")){
              this.setValue(this.ownerCt.init.tod);
            }
            this.ownerCt.updateValue();
            
            this.repeater1 = new Ext.util.ClickRepeater(this.triggers[0]);
            this.repeater1.on("click", this.click1, this, {preventDefault:true});
            this.repeater2 = new Ext.util.ClickRepeater(this.triggers[1]);
            this.repeater2.on("click", this.click2, this, {preventDefault:true});        
            this.triggers[0].on("mouseover", function() {this.triggers[0].addClass('spinTrigUpOver');}, this, {preventDefault:true});
            this.triggers[1].on("mouseover", function() {this.triggers[1].addClass('spinTrigDownOver');}, this, {preventDefault:true});
            this.triggers[0].on("mouseout", function() {this.triggers[0].removeClass('spinTrigUpOver');}, this, {preventDefault:true});
            this.triggers[1].on("mouseout", function() {this.triggers[1].removeClass('spinTrigDownOver');}, this, {preventDefault:true});
              
            this.keyNav = new Ext.KeyNav(this.el, {
        			"up" : function(e){
        				e.preventDefault();
        				this.click1();
        			},
        
        			"down" : function(e){
        				e.preventDefault();
        				this.click2();
        			},
        
        			"pageUp" : function(e){
        				e.preventDefault();
        				this.click1();
        			},
        
        			"pageDown" : function(e){
        				e.preventDefault();
        				this.click2();
        			},
        
        			scope : this
      		});   
            
        },
        afterrender : function(){
          TODDiv = this.getEl().findParent('div',null,true);
          TODDiv.setWidth(40);
          TODDiv.addClass('floatLeft');
        }           
      },
      switchTime : function(timeField) {
        if (timeField.getValue().toUpperCase() == "AM"){
            timeField.setValue('PM');
         } else {
            timeField.setValue('AM');
         }
         this.ownerCt.updateValue();
      }
      });
      this.add(TOD);
      this.setWidth((this.seconds)?117:91);
      
      this.add({xtype:'textfield', timeValue: true, hidden: true, setValue: function(value, isUpdate) {
		Ext.form.TextField.superclass.setValue.apply(this, arguments);
		  if (!isUpdate) { this.ownerCt.setTimeByStr(value); }
		  return this;
			}, name: ((this.name == undefined)?this.id:this.name), 
      listeners: {
        render: function(){
          this.ownerCt.updateValue();
        },
        disable: function(){
			for (i = 0; i < this.ownerCt.items.length; i++){
				if (this.ownerCt.items.items[i].timeValue === undefined){
					this.ownerCt.items.items[i].disable();
				}
			}
		},
        enable: function(){
			for (i = 0; i < this.ownerCt.items.length; i++){
				if (this.ownerCt.items.items[i].timeValue === undefined){
					this.ownerCt.items.items[i].enable();
				}
			}
		}		
      }
      });
  },
  setHour : function(hour){
 if (hour >= parseInt(this.items.items[0].minNumStr,10) && hour <= parseInt(this.items.items[0].maxNumStr,10)){
    this.items.items[0].setValue(this.numLeadZero(hour));
    }
    this.updateValue();
  },
  setMinute : function(minute){
 if (minute >= parseInt(this.items.items[2].minNumStr,10) && minute <= parseInt(this.items.items[2].maxNumStr,10)){  
    this.items.items[2].setValue(this.numLeadZero(minute));
    }
    this.updateValue();
  },
  setSecond : function(second){
    if (this.seconds) {
      if (second >= parseInt(this.items.items[4].minNumStr,10) && second <= parseInt(this.items.items[4].maxNumStr,10)){    
        this.items.items[4].setValue(this.numLeadZero(second));
      }
      this.updateValue();
    } 
  },
  setTOD : function(tod){
    this.items.items[this.items.length-2].setValue(tod);
    this.updateValue();
  },
  setTime : function(hour,minute,seconds){
    if (this.seconds){
      this.setHour(hour);
      this.setMinute(minute);
      this.setSecond(seconds); 
    }  
  },
  setTimeByStr : function(timeStr){
    if (timeStr != null){
      timeArray = timeStr.split(/:|\s/);
      if (timeArray.length == 3){
        this.setHour(parseInt(timeArray[0],10));
        this.setMinute(parseInt(timeArray[1],10));
        this.setTOD(timeArray[2]); 
      } else if (timeArray.length == 4 && this.seconds){
        this.setHour(parseInt(timeArray[0],10));
        this.setMinute(parseInt(timeArray[1],10));
        this.setSecond(parseInt(timeArray[2],10));      
        this.setTOD(timeArray[3]); 
      }
    }
  },
  
  //The funtions below are required for using within an editable grid
reset : function(){
    this.setTimeByStr("12:00 AM");
  },
  setValue : function(value){
    this.setTimeByStr(value);
  },
  getValue : function(){                                                           
      return this.value;
    
  },  
  isValid : function(){
    return true
  }     
});
Ext.ComponentMgr.registerType('timespinner', Ext.ux.TimeSpinner);

