/*
Creates a dynamic div scroller
id is the id of the div to target
direction - h or v
*/
 
/*
 * Orginal: http://adomas.org/javascript-mouse-wheel/
 * prototype extension by "Frank Monnerjahn" themonnie @gmail.com
 */
Object.extend(Event, {
        wheel:function (event){
                var delta = 0;
                if (!event) event = window.event;
                if (event.wheelDelta) {
                        delta = event.wheelDelta/120; 
                        if (window.opera) delta = -delta;
                } else if (event.detail) { delta = -event.detail/3;     }
                return Math.round(delta/Math.abs(delta)); //Safari Round
        }
});
/*
 * end of extension 
 */ 




//this is temporary, we need to check both that scriptaculous is available
//as well as prototype
if (typeof Prototype=='undefined')
  throw("panel.js requires the Prototype JavaScript framework >= 1.6.0");
if (typeof Effect=='undefined')
  throw("panel.js requires script.aculo.us' effects.js library");

/**
 * Scroll Bar
 *
 * @author      Chuck Neal <chuck@mediamacros.com>
 * @package
 * @subpackage
 * @copyright   Copyright (C) MediaMacros, Inc. All rights reserved.
 */
var DivScroller = Class.create();
DivScroller.prototype = {

    DefaultOptions: {
        axis:      'vertical'
    },
    
    initialize: function(containerId, gutterId, options) {
        this._options = Object.extend(Object.extend({ },this.DefaultOptions), options || { });
        this.height = 0;
        this.width = 0;
        this.innerwidth = 0;
        this.outerwidth = 0;
        this.started = 0;
        //get the base object
        this._targetDiv = $(containerId);
        //prep it by wrapping another item if needed
        this.wrapContent();
        
        //Make the parts we need
        this._scrollContainer = $(gutterId);
        this._name = this._scrollContainer.id;
        this.createComponents();
        //fire it up
        
        
        //delay for a sec so it can be ready
        setTimeout(this.buildScroller.bindAsEventListener(this), 50);
    },
    //first click fires it up
    buildScroller:function(){
        //active the thum to slide
        this._sliderController = new Control.Slider(this._thumb.id,this._gutter.id, {'axis' : this._options.axis,
        'onChange' : this.sliderChanged.bindAsEventListener(this),
        'onSlide' : this.sliderChanged.bindAsEventListener(this)});
        //recalc our size
        this._scrollValue = 0;
        this.recalculateDimensions();
        
    },
    //reprocess. Used for ajax returns to recalculate the scroll area
    reInitialize: function(){
        //set it
        this._sliderController.setValue(0);
        this._scrollArea.setStyle({'top' : '0px', 'position' : 'absolute'});
        this._scrollValue = 0;
        this.recalculateDimensions();
        if(this.height == 0){
            setTimeout(this.reInitialize.bindAsEventListener(this), 500);
        }
    },
    //variables
        
    /**
    * @var Object
    * @access private
    */
    _options: {},

    /**
    * Div to scroll
    * @var Object 
    * @access private
    */
    _targetDiv : null,
    /**
    * gutter for slider container
    * @var Object 
    * @access private
    */
    _scrollContainer : null,
    
    //functions
    //Hides the scroll var
    hideScrollBar:function(){
        this._scrollContainer.setStyle({'display' : 'none'});
    },
    //Show the scroll bar
    showScrollBar:function(){
        this._scrollContainer.setStyle({'display' : 'block'});
    },
    //auto hide checks if we need to show/hide and adjusts
    autoHide:function(){
        if(this.height >= this.innerheight){
            this.hideScrollBar();
        }else{
            this.showScrollBar();
        }
    },
    //Wraps the content area so it can scroll
    wrapContent:function(){
        //get the child elements
        var children = this._targetDiv.childElements();
        //make the sub
        this._scrollArea = Builder.node('div',{'id':this._targetDiv.id+'_scroll_area', 'class':'scroll_area'});
        
        
        //cycle on each
        while(children.length > 0){
            var item = children.shift();
            var e = item.remove();
            this._scrollArea.appendChild(e);
        }
        
        
        this._targetDiv.appendChild(this._scrollArea);
    },
    //recalculate the width and heights of the items
    recalculateDimensions:function(){
        var dim = $(this._targetDiv).getDimensions();
        this.width = dim.width;
        this.height = dim.height;

        //see if we exceed the bounds
        dim = $(this._scrollArea).getDimensions();
        this.innerwidth = dim.width;
        this.innerheight = dim.height;
        
        this.autoHide();
    },
    //Create the parts and activates the scroll
    createComponents:function(){
        //make the up button
        this._upButton = Builder.node('div',{'id':this._name+'_up', 'class':'scroll_button_up'});
        this._upButton.onmousedown = this.startScrollInterval.bindAsEventListener(this, 60);
        this._upButton.onmouseup = this.clearScrollInterval.bindAsEventListener(this);

        this._scrollContainer.appendChild(this._upButton);
        
        //make the gutter
        this._gutter = Builder.node('div',{'id':this._name+'_gutter', 'class':'scroll_gutter'})
        this._scrollContainer.appendChild(this._gutter);
        //make the down button
        this._downButton = Builder.node('div',{'id':this._name+'_down', 'class':'scroll_button_down'})
        this._downButton.onmousedown = this.startScrollInterval.bindAsEventListener(this, -60);
        this._downButton.onmouseup = this.clearScrollInterval.bindAsEventListener(this);

        this._scrollContainer.appendChild(this._downButton);
        
        //put the thumb into the slider gutter
        this._thumb = Builder.node('div',{'id':this._name+'_thumb', 'class':'scroll_thumb'});
        this._gutter.appendChild(this._thumb);
        
        Event.observe(document, "mousewheel", this.scrollWheel.bindAsEventListener(this), false);
        Event.observe(document, "DOMMouseScroll", this.scrollWheel.bindAsEventListener(this), false)
    },
    startScrollInterval:function(e, amt){
        this.clearScrollInterval();
        this._bound = this.clearScrollInterval.bindAsEventListener(this);
        $(document.body).observe('mouseup', this._bound);
        this._scrollInterval = setInterval(this.scrollAmmount.bindAsEventListener(this, amt), 50);        
    },
    clearScrollInterval:function(e){
        $(document.body).stopObserving('mouseup', this._bound);
        clearInterval(this._scrollInterval);
    },
    
    scrollWheel:function(e) {
        var w = Event.wheel(e);
        this.scrollAmmount(e, 50 * w);
    },

    //scroll
    scrollAmmount:function(e, vAmt){
        var s = Math.max(this.height - this.innerheight ,Math.min(0, (this.height - this.innerheight) * this._scrollValue + vAmt));
        iPercent = s / (this.height - this.innerheight);
		iPercent = Math.min(1, iPercent);
		iPercent = Math.max(0, iPercent);
        this._sliderController.setValue(iPercent);    
        this.sliderChanged(iPercent);  
    },
    //changed
    sliderChanged:function(iPercent){
        if(this.width == 0 || this.height == 0){
            this.recalculateDimensions();
        }
        this._scrollValue = iPercent;
        
        //change the scroll by percentage
        var s = Math.round(Math.min(0, (this.height - this.innerheight) * iPercent)) + ''
        if(s > 0 || s == Number.NaN || s == 'NaN'){
            s = 0;
        }
        s = s + 'px';
        this._scrollArea.setStyle({'top' : s, 'position' : 'absolute', 'left' : '0px'});
    },
	scrollToItem:function(iId){
		//get the item
		var i = $(iId);
		if(i != undefined){
			//get its height offset
			var offset = Element.positionedOffset(i);
			var topVal = offset[1] - 10;
			if(this.width == 0 || this.height == 0){
            	this.recalculateDimensions();
        	}
			//bar move
			var iPercent = Math.min(1, topVal/ (this.innerheight-this.height));
			this._sliderController.setValue(iPercent);
			//scroll move
			this.sliderChanged(iPercent);
		}
	}


}


//later
//adjust slider height based on ammount of scroll (?)
