0

I have a form written in HTML. In this form there are 2 buttons, and a table. Each row in the table contains a checkbox, and 2 text fields.

The buttons are to add and remove rows from the table. The remove button apply only to rows where their checkbox is checked. They have an onClick method that refers to 2 methods written in JavaScript on a <script> tag below, addRow(tableID) and deleteRow(tableID).

The addRow(tableID) works when I click its buttons, but nothing happens when I click the remove button, which refers to deleteRow(tableID) method.

This is the code of the form:

<form action="Page2.php" method="post" enctype="multipart/form-data">
  <!-- Contacts Details -->
  <p>
    <input type="button" value="Add Contact" onClick="addRow('contacts')" />
    <input type="button" value="Remove Contact" onClick="deleteRow('contacts')" />
    <p>(All actions apply only to entries with check marked check boxes only.)</p>
  </p>
  <table id="contacts" class="form" border="1">
    <tbody>
      <tr>
        <p>
          <td>
            <input type="checkbox" name="chk[]" checked="checked" />
          </td>
          <td>
            <label>Address</label>
            <input type="text" name="ADDRESS[]" />
          </td>
          <td>
            <label for="PHONE_NUMBER">Phone Number</label>
            <input type="text" class="small" name="PHONE_NUMBER[]" />
          </td>
        </p>
      </tr>
    </tbody>
  </table>
  <script>
    function addRow(tableID) {
      var table = document.getElementById(tableID);
      var rowCount = table.rows.length;
      if (rowCount < 10) {
        var row = table.insertRow(rowCount);
        var colCount = table.rows[0].cells.length;
        for (var i = 0; i < colCount; i++) {
          var newcell = row.insertCell(i);
          newcell.innerHTML = table.rows[0].cells[i].innerHTML;
        }
      } else {
        alert("Maximum Contacts Number is 10");
      }
    }

    function deleteRow(tableID) {
      var table = document.getElementById(tableID);
      var rowCount = table.rows.length;
      for (var i = 0; i < rowCount; i++) {
          debugger;
        var row = table.rows[i];
        var chkbox = row.cells[0].childNodes[0];
        if (null != chkbox && true == chkbox.checked) {
          if (rowCount <= 1) {
            alert("Cannot Remove all Contacts");
            break;
          }

          table.deleteRow(i);
          rowCount--;
          i--;
        }
      }
    }
  </script>

  <!-- Form Sending -->
  <input type="submit" value="Proceed">
</form>

EDIT #!:
I have just debugged the above code, and I found out that the variables chkbox and row from the deleteRow(tableID) method are shown in the debugger as undefined.

What can I do to fix this?

Ido Naveh
  • 2,442
  • 3
  • 26
  • 57
  • Do not ask two questions at once. Border set to 1 should be a separate question, that way it can be searched for and help others also. Also you should have a working example. Lastly, as Liam mentioned, what kind of debugging have you done? – Ruan Mendes Jun 28 '17 at 11:15
  • 1
    I edited your code to contain a debugger statement. Run it with dev tools open and you will what the problem is. Examine your `chkbox` variable. If you have never debugged before, see Liam's link https://stackoverflow.com/questions/988363/how-can-i-debug-my-javascript-code – Ruan Mendes Jun 28 '17 at 11:23
  • Did you even try what I suggested? My comment actually tells you exactly what the problem is. If you did, you should edit your question, show how you debugged it and what problems you are currently facing. Stack Overflow is not for others to debug your code for you, you have to show that you have done at least some level of debugging. Really, I have answered your question but I'm nudging you to learn how to figure it out on your own. Once you've added what debugging you have done, I'll be glad to vote to reopen, but I'm pretty sure you will figure it out on your own if you follow my tips. – Ruan Mendes Jun 28 '17 at 12:00
  • @JuanMendes I just debugged it, and I found that the variables `chkbox` and `row` are undefined. I will add it to the question and I will thank you if you will reopen the question. – Ido Naveh Jun 29 '17 at 08:33
  • row is not undefined.... chkbox is not undefined... It doesn't sound like you actually debugged it. – Ruan Mendes Jun 29 '17 at 11:20

1 Answers1

-1

The problem is that using row.cells[0].childNodes[0] is an extremely brittle way to find nodes. You are retrieving a text node instead of the checkbox. Using childNodes will break with even minimal changes to the HTML.

A more reliable way is to query for the element you are looking for

var chkbox = row.cells[0].querySelector('[type=checkbox]')

<form action="Page2.php" method="post" enctype="multipart/form-data">
  <!-- Contacts Details -->
  <p>
    <input type="button" value="Add Contact" onClick="addRow('contacts')" />
    <input type="button" value="Remove Contact" onClick="deleteRow('contacts')" />
    <p>(All actions apply only to entries with check marked check boxes only.)</p>
  </p>
  <table id="contacts" class="form" border="1">
    <tbody>
      <tr>
        <p>
          <td>
            <input type="checkbox" name="chk[]" checked="checked" />
          </td>
          <td>
            <label>Address</label>
            <input type="text" name="ADDRESS[]" />
          </td>
          <td>
            <label for="PHONE_NUMBER">Phone Number</label>
            <input type="text" class="small" name="PHONE_NUMBER[]" />
          </td>
        </p>
      </tr>
    </tbody>
  </table>
  <script>
    function addRow(tableID) {
      var table = document.getElementById(tableID);
      var rowCount = table.rows.length;
      if (rowCount < 10) {
        var row = table.insertRow(rowCount);
        var colCount = table.rows[0].cells.length;
        for (var i = 0; i < colCount; i++) {
          var newcell = row.insertCell(i);
          newcell.innerHTML = table.rows[0].cells[i].innerHTML;
        }
      } else {
        alert("Maximum Contacts Number is 10");
      }
    }

    function deleteRow(tableID) {
      var table = document.getElementById(tableID);
      var rowCount = table.rows.length;
      for (var i = 0; i < rowCount; i++) {
          debugger;
        var row = table.rows[i];
        var chkbox = row.cells[0].querySelector('[type=checkbox]');
        if (null != chkbox && true == chkbox.checked) {
          if (rowCount <= 1) {
            alert("Cannot Remove all Contacts");
            break;
          }

          table.deleteRow(i);
          rowCount--;
          i--;
        }
      }
    }
  </script>

  <!-- Form Sending -->
  <input type="submit" value="Proceed">
</form>
Ruan Mendes
  • 90,375
  • 31
  • 153
  • 217
  • I have just checked this method, but unfortunately this is still not working. I think it isn't working because that also `row` variable is undefined, as I wrote in the question – Ido Naveh Jul 05 '17 at 08:12
  • @IdoNaveh What do you mean it's not working? I pressed both the Add and the Remove Contact buttons and they added and removed rows. – Ruan Mendes Jul 05 '17 at 12:47
  • @downvoter This shouldn't bother me as much as it does... but who downvotes an answer with code that does exactly what the OP is asking for without any comment? – Ruan Mendes Jul 07 '17 at 13:42