# Form structure

Form elements can be used outside the form element, but they will not do anything on their own, and the behaviour must be customised with JavaScript. I.e. you need to add an event listener that triggers on changes in the element (more on that in later chapters). In this chapter we will only concern ourselves with the `<form>` element and elements inside it. Presented here are the elements `<fieldset>`, `<legend>`, `<label>`, `<output>` and `<input>`.

## Grouping and labeling

The element `<fieldset>` is used to create groups of elements within a form that share the same purpose. This can be to group radio buttons together, or several input fields that belong together, e.g. all the fields that make up the address (name, street address, city, zip code, country). A `<fieldset>` can be labeled with a `<legend>` element. This element describes the purpose of the `<fieldset>`. Assistive technologies, such as screen readers, use `<legend>` to label widgets inside the `<fieldset>` element.

The `<label>` element is used to label a widget, describing what the content for the form element should be, e.g. name or e-mail. The `<label>` can have a attribute `for`, which links the label to the widget with the same `id`. Using the `for` attribute lets assistive technologies read your page. That is not the only reason for using the `for` attribute though. With it, users can click the label to active the corresponding widget. This is especially useful for radio buttons and checkboxes.

You can see `<fieldset>`, `<legend>` and `<label>` used below, together with the `<input>` element. If you want the label to be placed after the `<input>` element, you should move it below the element, but within the `<label>` element. `<br>` is used to place the next `<label>` on a new line, rather than on the same line. This is not done for the widgets city and zip, thus they will be on the same line.

```
<form>
  <fieldset>
    <legend>What is your address?</legend>
    <label for="fullname">
      Full name:
      <input type="text" id="fullname" name="address">
    </label>
    <br>
    <label for="street">
      Street:
      <input type="text" id="street" name="address">
    </label>
    <br>
    <label for="city">
      City:
      <input type="text" id="city" name="address">
    </label>
    <label for="zip">
      Zip:
      <input type="number" id="zip" name="address">
    </label>
  </fieldset>
</form>
```

## Output

The `<output>` is used to store the result from a calculation, e.g. from several other `<input>` elements. You can use the `for` attribute to list the IDs of other elements that contribute input values to the calculation. These IDs must be divided by a space

```
<output for="income tax"></output>
```

## Input

The `<input>` element is the most essential element in the form, as it is the source of information from the user. This element can change radically, dependent on what value the `type` attribute is given. In the example below, the attribute `text` is given the value `text`, which will give a text field the user can fill out.

```
<input type="text" name="street" id="street">
```

The value for the `type` attribute can be categorised into four categories: single line text fields, controls without text input, time and date controls, and buttons. The `<input>` element supports many attributes, but not all are relevant for all `type` values. Below is a table summarising the relevant attributes.

