Tldr;拖动SVG会使其旋转和翻译。
我正在尝试使用D3(v.4)作为Angular服务的一部分在SVG组上实现拖动和缩放事件。
this.unitGroup = this.svg.append('g')
.attr('id', 'unitGroup')
.call(this.drag)
.call(this.zoom);
拖动可翻译SVG。
drag = d3.drag()
.on('start', () => {
console.log('drag start');
this.setClickOrigin(d3.event);
})
.on('drag', (d, i, n) => {
const target = d3.select(n[i]).node() as any;
const m = target.getCTM();
const x = d3.event.x - this.clickOrigin.x;
const y = d3.event.y - this.clickOrigin.y;
this.setClickOrigin(d3.event);
this.translate(target, x, y);
});
缩放时旋转SVG。
zoom = d3.zoom()
.on('zoom', (d, i, n) => {
const target = d3.select(n[i]).node() as any;
const m = target.getCTM();
const b = target.getBBox();
const dir = (d3.event.sourceEvent.deltaY > 0) ? 1 : -1;
this.rotate(target, dir);
});
我的原始代码运行正常。但是,将它集成到Angular中会引发一些问题。
目前的问题是,当您拖动unitGroup
时,它会触发zoom
事件以及drag
事件。
预期的行为是:
这是一个Plunker:https://embed.plnkr.co/0GrGG7T79ubpjYa2ChYp/
答案 0 :(得分:3)
实际上,你在这里看到的是预期的行为。
在D3中,d3.zoom()
不仅可以处理缩放,还可以处理平移。因此,鼠标移动由d3.drag()
和缩放功能处理。
正如Bostock(D3创造者)曾经说过的那样:
结合这两种行为*意味着手势解释模糊且对位置高度敏感。 (*缩放和拖动)
最简单的解决方案就是检查缩放功能中是否有“真正的”缩放(鼠标滚轮),如果没有(没有鼠标滚轮),则返回:
if(!d3.event.sourceEvent.deltaY) return;
以下是您的改编者:https://plnkr.co/edit/jz5X4Vm9wIzbKmTQLBAT?p=preview