d3.js学习笔记vue2(3)使用zoom进行缩放和平移
zoom从字面上看是缩放的意思,但是d3中的zoom除了能缩放,还能平移,因为这两个操作总是不分家的首先,整个显示区域中并不是所有的元素都要缩放和平移的,比如坐标轴、背景,这些都是不需要缩放和平移的,所以在设定zoom元素时,需要将其排除。最好的办法是使用svg的g标签对图形元素进行分组,把需要缩放的放在一个g标签里,其他的可以放在一个g标签里,也可以分开放。在本示例代码中svgGraph...
zoom从字面上看是缩放的意思,但是d3中的zoom除了能缩放,还能平移,因为这两个操作总是不分家的
首先,整个显示区域中并不是所有的元素都要缩放和平移的,比如坐标轴、背景,这些都是不需要缩放和平移的,所以在设定zoom元素时,需要将其排除。最好的办法是使用svg的g标签对图形元素进行分组,把需要缩放的放在一个g标签里,其他的可以放在一个g标签里,也可以分开放。
在本示例代码中svgGraphContainer就是放置需要缩放的图形元素的容器,所以在添加其他元素时要使用
d3.select(svgGraphContainer).append('path')
这里添加的是线条,如果是其他图形也按照这种方法添加到svgGraphContainer下。但是坐标轴和背景不要添加到svgGraphContainer,而要添加到svg根节点或者其他节点下。
在d3.zoom()中还要添加
.on('zoom', () => {
this.svgGraphContainer.attr('transform', d3.event.transform) // 添加缩放功能
this.axises.xContainer.call(this.axises.x.scale(d3.event.transform.rescaleX(this.axises.xScale))) // 设置坐标轴随zoom缩放
this.axises.yContainer.call(this.axises.y.scale(d3.event.transform.rescaleY(this.axises.yScale)))
})
其中transform包含了缩放和平移两项功能,中键滚轮缩放,左键拖拽平移。以前的版本中,需要对zoom响应函数分别设定translate和scale,从v4版不用了,直接合二为一
d3.js - d3 zoom and pan upgrade to version 4 - Stack Overflow
transform必须要设定在svgGraphContainer上,如果设定在svg上,则整个svg的高宽都会随zoom变化,却不一定有平移功能。
随后还要把比例尺的比例重新设置,d3.zoom()自带了比例尺调整功能,该功能参照
https://bl.ocks.org/mbostock/db6b4335bf1662b413e7968910104f0f
这样缩放过程中坐标轴的tick和文字都会随着缩放一起调整
最后要把zoom放到整个svg上,而不是特定的元素上,才能保证在整个图形元素区域都起作用
import * as d3 from 'd3'
export default {
data () {
return {
width: 0,
height: 0,
svgGraphContainer: null,
splines: { node: null, lineGenerator: null, lines: [] },
polylines: { node: null, lineGenerator: null, lines: [] },
symbols: { node: null, lines: [] },
svg: null,
axises: {
node: null,
x: null,
xScale: null,
xContainer: null,
y: null,
yScale: null,
yContainer: null },
dragHandler: null,
zoomHandler: null
}
},
mounted () {
this.addZoomBehavior()
}
methods: {
addZoomBehavior () {
this.zoomHandler = d3.zoom()
.scaleExtent([0.1, 10]) // zoom limit
.translateExtent([[-100, -100], [this.width + 90, this.height + 100]]) // translate limit
.on('zoom', () => {
this.svgGraphContainer.attr('transform', d3.event.transform)
this.axises.xContainer.call(this.axises.x.scale(d3.event.transform.rescaleX(this.axises.xScale)))
this.axises.yContainer.call(this.axises.y.scale(d3.event.transform.rescaleY(this.axises.yScale)))
})
this.svg.call(this.zoomHandler)
}
}
}
该样例代码来自于vue单文件组件,所以这里的this指的是vue上下文组件本身
更多推荐
所有评论(0)