```
<table>
  <tr>
    <th>Type</th>
    <th>Description</th>
    <th>Relevant attributes</th>
  </tr>
  <tr>
    <td colspan="3" style="text-align: center;">Single line text fields</td>
  </tr>
  <tr>
    <td>text</td>
    <td>A basic text field</td>
    <td><a href="#autocomplete">autocomplete</a>, <a href="#maxlength">maxlength</a>, <a href="#pattern">pattern</a>, <a href="#list">list</a>, <a href="#placeholder">placeholder</a>, <a href="#">required</a></td>
  </tr>
  <tr>
    <td>email</td>
    <td>A field for one or more e-mail addresses</td>
    <td><a href="#autocomplete">autocomplete</a>, <a href="#list">list</a>, <a href="#maxlength">maxlength</a>, <a href="#multiple">multiple</a>, <a href="#pattern">pattern</a>, <a href="#placeholder">placeholder</a>, <a href="#required">required</a></td>
  </tr>
  <tr>
    <td>password</td>
    <td>This value makes the text field obscured</td>
    <td><a href="#autocomplete">autocomplete</a>, <a href="#list">list</a>, <a href="#maxlength">maxlength</a>, <a href="#required">required</a></td>
  </tr>
  <tr>
    <td>search</td>
    <td>Creates a field for entering search strings</td>
    <td><a href="#autocomplete">autocomplete</a>, <a href="#list">list</a>, <a href="#maxlength">maxlength</a>, <a href="#pattern">pattern</a>, <a href="#placeholder">placeholder</a>, <a href="#required">required</a></td>
  </tr>
  <tr>
    <td>tel</td>
    <td>Creates a field for entering telephone numbers</td>
    <td><a href="#autocomplete">autocomplete</a>, <a href="#list">list</a>, <a href="#maxlength">maxlength</a>, <a href="#pattern">pattern</a>, <a href="#placeholder">placeholder</a>, <a href="#required">required</a></td>
  </tr>
  <tr>
    <td>url</td>
    <td>Creates a field for editing an absolute URL</td>
    <td><a href="#autocomplete">autocomplete</a>, <a href="#list">list</a>, <a href="#maxlength">maxlength</a>, <a href="#pattern">pattern</a>, <a href="#placeholder">placeholder</a>, <a href="#required">required</a></td>
  </tr>
  <tr>
    <td colspan="3" style="text-align: center;">Controls without text input</td>
  </tr>
  <tr>
    <td>checkbox</td>
    <td>A checbox</td>
    <td><a href="#checked">checked</a>, <a href="#required">required</a></td>
  </tr>
  <tr>
    <td>file</td>
    <td>A control that lets the user select a local file</td>
    <td><a href="#accept">accept</a>, <a href="#multiple">multiple</a>, <a href="#required">required</a></td>
  </tr>
  <tr>
    <td>number</td>
    <td>A control for entering a number</td>
    <td><a href="#autocomplete">autocomplete</a>, <a href="#list">list</a>, <a href="#max">max</a>, <a href="#min">min</a>, <a href="#required">required</a>, <a href="#step">step</a></td>
  </tr>
  <tr>
    <td>radio</td>
    <td>Only one radio button in a group can be selected at any given time</td>
    <td><a href="#checked">checked</a>, <a href="#required">required</a></td>
  </tr>
  <tr>
    <td>range</td>
    <td>A control for entering a number whose exact value is not important</td>
    <td><a href="#autocomplete">autocomplete</a>, <a href="#list">list</a>, <a href="#max">max</a>, <a href="#min">min</a>, <a href="#required">required</a>, <a href="#step">step</a></td>
  </tr>
  <tr>
    <td colspan="3" style="text-align: center;">Time and date controls</td>
  </tr>
  <tr>
    <td>date</td>
    <td>A control for entering the date (year, month, day)</td>
    <td><a href="#autocomplete">autocomplete</a>, <a href="#list">list</a>, <a href="#max">max</a>, <a href="#min">min</a>, <a href="#required">required</a></td>
  </tr>
  <tr>
    <td>time</td>
    <td>A control for entering a time</td>
    <td><a href="#autocomplete">autocomplete</a>, <a href="#list">list</a>, <a href="#max">max</a>, <a href="#min">min</a>, <a href="#required">required</a></td>
  </tr>
  <tr>
    <td colspan="3" style="text-align: center;">Buttons</td>
  </tr>
  <tr>
    <td>button</td>
    <td>A push button with no default behavior</td>
    <td>
      <a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/button#attr-formaction">formaction</a>,
      <a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/button#attr-formenctype">formenctype</a>,
      <a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/button#attr-formmethod">formmethod</a>,
      <a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/button#attr-formnovalidate">formnovalidate</a>,
      <a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/button#attr-formtarget">formtarget</a>
    </td>
  </tr>
  <tr>
    <td>reset</td>
    <td>A button that resets the contents of the form to default values</td>
    <td>
      <a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/button#attr-formaction">formaction</a>,
      <a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/button#attr-formenctype">formenctype</a>,
      <a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/button#attr-formmethod">formmethod</a>,
      <a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/button#attr-formnovalidate">formnovalidate</a>,
      <a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/button#attr-formtarget">formtarget</a>
    </td>
  </tr>
  <tr>
    <td>submit</td>
    <td>A button that submits the form</td>
    <td>
      <a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/button#attr-formaction">formaction</a>,
      <a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/button#attr-formenctype">formenctype</a>,
      <a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/button#attr-formmethod">formmethod</a>,
      <a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/button#attr-formnovalidate">formnovalidate</a>,
      <a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/button#attr-formtarget">formtarget</a>
    </td>
  </tr>
</table>
```

