How do I remove all children elements from a node and then apply them again with different color and size?
Your answer will work, but for posterity, these methods are more generic.
Remove all children from HTML:
d3.select("div.parent").html("");
Remove all children from SVG/HTML:
d3.select("g.parent").selectAll("*").remove();
The .html("")
call works with my SVG, but it might be a side effect of using innerSVG.
My first advice is that you should read the d3.js
API about selections: https://github.com/mbostock/d3/wiki/Selections
You have to understand how the enter()
command works (API). The fact that you have to use it to handle new nodes has a meaning which will help you.
Here is the basic process when you deal with selection.data()
:
-
first you want to "attach" some data to the selection. So you have:
var nodes = visualRoot.selectAll(".node") .data(graphData.nodes)
-
Then you can modify all nodes each times data is changed (this will do exactly what you want). If for example you change the radius of old nodes which are in the new dataset you loaded
nodes.attr("r", function(d){return d.radius})
-
Then, you have to handle new nodes, for this you have to select the new nodes, this is what
selection.enter()
is made for:var nodesEnter = nodes.enter() .attr("fill", "red") .attr("r", function(d){return d.radius})
-
Finally you certainly want to remove the nodes you don't want anymore, to do this, you have to select them, this is what
selection.exit()
is made for.var nodesRemove = nodes.exit().remove()
A good example of the whole process can also be found on the API wiki: https://github.com/mbostock/d3/wiki/Selections#wiki-exit
in this way, I have resolved it very easily,
visualRoot.selectAll(".circle").remove();
visualRoot.selectAll(".image").remove();
and then I just re-added visual elements which were rendered differently because the code for calculating radius and color had changed properties. Thank you.