I'm trying to create a table where each row is a form. I want that each input is in a different table division, but I still need that for example, all first inputs belong to the same table head and so on.
What I'm trying to do is an editable grid, more or less this:
<table>
<tr>
<form method="POST" action="whatever">
<td><input type="text"/></td>
<td><input type="text"/></td>
</form>
</tr>
<tr>
<form method="POST" action="whatever">
<td><input type="text"/></td>
<td><input type="text"/></td>
</form>
</tr>
</table>
But apparently I cannot arrange the tags in that way (or so is what the w3c validator said).
Any good way to do this?
If you want a "editable grid" i.e. a table like structure that allows you to make any of the rows a form, use CSS that mimics the TABLE tag's layout: display:table, display:table-row, and display:table-cell.
There is no need to wrap your whole table in a form and no need to create a separate form and table for each apparent row of your table.
Try this instead:
<style>
DIV.table
{
display:table;
}
FORM.tr, DIV.tr
{
display:table-row;
}
SPAN.td
{
display:table-cell;
}
</style>
...
<div class="table">
<form class="tr" method="post" action="blah.html">
<span class="td"><input type="text"/></span>
<span class="td"><input type="text"/></span>
</form>
<div class="tr">
<span class="td">(cell data)</span>
<span class="td">(cell data)</span>
</div>
...
</div>
The problem with wrapping the whole TABLE in a FORM is that any and all form elements will be sent on submit (maybe that is desired but probably not). This method allows you to define a form for each "row" and send only that row of data on submit.
The problem with wrapping a FORM tag around a TR tag (or TR around a FORM) is that it's invalid HTML. The FORM will still allow submit as usual but at this point the DOM is broken. Note: Try getting the child elements of your FORM or TR with JavaScript, it can lead to unexpected results.
Note that IE7 doesn't support these CSS table styles and IE8 will need a doctype declaration to get it into "standards" mode: (try this one or something equivalent)
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
Any other browser that supports display:table, display:table-row and display:table-cell should display your css data table the same as it would if you were using the TABLE, TR and TD tags. Most of them do.
Note that you can also mimic THEAD, TBODY, TFOOT by wrapping your row groups in another DIV with display: table-header-group, table-row-group and table-footer-group respectively.
NOTE: The only thing you cannot do with this method is colspan.
Check out this illustration: http://jsfiddle.net/ZRQPP/
If all of these rows are related and you need to alter the tabular data ... why not just wrap the entire table in a form, and change GET to POST (unless you know that you're not going to be sending more than the max amount of data a GET request can send).
(That's assuming, of course, that all of the data is going to the same place.)
<form method="POST" action="your_action">
<table>
<tr>
<td><input type="text" name="r1c1" value="" /></td>
<!-- ... snip ... -->
</tr>
<!-- ... repeat as needed ... -->
</table>
</form>
You may have issues with column width, but you can set those explicitly.
<table>
<tr>
<td>
<form>
<table>
<tr>
<td></td>
<td></td>
<td></td>
<td></td>
<td></td>
<td></td>
</tr>
</table>
</form>
</td>
</tr>
<tr>
<td>
<form>
<table>
<tr>
<td></td>
<td></td>
<td></td>
<td></td>
<td></td>
<td></td>
</tr>
</table>
</form>
</td>
</tr>
</table>
You may want to also consider making it a single form, and then using jQuery to select the form elements from the row you want, serialize them, and submit them as the form.
See: http://api.jquery.com/serialize/
Also, there are a number of very nice grid plugins:
http://www.google.com/search?q=jquery+grid&ie=utf-8&oe=utf-8&aq=t&rls=org.mozilla:en-US:official&client=firefox-a
If using JavaScript is an option and you want to avoid nesting tables, include jQuery and try the following method.
First, you'll have to give each row a unique id like so:
<table>
<tr id="idrow1"><td> ADD AS MANY COLUMNS AS YOU LIKE </td><td><button onclick="submitRowAsForm('idrow1')">SUBMIT ROW1</button></td></tr>
<tr id="idrow2"><td> PUT INPUT FIELDS IN THE COLUMNS </td><td><button onclick="submitRowAsForm('idrow2')">SUBMIT ROW2</button></td></tr>
<tr id="idrow3"><td>ADD MORE THAN ONE INPUT PER COLUMN</td><td><button onclick="submitRowAsForm('idrow3')">SUBMIT ROW3</button></td></tr>
</table>
Then, include the following function in your JavaScript for your page.
<script>
function submitRowAsForm(idRow) {
form = document.createElement("form"); // CREATE A NEW FORM TO DUMP ELEMENTS INTO FOR SUBMISSION
form.method = "post"; // CHOOSE FORM SUBMISSION METHOD, "GET" OR "POST"
form.action = ""; // TELL THE FORM WHAT PAGE TO SUBMIT TO
$("#"+idRow+" td").children().each(function() { // GRAB ALL CHILD ELEMENTS OF <TD>'S IN THE ROW IDENTIFIED BY idRow, CLONE THEM, AND DUMP THEM IN OUR FORM
if(this.type.substring(0,6) == "select") { // JQUERY DOESN'T CLONE <SELECT> ELEMENTS PROPERLY, SO HANDLE THAT
input = document.createElement("input"); // CREATE AN ELEMENT TO COPY VALUES TO
input.type = "hidden";
input.name = this.name; // GIVE ELEMENT SAME NAME AS THE <SELECT>
input.value = this.value; // ASSIGN THE VALUE FROM THE <SELECT>
form.appendChild(input);
} else { // IF IT'S NOT A SELECT ELEMENT, JUST CLONE IT.
$(this).clone().appendTo(form);
}
});
form.submit(); // NOW SUBMIT THE FORM THAT WE'VE JUST CREATED AND POPULATED
}
</script>
So what have we done here? We've given each row a unique id and included an element in the row that can trigger the submission of that row's unique identifier. When the submission element is activated, a new form is dynamically created and set up. Then using jQuery, we clone all of the elements contained in <td>'s of the row that we were passed and append the clones to our dynamically created form. Finally, we submit said form.
You can use the form attribute id to span a form over multiple elements each using the form attribute with the name of the form as follows:
<table>
<tr>
<td>
<form method="POST" id="form-1" action="/submit/form-1"></form>
<input name="a" form="form-1">
</td>
<td><input name="b" form="form-1"></td>
<td><input name="c" form="form-1"></td>
<td><input type="submit" form="form-1"></td>
</tr>
</table>
If you need form inside tr and inputs in every td, you can add form in td tag, and add attribute 'form' that contains id of form tag to outside inputs.
Something like this:
<tr>
<td>
<form id='f1'>
<input type="text">
</form>
</td>
<td>
<input form='f1' type="text">
</td>
</tr>
If all of these rows are related and you need to alter the tabular data ... why not just wrap the entire table in a form, and change GET to POST (unless you know that you're not going to be sending more than the max amount of data a GET request can send).
I cannot wrap the entire table in a form, because some input fields of each row are input type="file" and files may be large. When the user submits the form, I want to POST only fields of current row, not all fields of the all rows which may have unneeded huge files, causing form to submit very slowly.
So, I tried incorrect nesting: tr/form and form/tr. However, it works only when one does not try to add new inputs dynamically into the form. Dynamically added inputs will not belong to incorrectly nested form, thus won't get submitted. (valid form/table dynamically inputs are submitted just fine).
Nesting div[display:table]/form/div[display:table-row]/div[display:table-cell] produced non-uniform widths of grid columns. I managed to get uniform layout when I replaced div[display:table-row] to form[display:table-row] :
div.grid {
display: table;
}
div.grid > form {
display: table-row;
div.grid > form > div {
display: table-cell;
}
div.grid > form > div.head {
text-align: center;
font-weight: 800;
}
For the layout to be displayed correctly in IE8:
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
...
<meta http-equiv="X-UA-Compatible" content="IE=8, IE=9, IE=10" />
Sample of output:
<div class="grid" id="htmlrow_grid_item">
<form>
<div class="head">Title</div>
<div class="head">Price</div>
<div class="head">Description</div>
<div class="head">Images</div>
<div class="head">Stock left</div>
<div class="head">Action</div>
</form>
<form action="/index.php" enctype="multipart/form-data" method="post">
<div title="Title"><input required="required" class="input_varchar" name="add_title" type="text" value="" /></div>
It would be much harder to make this code work in IE6/7, however.
If you can use javascript and strictly require it on your web, you can put textboxes, checkboxes and whatever on each row of your table and at the end of each row place button (or link of class rowSubmit) "save". Without any FORM tag. Form than will be simulated by JS and Ajax like this:
<script type="text/javascript">
$(document).ready(function(){
$(".rowSubmit").click(function()
{
var form = '<form><table><tr>' + $(this).closest('tr').html() + '</tr></table></form>';
var serialized = $(form).serialize();
$.get('url2action', serialized, function(data){
// ... can be empty
});
});
});
</script>
What do you think?
PS: If you write in jQuery this:
$("valid HTML string")
$(variableWithValidHtmlString)
It will be turned into jQuery object and you can work with it as you are used to in jQuery.
I second Harmen's div suggestion. Alternatively, you can wrap the table in a form, and use javascript to capture the row focus and adjust the form action via javascript before submit.
I had a problem similar to the one posed in the original question. I was intrigued by the divs styled as table elements (didn't know you could do that!) and gave it a run. However, my solution was to keep my tables wrapped in tags, but rename each input and select option to become the keys of array, which I'm now parsing to get each element in the selected row.
Here's a single row from the table. Note that key [4] is the rendered ID of the row in the database from which this table row was retrieved:
<table>
<tr>
<td>DisabilityCategory</td>
<td><input type="text" name="FormElem[4][ElemLabel]" value="Disabilities"></td>
<td><select name="FormElem[4][Category]">
<option value="1">General</option>
<option value="3">Disability</option>
<option value="4">Injury</option>
<option value="2"selected>School</option>
<option value="5">Veteran</option>
<option value="10">Medical</option>
<option value="9">Supports</option>
<option value="7">Residential</option>
<option value="8">Guardian</option>
<option value="6">Criminal</option>
<option value="11">Contacts</option>
</select></td>
<td>4</td>
<td style="text-align:center;"><input type="text" name="FormElem[4][ElemSeq]" value="0" style="width:2.5em; text-align:center;"></td>
<td>'ccpPartic'</td>
<td><input type="text" name="FormElem[4][ElemType]" value="checkbox"></td>
<td><input type="checkbox" name="FormElem[4][ElemRequired]"></td>
<td><input type="text" name="FormElem[4][ElemLabelPrefix]" value=""></td>
<td><input type="text" name="FormElem[4][ElemLabelPostfix]" value=""></td>
<td><input type="text" name="FormElem[4][ElemLabelPosition]" value="before"></td>
<td><input type="submit" name="submit[4]" value="Commit Changes"></td>
</tr>
</table>
Then, in PHP, I'm using the following method to store in an array ($SelectedElem) each of the elements in the row corresponding to the submit button. I'm using print_r() just to illustrate:
$SelectedElem = implode(",", array_keys($_POST['submit']));
print_r ($_POST['FormElem'][$SelectedElem]);
Perhaps this sounds convoluted, but it turned out to be quite simple, and it preserved the organizational structure of the table.
Tables are not meant for this, why don't you use <div>'s and CSS?
it's as simple as not using a table for markup, as stated by Harmen. You're not displaying data after all, you're collecting data.
I'll take for example the question 23 here: http://accessible.netscouts-ggmbh.eu/en/developer.html#fb1_22_5
On paper, it's good as it is. If you had to display the results, it'd probably be OK.
But you can replace it with ... 4 paragraphs with a label and a select (option's would be the headers of the first line). One paragraph per line, this is far more simple.
I have some code below that contains a form which contains a hiddenTable element that will show up once you click the search button. My question is: how would I display the table in a modal popup window while still having it be apart of the same form. The table contains a comment box and a submit button, I want the comment to be submitted along with all the other field's data inside the form.
<!DOCTYPE html>
<html>
<head>
<style>
#hiddenStuff {
display: none;
}
</style>
</head>
<body>
<form action="...">
// search fields here
<input type="button"
value="Search"
onclick="document.getElementById('hiddenTable').style.display='block';">
<table id="hiddenTable" class="form_table" style="display:none;">
<tr>
<td class="form_field_name">Enter a comment</td>
</tr>
<tr>
<td class="form_field_entry">
<textarea required ="true"
name="textarea" rows="10"
cols="50"
placeholder="Please enter a description for the performed task."></textarea>
</td>
</tr>
<tr>
<td class="form_field_entry">
<cfinput type="submit" name="createPeriod" value="Submit"/>
</td>
</tr>
</table>
</form>
</body>
</html>
Please excuse my messy code.
I agree with #Dan that it might be a pain for a ux standpoint to make this an extra modal, but if that's the result you want, you can surround your table in a div and add javascript to make the box "popup". Add CSS styles to create the black transparent background on click, and you will have a very simple modal popup.
I created a codepen for a reference - http://codepen.io/anon/pen/brEHI
I want to change the color of the text box in html when on focus. But my color is not changing.!
Html
<!DOCTYPE html>
<html>
<head>
<title>Make a new account</title>
<script src="http://ajax.googleapis.com/ajax/libs/jquery/1.10.2/jquery.min.js"></script>
<script src="script.js" type="text/javascript" ></script>
</head>
<body>
<h2 align="center" class="Heading">Want an account</h2>
<h3 align="center" class="Heading">Enter your details</h3>
<div align="center">
<form name="Info_Form">
<table>
<tr>
<td class="TD">Your Name Pal :</td> <td><input type="text" name="Name"></td>
</tr>
<tr>
<td class="TD">Your Password :</td> <td><input type="password" name="pwd"></td>
</tr>
<tr>
<td align="right" ><input type="submit" value="Submit"></td>
</tr>
</table>
</form>
</div>
</body>
</html>
my js file:
$(document).ready(function(){
$('h2').fadeOut(3000);
$(".TD").focus(function(){
$(this).css("background-color","blue");
});
});
What am i doing wrong?
Instead of :
$(".TD").focus(function(){
$(this).css("background-color","blue");
});
Use:
$("input").focus(function(){
$(this).css("background-color","blue");
});
It's because you can apply .focus() to only a limited number of element (links, form inputs).
From jQuery documentation :
The focus event is sent to an element when it gains focus. This event
is implicitly applicable to a limited set of elements, such as form
elements (, , etc.) and links (). In recent
browser versions, the event can be extended to include all element
types by explicitly setting the element's tabindex property. An
element can gain focus via keyboard commands, such as the Tab key, or
by mouse clicks on the element.
Here you try to apply it to a <td> tag.
Moreover, your <input> is not a child of .TD, so it's another problem in your code.
Why not simply use css :focus selector to achieve this ?
I have a list of records, e.g. addresses. It's displayed using the following html5/knockout code.
<section id="lists" data-bind="foreach: addresses, visible: addresses().length > 0">
<article>
<div>
<button>Edit</button>
<span data-bind="text: DisplayAddress"></span>
</div>
<p class="error" data-bind="visible: ErrorMessage, text: ErrorMessage"></p>
</article>
</section>
I want to show a table of editable input boxes () under the row after Edit button is clicked. Is there any way without generate a big html5 code?
I want to show the following editing html below the <div> after click the Edit button. (not completed)
<div>
<table>
<tr>
<th>Street address</th><th>Apt#</th><th>City</th><th>State</th><th>Zip</th>
</tr>
<tr>
<td><input type="text" class="col1"/></td>
<td><input type="text" class="col2"/></td>
<td><input type="text" class="col3"/></td>
<td><input type="text" class="col4"/></td>
<td><input type="text" class="col5"/></td>
</tr>
</table>
<button data-bind="click: saveAddress">Save</button>
<button data-bind="click: cancelAdding">Cancel</button>
</div>
There are a few reasonable options:
1) Use the if binding to control the rendering (not just visibility) of a block of HTML. Each row of data would have an observable property called isEditing. Then, add behavioral functions to control edit/cancel/etc. Your article template would include something like the following:
<div data-bind="if:isEditing">
<input type="text" data-bind="value: DisplayAddress" />
</div>
2) If it's just one field, you might want to create a custom binding handler that adds the behavior you want to an element (it would dynamically add/remove a field). There are a few good examples on Stackoverflow of this technique.
I wrote the following code to Calculate determinant of a nXn matrix.
I could successfully check if the order (i.e. n )entered by the user is valid or not.
However I am stuck now:
If I enter 3, I must display 9 text boxes and each must be checked. Firstly how do i display in general n^2 text boxes(i.e. n rows and n columns).
Secondly how I check each of them individually(i.e. it is a valid entry).
code:
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>Javascript App</title>
<script type="text/javascript" src="app1.js">
</script>
</head>
<body><h1 id="heading1" style="text-align:center; height:auto; width:auto; font-family:'Arial Black', Gadget, sans-serif">Determinant of a nxn matrix</h1>
<p id="paragraph1" style="font-family:'Arial Black', Gadget, sans-serif"> This program allows you to compute the determinant of a nxn matrix</p>
<p>
Input the order of the matrix
<br />
<input type="text" maxlength="3" name="fname" id="value" />
<input type="button" value="submit" onclick="verifyorder()" />
</p>
<p id="error"></p>
<p id="detspace">
<form method="post" action="displaydet()" name="matrix">
</p>
</body>
</html>
javascript:
var order;
function verifyorder(){
order=document.getElementById('value').value;
if(order>0){
displaydet();
}
else{
alert("Sorry, you need to enter a positive integer value, try again");
document.getElementById('error').innerHTML="Sorry, you need to enter a positive integer value, try again";
}
}
You will need to dynamically generate the text boxes since you don't know how many there will be in advance. Use the Document Object Model (DOM) for this, or alternatively, use a framework like JQuery which makes the DOM easier to use.
In this case, you need to create n * n text fields, and store them in a grid in two distinct senses of "grid". Firstly, you will want to store them in a physical HTML table, so the user sees them as a grid (that answers question 1). Secondly, you will want to store them in a 2D JavaScript array, so your code can manipulate them (that answers question 2).
So, use document.createElement("input") to create each text field. Use the setAttribute method to set the attributes of the text field, such as its "value" attribute to store the text inside it (these are the same attributes as you would see in the static HTML source for a text field). Then, store the text fields in a 2D array so you can refer back to them later. You should also be dynamically creating an HTML table (using the DOM), dynamically creating rows (tr) and cells (td), and then inserting into each td the generated text field.
Once you have done all that, the user can see all the text fields. When you need to validate them, just refer back to the 2D array you created. Use getAttribute("value") on each of the text fields to get their value back as a string. Then you can validate it as you like.
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>Untitled Document</title>
<script type="text/javascript" language="javascript">
function validation_reg()
{
var f1=document.form1;
var vname=f1.Login_Name.value;
var Password=f1.Password.value;
var submitv=f1.submita.value;
{
alert(vname);
alert(password);
}
}
</script>
</head>
<body>
<form name="form1" id="form1" action="" method="POST">
<table align="center" border="1" cellpadding="5">
<tr>
<td>Login Name*</td>
<td><input id="cname" input name="Login_Name" size="30" type="text" title="Your login name, please!" class="required" maxlength="20" /></td>
</tr>
<tr>
<td> Password*</td>
<td><input id="cpaswd" input name="Password" size="31" type="password" maxlength="12" title="Your Password, please!" class="required password" />
<br /></td>
</tr>
<tr>
<td><input class="submit" name="submita" type="submit" value="Submit" onclick="return validation_reg()"/></td></tr>
</table>
</form>
</body>
</html>