(function($){

var Weagraph  = { 
    getRange: function () { return this._getData('range'); }, // note: we could use this.options.level directly, but using the 
    setRange: function (x) {                                  // functions gives us more flexibility 
        var ranges = this._getData('ranges'); 
        var oldrange = this._getData('range');
        
        if (x != oldrange) {
            this.element.find('.weagr-t' + ranges[oldrange].name).removeClass('weagr-navb-active');
        }
        this.element.find('.weagr-t' + ranges[x].name).addClass('weagr-navb-active');
        this._setData('range', x); 
    }, 
    getTime: function () { return this._getData('time'); }, 
    setTime: function (x) {                                
        this._setData('time', x); 
    }, 

    _init: function() {
        this.setRange(this.getRange());
        
        var _this = this;
        // callback for range chooser
        this.element.find(".weagr-rangeselect").change(function() {
            _this.setRange(parseInt(this.value));
            _this.doReload();
        });
        // callback for next/prev buttons
        this.element.find(".weagr-btn-prev").click(function() {
            var range = _this.getRangeInSec();
            var time = _this._getData('time');
            time = time - range;

            _this.setTime(time);
            _this.doReload();
        });
        this.element.find(".weagr-btn-next").click(function() {
            var range = _this.getRangeInSec();
            var time = _this._getData('time');
            time = time + range;

            _this.setTime(time);
            _this.doReload();
        });
        // callback for date chooser
        $datefield = this.element.find(".weagr-dt");
        $datefield.datepicker({
            dateFormat: 'yy-mm-dd', 
            //minDate:'-6M', 
            maxDate:1,
            firstDay:1,
            onSelect: function(dateText, inst) {
                var date = new Date(dateText.substr(0,4), dateText.substr(5,2) - 1, dateText.substr(8,2));
                var ts = Math.round(date.getTime() / 1000.0);
                _this.setTime(ts);
                _this.doReload();
            }
        });
        var date = $.datepicker.formatDate('yy-mm-dd', new Date());
        $datefield.val(date);

        // load data via ajax service
        this.doReload();
    }, 

    getRangeInSec: function() {
        var ranges = this._getData('ranges'); 
        var range = this._getData('range');
        range = ranges[range];
        return range.val;
    },
    
    doReload: function () {
        var ranges = this._getData('ranges'); 
        var range = ranges[this._getData('range')].val;
        var time = this._getData('time');
        var url = this._getData('url');
        
        var $targ = this.element.find(".weagr-target");
        var $text = this.element.find(".weagr-text");
        var $lgnd = this.element.find(".weagr-legend");
        var $main = this.element;
        var $datefield = this.element.find(".weagr-dt");

        var _this = this;

        // block UI
        $main.mask("Loading...");

        $.ajax({
          url: url + '/' + range + '/' + time,
          cache: false,
          dataType: "jsonp",
          jsonp: 'jsonp_callback',
          success: function(data){
            var mydata = data.data;
            var options = {
                xaxis: { mode: "time" },
                selection: { mode: "x" },
                grid: { markings: $.ui.weagraph.defaults.weekendAreas },
                legend: { container: $lgnd },
                yaxis: { tickFormatter: function (v, axis) { return v.toFixed(axis.tickDecimals) + " " + data.y_unit; }},
                y2axis: { tickFormatter: function (v, axis) { return v.toFixed(axis.tickDecimals) + " " + data.y2_unit; }}
            };
            var plot = $.plot($targ, mydata, options);
            $text.html(data.title);
            // update date field to reflect last time show in graph
            var time_to = new Date(data.to * 1000);
            var datepart = $.datepicker.formatDate('yy-mm-dd', time_to);
            var time_hour = time_to.getHours();
            var time_min = time_to.getMinutes();
            if (time_hour < 10) { time_hour = '0' + time_hour; }
            if (time_min < 10) { time_min = '0' + time_min; }
            $datefield.val(datepart + ' ' + time_hour + ':' + time_min);
            _this._setData('time', data.to);
            // add checkboxes to legend
            var chkidx=0;
            _this.plot_visible = []; // stores which plots are currently visible
            $main.find('.legendLabel').each(function() {
                $(this).prepend('<input type="checkbox" value="' + chkidx + '" class="weagr-lgchk" checked />');
                _this.plot_visible[chkidx] = true; // all plots default to visible
                chkidx++;
            }); 
            // checkbox click event: show/hide clicked plot
            $main.find('.weagr-lgchk').each(function() {
                $(this).click(function(){
                    _this.plot_visible[this.value] = this.checked;
                    var newdata = [];
                    for (var i=0; i<_this.plot_visible.length; i++) {
                        newdata[i] = (_this.plot_visible[i] == 1 ? mydata[i] : []);
                    }
                    plot.setData(newdata);
                    plot.draw();
                    delete newdata;
                });
            }); 
            $main.unmask();
          },
          error: function(e, xhr){
            alert('error! ' + e);
          }
        });
    },
    off: function() { 
        this._trigger('done'); 
        this.destroy(); // use the predefined function 
    } 
}; 
$.widget("ui.weagraph", Weagraph); 
$.ui.weagraph.getter = "getTime,getRange"; 
$.ui.weagraph.defaults = { 
    response: null,
    url: '/data/1',
    range: 1,
    ranges: [{val:4*60*60, name:'4h'}, {val:36*60*60, name:'36h'}, {val: 7*24*60*60, name:'1w'}, {val: 30*24*60*60, name:'1m'}, {val: 182*24*60*60, name:'6m'}],
    time: 0,

    // helper for returning the weekends in a period
    weekendAreas: function(axes) {
        var markings = [];
        var d = new Date(axes.xaxis.min);
        // go to the first Saturday
        d.setUTCDate(d.getUTCDate() - ((d.getUTCDay() + 1) % 7))
        d.setUTCSeconds(0);
        d.setUTCMinutes(0);
        d.setUTCHours(0);
        var i = d.getTime();
        do {
            // when we don't set yaxis the rectangle automatically
            // extends to infinity upwards and downwards
            markings.push({ xaxis: { from: i, to: i + 2 * 24 * 60 * 60 * 1000 } });
            i += 7 * 24 * 60 * 60 * 1000;
        } while (i < axes.xaxis.max);

        return markings;
    }
		    
}; 

})(jQuery);

/**
 * Copyright (c) 2009 Sergiy Kovalchuk (serg472@gmail.com)
 * 
 * Dual licensed under the MIT (http://www.opensource.org/licenses/mit-license.php)
 * and GPL (http://www.opensource.org/licenses/gpl-license.php) licenses.
 *  
 * Following code is based on Element.mask() implementation from ExtJS framework (http://extjs.com/)
 *
 */
(function(a){a.fn.mask=function(c){this.unmask();if(this.css("position")=="static"){this.addClass("masked-relative")}this.addClass("masked");var f=a('<div class="loadmask"></div>');var d=navigator.userAgent.toLowerCase();var h=document.compatMode=="CSS1Compat";var e=d.indexOf("msie")>-1;var g=d.indexOf("msie 7");if(e&&!(g&&h)&&this.css("height")=="auto"){f.height(this.height());f.width(this.width())}this.append(f);if(typeof c=="string"){var b=a('<div class="loadmask-msg" style="display:none;"></div>');b.append("<div>"+c+"</div>");this.append(b);b.css("top",Math.round(this.height()/2-b.height()/2)+"px");b.css("left",Math.round(this.width()/2-b.width()/2)+"px");b.show()}};a.fn.unmask=function(b){this.find(".loadmask-msg,.loadmask").remove();this.removeClass("masked");this.removeClass("masked-relative")}})(jQuery);


