Search code examples
javascripthtmldomchild-nodes

Can't select HTML element with Javascript


     <body>
    <table id="table_x">
        <tbody>
            <tr>
                <td></td>                         
                <td>this box should be selected</td>
                <td></td>
                <td></td>
           </tr>
            <tr>
                <td></td>
                <td></td>
                <td></td>
                <td></td>
            </tr>
            <tr>
                <td></td>
                <td></td>
                <td></td>
                <td></td>
            </tr>
            <tr>
                <td></td>
                <td></td>
                <td></td>
                <td></td>
            </tr>
        </tbody>
     </table>
  </body>

With the following javascript code, I want to select the second "box" in the first row of the table with the id "table_x":

        var matrix = document.querySelector("#table_x");
        var row;
        var box;

        function select(x,y){
            row = matrix.childNodes[x];
            box = row.childNodes[y];
            return box;
        }

        var test = select(0,1);

However, when I want to output the element in the console (using the command console.log(test);) I just get back "undefined". What's wrong with my selection of the html element?


Solution

  • I'm going to assume you're trying to get row x, and then get cell y from it. (I'd've used y for rows and x for cells, but your code appears to be doing the opposite.)

    If so, you don't want to use childNodes because that includes not only elements, but also comment nodes, text nodes, etc.

    Separately, you'll want to make sure that matrix refers to the tbody element, not the table element..

    Then you can use any of these; note that one of them doesn't even need the matrix variable:

    function select1(x, y) {
      return matrix.children[x].children[y];
    }
    
    function select2(x, y) {
      return matrix.rows[x].cells[y];
    }
    
    function select3(x, y) {
      var selector = "#table_x tr:nth-child(" + (x + 1) + ") > td:nth-child(" + (y + 1) + ")";
      return document.querySelector(selector);
    }
    

    Example of all three:

    var matrix = document.querySelector("#table_x tbody");
    
    function select1(x, y) {
      return matrix.children[x].children[y];
    }
    
    function select2(x, y) {
      return matrix.rows[x].cells[y];
    }
    
    function select3(x, y) {
      var selector = "#table_x tr:nth-child(" + (x + 1) + ") > td:nth-child(" + (y + 1) + ")";
      return document.querySelector(selector);
    }
    
    select1(0, 0).style.color = "blue";
    select2(1, 1).style.color = "green";
    select3(2, 2).style.color = "red";
    <table id="table_x">
      <tbody>
        <tr>
          <td>x</td>
          <td>x</td>
          <td>x</td>
          <td>x</td>
        </tr>
        <tr>
          <td>x</td>
          <td>x</td>
          <td>x</td>
          <td>x</td>
        </tr>
        <tr>
          <td>x</td>
          <td>x</td>
          <td>x</td>
          <td>x</td>
        </tr>
        <tr>
          <td>x</td>
          <td>x</td>
          <td>x</td>
          <td>x</td>
        </tr>
      </tbody>
    </table>