admin管理员组

文章数量:1414614

Vanilla JS. Trying to run a function on click of an element if the body tag has a class of example. No jQuery solutions please, I e from jQuery and want to learn and understand this simple task in JavaScript.

More so if you care to let me know, where is the error in my thinking please? Do I need to wrap the onclick event inside the condition for the body class? Tried that but also not getting the alert.

    var imgContainer = document.querySelector('.img-container');

    var bodyTag = document.getElementsByTagName('body');

    var bodyClassName = bodyTag.classname;

    imgContainer.onclick = infoBox;

    function infoBox(event) {

      if (bodyTag.classList.contains("example")) {

        alert('img-container has been clicked');

      }
    }
<body class="example">
  <div class="img-container">
    <img src="" alt="dummy image">
    <div class="img-infobox">
      <p>This is a dummy image from /</p>
    </div>
  </div>
</body>

Vanilla JS. Trying to run a function on click of an element if the body tag has a class of example. No jQuery solutions please, I e from jQuery and want to learn and understand this simple task in JavaScript.

More so if you care to let me know, where is the error in my thinking please? Do I need to wrap the onclick event inside the condition for the body class? Tried that but also not getting the alert.

    var imgContainer = document.querySelector('.img-container');

    var bodyTag = document.getElementsByTagName('body');

    var bodyClassName = bodyTag.classname;

    imgContainer.onclick = infoBox;

    function infoBox(event) {

      if (bodyTag.classList.contains("example")) {

        alert('img-container has been clicked');

      }
    }
<body class="example">
  <div class="img-container">
    <img src="https://dummyimage./320x120/000/fff" alt="dummy image">
    <div class="img-infobox">
      <p>This is a dummy image from https://dummyimage./</p>
    </div>
  </div>
</body>

Edit
From the given answers I am thinking that instead of returning an array like object and querying the DOM it would be fastest to just just document.body. no?

And this then means this question does not really have to do with

What do querySelectorAll, getElementsByClassName and other getElementsBy* methods return?

since the answer provided by the ment from https://stackoverflow./users/949476/dfsq uses neither of the methods from the linked answer.

Also
How can I pare the speed of using the document.querySelector vs. document.getElementsByTagName('body')[0]; vs. document.body please?

Like to give an explanation why I accepted what answer to be fair as all answers provide a working solution.

Answer
Since all answers work and document.body is fastest but also for another reason I like to post my answer here.

I am using this script from "4 novel ways to deal with sticky :hover effects on mobile devices" to handle the sticky hover problem. With this a class is added to the html tag of the site.

At first I had the click function inside the condition to check for the body or html class and only fire the click functions once the class is met, however with using this script I had to first run the function and only once it is run check if the html/body has the wanted class.

So while

  if (bodyTag.classList.contains("example")) {

    imgContainer.onclick = infoBox;

    function infoBox(event) {
        alert('img-container has been clicked and body has class "example"');    
    }

as well as

var bodyClassName = bodyTag.classname;

imgContainer.onclick = infoBox;

function infoBox(event) {

  if (bodyTag.classList.contains("example")) {

    alert('img-container has been clicked');

  }
}

works in a pure JSFiddle, it won't work with this setting since the sticky hover script sets the desired class on the element once a touch is made.

So once a click is made (I assume) it is then already too late to check for a condition outside of this touch/tap/click event and hence it won't fire.

In the end this leads to these simple lines that work together fine with the sticky hover script. The click event must run first and then check for the desired class/condition.

var imgContainer = document.querySelector('.img-container');

imgContainer.onclick = infoBox;

function infoBox(){

    if (document.documentElement.classList.contains('can-touch')) {
        alert('click on touch');
    }
}
Share Improve this question edited May 23, 2017 at 10:29 CommunityBot 11 silver badge asked Jan 15, 2017 at 15:24 lowtechsunlowtechsun 1,9555 gold badges27 silver badges56 bronze badges 8
  • 4 var bodyTag = document.getElementsByTagName('body')[0];: jsfiddle/z6yad20p/2 – haim770 Commented Jan 15, 2017 at 15:26
  • 1 Or simply var bodyTag = document.body; – haim770 Commented Jan 15, 2017 at 15:27
  • .getElementsByTagName(): "Returns an HTMLCollection of elements with the given tag name." – Andreas Commented Jan 15, 2017 at 15:27
  • So the [0] tells it to look for the first item in the array, but why when there is only one body tag? Do I need to explicitly declare that I am looking for the first body tag in the collection of elements even if there is only one element in the collection? – lowtechsun Commented Jan 15, 2017 at 15:31
  • 1 Up to you. I would say that it's preferred. But it's good that you learned about document.getElementsByTagName being a collection too. – dfsq Commented Jan 15, 2017 at 15:38
 |  Show 3 more ments

2 Answers 2

Reset to default 4

Selector used for selecting body element is not appropriate.

getElementsByTagName will give an array like object so you will have to use index to get the first element.

Read : https://developer.mozilla/en-US/docs/Web/API/Element/getElementsByTagName

you are already using querySelector which return the first matching element , do the same for body as well.

Read : https://developer.mozilla/en-US/docs/Web/API/Document/querySelector

var imgContainer = document.querySelector('.img-container');

var bodyTag = document.querySelector('body');

var bodyClassName = bodyTag.classname;

imgContainer.onclick = infoBox;

function infoBox(event) {

  if (bodyTag.classList.contains("example")) {
  
    alert('img-container has been clicked and body has class "example"');
    
  }
}
<body class="example">

  <div class="img-container">
    <img src="https://dummyimage./320x120/000/fff" alt="dummy image">
    <div class="img-infobox">
      <p>This is a dummy image from https://dummyimage./</p>
    </div>
  </div>

</body>

Performance Comparision : https://jsperf./body-selector-parision

The document.getElementsByTagName returns a HTMLCollection which can be accessed as an array of objects, all you need is to select the first by using [0] after it like the following example:

var imgContainer = document.querySelector('.img-container');

    var bodyTag = document.getElementsByTagName('body')[0];

    var bodyClassName = bodyTag.classname;

    imgContainer.onclick = infoBox;

    function infoBox(event) {

      if (bodyTag.classList.contains("example")) {

        alert('img-container has been clicked');

      }
    }
<body class="example">
  <div class="img-container">
    <img src="https://dummyimage./320x120/000/fff" alt="dummy image">
    <div class="img-infobox">
      <p>This is a dummy image from https://dummyimage./</p>
    </div>
  </div>
</body>

本文标签: javascriptCheck if element has class on click of another element and run a functionStack Overflow