Best way to layout in HTML forms? - html

I want to display an HTML form containing labelled text fields, like this:
First Name: [_____________]
Last Name: [_____________]
Date of Birth: [________]
My obvious approach is to use a <TABLE> and simply place the labels and text fields in its cells, but is there a better way, e.g. a CSS-based approach?
EDIT:
I'm looking for a way that reduces the verbosity in the HTML file.
And yes, I'm looking for auto-sizing of the labels. See a related question about wrapping labels

If you need the labels to the left of the fields like that, just go ahead and use a table. Not only do tables degrade nicely on older browsers, but they auto-size the column of labels to the text in them (assuming you use white-space: no-wrap on the cells containing the labels, and/or — and this is true heresy — the trusty old nowrap attribute on the th tag), they handle being made fairly narrow well, and they're easy. Make each label cell a header and each field cell a normal cell. And it's a pain, but make sure the labels really are labels and link to their fields, because accessibility matters, even if (perhaps especially if) you're using a table non-semantically.
I'd love to hear about CSS solutions that auto-size the label columns, handle being narrow well, and don't involve 18 hacks to deal with inconsistencies across browsers. I'd be thrilled to see them. But every time I've looked (and that's several), it's still been a gap. A gap that needs filling, IMV, so we can stop doing this without wearing hairshirts.
For anyone reading who doesn't need the labels to the left like that, check out jball's answer for a good-looking, semantic alternative.

In terms of usability and if vertical space is not a limiting factor, a list of fields with the label above each field is the quickest to read and fill out, and can be done aesthetically. See many of the usability studies on the web for more info, eg. http://www.lukew.com/resources/articles/web_forms.html

I'd like to use definition lists (<dl>) they tends to be semantically correct.
A label is defined by an user input. It has sense to me.
<dl> expresses semantic contents more accurately than a table.
<dl>
<dt><label for="name>Name</label></dt>
<dd><input type="text" id="name" /></dd>
<dt><label for="email>Email</label></dt>
<dd><input type="text" id="email" /></dd>
</dl>
Here is an example
By the way they degrade gracefully in all browser, even text-based.

I think something like this is what i do but also won't autosize to the length of the text but it's cleaner in my opinion
<form>
<label for="firstName">First Name</label>
<input type="textfield" name="firstName" />
<label for="lastName">Last Name</label>
<input type="textfield" name="lastName" />
</form>
label {
float:left;
width:30px;
}
input {
float:left;
margin-left:30px;
}

The article is a bit old, but I've always found a list apart's advice to be solid: (if you do want to get rid of your tables)
http://www.alistapart.com/articles/prettyaccessibleforms/

CSS Table Display
From IE8+ you can use CSS Table Display for this:
<!DOCTYPE html>
<html>
<head>
<style>
form > div > label { text-align: right; vertical-align: top }
form { display: table; }
form > div { display: table-row; }
form > div > label,
form > div > textarea,
form > div > input { display: table-cell; }
</style>
</head>
<body>
<form method="post">
<div>
<label for="name">Name</label>
<input type="text" id="name" size="14"/>
</div>
<div>
<label for="message">Message</label>
<textarea id="message"></textarea>
</div>
<div>
<label for="ssn">Social Security Number</label>
<input type="text" id="ssn"/>
</div>
<div>
<label></label>
<input type="submit" value="Send"/>
</div>
</form>
</body>
</html>

Use a CSS framework like Blueprint and use that to style the forms.
Another trick would be to create virual "columns" with css and float them next to each other. Labels in one column and inputs in another. Put that (both columns) in a div with a large enough width and float the columns the opposite way you want to align them.
Here's some code (because I am creating a form) that will work for basic forms. The only constraint is the large right margin on inputs.
form input, form select
{
float: right;
margin-right: 650px;
}
form label
{
float: right;
margin-top: 5px;
margin-right: 10px;
}
form .nofloat
{
float: none;
margin: 0;
}
form br
{
clear: both;
}
And layout like so
<input type="text" id="name" />
<label for="name">Name</label>
<br />
On top of this small, narrowly written code, there is an entire article related to creating tableless forms in CSS.

Typically, I have found that there are at least some issues when not using Tables for forms. The general things I have not been able to solve:
Background-color for fields/inputs is not really possible without a faux background
Auto-sizing columns, but I think this is OK
Field hover with CSS, you could use JS but Tables can do this with pure CSS
I might be missing a few things, but the most flexible mark-up if you are using CSS is as below:
<div class='form-field'>
<label>Name</label>
<input />
</div>
You have issues if you want multiple fields per label section, so you have to introduce another div to hold the inputs (to allow the label to still float left etc):
<div class='form-field'>
<label>Name</label>
<div class='form-inputs'>
<input />
<input />
</div>
</div>
With the above mark-up you can achieve very flexible forms, I won't post the CSS as it's very similar to a 2 Column-Layout.
I still need to sit down and try and figure out if pure CSS forms are viable for all occasions but tbh it's very unlikely!
Forms are the worst thing to style using CSS. The only major Cross Browser problems i've had are when styling the FieldSet and Legend elements. No real hacks, but they take some work to look good.

One problem with tables is the space bug. When you don't use tables you can write your label and input like this:
<label for="foo">Blah <input id="foo" type="text"/></label>
which properly encapsulates the input and the label.
In a table, on the other hand, you get those separated:
<td><label for="foo">Blah</label></td><td><input id="foo" type="text"/></td>
That means the area between the </label> and the <input/> does not respond to mouse clicks.
It's not too bad with plain fields, it's really annoying with radio buttons and checkboxes though (or maybe I'm just being super picky.)
Now, to answer your question: I don't think there is a good way to do formatting of a column in CSS (unless the column width is known--you could obtain that feat with JavaScript...) So T.J. Crowder certainly has an excellent answer.
However, there's one argument for CSS (and forced widths) as in one case I created a very large form that covered the whole screen. All the fields would appear in one screen (As the customer wanted) and the CMS did not output a table. But even though, a table would have been a nightmare simply because all the fields were for many placed in non-aligned columns. That would be quite difficult with a table (lots of rowspan using the table as a grid which would be a table for layout!).
Update:
As per comment below, singe31 says that <input/> cannot be defined within the <label> tag. This is wrong. The HTML 4.01 DTD is easy to read and we see that:
<!ELEMENT LABEL - - (%inline;)* -(LABEL) -- form field label text -->
<!ENTITY % inline "#PCDATA | %fontstyle; | %phrase; | %special; | %formctrl;">
<!ENTITY % formctrl "INPUT | SELECT | TEXTAREA | LABEL | BUTTON">
So in other words an <input/> can appear in a <label> tag. It is perfectly legal.
HTML 5 clearly shows that this is legal in the documentation on w3c here:
http://www.w3.org/html/wg/drafts/html/master/forms.html#the-label-element
Scroll down a bit up to the "Code Example" and you see:
Code Example
For example, on platforms where clicking or pressing a checkbox label checks the checkbox, clicking or pressing the label in the following snippet could trigger the user agent to run synthetic click activation steps on the input element, as if the element itself had been triggered by the user:
<label><input type=checkbox name=lost> Lost</label>
On other platforms, the behavior might be just to focus the control, or do nothing.

Related

Customising Insightly HTML contact form (aligned, spaced fields)

My apologies in advance, I have VERY modest coding experience and am trying to get to grips with HTML...
While applying some basic code for a contact form from insightly (below/attached), I'm trying to incorporate whats discussed here
Can't seem to get it right though, would just like the field titles on the left with the actual fields behind them aligned, with a return between each and while sticking to the coding needed for it to work with Insightly..
Thanks in advance for any help!
[EDIT 1]
Thanks a lot, I have now managed to make it appear more or less as wanted with a bit of CSS (attached). Unfortunately I can't quite get it to behave as need be though, it submits to insightly fine but it doesn't clear the fields upon submit, nor have I found a working method to provide confirmation that it was sent, other than a particularly ugly alert window (especially in chrome)..Any help on 'resetting on submit' and a way of telling the user that it was sent would be great! I did try a bit of CSS from here but to no avail...
<style type="text/css">
/*************CHSE Stylesheet ***/
body {
background-color: transparent;
height:360px;
width:280px;
}
textarea {
height:70px;
width:273px;
}
</style>
<style>
form label{
display: inline-block;
width: 100px;
font-weight: bold;
}
</style>
<form name="insightly_web_to_contact" action="https://example.insight.ly/WebToContact/Create" method="post"<span style="font-size:14px;"><span style="color:#FFFFFF;font-weight:bold"><span style="font-family:Open Sans;"><input type="hidden" name="formId" value="xxxxxxxxxxxxxxx/xxxxxx=="/>
<span style="font-size:14px;"><span style="color:#FFFFFF;font-weight:bold"><span style="font-family:Open Sans;"><center>Quick Message:</center><br/>
<label for="insightly_firstName">First Name: </label><input id="insightly_firstName" name="FirstName" required="" type="text"/><br/><br/><label for="insightly_lastName">Last Name: </label><input id="insightly_lastName" name="LastName" required="" type="text"/><br/><br/><input type="hidden" name="emails[0].Label" required="" value="Work"/><label for="email[0]_Value">Email: </label><input id="emails[0]_Value" name="emails[0].Value" required="" type="text"/><br/><br/><label for="insightly_background">Message: </label><textarea id="insightly_background" name="background">
</textarea><br/><br/><center><input type="submit" value="Send Message"></center></form>
The key to attractive layouts is DIVs and CSS.
First, use DIVs to group the various input areas, and to divide each area into left/right (via float).
For example, you might want the label and the input fields to be nicely aligned:
.frmGroup{overflow:hidden;}
.frmLeft {float:left;width:120px;}
.frmRight{float:left;width:300px;}
#thisone{margin-top:50px;}
<form>
<div class="frmGroup">
<div class="frmLeft"><label for="fn">First Name:</label></div>
<div class="frmRight"><input id="fn" type="text" /></div>
</div>
<div class="frmGroup">
<div class="frmLeft">Last Name:</div>
<div class="frmRight"><input type="text" /></div>
</div>
<div id="thisone">
<textarea cols="50" rows="5"></textarea>
</div>
</form>
The float instruction is particularly useful, as it allows you to align the DIVs side-by-side. However! It also removes the DIVs from the HTML "flow", meaning that they take zero vertical space. To counter that, add overflow:____ to the parent DIV. In example, I used overflow:hidden]. In the jsFiddle at bottom, experiment by deleting/adding that line.
You can also give an ID to a specific DIV and style it to have either margin or padding above/below/left/right.
DIVs have the added advantage of being block elements, which has the same effect as adding a <br> to the end.
*Also note that the <label> tag is really only useful for buttons, checkboxes, etc. because they allow the user to click the button/checkbox by also clicking on the text label.
Here is a jsFiddle of the above demo that you can experiment with.

how to keep more space between text in html page?

How do I get five more space between text in an HTML page? I am regularly suing but it is not enough.
In below example I need more space between LANDMARK and STREET in one line
<html>
<body>
LANDMARK:<input type="text" name="land_mark">
SREET:<input type="text" name="street">
</body>
</html>
You can seprate the elements close to each other using the margin property.
input {margin-right: 20px;}
However, a better way of achieving this would be to change your markup to become a little more semantic, a demo here
HTML :
<div class="form_container">
<form method="POST" name="form_name" class="some_form">
<label for="land_mark">
landmark
</label>
<input type="text" name="land_mark" id="land_mark" />
<label for="street">
street
</label>
<input type="text" name="street" id="street" />
</form>
</div>
CSS
.some_form label {
text-transform : uppercase;
margin-right: 5px;
}
.some_form input {
margin-right: 20px;
}
Update
The reason it is better to use labels to denote the input actions :
(source)
clicking the label focuses on the
text field, which is something a lot
of users expect
it's helpful for the accessibility reasons
how else is the user going to know which field is which? you could you
just text or a span or something, but
why would you?
It leads to a more semantic markup.
As far as not usng goes, it's best to seprate appearance and content, it helps keeping it much cleaner and maintainable. It is much better to just use something like margin-right : 10px, than specifying tons of
In this particular case(because the two words are in separate tags) a simple
margin-left: 20px;
would do.
But you should use the word-spacing CSS style to achieve this effect without &nbsp
take some lesson of css. It's very important to use css. margin property is a well solution given to you.But please take some knowledge of css. I bet it will be more helpful for your future plan

Is there a more efficient way to group-up a label with an input field so that they become block-like?

I want to make a HTML form for a webpage that is re-size-able ranging form full HD to smartphones. I want the distance form the label to the input to be the same distance such that if the form was to be placed in a div that for instance is 600px and the label and input field as line totals to 300px (including padding,margin, etc) that the fields order in 2 columns. If the div than after re-size would become 900px the form would spread over 3 columns.
The fields should then be ordered in the following manner:
with 2 columns:
F1 F4
F2 F5
F3 F6
with 3 columns:
F1 F3 F5
F2 F4 F6
Now since i am relatively new to HTML and CSS i personally would do this with a lot of div's but that seems a little bit redundant or just as really bad coding. I tried to do this with a <span style="width:300px;"> but the span wont be 300 px nor will it include the input field.
my current form:
<div class='main_text' style='width:55%;padding-left:10%;padding-right:10%;'>
<label>Name:</label>
<input id="name" type="text" value='Name'/><br />
Age:
<input id="age" type="text" value='21'/><br />
Insterests:
<input id="interests" type="text" value='Socer'/><br />
Targets:
<input id="targets" type="text" value='stop smoking for at least 2 years'/><br/>
Other:
<input id="other" type="text" value='I have 3 cats'/><br />
</div>
So the question in short is:
Is there a more efficient way to group-up a label with an input field so that they become block-like?
P.S. Im using XHTML 1.0 transitional
I suggest taking a look at existing frameworks like Bootstrap or Foundation that will provide you with a good base to start writing a responsive design.
For the record, a span is an inline element hence you cannot define a width on it. Declare it as display: inline-block; and you'll notice the width property is now respected.
It's common to see radio buttons and checkboxes element tuples wrapped from the label, like this:
<label> <input /> text </label>
However you will find more and better examples on bootstrap.
First of all: use the <label>´s "for"-attribute to link the label to the input-field:
<label for="name">Name:</label>
<input id="name" type="text" value='Name'/><br />
And then, no: if you want to "group them together", in a box with borders for example, the best is to use div. That´s my opinion.
EDIT:
I´m not that good at reading the whole question before I answer.
I agree that you should take a look at a responsive framework if you want to make things easier for you when you create web pages that should look great on mobile as well as desktop.
Twitter bootstrap is one: http://twitter.github.io/bootstrap/
Foundation is another: http://foundation.zurb.com/
Find one you like and try it out. Personally, I like Bootstrap the most.

checkboxes inside labels?

I see all over the web two ways that people code checkboxes, which one is correct?
<input id="a" type="checkbox"/><label for="a">checkbox</label>
<label for="b"><input id="b" type="checkbox">checkbox</label>
They both work fine in Chrome, is one more cross browser than the other? Is there any difference?
DEMO
Both are perfectly correct, valid and accessible as long as you associate input and label with for/id attributes, even when the input is right into the label` (see the best answer to the question linked by #AramKocharyan and my comment there)
Screen readers will read the associated label content when its user focus on a form element (input, select or textarea). When in a form, chances are they'll only read labels, legends and buttons (I mean reset, submit, image or button) because JAWS and alike have special modes; roughly the aim is to fill a form, not to read the content as with the rest of a web page.
You'll often find forms with a label on the left, input on center and some help on the right:
E-mail [ ] ex: johndoe#domain.com
With an input outside the label element, the hint will be coded with a span for example. It won't be heard by screen readers because it's not part of a label or submit button.
With an input inside a label element, you can put both the label and the hint into the label element:
<label for="email">
<strong>E-mail</strong>
<input type="text" id="email" name="whatever"> <!-- HTML4.01 doctype -->
<span>ex: johndoe#domain.com</span>
</label>
That way, the hint will be read to the AT user along with the real label.
Note: of course you'll style the strong and span differently, say resp. bold right-aligned and italic left-aligned. span isn't necessary for styling (just style label and cancel half of rules for strong) but it's more simple (simpler?) :)
It's as useful for errors as for hints:
<p class="error>
<label for="email">
<strong>E-mail</strong>
<input type="text" id="email" name="whatever" value="aaa"> <!-- HTML4.01 doctype -->
<span>ERROR: not a valid e-mail address. Example of a valid e-mail: johndoe#domain.com</span>
</label>
</p>
.error strong {
color: red;
font-weight: bold;
}
.error input {
border: 1px solid red;
}
.error span {
color: red;
}
That way, the error is read to screen readers (and color that they can't see or barely see isn't the only way of conveying information to them with the help of this text).
Either is correct.
Labels may contain inline elements (except other labels). Input elements are inline elements.
imho below:
Anyhow, I would not put the checkbox inside the label since it seems kinda weird to me. Labels are meant to label the input fields, hold a description, not to contain them.

Should I put input elements inside a label element?

Is there a best practice concerning the nesting of label and input HTML elements?
classic way:
<label for="myinput">My Text</label>
<input type="text" id="myinput" />
or
<label for="myinput">My Text
<input type="text" id="myinput" />
</label>
From the W3's HTML4 specification:
The label itself may be positioned before, after or around the
associated control.
<label for="lastname">Last Name</label>
<input type="text" id="lastname" />
or
<input type="text" id="lastname" />
<label for="lastname">Last Name</label>
or
<label>
<input type="text" name="lastname" />
Last Name
</label>
Note that the third technique cannot be used when a table is being used for layout, with the label in one cell and its associated form field in another cell.
Either one is valid. I like to use either the first or second example, as it gives you more style control.
I prefer
<label>
Firstname
<input name="firstname" />
</label>
<label>
Lastname
<input name="lastname" />
</label>
over
<label for="firstname">Firstname</label>
<input name="firstname" id="firstname" />
<label for="lastname">Lastname</label>
<input name="lastname" id="lastname" />
Mainly because it makes the HTML more readable. And I actually think my first example is easier to style with CSS, as CSS works very well with nested elements.
But it's a matter of taste I suppose.
If you need more styling options, add a span tag.
<label>
<span>Firstname</span>
<input name="firstname" />
</label>
<label>
<span>Lastname</span>
<input name="lastname" />
</label>
Code still looks better in my opinion.
Behavior difference: clicking in the space between label and input
If you click on the space between the label and the input it activates the input only if the label contains the input.
This makes sense since in this case the space is just another character of the label.
div {
border: 1px solid black;
}
label {
border: 1px solid black;
padding: 5px;
}
input {
margin-right: 30px;
}
<p>Inside:</p>
<label>
<input type="checkbox" />
Label. Click between me and the checkbox.
</label>
<p>Outside:</p>
<input type="checkbox" id="check" />
<label for="check">Label. Click between me and the checkbox.</label>
Being able to click between label and box means that it is:
easier to click
less clear where things start and end
Bootstrap checkbox v3.3 examples use the input inside: http://getbootstrap.com/css/#forms Might be wise to follow them. But they changed their minds in v4.0 https://getbootstrap.com/docs/4.0/components/forms/#checkboxes-and-radios so I don't know what is wise anymore:
Checkboxes and radios use are built to support HTML-based form validation and provide concise, accessible labels. As such, our <input>s and <label>s are sibling elements as opposed to an <input> within a <label>. This is slightly more verbose as you must specify id and for attributes to relate the <input> and <label>.
UX question that discusses this point in detail: https://ux.stackexchange.com/questions/23552/should-the-space-between-the-checkbox-and-label-be-clickable
If you include the input tag in the label tag, you don't need to use the 'for' attribute.
That said, I don't like to include the input tag in my labels because I think they're separate, not containing, entities.
Personally I like to keep the label outside, like in your second example. That's why the FOR attribute is there. The reason being I'll often apply styles to the label, like a width, to get the form to look nice (shorthand below):
<style>
label {
width: 120px;
margin-right: 10px;
}
</style>
<label for="myinput">My Text</label>
<input type="text" id="myinput" /><br />
<label for="myinput2">My Text2</label>
<input type="text" id="myinput2" />
Makes it so I can avoid tables and all that junk in my forms.
See http://www.w3.org/TR/html401/interact/forms.html#h-17.9 for the W3 recommendations.
They say it can be done either way. They describe the two methods as explicit (using "for" with the element's id) and implicit (embedding the element in the label):
Explicit:
The for attribute associates a label with another control explicitly: the value of the for attribute must be the same as the value of the id attribute of the associated control element.
Implicit:
To associate a label with another control implicitly, the control element must be within the contents of the LABEL element. In this case, the LABEL may only contain one control element.
Both are correct, but putting the input inside the label makes it much less flexible when styling with CSS.
First, a <label> is restricted in which elements it can contain. For example, you can only put a <div> between the <input> and the label text, if the <input> is not inside the <label>.
Second, while there are workarounds to make styling easier like wrapping the inner label text with a span, some styles will be in inherited from parent elements, which can make styling more complicated.
3rd party edit
According to my understanding html 5.2 spec for label states that the labels Content model is Phrasing content. This means only tags whose content model is phrasing content <label> are allowed inside </label>.
Content model A normative description of what content must be included
as children and descendants of the element.
Most elements that are categorized as phrasing content can only
contain elements that are themselves categorized as phrasing content,
not any flow content.
A notable 'gotcha' dictates that you should never include more than one input element inside of a <label> element with an explicit "for" attribute, e.g:
<label for="child-input-1">
<input type="radio" id="child-input-1"/>
<span> Associate the following text with the selected radio button: </span>
<input type="text" id="child-input-2"/>
</label>
While this may be tempting for form features in which a custom text value is secondary to a radio button or checkbox, the click-focus functionality of the label element will immediately throw focus to the element whose id is explicitly defined in its 'for' attribute, making it nearly impossible for the user to click into the contained text field to enter a value.
Personally, I try to avoid label elements with input children. It seems semantically improper for a label element to encompass more than the label itself. If you're nesting inputs in labels in order to achieve a certain aesthetic, you should be using CSS instead.
As most people have said, both ways work indeed, but I think only the first one should. Being semantically strict, the label does not "contain" the input. In my opinion, containment (parent/child) relationship in the markup structure should reflect containment in the visual output. i.e., an element surrounding another one in the markup should be drawn around that one in the browser. According to this, the label should be the input's sibling, not it's parent. So option number two is arbitrary and confusing. Everyone that has read the Zen of Python will probably agree (Flat is better than nested, Sparse is better than dense, There should be one-- and preferably only one --obvious way to do it...).
Because of decisions like that from W3C and major browser vendors (allowing "whichever way you prefer to do it", instead of "do it the right way") is that the web is so messed up today and we developers have to deal with tangled and so diverse legacy code.
I usually go with the first two options. I've seen a scenario when the third option was used, when radio choices where embedded in labels and the css contained something like
label input {
vertical-align: bottom;
}
in order to ensure proper vertical alignment for the radios.
I greatly prefer to wrap elements inside my <label> because I don't have to generate the ids.
I am a Javascript developer, and React or Angular are used to generate components that can be reused by me or others. It would be then easy to duplicate an id in the page, leading there to strange behaviours.
Referring to the WHATWG (Writing a form's user interface) it is not wrong to put the input field inside the label. This saves you code because the for attribute from the label is no longer needed.
One thing you need to consider is the interaction of checkbox and radio inputs with javascript.
Using below structure:
<label>
<input onclick="controlCheckbox()" type="checkbox" checked="checkboxState" />
<span>Label text</span>
</label>
When user clicks on "Label text" controlCheckbox() function will be fired once.
But when input tag is clicked the controlCheckbox() function may be fired twice in some older browsers. That's because both input and label tags trigger onclick event attached to checkbox.
Then you may have some bugs in your checkboxState.
I've run into this issue lately on IE11. I'm not sure if modern browsers have troubles with this structure.
There are several advantages of nesting the inputs into a label, especially with radio/checkbox fields,
.unchecked, .checked{display:none;}
label input:not(:checked) ~ .unchecked{display:inline;}
label input:checked ~ .checked{display:inline;}
<label>
<input type="checkbox" value="something" name="my_checkbox"/>
<span class="unchecked">Not Checked</span>
<span class="checked">Is Checked</span>
</label>
As you can see from the demo, nesting the input field first followed by other elements allows,
The text to be clicked to activate the field
The elements following the input field to be dynamically styled according to the status of the field.
In addition, HTML std allows multiple labels to be associated with an input field, however this will confuse screen readers and one way to get round this is to nest the input field and other elements within a single label element.