我不确定这是d3.js问题还是javascript可见性问题。我有两个函数将相同的事件监听器分配给不同的节点:
function render_line(){
var x = d3.scale.ordinal();
...
d3.select("#my_line").on("click", onclick);
}
function render_bar(){
var y= d3.scale.linear();
...
d3.select("#my_bar").on("click", onclick);
}
function onclick(d,i){
use(x,y) // error: can't access x or y
...
}
我认为render_line()
和render_bar()
共享相同的事件监听器功能是有意义的,因为点击一个也应该更新另一个,但我不知道如何解决变量范围问题。
答案 0 :(得分:1)
如果您在函数之外声明变量然后分配给它们(不使用函数中的var
关键字)那么您的函数将是 closures ,被授予访问权限设置并从这些变量中获取值。
var x,y;
function foo(){
x = d3.scale.ordinal();
d3.select("...").on("click",onclick);
}
function bar(){
y = d3.scale.linear();
d3.select("...").on("click",onclick);
}
function onclick(){
// has access to both x and y here
}
或者,如果感觉太脏,那么在事件注册期间在局部变量周围创建一个闭包,将值传递给共享函数:
function foo(){
var x = d3.scale.ordinal();
d3.select("...").on("click",function(evt){
onclick.call(this,evt,x);
});
}
function foo(){
var y = d3.scale.linear();
d3.select("...").on("click",function(evt){
onclick.call(this,evt,y);
});
}
function onclick(evt,scale){
// Use 'scale' passed in
}
请注意,在这种情况下,您无法在以后取消注册onclick
,因为这不是向处理程序注册的函数。