Frage forJeder Callback wird nicht mit getElementsByClassName ausgeführt


Im folgenden Code,

<!DOCTYPE html>
<html>
    <head>
        <title>Hide odd rows</title>
        <meta charset="UTF-8">
    </head>
    <body>
        <div style="background-color:#8F9779;width:200px;height:30px;">
        </div>
        <hr style="width:200px" align="left">
        <table border="1" >
            <tr class="hide" >
                <td width="40" height="20">row 1</td>
            </tr>
            <tr>
                <td width="40" height="20">row 2</td>
            </tr>
            <tr class="hide">
                <td width="40" height="20">row 3</td>
            </tr>
            <tr>
                <td width="40" height="20">row 4</td>
            </tr>
            <tr class="hide">
                <td width="40" height="20">row 5</td>
            </tr>
        </table><br>
        <button type="button" name="HideRows">Hide Odd Rows</button>
        <script type="text/javascript" src="hideOddRows.js"></script>
    </body>
</html>

/* hideOddRows.js */
document.querySelector('[name=HideRows]').onclick = hideRows;

function hideRows(){
    var elements = document.getElementsByClassName('hide');
    elements.forEach(function(element){
        element.style.visibility = "hidden";
    });
    return true;
}

Wie pro Debugging, Callback-Funktion für jeden element von elements Array wird nicht bei Klickereignis ausgeführt.

Ich betrachte elements als Keyed-Sammlung, wie unten gezeigt.

enter image description here

-

Wie kann ich diesen Fehler beheben?


5
2017-12-16 04:10


Ursprung


Antworten:


forEach ist nicht im Prototyp des Array-like enthalten HTMLCollection Objekt zurückgegeben von getElementsByClassName.

Ein HTMLCollection Instanz ist Array-ähnlich, in der Sie auf Elemente durch Indizes zugreifen können, aber es enthält nicht alle Methoden eines Arrays, wie Sie mit entdeckt haben forEach.

Sie können die Methode für das Objekt jedoch manuell aufrufen, indem Sie auf die Methode aus dem Objekt zugreifen Array Prototyp.

var elements = document.getElementsByClassName('hide');
Array.prototype.forEach.call(elements, function(element){
    element.style.visibility = "hidden";
});

8
2017-12-16 04:12



Das forEach Methode ist für Arrays. Es funktioniert nicht, weil .getElementsByClassName() Gibt eine HTMLCollection zurück.

Um dies zu umgehen, verwenden Sie:

var elements = document.getElementsByClassName('hide');
Array.prototype.forEach.call(elements, function(element){
    element.style.visibility = "hidden";
});

oder kürzer:

var elements = document.getElementsByClassName('hide');
[].forEach.call(elements, function(element){
    element.style.visibility = "hidden";
});

2
2017-12-16 04:12



Sie können konvertieren elements zu einem Array und dann forEach () aufrufen.

 var elements = document.getElementsByClassName('hide');
 elements = Array.prototype.slice.call(elements,0);
    elements.forEach(function(element){
        element.style.visibility = "hidden";
    });

Geige :https://jsfiddle.net/assx7hmh/


1
2017-12-16 04:16



Basieren Sie auf Ihrem Code, hier ist meine Lösung:

function hideRows(){
  var elements = document.getElementsByClassName('hide');
  for(var key in elements) {
    if(elements.hasOwnProperty(key))
      elements[key].style.visibility = "hidden";
  }
  return true;
}

Sie müssen nur Objekt durchlaufen, weil forEach akzeptiere einfach das Array.


0
2017-12-16 04:38