The table above is a subset of the table found at \[How to structure an HTML form, from [Mozilla Developer Network](https://developer.mozilla.org/en-US/docs/Learn/HTML/Forms/How_to_structure_an_HTML_form#HTML_widgets)

If the browser doesn't support the value in the `type` attribute, the input field will be rendered as a `text` input.

Below is an explanation for the attributes with examples. The attributes for the buttons are linked to an external resource, as they are out of scope for this course.

### \<span id="accept">accept\</span>

If the value of the type attribute is file, then this attribute will indicate the types of files that the server accepts, otherwise it will be ignored. The value must be a comma-separated list of unique content type specifiers:

* A file extension starting with the STOP character (e.g. .jpg, .mp4, .wav)
* audio: representing audio files
* video: representing video files
* image: representing image files

```
<label for="file">Choose a file to upload:
    <input type="file" name="file" id="file" accept="image/*">
</label>
```

```
<label for="file">Choose a file to upload:
    <input type="file" name="file" id="file" accept=".jpg, .png">
</label>
```

### \<span id="autocomplete">autocomplete\</span>

This attribute indicates whether the value of the control can be automatically completed by the browser.

```
<label for="e-mail"> E-mail:
    <input type="email" name="e-mail" id="e-mail" autocomplete>
</label>
```

### \<span id="checked">checked\</span>

When the value of the type attribute is radio or checkbox, the presence of this Boolean attribute indicates that the control is selected by default, otherwise it is ignored.

```
<label for="alligator"> Are you an alligator?
    <input type="checkbox" name="alligator" id="alligator" checked>
</label>
```

### \<span id="list">list\</span>

Identifies a list of pre-defined options to suggest to the user. The value must be the id of a `<datalist>` element in the same document. The browser displays only options that are valid values for this input element.

```
<label for="language">Select your preferred programming language:
    <input type="text" name="language" list="prog-lang">
</label>
<datalist id="prog-lang">
    <option value="Python"></option>
    <option value="JavaScript"></option>
    <option value="Java"></option>
    <option value="Elm"></option>
    <option value="Haskell"></option>
</datalist>
```

The most known use case for this is an autocompletion list for text fields. The values available are set with `<option>` elements within the `<datalist>` element.

### \<span id="max">max\</span>

The maximum (numeric or date-time) value for this item, which must not be less than its minimum (min attribute) value.

```
<label for="class"> What class are you in?
    <input type="number" name="class" id="class" max="5">
</label>
```

### \<span id="maxlength">maxlength\</span>

If the value of the type attribute is `text`, `email`, `search`, `password`, `tel`, or `url`, this attribute specifies the maximum number of characters that the user can enter.

```
<label for="e-mail">What is your e-mail?
    <input type="email" name="email" id="email" maxlength="40">
</label>
```

### \<span id="min">min\</span>

The minimum (numeric or date-time) value for this item, which must not be greater than its maximum (max attribute) value.

```
<label for="class"> What class are you in?
    <input type="number" name="class" id="class" min="1">
</label>
```

### ##### \<span id="multiple">multiple\</span>

This Boolean attribute indicates whether the user can enter more than one value. This attribute applies when the type attribute is set to `email` or `file`, otherwise it is ignored.

```
<label for="file">Choose a file:
    <input type="file" name="file" id="file" multiple>
</label>
```

### \<span id="pattern">pattern\</span>

A regular expression (RegEx) that the control's value is checked against. The regular expression language is the same as JavaScript RegExp algorithm, with the 'u' parameter that makes it treat the pattern as a sequence of unicode code points. The pattern is not surrounded by forward slashes. In the example below (borrowed from [w3schools.com](http://www.w3schools.com/tags/att_input_pattern.asp)), the input can only be three letter long, no numbers or special characters.

```
<label for="iata">Airport code:
    <input type="text" name="iata-code" id="iata"
    pattern="[A-Za-z]{3}" title="Three letter IATA airport code">
</label>
```

### \<span id="placeholder">placeholder\</span>

A hint to the user of what can be entered in the control . The placeholder text must not contain carriage returns or line-feeds.

```
<label for="email">What is your e-mail?
    <input type="email" name="email" id="email" placeholder="your@domain.com">
</label>
```

Note: Do not use the `placeholder` attribute instead of a `<label>` element. The `<label>` is used to describe the role of the form element, and the `placeholder` attribute is a hint about the format that the value should be. There are cases in which the `placeholder` attribute is never displayed to the user.

### \<span id="required">required\</span>

This attribute specifies that the user must fill in a value before submitting a form.

```
<label for="password">What is your e-mail?
    <input type="password" name="password" id="password" required>
</label>
```

### \<span id="step">step\</span>

Works with the min and max attributes to limit the increments at which a numeric or date-time value can be set. It can be the string any or a positive floating point number. If this attribute is not set to any, the control accepts only values at multiples of the step value greater than the minimum.

```
<label for="income">
    <input type="range" name="income" id="income" step="1000" min="0" max="100000">
</label>
```

## name

In addition to the above mentioned attributes, all input elements can, and should, take the attribute `name`. This attribute is used when sending data with GET or POST, as the name for that input element. E.g.: You will see that radio buttons in the same group will share the same `name`. Thus, the data that is sent to the server will be labeled with that name, followed by the value provided by the different radio buttons.

## Textarea

The `<textarea>` element is a multiline text field. It works like a single line text field, except it allows line break in the typed text by the user. It also accepts three extra attributes to control the rendering across several lines:

| Attribute | Default value | Description                                                    |
| --------- | ------------- | -------------------------------------------------------------- |
| cols      | 20            | The visible width of the textarea, in average character widths |
| rows      |               | The number of visible text lines in the textarea               |
| wrap      | soft          | Indicates how the texarea wraps text, either `hard` or `soft`. |

Unlike the `<input>` element (which is a self closing element) the `<textarea>` is a regular element that can contain text content child elements (e.g. `<code>`). The `<textarea>` element only accepts text as content. Any code or markup (HTML) will be rendered as plain text.

```
<form>
    <label for="text">Write your story:</label>
    <textarea name="text" rows="8" cols="80" wrap="soft">
        This is my story, and it's about web technologies!
    </textarea>
</form>
```

Note that since the `<textarea>` element is an element with opening and closing tags, the value is written inside the element, and not as the value to the `value` attribute.

## Select, option and optgroup

The `<select>` element lets you build select boxes (sometimes also known as combo boxes). A select box is a widget that lets a user choose one or more predefined values. Each value inside the select box is defined with an `<option>` element and those elements can be grouped inside `<optgroup>` elements.

```
<form>
  <label for="language">Choose a programming language</label>
  <select id="language" name="language">
    <option value="python">Python</option>
    <option>JavaScript</option>
    <optgroup label="functional">
      <option>Haskell</option>
      <option>Elm</option>
    </optgroup>
  </select>
</form>
```

If an `<option>` element is set with a value attribute, that attribute's value is sent when the form is submitted. If the value attribute is omitted, the content of the `<option>` element is used as the select box's value.

On the `<optgroup>` element, the label attribute is displayed before the values, but even if it looks somewhat like an option, it is not selectable.
