D3缩放同时触摸两次

时间:2016-11-23 23:27:36

标签: ios d3.js

我在移动设备上遇到D3(版本4)问题时,在完全同时触摸两个元素时,缩放功能似乎无效。我测试的唯一设备是iPhone 7(iOS 10.1.1),移动版Safari和Chrome浏览器应用程序都存在问题。

我创建了一个简单的示例(下面)我可以重现这个问题,它在黄色背景上只有两个矩形。在我的iPhone上:

  • 如果我用两根手指在完全同时触摸它们,当我将手指分开并一起移动时,变焦不会改变。
  • 但是,如果触摸不是同时(即使是稍微分开),缩放也能正常工作。

我是否遗漏了造成这种行为的事情?我试着寻找有同样问题的人,却找不到任何东西......但鉴于D3的受欢迎程度,这一定是我做错了。

这对我的用户造成了问题。很多时候它的工作原理是因为触摸事件并非完全同时......但是通常触摸将同时进行,并且它向用户看起来像缩放被破坏或需要多次尝试才能成功。非常令人沮丧。



var svg = d3.select('#svgLocation').append('svg')
	.attr('style', 'width:300px;height:300px;background-color:yellow;');

var grp = svg.append("g");
grp.append("path").attr('d','M25,25 275,25 275,125 25,125Z');
grp.append("path").attr('d','M25,175 275,175 275,275 25,275Z');

var zoom = d3.zoom()
  .scaleExtent([1, 10])
  .on("zoom", function() { grp.attr("transform", d3.event.transform) });
svg.call(zoom);

#svgLocation {
  width:100%;
  height:100%;
}

<!DOCTYPE html>
<html>

  <head>
    <meta name="viewport" content="width=device-width, initial-scale=1">
    <script src="http://d3js.org/d3.v4.min.js"></script>
  </head>

  <body>
    <div id="svgLocation"></div>
  </body>
  
</html>
&#13;
&#13;
&#13;

1 个答案:

答案 0 :(得分:0)

所以,这似乎是D3v4中的一个错误,它会影响至少一个设备(运行iOS 10的iPhone 7设备,包括Safari和Chrome浏览器)。它不会影响所有设备:当我在Windows 7多功能一体机上尝试时,我无法重现这个问题。

在iPhone上,如果同时发生两次触摸(或非常接近),将会按预期触发两个触摸起动事件。但是,在两个事件中,&#34;触及&#34;属性将包含一个两个触摸的数组。 (&#34; changedTouches&#34;属性仅包含相应的触摸。)

(请注意,在Windows触摸设备上,两个事件中的第一个事件的&#34;触摸&#34;属性只有一个触摸值。)

在D3缩放touchstarted功能中,&#34;开始&#34;仅当触摸计数与changedTouches的计数匹配时才触发手势...这是由&#34; if&#34;强制执行的。声明(Commit #17)如下:

var g = gesture(this, arguments),
  touches = event.changedTouches,
  n = touches.length, i, t, p;

[...]

if (event.touches.length === n) {
  touchstarting = setTimeout(function() { touchstarting = null; }, touchDelay);
  interrupt(this);
  g.start();
}

我试着评论&#34; if&#34;声明所以g.start()总是被调用(即使有两个触摸和一个touchChanged)......它立即开始在iPhone上工作。双击缩放也继续工作,这是添加此检查的提交。

但是,我对在项目中留下这个问题犹豫不决;显然这个if语句检查由于某种原因被放在那里。我担心通过禁用它,我会打开其他一些我不知道的边缘情况。我将此问题发布到Github项目,希望能找到解决方案。