Welcome to the Treehouse Community
Want to collaborate on code errors? Have bugs you need feedback on? Looking for an extra set of eyes on your latest project? Get support with fellow developers, designers, and programmers of all backgrounds and skill levels here with the Treehouse Community! While you're at it, check out some resources Treehouse students have shared here.
Looking to learn something new?
Treehouse offers a seven day free trial for new students. Get access to thousands of hours of content and join thousands of Treehouse students and alumni in the community today.
Start your free trialWilfredo Casas
6,174 PointsI don't understand very well the utility of parentNode?
I don't seem to grasp why I need parentNode.
Isn't it possible to remove the li's without using parentNode (and removeChild)?
Also, the event.target syntax kinda confuses me.
list.addEventListener('click', (e) => {
if (e.target.tagName == 'BUTTON') {
let li = event.target.parentNode;
let ul = li.parentNode;
ul.removeChild(li);
}
})
2 Answers
miikis
44,957 PointsHi Wilfredo,
You need parentNode and removeChild because that is just how the DOM API works — you just have to work with it on its own terms.
As to your second question, whenever an event-listener is fired it is passed an Event object that contains the event details. One of these details is which DOM Element actually triggered the Event. This particular detail is what is stored in event.target.
Bappy Golder
13,449 PointsHey Wifredo,
First of all yes you can achieve the same behaviour though other means. Such as use jQuery or us an ID or class to target the element and then remove them. However here we are using parentNode so that we can learn about DOM traversal.
Also DOM traversal seems useless when you are working on your own project and have access to all your HTML & CSS files. However as you move forward with web programming DOM traversal will become more and more useful to you.
Second: event.target
Here is how I understand it:
- The whole
event.target
holds a value. Since we are using it inside an event listener, it only comes in action when we mouseover/click on the specific section we are invoking it on. - It also hold the value (element) on which we are calling the event listener, thus the "event" & the "target"
In our example we are using the event listener on the whole list section so a number of other elements and buttons also gets stored in the event.target
. To element storing everything we are using the if statement. Now event.target
only holds the button/list items. Here is how this work:
- User performs an action (i.e: mouse over or click)
- Our event listener listens to that event and fires up the
event
object and stores whatever we want inevent.target
- Now we use whatever is stored in
event.target
and use for what we need it for. (i.e: get the tag name, or go to the parent node etc.)
Hope that helps.
miikis
44,957 PointsHi Bappy,
Wilfredo's question is:
Isn't it possible to remove the li's without using parentNode (and removeChild)?
The answer to this question is not:
Yes, Wilfredo. Use jQuery.
Because jQuery is just a JavaScript library — written in JavaScript. And as far as JavaScript and the DOM goes, there is only one way to remove a DOM Element.
As to the rest of your answer, you might find my response to Wilfredo's follow-up question enlightening. In the case that it's still not clear for you, feel free to ask for clarification ;)
Lee Zamastil
21,628 PointsThe following is the DOM Removal code from the jQuery library —
function remove( elem, selector, keepData ) {
var node,
nodes = selector ? jQuery.filter( selector, elem ) : elem,
i = 0;
for ( ; ( node = nodes[ i ] ) != null; i++ ) {
if ( !keepData && node.nodeType === 1 ) {
jQuery.cleanData( getAll( node ) );
}
if ( node.parentNode ) {
if ( keepData && jQuery.contains( node.ownerDocument, node ) ) {
setGlobalEval( getAll( node, "script" ) );
}
node.parentNode.removeChild( node );
}
}
return elem;
}
Though jQuery simplifies the process of removing a node from the DOM tree, it still relies on parentNode
and removeChild
to perform this action.
Wilfredo Casas
6,174 PointsWilfredo Casas
6,174 PointsThanks Mikis
As for the first answer, are you sure there is no alternative solution?
As for the second, we used event listeners in previous courses and we didn't have to use arguments. So why do I have to use one now? And why do I have to write 'target' after it?
miikis
44,957 Pointsmiikis
44,957 PointsYes, I'm sure that there is not another way of removing DOM Elements from the DOM Tree that does not involve the parentNode -> childNode dance. Of course, this doesn't mean that people can't create libraries that act as wrappers for such kind of tasks. In fact, the DOM itself does have an API for this called removeChild but it doesn't have sufficient cross-browser support and — like I've said — it's simply doing the parentNode -> childNode thing under the hood.
So event listeners are functions that don't return anything but get passed an Event object as an argument whenever they are called/fired. I'm not sure if you've covered objects yet in your learning but if you haven't, you should do so ASAP; not much will make any sense without this prerequisite knowledge.
In any case, if you're not going to do anything with the Event object that the Browser passes in to your event-listener anytime your chosen event is triggered, you don't have to list it as a parameter:
This is probably the reason why you didn't see the "event" parameter in previous courses — because you didn't need it, because you weren't going to do anything with it. But now, it seems you need to know what element just got clicked on. So, now, you do need to use the Event object. Specifically, you need the target property on the Event object. If you're wondering what a property is, you need to go learn Object-Oriented Programming. For now, suffice it to say that the target property is where the Browser stores the "target" (naturally) of your event listener. The target will usually be a DOM Element but if you were listening for the scroll event or something, then it would just be the global window. Let me know if that makes sense.