Be the first user to complete this post
|
Add to List |
A visual explanation of the Enter, Update and Exit Selections in D3js
var multiples = [5, 10, 15, 20, 25];
<ul id="#example">
<li></li>
<li></li>
<li></li>
</ul>
What we wish to do directly implies a few things :-
At this point, it is necessary to be aware of three important terms
Update Selection: Represents mappings to DOM nodes that already exist on the DOM for which there exists a corresponding data point.
Enter Selection: Represents mappings to DOM nodes that will need to be created in order to map the excess data points.
Exit Selection: Represents mappings to DOM that dont have corresponding data points. The DOM nodes of these mappings will probably need to be deleted.
Now lets achieve this one step at a time.
// Get hold of your container
var container = d3.select('#example');
// Get hold of all the existing list items within the container
var children = container.selectAll('li');
// Create a one-on-one mapping of the node with the data array.
var updateSelection = children.data(multiples);
AHA ! : When you bind data to a d3 selection, the value that is immediately returned is the update selection itself. The enter and exit selections are properties on the update selection object.
// Mappings that represent pseudo DOM nodes that can potentially
// be created for each data unit
var enterSelection = updateSelection.enter();
// mapping representing real DOM nodes that could not be
// mapped to any item in the data
var exitSelection = updateSelection.exit();
Aha! By default D3 maps your array to the DOM nodes using index positions. i.e. it matches elements that have the same index in the result of the DOM selection to the data points that have the corresponding index.
The next AHA moment for me was when I realized that I can actually specify my own criteria when mapping elements by passing a second criteria to the data() function.
AHA! : You can specify your own function - a key function - in the second argument to the data() function. This function needs to return a value that will be used to make a comparison.
// Lets say our data is of this form
var multiples = [{'num':2},{'num': 4},{'num': 6}, {'num': 8}, {'num': 10}];
// Create a one-on-one mapping of the node with the data array.
var updateSelection = children.data(multiples, function (d) {
return d.num;
});
AHA! If you specify a key function, it gets executed for each DOM node as well as each data point in order to match the data point to the DOM node.
If a dom node exists, the function is executed using its data. If not, you get a null mapping which essentially becomes a part of your enter selection just like before.
And if a DOM node does not match with any data point after executing its key function, it becomes part of your exit selection.
Armed with this knowlege, you can now act in confidence and create/remove elements on the DOM.
d3.select('#example')
.selectAll('li')
.data(multiples, function (d) {return d.num;})
.enter() // Mappings that need DOM node creation
.append('li') // Create the DOM nodes for those mappings
.text(function (d) {return d.num;});
Also Read:
- d3 Fundamentals: Creating a simple bar graph
- Using d3js to draw a bar chart with an axis and some basic transitions
- Render a d3js Tree as a React Component
- Selecting a node in d3js based upon the value of its data
- Render a d3 tree with a minimum distance between the tree nodes