/* 
 *  NAME    createSlider
 *  SYNOPSIS var slider = createSlider(cfg);
 *  AUTHOR:           Stergios Marinopoulos, stergios_marinopoulos at yahoo dot com
 *  CREATION DATE:    3/1/2007
*/
var g_sliders = { list:[], resizeCallBack:null, module:null, lastSize:null };
var createSlider = function(cfg) {
  var cs;
  var leftThumb = null, rightThumb = null;
  var handleDragged = null;
  var bb;
  var leftThumbDiv;
  var thumbRegion;
  var thumbWidth;
  var containerRegion;
  var containerWidth;
  var containerLeft;
  var span;
  var tickCount=1;
  var constraintAdjust=0;
  var rightThumbDiv;
  var leftThumbValue;
  var rightThumbValue;
  var resetLeftConstraint = function(ltx, rtx) {
    var leftThumbTravel2Left  = Number(ltx - containerLeft).toFixed(0);
    var leftThumbTravel2Right = Number(rtx - ltx - thumbWidth ).toFixed(0);
    if ( ! cs.allowEqual ) leftThumbTravel2Right -= constraintAdjust; 
    leftThumb.setXConstraint(leftThumbTravel2Left, leftThumbTravel2Right, Math.floor(tickCount) );
    leftThumb.resetConstraints(true);  
  };
  var resetRightConstraint = function (ltx, rtx) {
    var rightThumbTravel2Left  = Number(rtx - ltx - thumbWidth).toFixed(0);
    var rightThumbTravel2Right = Number((containerLeft + containerWidth) - ( rtx + thumbWidth )).toFixed(0);
    if ( ! cs.allowEqual ) rightThumbTravel2Left -= constraintAdjust; 
    rightThumb.setXConstraint(rightThumbTravel2Left, rightThumbTravel2Right, Math.floor(tickCount) );
    rightThumb.resetConstraints(true);  
  };
  if (g_sliders.resizeCallBack === null ) {
    flexListener.init();
    g_sliders.resizeCallBack = function(e,obj, p3) { 
      YAHOO.util.Event.stopEvent(e);
    };
  }
  var thisSlider = {
    updateGeometry: function() {
      if ( YAHOO.util.Dom.getStyle(bb, 'display') === 'none' ) {
        return;
      } 
      bb.lastBBPos    = YAHOO.util.Dom.getXY(bb);
      thumbRegion     = YAHOO.util.Dom.getRegion(leftThumbDiv);
      thumbWidth      = thumbRegion.right - thumbRegion.left;
      containerRegion = YAHOO.util.Dom.getRegion(bb);
      containerWidth  = containerRegion.right - containerRegion.left;
      containerLeft   = containerRegion.left;
      span            = containerWidth - 2*thumbWidth;
      if ( cs['stepCount'] ) {
        if ( cs.stepCount > 1 ) {
          tickCount = span / cs.stepCount;
          tickCount = tickCount.toFixed(0);
          constraintAdjust = tickCount / 2;
          constraintAdjust = constraintAdjust.toFixed(0);
        }
      } 
    },
    init: function() {
      YAHOO.util.DragDropMgr.clickPixelThresh = 1;
      cs              = cfg;
      leftThumbValue  = cs.minValue;
      rightThumbValue = cs.maxValue;
      var configDD    = {scroll:false};
      bb              = document.getElementById(cs.containerDiv);
      bb.mm_cfg       = cfg;
      leftThumbDiv    = document.getElementById(cs.leftHandleDiv);
      leftThumb       = new YAHOO.util.DD(cs.leftHandleDiv, cs.groupName, configDD);
      rightThumbDiv   = document.getElementById(cs.rightHandleDiv);
      rightThumb      = new YAHOO.util.DD(cs.rightHandleDiv, cs.groupName, configDD);
      if ( YAHOO.util.Dom.getStyle(bb, 'display') === 'none' ) {}else{} 
      if (! cs.hasOwnProperty('allowEqual') ){ cs['allowEqual'] = true; }
      this.updateGeometry();
      if ( cs['leftDisplay'] ) {
        bb.mm_cfg.leftDisplayElem = document.getElementById(cs.leftDisplay);
        if ( cs['formatFunction'] ) {
          bb.mm_cfg.leftDisplayElem.innerHTML = cs.formatFunction(cs.minValue);
        }else{
          bb.mm_cfg.leftDisplayElem.innerHTML = cs.minValue;
        }
      }
      if ( cs['rightDisplay'] ) {
        bb.mm_cfg.rightDisplayElem = document.getElementById(cs.rightDisplay);
        if ( cs['formatFunction'] ) {
          bb.mm_cfg.rightDisplayElem.innerHTML = cs.formatFunction(cs.maxValue);
        }else{
          bb.mm_cfg.rightDisplayElem.innerHTML = cs.maxValue;
        }
      }
      var leftTravel2Right = containerWidth - 2 * thumbWidth;
      if ( ! cs.allowEqual ) { leftTravel2Right -= constraintAdjust; }
      leftThumb.setXConstraint(0, leftTravel2Right, Math.floor(tickCount));
      leftThumb.setYConstraint(0, 0, 0);
      var rightTravel2Left = containerWidth - 2 * thumbWidth;
      if ( ! cs.allowEqual ) { rightTravel2Left -= constraintAdjust; }
      rightThumb.setXConstraint(rightTravel2Left, 0, Math.floor(tickCount));
      rightThumb.setYConstraint(0, 0, 0);
      var mapValue = function(p) {
        var base = containerLeft + thumbWidth;
        var v = (p - base)/span * (cs.maxValue - cs.minValue) + cs.minValue;
        if ( cs['stepCount'] ) {
          var stepInterval = (cs.maxValue - cs.minValue) / cs.stepCount;
          var zeroBase = v - cs.minValue;
          var stepIntervalUnits =  zeroBase / stepInterval;
          var stepIntervalUnitsRounded = Math.round ( stepIntervalUnits );
          v = stepIntervalUnitsRounded * stepInterval + cs.minValue;
        } 
        return v;
      };
      var endDrag = function(e) {
        var x = YAHOO.util.Dom.getX(handleDragged);
        var y = YAHOO.util.Dom.getY(handleDragged);
        if ( leftThumbDiv === handleDragged) {
          var rtx01 = YAHOO.util.Dom.getX(rightThumbDiv);
          resetRightConstraint(x, rtx01);
          leftThumbValue = mapValue(x + thumbWidth);
          cs.callBack( leftThumbValue, rightThumbValue, cs.containerDiv, false, bb);
        } else if ( rightThumbDiv === handleDragged) {
          var ltx01 = YAHOO.util.Dom.getX(leftThumbDiv);
          resetLeftConstraint(ltx01, x);
          rightThumbValue = mapValue(x);
          cs.callBack( leftThumbValue, rightThumbValue, cs.containerDiv, false, bb);
        }
      };
      rightThumb.endDrag   = endDrag;
      leftThumb.endDrag    = endDrag;
      var startDrag = function(x,y) {};
      rightThumb.startDrag = startDrag;
      leftThumb.startDrag  = startDrag;
      var mouseDown = function(e) {
        handleDragged = YAHOO.util.Event.getTarget(e);
        var x = YAHOO.util.Dom.getX(handleDragged);
        var y = YAHOO.util.Dom.getY(handleDragged);
      };
      rightThumb.onMouseDown = mouseDown;
      leftThumb.onMouseDown  = mouseDown;
      var mouseMove = function(e) {
        var x_mm;
        if ( handleDragged === leftThumbDiv ) {
          x_mm = YAHOO.util.Dom.getX(leftThumbDiv);
          var tmpLeftThumbValue = mapValue(x_mm + thumbWidth);
          cs.leftMoveCallBack( tmpLeftThumbValue, cs.containerDiv, bb );
        } else if ( handleDragged === rightThumbDiv ) {
          x_mm = YAHOO.util.Dom.getX(rightThumbDiv);
          var tmpRightThumbValue = mapValue(x_mm);
          cs.rightMoveCallBack( tmpRightThumbValue, cs.containerDiv, bb );
        }
      };
      if ( cs['leftMoveCallBack'] ) { leftThumb.onDrag  = mouseMove; }
      if ( cs['rightMoveCallBack'] ) { rightThumb.onDrag = mouseMove; }
    },
    reset: function(min, max, newStepCount) {
      cs.minValue = min;
      cs.maxValue = max;
      if ( newStepCount > 1 ) {
        tickCount = span / newStepCount;
        tickCount = tickCount.toFixed(1);
        constraintAdjust = tickCount / 2;
        constraintAdjust = constraintAdjust.toFixed(0);
      }else{ tickCount = 1;}
      this.setValue(min, 'left');
      this.setValue(max, 'right');
    },
    setValue: function(x, whichHandle) {
      if ( whichHandle === 'left' ) {
        if ( x < cs.minValue ) { x = cs.minValue; }
        if ( x > cs.maxValue ) { x = cs.maxValue; }
        leftThumbValue = x;
        if ( YAHOO.util.Dom.getStyle(bb, 'display') === 'none' ) { return; }
        var base = containerLeft + thumbWidth;
        var ltx02 = (x - cs.minValue) * span / (cs.maxValue - cs.minValue)  + base - thumbWidth;
        var rtx02 = YAHOO.util.Dom.getX(rightThumbDiv);
        if ( ltx02 + thumbWidth > rtx02 ) { return; }
        YAHOO.util.Dom.setX(leftThumbDiv, ltx02);
        resetRightConstraint(ltx02, rtx02);
        resetLeftConstraint (ltx02, rtx02);
        if ( cs['leftDisplay'] ) { bb.mm_cfg.leftDisplayElem.innerHTML = x; }
      } else if ( whichHandle === 'right' ) {
        if ( x > cs.maxValue ) { x = cs.maxValue; }
        if ( x < cs.minValue ) { x = cs.minValue; }
        rightThumbValue = x;
        if ( YAHOO.util.Dom.getStyle(bb, 'display') === 'none' ) { return; }
        var base = containerLeft + thumbWidth;
        var rtx03 = (x - cs.minValue) * span / (cs.maxValue - cs.minValue)  + base;
        var ltx03 = YAHOO.util.Dom.getX(leftThumbDiv);
        if ( ltx03 + thumbWidth > rtx03 ) { return; }
        YAHOO.util.Dom.setX(rightThumbDiv, rtx03);
        resetLeftConstraint (ltx03, rtx03);
        resetRightConstraint(ltx03, rtx03);
        if ( cs['rightDisplay'] ) { bb.mm_cfg.rightDisplayElem.innerHTML = x; }
      }
    },

    adjust: function() {
      if ( YAHOO.util.Dom.getStyle(bb, 'display') === 'none' ) { return; } 
      this.updateGeometry();
      this.setValue(leftThumbValue, 'left');
      this.setValue(rightThumbValue, 'right');
    },

    detectNewYPosition:function() {
      if ( YAHOO.util.Dom.getStyle(bb, 'display') === 'none' ) { return false; } 
      var newPos = YAHOO.util.Dom.getXY(bb); 
      if ( !( 'lastBBPos' in bb) ) {
        bb.lastBBPos = newPos;
        return true;
      }
      if ( newPos[1] !== bb.lastBBPos[1] ) {
        bb.lastBBPos = newPos;
        return true;
      }
      return false;
    },
    getValues: function() { return [leftThumbValue, rightThumbValue];},
    getRange: function() { return [cs.minValue, cs.maxValue];}
  };
  g_sliders.list[g_sliders.list.length] = thisSlider;
  return thisSlider;
}; 
var flexListener = function()
{
  var intervalDelay = 200;
  var interval      = null;
  var el            = null;
  var baseTextSize  = null;
  var currTextSize  = null;
  var addTextElement = function() {
    el                = document.createElement('span');
    el.id             = 'flexListener';
    el.innerHTML      = '&nbsp;';
    el.style.position = 'absolute';
    el.style.left     = '-12345px';
    var elC           = document.getElementsByTagName('body')[0];
    if (elC) { elC.insertBefore(el,elC.firstChild); }
    baseTextSize = flexListener.getTextSize();
    currTextSize = baseTextSize;
  }; 
  function _startDetector() {
    if (!interval) { interval = window.setInterval('flexListener.detect()',intervalDelay); }
  };
  function _detect() {
    var newTextSize = flexListener.getTextSize();
    if(newTextSize !== currTextSize) {
      currTextSize = newTextSize;
    }else{
      var iLength = g_sliders.list.length;
      var i=0;
      var changed=false;
      for (i=0; i<iLength; i++ ) { if ( g_sliders.list[i].detectNewYPosition() ) { changed = true;} }
      if ( changed === true ) { for (i=0; i<iLength; i++ ) { g_sliders.list[i].adjust();} }
    }
    return currTextSize;
  };
  return {
    getTextSize:function() { return el.offsetHeight; },
    init:function() {
      addTextElement();
      _startDetector();
    },
    detect:function() {
      return _detect();
    }
  } 
}();

