Reputation: 10217
I am playing with D3 force layout. In force layout, you have to give "links" and "nodes" in order to make the force graph. D3 interprets the "source" and "target" of the links to be the index of the nodes in the "nodes" array. My question is: How to index data by its ID in "nodes" attributes instead of its index in "nodes" array? Here is my Json file:
{
"nodes":
[
{"name": "A", "ID": 10},
{"name": "B", "ID": 20},
{"name": "C", "ID": 30},
{"name": "D", "ID": 40}
],
"links":
[
{"source": 10, "target": 20},
{"source": 20, "target": 30},
{"source": 30, "target": 40}
]
}
I know it has been asked here: D3: Using node attribute for links instead of index in array
But the solution is not what I want. Because recently I have seen some people doing the special indexing just by passing a simple key funciton:
http://flowingdata.com/2012/08/02/how-to-make-an-interactive-network-visualization/
node = nodesG.selectAll("circle.node")
.data(curNodesData, (d) -> d.id)
link = linksG.selectAll("line.link")
.data(curLinksData, (d) -> "#{d.source.id}_#{d.target.id}")
The problem is I do not understand the meaning of "#{d.source.id}_#{d.target.id}".
Would some like to explain it a little bit?
OK. The above is written in coffescript. When I tried to convert it to regular D3 javascript, the following cannot work:
node = nodesG.selectAll("circle.node")
.data(curNodesData,function(d) {return d.ID;})
link = linksG.selectAll("line.link")
.data(curLinksData, function(d) {return "#{d.source.id}_#{d.target.id}";})
Cannot work as expected either:
link = linksG.selectAll("line.link")
.data(curLinksData, function(d) {return d.source.id+"_"+d.target.id;})
Thanks Derek
Upvotes: 8
Views: 3097
Reputation: 54
This part is creating a unique id to be used when binding the data to the DOM objects.
(d) -> "#{d.source.id}_#{d.target.id}
I think this code would be equivalent without the lambda expression -
node = nodesG.selectAll("circle.node")
.data(curNodesData, function(d) { return d.source.id + _ + d.target.id; });
Upvotes: 1