当前位置: 首页 > 知识库问答 >
问题:

HTML5 Drag'n'Drop-不工作在iOS12.1.2(Safari和Chrome)

江宏深
2023-03-14

我有一个可以通过拖放排序的列表。它可以在桌面浏览器上完美工作,在Android系统上Chrome。然而,它在Safari和Chrome12.1.2iOS(苹果8)上根本不起作用。

请参阅下面的代码片段,也可以轻松地进行移动测试:https://codepen.io/Kelderic/pen/KJMRgb

var dragging = null;

document.addEventListener('dragstart', function(event) {
  var target = getLI(event.target);
  dragging = target;
  event.dataTransfer.setData('text/plain', null);
  event.dataTransfer.setDragImage(self.dragging, 0, 0);
});

document.addEventListener('dragover', function(event) {
  event.preventDefault();
  var target = getLI(event.target);
  var bounding = target.getBoundingClientRect()
  var offset = bounding.y + (bounding.height / 2);
  if (event.clientY - offset > 0) {
    target.style['border-bottom'] = 'solid 4px blue';
    target.style['border-top'] = '';
  } else {
    target.style['border-top'] = 'solid 4px blue';
    target.style['border-bottom'] = '';
  }
});

document.addEventListener('dragleave', function(event) {
  var target = getLI(event.target);
  target.style['border-bottom'] = '';
  target.style['border-top'] = '';
});

document.addEventListener('drop', function(event) {
  event.preventDefault();
  var target = getLI(event.target);
  if (target.style['border-bottom'] !== '') {
    target.style['border-bottom'] = '';
    target.parentNode.insertBefore(dragging, event.target.nextSibling);
  } else {
    target.style['border-top'] = '';
    target.parentNode.insertBefore(dragging, event.target);
  }
});

function getLI(target) {
  while (target.nodeName.toLowerCase() != 'li' && target.nodeName.toLowerCase() != 'body') {
    target = target.parentNode;
  }
  if (target.nodeName.toLowerCase() == 'body') {
    return false;
  } else {
    return target;
  }
}
ul.sorting {
  padding: 0;
  margin: 0;
  list-style: none;
  max-height: 300px;
  overflow-y: auto;
  box-shadow: inset 0 0 3px 1px rgba(0, 0, 0, 0.2);
}

ul.sorting li {
  padding: 10px;
  border-bottom: 1px solid black;
  user-select: none;
  cursor: move;
}

ul.sorting li:last-child {
  border-bottom: none;
}
<ul class="sorting">
  <li draggable="true" style="user-drag:element;">List Item 15</li>
  <li draggable="true" style="-webkit-user-drag:element;">List Item 2</li>
  <li draggable="true" style="-webkit-user-drag:element;">List Item 3</li>
  <li draggable="true" style="-webkit-user-drag:element;">List Item 4</li>
  <li draggable="true" style="-webkit-user-drag:element;">List Item 5</li>
  <li draggable="true" style="-webkit-user-drag:element;">List Item 6</li>
  <li draggable="true" style="-webkit-user-drag:element;">List Item 7</li>
  <li draggable="true" style="-webkit-user-drag:element;">List Item 8</li>
  <li draggable="true" style="-webkit-user-drag:element;">List Item 9</li>
  <li draggable="true" style="-webkit-user-drag:element;">List Item 10</li>
  <li draggable="true" style="-webkit-user-drag:element;">List Item 11</li>
  <li draggable="true" style="-webkit-user-drag:element;">List Item 12</li>
</ul>

https://imgur.com/a/I8hzPxC(尺寸太大,无法直接嵌入

为什么这在iOS上不起作用?我甚至无法启动dragstart事件。在Android Chrome上,长按启动dragstart

我的备用方案是使用touchtstarttouchtend制作一个长按,然后创建我自己的绝对定位的ghost元素并手动拖动它。当拖动*事件正常工作时,会产生大量额外的代码

我错过什么了吗?

移动Safari中的LI元素有一个ondragstart事件作为其原型的一部分。问题是让它着火。

此外,根据caniuse的说法,移动Safari应该支持这一点。然而,caniuse也显示AndroidChrome不支持,这不是真的。

共有3个答案

朱宏爽
2023-03-14

我在这里分叉了您的codepen测试用例:https://codepen.io/bobacus/pen/MLjZMg

我想知道是否需要将侦听器添加到

listEl = document.getElementById('my_list');
for (var i = 0; i < listEl.children.length; i ++) {
    itemEl = listEl.children[i];
    itemEl.addEventListener('dragstart', function(event) {
      dragging = getLI(event.target);
      if (dragging) {
          event.dataTransfer.setData('text/plain', null);
          event.dataTransfer.setDragImage(dragging, 0, 0);
      }
    });
}

但那没用。

我尝试了一些不同的东西,但最终让它在Safari工作的是添加一个聚填充物:https://www.codeproject.com/Articles/1091766/Add-support-for-standard-HTML-Drag-and-Drop-operat

我将此添加到超文本标记语言片段的顶部:

<script src="http://bernardo-castilho.github.io/DragDropTouch/DragDropTouch.js"></script>

我希望这是有帮助的。

