define(["jquery"], function (jq) {

    "use strict";

    return (function() {

        var
            isIOS = (/iphone|ipad|ipod/i.test( navigator.userAgent.toLowerCase() ) );

        function getFirstSupportedEvent(tagName, eventNames) {
            var result = "";
            jq.each(eventNames.split(" "), function (i, evtName) {
                if (isEventSupported(evtName, tagName)) {
                    result = evtName;
                    return false; // jq.each break
                }
                return true; // jq.each continue
            });
            return result;
        }

        function isEventSupported(eventName, tagName) {
            var elem = tagName ? document.createElement(tagName) : document,
                onEventName = "on" + eventName,
                isSupported;

            isSupported = !!(onEventName in elem);
            if (!isSupported && typeof elem.setAttribute !== "undefined") {
                elem.setAttribute(onEventName, "return;");
                isSupported = typeof elem[onEventName] === "function";
            }

            return isSupported;
        }

        return {
            /**
             * Attach the event handler <b>handler</b> for the first supported event specified by <b>eventNames</b>
             * to the element <b>jqObject</b>.
             * Example: attachFirstSupportedEvent( myObject, "pointerdown mousedown touchend", myHandler );
             *
             * @param element
             * @param {String} eventNames
             * @param handler
             * @return {String} the event name or ""
             */
            attachFirstSupportedEvent: function (element, eventNames, handler) {
                var jqObject = jq(element),
                    evtName = getFirstSupportedEvent(element.nodeName, eventNames);

                if (!evtName) {
                    return "";
                }

                jqObject.on(evtName, handler);
                return evtName;
            },

            /**
             * Remove attached event handler <b>handler</b> for the first supported event specified by <b>eventNames</b>
             * from the element <b>jqObject</b>.
             * Example: removeFirstSupportedEvent( myObject, "pointerdown mousedown touchend", myHandler );
             *
             * @param element
             * @param {String} eventNames
             * @param handler
             * @return {String} the event name or ""
             */
            removeFirstSupportedEvent: function (element, eventNames, handler) {
                var jqObject = jq(element),
                    evtName = getFirstSupportedEvent(element.nodeName, eventNames);

                if (!evtName) {
                    return "";
                }

                jqObject.off(evtName, handler);
                return evtName;
            },

            getPointerDownEvent: function( element ) {
                if( !isIOS ) {
                    return getFirstSupportedEvent( element.nodeName, "pointerdown mousedown touchstart" );
                }

                // iOS 9.3 unterstÃ¼tzt zwar click und mouseup, weshalb sich auf diese Events attached wird, aber sie werden
                //  aus unbekannten GrÃ¼nden nicht gesendet.
                return "touchstart";
            },

            getPointerUpEvent: function( element ) {

                if( !isIOS ) {
                    return getFirstSupportedEvent( element.nodeName, "click pointerup mouseup touchend" );
                }

                // iOS 9.3 unterstÃ¼tzt zwar click und mouseup, weshalb sich auf diese Events attached wird, aber sie werden
                //  aus unbekannten GrÃ¼nden nicht gesendet.
                return "touchend";
            }
        };
    })();
});
