0

How can I make event.target work for not just the div given but also all it's children? The best I can come up with is to either:

1) list all children in the event.target function ie:

window.addEventListener('mouseup', function (event) {

  if(event.target != div && event.target != divChild1 && event.target != divChild2 && event.target != divChild3 && event.target != divChild4 && event.target != divChild5 ... && event.target != divChildn) {

  closeWindow();

  } });

OR

2) put all the children in a class (which seems like an awful lot of html) and then just have event.target refer to that class i.e.:

window.addEventListener('mouseup', function (event) {

      if(event.target != classWithAbout50divs) {

      closeWindow();

      } });

But surely there is a way that requires less code..?

And please, no jquery. Thanks

Normajean
  • 1,075
  • 3
  • 11
  • 28
  • Can you explain the big picture? Which problem are you trying to solve by implementing this solution? –  Nov 29 '19 at 10:36
  • I'm trying to make a div and its children disappear whenever I click anywhere on the screen, as long as I don't click on the actual div or its children. – Normajean Nov 29 '19 at 10:40
  • Right, one way to do that is to put the div inside a window-filling transparent overlay div and simply detect clicks on the overlay. –  Nov 29 '19 at 10:42
  • Possible duplicate of [Detect click outside div using javascript](https://stackoverflow.com/questions/36695438/detect-click-outside-div-using-javascript) –  Nov 29 '19 at 10:45

3 Answers3

0

If you only need direct children you can use element.children to loop though the children of said div.

Otherwise element.querySelectorAll('*'); should get you all elements inside of said element.

Gavin
  • 2,214
  • 2
  • 18
  • 26
0

You can use a variation of the answer provided here to check whether event.target is the div in question or any of its children.

For example:

function isDescendantOrSelf(parent, child) {
     let node = child;
     while (node != null) {
         if (node == parent) {
             return true;
         }
         node = node.parentNode;
     }
     return false;
}

window.addEventListener('mouseup', function (event) {
    const root = document.getElementById('handle');
    
    if (! isDescendantOrSelf(root, event.target)) {
        console.log('Passed!');
    }
});
<div id="handle">
    <div>Thou</div>
    <div>
        shall <div>not</div>
    </div>
    <div>pass</div>
<div>

If you have the luxury of ignoring older browsers, you can refactor isDescendantOrSelf() to use Node.contains() (https://developer.mozilla.org/en-US/docs/Web/API/Node/contains), as pointed out by Adam Heath in the comments.

0

I seem to have found a solution I like. First thing's first:

event.target != document.getElementsByClassName("myClassName");

Event.target doesn't seem to work if classes are referenced. I've only managed to make it work if I reference elements by ID. That is:

event.target != document.getElementById("myDivId");

Now, if I wanted something to happen whenever I DON'T click on a div and all it's children, instead of writing:

window.addEventListener('click', function (event) {
  if(event.target != myDivId) {
    doSomething();
    console.log("something is done");
  }
})

I've found success with this:

window.addEventListener('click', function (event) {
  if(!myDivId.contains(event.target) {
    doSomething();
    console.log("something is done");
  }
})

For potential support issues, see https://stackoverflow.com/a/43249467/11930305

Normajean
  • 1,075
  • 3
  • 11
  • 28