曾航
2023-03-14

不幸的是,我没有带iOS12的设备(我的设备不支持它),我不能测试它。我不知道为什么iOS /Apple支持写他们支持这个事件iOS11.2和您的新设备上不支持。

替代工作区

通过此解决方案,您将获得适用于所有现代设备和浏览器的解决方案。这比等待iOS/苹果的支持要好。

dragstartdragoverdragleavedrop事件不适用于所有触摸设备。

您必须为触摸事件使用适当的事件名称,例如:

  • touchstart

阅读有关此事件的文档。

为了为基于触摸的用户界面提供高质量的支持,触摸事件提供了在触摸屏或触摸板上解释手指(或触笔)活动的能力。

触摸事件界面是相对低级的API,可用于支持特定于应用程序的多点触摸交互,如双指手势。当手指(或触笔)第一次接触接触面时,多点触摸交互开始。其他手指随后可触摸该表面,并可选地在该触摸表面上移动。当手指从曲面上移除时,交互结束。在此交互过程中,应用程序在开始、移动和结束阶段接收触摸事件。

触摸事件与鼠标事件类似,不同之处在于它们支持同时触摸,并且位于触摸表面的不同位置。TouchEvent界面封装了当前处于活动状态的所有触点。表示单个触摸点的触摸界面包含触摸点相对于浏览器视口的位置等信息。

不幸的是,事件触摸板触摸板被从规范中删除,因此,如果您需要它,那么您必须使用document.elementFromPoint()编写一个解决方案,如下所示:

document.addEventListener('touchmove', function(e)
{
    var touch = e.touches[0],
        elementFromPoint = document.elementFromPoint(touch.pageX - window.pageXOffset, touch.pageY - window.pageYOffset);

    if(elem == elementFromPoint) //elem is your element which was entered
    {
        //your code for touchenter event
    }
    else //the code for touchleave event
});

可能对于其他一些移动设备及其浏览器,您需要使用polyfills(1,2),它在移动(触摸)设备上支持HTML5拖放。

宗政欣可
2023-03-14

在过去的一周里,我对这个主题做了大量的研究,并且做了大量的测试和调试。我发现iOS支持拖动事件,但iOS不触发它们。(截至12日)

如果您在iOSSafari上测试网页,您将看到所有超文本标记语言元素都将ondragstart附加到其原型。拖动事件都在那里。它们永远不会被触发。

其他人也遇到了这个问题。由于此错误支持,事件现代化程序未检测到拖放支持。

此外,我翻阅了Safari文档,发现:

iOS注意:虽然不支持拖放,但您可以生成。。。

它表示“支持”,但紧接着下面是一个事件表,它显示了拖动,并表示它不是“生成的”。

这意味着caniuse目前是错误的,需要更新。

这段代码之所以不能正常工作,完全是因为苹果选择不触发拖动事件。

 类似资料:
  • 我在Socket.io的nodejs服务器上遇到了一个与Socket.io相关的问题。问题是与socket.io在iOS8+中的IOS移动浏览器上不起作用。我已经寻找了它,并通过了一些解决方案,但没有奏效。以下是问题链接: https://github.com/automattic/socket.io/issues/976 http://www.codedisqus.com/7yzsqugqge/

  • 但是,它在Safari中并不起作用。但是如果我们将中的高度从更改为,我们将观察到拆分器(从上到下到)变得可拖动。这意味着在Safari中不起作用。 有没有人知道如何修改代码,使拆分器在Chrome和Safari中都能工作? 编辑1:

  • 我做了一个动画为一些元素(图像和按钮)淡入淡出使用不透明度。除了Safari之外,它在所有浏览器上都能完美地工作。当我尝试在Safari中运行它时,我的所有元素都有100%的不透明度,没有任何动画可以看到… 来自button元素的示例: 以下是我的HTML: 和我的CSS:

  • 我正在工作的HTML5横幅有很多CSS3动画。为了制作可重用的关键帧动画,我在单个元素上使用了多个动画。除了Safari之外一切都很顺利。 CSS: jsfiddle链接 可行的解决方案: 用另一个/更多元素包装该元素&为每个元素添加单个动画。此解决方案需要为包装器元素设置额外的样式。 将多个动画合并为一个&此解决方案增加了的复杂性,并且对于复杂的动画不容易维护。 根据另一个stackOverfl

  • 我为我的个人网站创建了一个动画,它可以在Chrome和Firefox中运行,没有任何问题,我也不关心IE,但它不能在Safari上运行,我想是因为Safari不会识别fill:url(..)和筛选器:URL(..)从分离的css文件。下面是CodePen的实际动画链接:http://codepen.io/getturnt/pen/kxreww我真的想知道发生了什么。 下面是实际代码: 请注意,我尝

  • 问题内容: 在我的聊天应用程序中,我需要在关闭应用程序时从user确认。 所以我使用了确认警报和logout()。 但是这两个功能都可以在IE和Chrome中使用。(应用程序运行正常) 在Opera中无法使用,并且我的消息不会在Firefox中显示。 在Safari,Opera和Firefox中不起作用。 我的javaScript代码为 我也尝试过使用JQuery同样的功能, 问题答案: 通过将A