触摸设备(iPad、Android)上的 jQuery 拖放 [英] jQuery Drag and Drop on touch devices (iPad, Android)

查看:33
本文介绍了触摸设备(iPad、Android)上的 jQuery 拖放的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我们有一个纸牌游戏网站,广泛使用了 jQuery Draggable &Droppable 并且几乎完美运行(使用鼠标时)将近一年.

We have a card game website that makes extensive use of jQuery Draggable & Droppable and which has worked nearly flawlessly (when using a mouse) for almost a year.

我们真的很想让网站在触摸屏设备上工作,但我们似乎无法让 jQuery 的拖放功能可靠地工作.

We would REALLY like to have the site work on touch screen devices, but we cannot seem to get jQuery's drag and especially drop functionality to work reliably.

拖动工作正常",除非被拖动的 div 位于另一个具有任何类型的偏移、边距、填充等的 dom 元素内.如果是这样,拖动的元素也会从用户的手指偏移类似的量.听起来可能没什么大不了,但它使界面无法使用.

Dragging works "ok" unless the div being dragged is inside another dom element with any kind of offset, margin, padding, etc. If it is, the dragged element is also offset from the user's finger by a similar amount. May not sound like a big deal, but it makes the interface unusuable.

删除似乎不起作用.

我们研究了在 SO 上提供的各种选项(如果可以,我会尝试更新这篇文章并提供其中一些的链接),但没有一个对我们有用.

We've researched various options presented here on SO (will try to update this post with links to some of them if I can), but none work for us.

我们还研究了 jQuery Mobile,但它仍处于 alpha 阶段,即便如此,它似乎更像是一个框架,可以让网站模拟手机的 UI,而不是我们正在寻找的内容.

We've also researched jQuery Mobile but this is still in alpha and even so seems to be more of a framework for making a site emulate the UI of a phone vs what we're looking for.

关于这个主题的大多数 SO 和 Google 帖子似乎在 2010 年末逐渐减少,这让我觉得有一个明显的答案,也许我们只是错过了.

Most of the SO and Google posts on this topic seem to trail off in late 2010 which makes me think there is an obvious answer that maybe we're just missing.

顺便说一句,我们正在寻找的功能在技术上显然是可行的,因为用于拖放的 YUI 库按预期工作.不幸的是,我们无法证明重构站点以从 jQuery 切换到 YUI.

BTW, the functionality we're looking for is clearly technically possible because the YUI libraries for drag and drop work as expected. Unfortunatly, we can't justtify refactoring the site to switch from jQuery to YUI.

有人有什么想法吗?我们会满足于只支持 iPad,但它确实不需要我们重构现有网站.

Anyone out there have any ideas? We would settle for a answer that supports only iPad, but it really needs to not require we refactor the existing site.

谢谢!

推荐答案

将此粘贴​​到 .js 文件的开头:

Paste this at the beginning of your .js file:

(function ($) {
    // Detect touch support
    $.support.touch = 'ontouchend' in document;
    // Ignore browsers without touch support
    if (!$.support.touch) {
    return;
    }
    var mouseProto = $.ui.mouse.prototype,
        _mouseInit = mouseProto._mouseInit,
        touchHandled;

    function simulateMouseEvent (event, simulatedType) { //use this function to simulate mouse event
    // Ignore multi-touch events
        if (event.originalEvent.touches.length > 1) {
        return;
        }
    event.preventDefault(); //use this to prevent scrolling during ui use

    var touch = event.originalEvent.changedTouches[0],
        simulatedEvent = document.createEvent('MouseEvents');
    // Initialize the simulated mouse event using the touch event's coordinates
    simulatedEvent.initMouseEvent(
        simulatedType,    // type
        true,             // bubbles                    
        true,             // cancelable                 
        window,           // view                       
        1,                // detail                     
        touch.screenX,    // screenX                    
        touch.screenY,    // screenY                    
        touch.clientX,    // clientX                    
        touch.clientY,    // clientY                    
        false,            // ctrlKey                    
        false,            // altKey                     
        false,            // shiftKey                   
        false,            // metaKey                    
        0,                // button                     
        null              // relatedTarget              
        );

    // Dispatch the simulated event to the target element
    event.target.dispatchEvent(simulatedEvent);
    }
    mouseProto._touchStart = function (event) {
    var self = this;
    // Ignore the event if another widget is already being handled
    if (touchHandled || !self._mouseCapture(event.originalEvent.changedTouches[0])) {
        return;
        }
    // Set the flag to prevent other widgets from inheriting the touch event
    touchHandled = true;
    // Track movement to determine if interaction was a click
    self._touchMoved = false;
    // Simulate the mouseover event
    simulateMouseEvent(event, 'mouseover');
    // Simulate the mousemove event
    simulateMouseEvent(event, 'mousemove');
    // Simulate the mousedown event
    simulateMouseEvent(event, 'mousedown');
    };

    mouseProto._touchMove = function (event) {
    // Ignore event if not handled
    if (!touchHandled) {
        return;
        }
    // Interaction was not a click
    this._touchMoved = true;
    // Simulate the mousemove event
    simulateMouseEvent(event, 'mousemove');
    };
    mouseProto._touchEnd = function (event) {
    // Ignore event if not handled
    if (!touchHandled) {
        return;
    }
    // Simulate the mouseup event
    simulateMouseEvent(event, 'mouseup');
    // Simulate the mouseout event
    simulateMouseEvent(event, 'mouseout');
    // If the touch interaction did not move, it should trigger a click
    if (!this._touchMoved) {
      // Simulate the click event
      simulateMouseEvent(event, 'click');
    }
    // Unset the flag to allow other widgets to inherit the touch event
    touchHandled = false;
    };
    mouseProto._mouseInit = function () {
    var self = this;
    // Delegate the touch handlers to the widget's element
    self.element
        .on('touchstart', $.proxy(self, '_touchStart'))
        .on('touchmove', $.proxy(self, '_touchMove'))
        .on('touchend', $.proxy(self, '_touchEnd'));

    // Call the original $.ui.mouse init method
    _mouseInit.call(self);
    };
})(jQuery);

早上给我打电话;)(这真的很傲慢,我没有写这个解决方案,虽然我希望我有,如果我记得我在哪里找到它,如果有人知道这个代码来自哪里,我会参考它请评论并信任那个人)

Call me in the morning ;) (that's really arrogant, I didn't write this solution although I wish that I had, I'd reference it if I remember where I found it, if anyone know where this code came from please comment and credit that person)

更新:给你:这是我发现的地方

这篇关于触摸设备(iPad、Android)上的 jQuery 拖放的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