【发布时间】:2018-02-27 13:44:55
【问题描述】:
我在 d3 中结合手动更新和缩放功能时遇到问题。
这是一个从一个较大的模块中截取的小演示代码,它只创建一个线性比例。
https://jsfiddle.net/superkamil/x3v2yc7j/2
class LinearScale {
constructor(element, options) {
this.element = d3.select(element);
this.options = options;
this.scale = this._createScale();
this.axis = this._createAxis();
this.linearscale = this._create();
}
update(options) {
this.options = Object.assign(this.options, options);
this.scale = this._createScale();
this.axis = this._createAxis();
this.linearscale.call(this.axis);
}
_create() {
const scale = this.element
.append('g')
.attr('class', 'linearscale')
.call(this.axis);
this.zoom = d3.zoom().on('zoom', () => this._zoomed());
this.element.append('rect')
.style('visibility', 'hidden')
.style('width', this.options.width)
.style('height', this.options.height)
.attr('pointer-events', 'all')
.call(this.zoom);
return scale;
}
_createScale() {
let range = this.options.width;
this.scale = this.scale || d3.scaleLinear();
this.scale.domain([
this.options.from,
this.options.to
]).range([0, range]);
return this.scale;
}
_createAxis() {
if (this.axis) {
this.axis.scale(this.scale);
return this.axis;
}
return d3.axisBottom(this.scale);
}
_zoomed() {
this.linearscale
.call(this.axis.scale(d3.event.transform.rescaleX(this.scale)));
let domain = this.axis.scale().domain();
this.element.dispatch('zoomed', {
detail: {
from: domain[0],
to: domain[1],
},
});
}
}
const scale = new LinearScale(document.getElementById('axis'), {
from: 0,
to: 600,
width: 600,
height: 100
});
document.getElementById('set').addEventListener('click', () => {
scale.update({
from: 0,
to: 100
});
});
- 将 x 轴缩小到 0 - 10000(随机数)
- 点击“设置”按钮
- X 轴将域设置为 0 - 100
- 再次开始缩小
-> 预期:缩放从域 0 - 100 开始
-> 结果:缩放跳回到之前的缩放级别 0 - 10000
我知道,d3 正在使用比例副本,我正在更新原始比例,但我没有找到如何组合它们或如何将缩放级别设置为原始比例的方法。
https://github.com/d3/d3-zoom/blob/master/README.md#transform_rescaleX
谢谢!
【问题讨论】:
-
当我按下“设置”按钮时,我得到了 0-100。
-
问题后来出现在“4. 再次开始缩小”。但现在已经修好了。看看 Cosma 的回答。
标签: javascript html d3.js