Javascript Can d3';s的转换和旋转配合得好吗?
结合旋转的变换会产生奇怪的结果 下面是我的问题: 尝试单击每个方块以查看不同的行为 请原谅被黑客攻击的代码,但是如果我使用带有旋转(和x/y位置)的转换,那么它会循环 我试过: 1) 所有这些都在变换中(旋转然后平移),这看起来基本上是可以的。有点摇晃 2) 只需在变换中旋转,使用x/y属性定位即可。飞来飞去,但最后却飞到了正确的地方。很奇怪 3) 所有这些都在变换(平移然后旋转)中飞走,并最终到达(完全)错误的位置 嗯,奇怪 是否有一种正确的方法来旋转带有过渡的形状 直觉上,如果第二种选择奏效,那就好了Javascript Can d3';s的转换和旋转配合得好吗?,javascript,rotation,d3.js,transition,jsfiddle,Javascript,Rotation,D3.js,Transition,Jsfiddle,结合旋转的变换会产生奇怪的结果 下面是我的问题: 尝试单击每个方块以查看不同的行为 请原谅被黑客攻击的代码,但是如果我使用带有旋转(和x/y位置)的转换,那么它会循环 我试过: 1) 所有这些都在变换中(旋转然后平移),这看起来基本上是可以的。有点摇晃 2) 只需在变换中旋转,使用x/y属性定位即可。飞来飞去,但最后却飞到了正确的地方。很奇怪 3) 所有这些都在变换(平移然后旋转)中飞走,并最终到达(完全)错误的位置 嗯,奇怪 是否有一种正确的方法来旋转带有过渡的形状 直觉上,如果第二种选择奏效
感谢iirc平移是相对于0,0的,而旋转是围绕对象的中心点 因此,由于形状从0,0(例如100200或200100)偏移,因此在转换时它们最终会迁移。这可以通过将Diamond3的偏移量更改为[50,50]——屏幕周围的偏移量要小得多
解决方案是将0,0点重设为菱形中心。在D3中有一种方法可以做到这一点,但我记不起它在我的头顶上是什么:(要在任意轴上旋转SVG对象,需要两种转换:
translate
(要设置轴)和rotate
。您真正想要的是首先完全应用translate
,然后旋转已经移动的元素,但是translate
和rotate
似乎是独立且同时操作的。这在正确的位置结束,但是设置translate
的动画实质上就是移动a旋转期间的xis,创建抖动。您可以将平移
与旋转
隔离开来,方法是使它们出现在SVG元素层次结构中的不同位置。例如,请查看以下内容:
<g class="outer">
<g class="rect-container">
<rect class="rotate-me" width=200 height=100 />
</g>
</g>
现在可以通过传递未包装的元素(使用D3的.node()
方法)将元素/组居中
对于在单个
和
的2个rect
s(带重新定位和缩放)上实现此功能的代码
*上述代码的Javascript:
var center, centerToOrigin, group;
centerToOrigin = function(el) {
var boundingBox;
boundingBox = el.getBBox();
return {
x: -1 * Math.floor(boundingBox.width / 2),
y: -1 * Math.floor(boundingBox.height / 2)
};
};
group = d3.select("g.rotate-me");
center = centerToOrigin(group.node());
group.attr("transform", "translate(" + center.x + ", " + center.y + ")");
可能我误解了你的意思,但实际上,1和2应该是相同的。它们最终位于相同的位置(过渡的端点没有几何差异),但在转换过程中,路径是伟大的循环本轮。我猜小抖动是由于arctan函数或类似函数中的错误造成的,但大循环只是奇数。在示例中,单击时,您将再次(一次又一次)将X、Y值添加到起点。因此,当页面加载时,您将Diamond2转换为100200。当用户单击时,Diamond2旋转65度,并再次转换为100200。不同的行为是由先旋转、然后平移、平移时旋转或先平移引起的,而不同的比例是由tra中的不同引起的nslation值。为了证明这一点,请编辑您的小提琴,从单击处理程序变换中删除'Diamond2.x'和'Diamond2.y'。不,它不会重复更改平移。旋转会增加,但平移保持完全相同。我已经稍微清理了一些。问题似乎在于插值的方式。嗯,我知道了不要做一个纯svg动画,看看它是否做了同样的事情。好吧。在搞乱了本机svg动画,并与绝对相对定位和旋转进行了较量之后(太不直观了),我现在知道了避免这个问题的方法。因此,在我得到答案之前,这里是我的解决方法,尽管我没有屏住呼吸。围绕原点构建所有形状。使用组和变换定义自己的相对帧(以避免绝对位置,但相对旋转不愉快).分别进行转换。现在我需要查看转换是并行运行(la SVG)还是顺序运行。在任何情况下,都不会出现抖动,耶!根据您的规则,第一段和示例是无价的!谢谢!很高兴它有帮助!
group = d3.select("g.rotate-me")
center = centerToOrigin(group.node())
group.attr("transform", "translate(#{center.x}, #{center.y})")
var center, centerToOrigin, group;
centerToOrigin = function(el) {
var boundingBox;
boundingBox = el.getBBox();
return {
x: -1 * Math.floor(boundingBox.width / 2),
y: -1 * Math.floor(boundingBox.height / 2)
};
};
group = d3.select("g.rotate-me");
center = centerToOrigin(group.node());
group.attr("transform", "translate(" + center.x + ", " + center.y + ")");