﻿Controls.RangeSlider = function (obj) {
    var _thisRef = this;
    var _self = $('#' + obj.id);
    var _minTbx = obj.minId ? $('#' + obj.minId) : null;
    var _maxTbx = obj.maxId ? $('#' + obj.maxId) : null;
    var _min = obj.min; // (obj.min != undefined) ? obj.min : _minTbx.val() - 0;
    var _max = obj.max; // (obj.max != undefined) ? obj.max : _maxTbx.val() - 0;
    var _useDouble = obj.useDouble;
    var onMinValueChange = (_minTbx) ? function (min) {
        _minTbx.val(min);
    } : function () { }

    var onMaxValueChange = _maxTbx ? function (max) {
        _maxTbx.val(max);
    } : function () { };

    function onMaxRangeChange() {
        var val = _maxTbx.val() - 0;
        val = val > _max ? _max : val;
        val = val < _min ? _min : val;

        if (val) {
            lastMax = val;
            var cmin = _minTbx.val() - 0;

            if (val < cmin) {
                var w = unconvert(val);
                _self.find('.leftRoller').width(w);
                _minTbx.val(val);
            }

            var w = unconvert(val);

            _self.find('.rightRoller').width(generalWidth - w);
        }
        else
            val = lastMax;

        _maxTbx.val(val);
    }

    if (_maxTbx) {
        var lastMax = _max;
        _maxTbx.change(function () {
            onMaxRangeChange();
        });
    }

    function onMinRangeChange() {
        var val = _minTbx.val() - 0;
        val = val < _min ? _min : val;
        val = val > _max ? _max : val;

        if (val) {
            lastMin = val;

            var cmax = _maxTbx.val() - 0;

            if (val > cmax) {
                var w = unconvert(val);
                _self.find('.rightRoller').width(generalWidth - w);
                _maxTbx.val(val);
            }
            var w = unconvert(val);
            _self.find('.leftRoller').width(w);
        }
        else
            val = lastMin;
        _minTbx.val(val);
    }

    if (_minTbx) {
        var lastMin = _min;
        _minTbx.change(function () {
            onMinRangeChange();
        });
    }

    _self.append('<div class="range-slider">' +
        '<div class="scaleContainer">' +
            '<div class="scale">' +
            '</div>' +
            '<div class="range">' +
            '</div>' +
        '</div>' +
        '<div class="rollerContainer">' +
           ' <span class="leftRoller"><span class="roller"></span></span>' +
           ' <span class="rightRoller">' +
                '<span class="roller"></span></span>' +
        '</div>' +
    '</div>');

    ///#region public fields
    this.wigth = obj.wigth || _self.find('.rollerContainer').width() || 200;
    ///#endregion 

    var moveRoller = function (x) { };
    var oldX;
    var generalWidth = this.wigth;
    var range = (_max - _min);
    {

        function getCool(p, min, max) {
            var v1 = fromPercent(p, min, max);
            var v2 = cool(v1, min, max);

            if (v2 < 1)
                v2 = Math.round(v2 * 10) / 10;

            return v2;
        }

        function cool(v, min, max) {

            function log10(v) {
                var val = (Math.log(v) / Math.log(10));
                return val;
            }

            var pow = log10(max - min) || 1;

            if (pow > 1)
                pow = pow - 1;

            var pp = Math.pow(10, Math.floor(pow));
            var d = Math.round(v / pp) * pp;
            return d;
        }

        function fromPercent(p, min, max) {
            var v = ((max - min) / 100) * p + min;
            return v;
        }

        var scaleNumbers = [];

        scaleNumbers.push(_min);
        scaleNumbers.push(getCool(25, _min, _max));
        scaleNumbers.push(getCool(50, _min, _max));
        scaleNumbers.push(getCool(75, _min, _max));
        scaleNumbers.push(_max);

        var innerScale = '<div class="innerScale">';
        innerScale += '<div class="scaleNotch" style="left:' + unconvert(scaleNumbers[0]) 
        + 'px"><div class="notchValue">' + scaleNumbers[0] + '</div></div>';
        for (var i = 1; i < scaleNumbers.length; i++) {
            innerScale += '<div class="scaleNotch" style="left:' + unconvert(scaleNumbers[i]) 
            + 'px"><div class="notchValue">' + scaleNumbers[i] + '</div></div>';
            console.log(unconvert(scaleNumbers[i]));
        }
        innerScale += '</div>';
        _self.find('.scale').append(innerScale);
    }

    function convert(val) {

        var p = val / generalWidth;
        var res = _min + p * range;
        if (!_useDouble)
            res = Math.floor(res);
        return res;
    }

    function unconvert(res) {
        var p = (res - _min) / range;
        var val = p * generalWidth;
        return val;
    }

    onMaxRangeChange();
    onMinRangeChange();

    _self.find('.roller').mousedown(function (event) {

        beginX = event.layerX;

        var roller = $(this).parent();

        var isLeft = roller.is('.leftRoller');

        oldX = isLeft ? roller.offset().left : roller.offset().left + roller.width(); // ; event.clientX; //  //;

        var otherRollerWidth = roller.parent().find(isLeft ? '.rightRoller' : '.leftRoller').width();
        generalWidth = _self.find('.rollerContainer').width();

        var op = isLeft ? function (x0, x1) { return x1 - x0; } : function (x0, x1) { return x0 - x1; }

        var onChange = isLeft ? function (val) { onMinValueChange(convert(val)); } : 
        function (val) { onMaxValueChange(convert(generalWidth - val)); };

        moveRoller = function (newX) {

            var d = op(oldX, newX);

            if (d < 5) d = 0;

            var summW = otherRollerWidth + d;

            if (summW <= generalWidth) {

                roller.width(d);

                setTimeout(function () { onChange(d); }, 100);
            }
        };
        return false;
    });

    $('body').mouseup(function () {
        moveRoller = null;
    });

    $('body').mousemove(function (event) {
        if (moveRoller)
            moveRoller(event.clientX);
    });
}

