/*!
 * jQuery UI Touch Punch 0.2.3
 *
 * Copyright 2011–2014, Dave Furfero
 * Dual licensed under the MIT or GPL Version 2 licenses.
 *
 * Depends:
 *  jquery.ui.widget.js
 *  jquery.ui.mouse.js
 */

(function ($) {
    function simulateMouseEvent(event, simulatedType)
    {
        if (event.originalEvent.touches.length > 1) {
            return;
        }

        event.preventDefault();

        var touch = event.originalEvent.changedTouches[0];
        var simulatedEvent = document.createEvent('MouseEvents');
        simulatedEvent.initMouseEvent(
            simulatedType,
            true,
            true,
            window,
            1,
            touch.screenX,
            touch.screenY,
            touch.clientX,
            touch.clientY,
            false,
            false,
            false,
            false,
            0,
            null
        );
        event.target.dispatchEvent(simulatedEvent);
    }

    $.support.touch = 'ontouchend' in document;

    if (!$.support.touch) {
        return;
    }

    var touchHandled;
    var mouseProto = $.ui.mouse.prototype;
    var mouseInit = mouseProto._mouseInit;
    var mouseDestroy = mouseProto._mouseDestroy;

    mouseProto._touchStart = function (event) {
        var self = this;
        if (!touchHandled && self._mouseCapture(event.originalEvent.changedTouches[0])) {
            touchHandled = true;
            self._touchMoved = false;
            simulateMouseEvent(event, 'mouseover');
            simulateMouseEvent(event, 'mousemove');
            simulateMouseEvent(event, 'mousedown');
        }
    };

    mouseProto._touchMove = function (event) {
        if (touchHandled) {
            this._touchMoved = true;
            simulateMouseEvent(event, 'mousemove');
        }
    };

    mouseProto._touchEnd = function (event) {
        if (!touchHandled) {
            return;
        }

        simulateMouseEvent(event, 'mouseup');
        simulateMouseEvent(event, 'mouseout');

        if (!this._touchMoved) {
            simulateMouseEvent(event, 'click');
        }

        touchHandled = false;
    };

    mouseProto._mouseInit = function () {
        var self = this;
        self.element.bind({
            touchstart: $.proxy(self, '_touchStart'),
            touchmove: $.proxy(self, '_touchMove'),
            touchend: $.proxy(self, '_touchEnd')
        });
        mouseInit.call(self);
    };

    mouseProto._mouseDestroy = function () {
        var self = this;
        self.element.unbind({
            touchstart: $.proxy(self, '_touchStart'),
            touchmove: $.proxy(self, '_touchMove'),
            touchend: $.proxy(self, '_touchEnd')
        });
        mouseDestroy.call(self);
    };
})(jQuery);