简体   繁体   English

D3单击事件处理程序

[英]D3 Click Event Handler

I'm currently learning D3 and had a question relating to interactivity. 我目前正在学习D3并且有一个与交互性有关的问题。

The following example works to resize a group of circles on-screen based on the button clicked. 以下示例适用于根据单击的按钮在屏幕上调整一组圆圈的大小。 It works (I am following a tutorial). 它工作(我正在按照教程)。 Essentially, key names from a CSV file are bound to each button, which when clicked, relays that key name to an attached function (named buttonClick in this example) which is used to access the values for that key/value pair in each object of my data. 本质上,CSV文件中的键名绑定到每个按钮,单击该按钮时,将该键名称中继到附加函数(在此示例中名为buttonClick),该函数用于访问每个对象中的键/值对的值。我的数据。 The d3.max() function then is used to calculate the max value, which is used to determine a new scale and redraw the circles accordingly. 然后使用d3.max()函数计算最大值,该最大值用于确定新比例并相应地重绘圆圈。

My question is: How does the function buttonClick know to accept the "data" attribute bound to each button as an argument? 我的问题是:函数buttonClick如何知道接受绑定到每个按钮的“data”属性作为参数? Why are there no parentheses for the function when it is called inside the onclick event handler? 为什么在onclick事件处理程序中调用函数时没有括号?

Thanks for any help you can provide. 感谢您的任何帮助,您可以提供。

function createSoccerViz() {

d3.csv("worldcup.csv", data => {overallTeamViz(data)

});

function overallTeamViz(incomingData) {   
d3.select("svg")
.append("g")
.attr("id","teamsG")
.attr("transform", "translate(50,300)")
.selectAll("g").data(incomingData).enter()
.append("g")
.attr("class", "overallG")
.attr("transform", (d,i) => "translate(" + i * 60 + "," + 0 +")");
var teamG = d3.selectAll("g.overallG")
teamG.append("circle")
.attr("r",20)
teamG.append("text")
.text(d => d.team)
.attr("y", 30)

dataKeys = Object.keys(incomingData[0])
.filter(d => d !== "team" && d !== "region")

d3.select("#controls").selectAll("button.teams")
.data(dataKeys).enter()
.append("button")
.html(d => d)
.on("click", buttonClick) ////// Why no parentheses here?


function buttonClick(datapoint) {
var maxValue = d3.max(incomingData, d => parseFloat(d[datapoint]))
var radiusScale = d3.scaleLinear().domain([0, maxValue]).range([2,20])
d3.selectAll("g.overallG").select("circle")
    .attr("r", d => radiusScale(d[datapoint]))
}

You have two questions here: 你有两个问题:

  1. Why are there no parentheses for the function when it is called inside the onclick event handler? 为什么在onclick事件处理程序中调用函数时没有括号?

Regarding the parenthesis, if you had them... 关于括号,如果你有它们......

.on("click", buttonClick())

... you'd be passing the result of the function to the event listener (in your case, undefined ), and that's not what you want. ...你将把函数的结果传递给事件监听器(在你的情况下, undefined ),这不是你想要的。

Instead, you want the function to be called when you click the button, hence: 相反,您希望在单击按钮时调用该函数,因此:

.on("click", buttonClick)

Or, alternatively: 或者,或者:

.on("click", function(){
    buttonClick()
})
  1. How does the function buttonClick know to accept the "data" attribute bound to each button as an argument? 函数buttonClick如何知道接受绑定到每个按钮的“data”属性作为参数?

Regarding the first argument the API is clear: 关于API的第一个论点是明确的:

When a specified event is dispatched on a selected element, the specified listener will be evaluated for the element, being passed the current datum (d), the current index (i), and the current group (nodes), with this as the current DOM element (nodes[i]). 当在所选元素上调度指定事件时,将为元素评估指定的侦听器,传递当前数据 (d),当前索引(i)和当前组(节点),并将其作为当前值DOM元素(nodes [i])。 (emphasis mine) (强调我的)

Therefore, you don't need to explicitly specify the first argument: it will be the datum by default. 因此,您不需要显式指定第一个参数:默认情况下它将是数据。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM