Avi
Avi

Reputation: 39

How to populate a table with javascript and print it

I have a form that the user can fill and print the table when they are done. I can not seem to validate if the user finished. Once the user finished populating the table, I would like the whole table to be printed. Right now it is only printing the last entry.

<!DOCTYPE html>

    <html>
    <head>
        <title>TODO supply a title</title>
        <meta charset="UTF-8">
        <meta name="viewport" content="width=device-width, initial-scale=1.0">

        <script type="text/javascript">

            function validateForm() 
            {       
                var x = document.getElementById('fname').value;

                if(x === null || x === "")
                {
                    document.getElementById('error1').innerHTML = "Invalid Entry";            
                }
                else
                    //tableCreate();
                addMore();
            }

            function addMore()
            {

                if(confirm("Would you like to add more names?") === true)
                {
                    document.getElementById('theForm').reset();
                //tableCreate();
                //console.log("ADD MORE");
                }
                else
                    tableCreate();
            }

            function tableCreate()
            {
                var N = document.getElementById('fname').value;
                var L = document.getElementById('lname').value;
                var D = document.getElementById('dob').value;

                var ar = [N, L, D];
                console.log(ar);
                document.write('<table>');
                document.write('<tr>');
                document.write('<th>First Name</th>');
                document.write('<th>Last Name</th>');
                document.write('<th>Date of Birth</th>');
                document.write('</tr>');                

                document.write('<tr');
                for(var i = 0; i < ar.length; i++)
                {
                    document.write('<br><td>' + ar[i] + '</td>');
                }
                document.write('</tr>');

                document.write('</table>');
            }            
        </script>
    </head>
    <body>

        <form name="theForm" action="FormAndTable.html" method="post">
            First Name: <input type="text" id="fname">
            <span style="color:red" id="error1"></span><br>
            Last Name: <input type="text" id="lname"><br>
            Date of Birth: <input type="text" id="dob"><br>
            <input type="button" value="Save" onclick="validateForm()">
        </form>

    </body>
    </html>

Upvotes: 0

Views: 2204

Answers (1)

Scott Marcus
Scott Marcus

Reputation: 65806

There is quite a bit wrong with your code.

  1. You are using document.write() to generate new content on the page. Not only does this cause the DOM to be modified each time you do it (performance), but you must include your document.write statements as the DOM is being built, which means the location of your code will determine if the results are what you expect. Instead, you should set up an "output area" that already exists in the DOM and when you have new data for the page, you just inject it into that output area. This is why you kept losing the earlier input, each time you added a new user, you were writing out an entirely new table, which was replacing the old content already written to the page.

  2. You are retrieving the DOM elements you need more than once. Instead just wait until the page is ready and then set up variables to hold on to the DOM reference you'll need throughout the code.

Please look at the working code snippet below for a much more modern, standards compliant and leaner solution to your problem.

// Wait until the DOM is loaded...
window.addEventListener("DOMContentLoaded", function(){  

  // Set up references to the DOM elements you'll need acces to:
  var fName = document.getElementById('fname');
  var lName = document.getElementById('lname');
  var dob = document.getElementById('dob');
  var oa = document.getElementById("outputArea");
  var btn = document.getElementById("btnSave");
  var frm = document.getElementById("theForm");
  var err = document.getElementById("error1");
  
  // Set up string variables for the beginning and end of the table
  var beginTable = '<table><tr><th>First Name</th><th>Last Name</th><th>Date of Birth</th></tr>';
  var endTable =   '</table>';
  
  // Variable to store the entire table as it grows
  var output = beginTable;

  
  // When the button is clicked, run the suppied function
  btn.addEventListener("click", function() {  
    
     // Gather up the input into an array
     var ar = [fName.value, lName.value , dob.value];
    
     // If there is no first name
     if(!fName.value) {
       // Display an error
       err.innerHTML = "Invalid Entry";            
     } else {
       // There is data, begin a new row
       output +="<tr>";
       
       // Loop over the array and inject the input element's values into new table cells
       for(var i = 0; i < ar.length; ++i) {
           output += '<td>' + ar[i] + '</td>';
       }
       // End the row
       output +="</tr>";
       
       // Ask if user is done
       addMore();
     }
  });
  
                          
  function addMore() {

    if(confirm("Would you like to add more names?")) {
      // Not done yet, clear form out
      theForm.reset();
    } else {
      // Done. close up the table
       output += endTable;
      // Write the string to the waiting output area
       oa.innerHTML = output;
    }
   
  }

    
});
<form name="theForm" id="theForm" action="FormAndTable.html" method="post">
            First Name: <input type="text" id="fname"><span style="color:red" id="error1"></span><br>
            Last Name: <input type="text" id="lname"><br>
            Date of Birth: <input type="text" id="dob"><br>
            <input type="button" value="Save" id="btnSave">
        </form>


        <!-- Instead of document.write, which writes over the document, set up a placeholder
             for output that starts off empty, but at least is positioned in the DOM ahead of time. -->
        <div id="outputArea"></div>

Upvotes: 1

Related Questions