Why doesn’t getElementsByClassName work without for?

Asked

Viewed 81 times

1

was creating a menu that had two buttons, a Description tab and another show tab of the data sheet.

I created a function in javascript that when clicking the button display of an would None and another block.

I did the following:

HTML

<button onclick='funcao("tec","des")'>Descricao</button>
<button onclick='funcao("des","tec")'>Tecnico</button>


<div class="des">
   <p>
      Isso eh uma descricao
   </p>
</div>

<div class="tec">
   <p>
      isso eh uma ficha tecnica
   </p>
</div>

JAVASCRIPT

function funcao(desaparece, aparece){
var desa, apar;

desa = document.getElementsByClassName(desaparece);
apar = document.getElementsByClassName(aparece);

desa.style.display = 'none';
apar.style.display = 'block';
}

but it wasn’t working I researched a little I did another function:

function funcao(desaparece, aparece){
     var desa, apar;

     desa = document.getElementsByClassName(desaparece);
     apar = document.getElementsByClassName(aparece);

     for (i = 0; i < desa.length; i++) {
         desa[i].style.display = "none";
     }

     for (i = 0; i < apar.length; i++) {
         apar[i].style.display = "block";
     }
}

and that worked , but I can not understand why one worked and another not.

1 answer

5


The getElementsByClassName returns a list, this is in the documentation:

The getElementsByClassName(classNames) method, when Invoked, must Return the list of Elements with class Names classNames for this.

A call to document.getElementById("example").getElementsByClassName("aaa") would Return a Htmlcollection.

Source: https://dom.spec.whatwg.org/#dom-Document-getelementsbyclassname

About the Htmlcollection (the "array" returned by getElementsByClassName), it is specified that:

  • collection . length:
    Returns the number of Elements in the Collection.
  • element = collection . item(index) or element = collection[index]:
    Returns the element with index index from the Collection. The Elements are Sorted in Tree order.
  • element = collection . namedItem(name) or element = collection[name]:
    Returns the first element with ID or name name from the Collection.

Source: https://dom.spec.whatwg.org/#htmlcollection.


Therefore, whenever you use the getElementsByClassName you will get a HTMLCollection, which is similar to a list, an array. So, to access each of the items in this list, you must use collection[index] or collection.item(index).


In case you don’t need to use the for since there is only one element. In the case of ONLY ONE element with the class, you could use:

desa = document.getElementsByClassName(desaparece)[0];
apar = document.getElementsByClassName(aparece)[0];

The [0] will fetch the first item of such a list (from Htmlcollection). However, for general cases, assuming there can be multiple elements with the same class you will need to use the for (or any other similar form).

That’s what you did, and that’s what worked:

 for (i = 0; i < desa.length; i++) {
     desa[i].style.display = "none";
 }

 for (i = 0; i < apar.length; i++) {
     apar[i].style.display = "block";
 }

That way, first you use the desa.length/apar.length (which is the collection.length) to know your limit, and get each item using the desa[i]/apar[i] (which is the collection[index]).

Browser other questions tagged

You are not signed in. Login or sign up in order to post.