You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
title: A newbie's guide to designing good web forms
3
+
tags: [web development, design]
4
+
date: 2026-03-17
5
+
cssComponents:
6
+
- character
7
+
---
8
+
9
+
Forms have existed since 1677, when the outlaw Jonathan Formsby decided to extort money by leaving blank spaces on a piece of parchment and coercing the landed gentry into writing illicit personal details into the spaces at blunderbuss-point.
10
+
11
+
In the 350 years hence, no one has created a better way of acquiring information from others, voluntarily or not.
12
+
13
+
An awful lot of the world wide web involves forms. Indeed, they're practically the only means of explicitly acquiring information from a user that isn't duplicitously tracking their online behaviour so you can extort money from them (a practice more commonly known as 'digital marketing').
14
+
15
+
But a lot of online forms are also kind of... bad. They so often seek to reproduce paper forms, where materials is money and you need to cram as many fields onto a page as possible. The web is _not_ paper! We can make things so much better here!
16
+
17
+
So I'm gonna drop some of the wisdom I've gained in designing forms across my career, be it for marketing, for membership organisations, for government, and for events.
18
+
19
+
This is (hopefully) going to be a series of blog posts covering the design and development of good online forms, starting with **what you ask for in the first place**.
20
+
21
+
{% character character='ash', variant='paw' %}
22
+
There's inevitably going to be situations where one or more of my points isn't going to stand up as a universal truth. Still, I think these are solid enough for the vast majority of form design situations.
23
+
24
+
I'm also going to shout out [Adam Silver](https://adamsilver.io/) here—and his book _[Form Design Patterns](https://formdesignpatterns.com/)_—who I consider to basically be the foremost authority on this kind of thing.
25
+
{% endcharacter %}
26
+
27
+
## Strip away the cruft
28
+
29
+
My absolute first principle of form design is to remember is that **nobody wants to be filling out a form**. A form is a barrier that prevents people from reaching the information they're trying to get or the outcome they're trying to achieve.
30
+
31
+
It may be a necessary evil, but it's still an evil. Forms are therefore the ideal place to trim as much cruft as you possibly can.
32
+
33
+
If you don't need a piece of information, don't ask for it. If you don't need it right now, ask for it later in the user journey or as part of a supplementary flow separate from collecting the things you need to know _immediately_.
34
+
35
+
In the case of time-sensitive forms (say for example, a popular concert with limited availability), you could provide users with the ability to create an account and fill out their personal information ahead of time, with the actual ticket sale only requiring them to log in and confirm the quantity-limited tickets and addons they want.
36
+
37
+
## Ask questions
38
+
39
+
Imagine that you're at an office to renew a passport for a relative. You walk up to the reception desk and, without letting you say anything or even looking up at you, the person behind the desk just says 'Name.'
40
+
41
+
That's a little rude, isn't it? And what do they even mean? Your first name or full name? The name the office might have on their records? The name on your passport? The name you go by, if that's different? Your name at birth, if that's different too? Do they even want _your_ name, or do they actually want the name of the person whose passport you're renewing?
42
+
43
+
If the same person asked 'What's the name on the passport to be renewed?', it would both be more pleasant and easier to understand what information they need from you. Humans don't talk like that to one another, so why should an interface talk like that to a human?
44
+
45
+
This conversational style of asking questions reduces cognitive burden and helps to avoid jargon. 'What is your date of birth?' is a more readily understandable question than asking for a 'DOB', for example, as is asking 'What is the card's security code?' instead of just asking for a 'CVV'.
46
+
47
+
## Accept answers
48
+
49
+
Questions asked specifically enough will often only have a single answer. There are some questions, however, where no amount of specificity will guarantee you the exact same response.
50
+
51
+
If a _person_ asks you 'What is your date of birth?', these are all valid answers:
52
+
53
+
- 11/08/1991
54
+
- 11/8/91
55
+
- 1991-08-11
56
+
- 11.08.1991
57
+
- 8/11/91 (confusing!)
58
+
- 11th August 1991
59
+
- August 11, 1991
60
+
- 11 Aug '91
61
+
- Sunday, 11 August 1991
62
+
63
+
If the answer is correct, why would you return an error saying it's wrong? Why shouldn't a digital form permit a similar level of flexibility?
64
+
65
+
You could try to design around the problem, such as adding hint text specifying 'DD/MM/YYYY' format or similar, but that doesn't mean that someone has answered incorrectly just because they wrote it as '11 8 1991' instead.
66
+
67
+
On GOV.UK, even though [the date input component]() is built to encourage a 'DD MM YYYY' formatted answer, we encourage developers to accept a variety of variations for that format, allowing the names and abbreviations of months and not requiring leading zeroes.
68
+
69
+
As much as possible, be flexible with what format an answer can be given in. If an answer is 'good enough' to be unambiguously understood, then accept it. Doing so reduces the likelihood that a user encounters an unnecessary validation error, lowering a barriers to completion.
70
+
71
+
## Mark what's optional, not required
72
+
73
+
Don't do the whole 'required fields are marked with a <abbrtitle="asterisk">\*</abbr>' thing. That entire practice is a relic of paper forms, where space is limited by physical dimensions and the questions are unable to adapt to known information.
74
+
75
+
On the web nearly every question in a form should be required, as a natural consequence of stripping away cruft.
76
+
77
+
If you're unsure, you can often determine what questions need to be asked based on previously provided answers or a simple 'gate' question. You don't need to present a user with a whole address form of optional fields if you ask 'Do you want the thing posted to you?' first!
78
+
79
+
If something is truly not required, you have virtually unlimited space to include the word 'optional'.
80
+
81
+
The asterisk approach adds an extra, utterly unnecessary, step to a user understanding a form and what it wants from them. Don't do it.
82
+
83
+
---
84
+
85
+
That's it for this one. If you have any questions, you're welcome to [drop me a line]({{ '/contact/' | url }}) and I might answer them in a future post.
title: A newbie's guide to designing and building good web forms
2
+
title: infodump, A newbie's guide to designing and building good web forms
3
3
tags: [web development, design]
4
4
cssComponents:
5
-
- character
6
5
- code
7
6
---
8
7
9
-
Forms have existed since 1677, when the outlaw Jonathan Formsby decided to extort money by leaving blank spaces on a piece of parchment and coercing the landed gentry into writing illicit personal details into the spaces at blunderbuss-point.
8
+
## Design
10
9
11
-
In the 350 years hence, no one has created a better way of acquiring information from others, voluntarily or not.
10
+
### One thing per page
12
11
13
-
An awful lot of the world wide web involves forms. Indeed, they're practically the only means of explicitly acquiring information from a user that isn't duplicitously tracking their online behaviour so you can extort money from them (a practice more commonly known as 'digital marketing').
12
+
### Replay everything for review and amendment
14
13
15
-
But a lot of online forms are also kind of... bad. They so often seek to reproduce paper forms, where materials is money and you need to cram as many fields onto a page as possible. The web is _not_ paper! We can do things so much better here.
14
+
If a form is quite long, it can
16
15
17
-
{% character character='ash', variant='paw' %}
18
-
I'm calling these guidelines in my head, because there's inevitably going to be situations where one or more of my points isn't going to stand up as a universal truth. Still, I think these are solid enough for the vast majority of form design situations.
16
+
### Size inputs according to their expected answers
19
17
20
-
I'm also going to shout out [Adam Silver](https://adamsilver.io/) here—and his book _[Form Design Patterns](https://formdesignpatterns.com/)_—who I consider to basically be the foremost authority on this kind of thing.
21
-
{% endcharacter %}
22
-
23
-
## Keep it simple
24
-
25
-
The absolute first principle of form design is to remember is that **nobody wants to be filling out a form**. A form is a barrier that's preventing people from reaching the information they're trying to get or the outcome they're trying to achieve.
26
-
27
-
It may be a necessary evil, but it's still an evil. Forms are therefore the ideal place to trim as much cruft as you possibly can.
18
+
## Technical implementation
28
19
29
-
If you don't need a piece of information, don't ask for it. If you don't need it right now, ask for it later in the user journey or as part of a supplementary flow seperate from collecting the things you need to know _immediately_.
20
+
### Input, label, ID
30
21
31
-
In the case of time-sensitive forms (say for example, an event registration system), you could provide users the ability to create an account and prefill information ahead of time, with the actual 'registration' only requiring them to log in and select the quantity-limited options like tickets and addons.
22
+
Something that should be obvious to seasoned frontend developers, but this is a newbie's guide...
32
23
33
-
## Ask questions
34
-
35
-
Imagine that you're at a bank, local government office, or doing some other kind of dreary in-person task. You walk up to the reception desk and without even looking up at you, the person behind the desk just says 'Name.'
36
-
37
-
That's a little rude, isn't it? And what do they even mean? Your first name or full name? The name you go by, if that's different? The name this organisation might have on their records? The name on your identity documents, or your name at birth? Do they even want your name, or do they need the name of someone you're acting on behalf of?
24
+
This is a much more technical point than the others, but it's shocking how often [when doing accessibility audits]({{ '/accessibility-for-furries/' | url }}) that I find form inputs that don't have labels, or have labels that aren't programmatically associated to the input.
38
25
39
-
If the same person asked 'What's your full name, as it appears on your licence?' it would both be more pleasant and more immediately understandable as to what information they need from you.
26
+
Every `<input>`, `<textarea>` and `<select>` element in a form _needs_ an associated text label, and 99% of the time that's going to be via an `id` attribute and a `<label>` element.
40
27
41
-
This style of questioning also helps to avoid jargon. 'What is your date of birth?' is more readily understandable than 'DOB'. Likewise 'What is your postal address?' more understandable than the frankly awful 'Address line 1'/'Address line 2' combo. Humans don't talk like that to one another, so why should an interface talk to a human like that?
28
+
If your basic text input doesn't look something like this, there's probably something wrong with it.
42
29
43
-
## Accept answers
30
+
```html
31
+
<labelfor="display-name">What name should we print on your badge?</label>
32
+
<inputtype="text"id="display-name" />
33
+
```
44
34
45
-
Questions, asked specifically enough like the name example above, can only have a single answer. That's easy enough. There are others, however, where no amount of specificity will guarantee the same result.
35
+
This includes radio buttons and checkboxes. Each of them should have their own, individual `<label>` elements.
46
36
47
-
'What is your date of birth?' Well, these are all valid answers:
Hints and error messages should also have `id` attributes and be associated with inputs using `aria-describedby`.
58
47
59
-
You could try and design around the problem, such as adding hint text specifying 'DD/MM/YYYY' format or similar, but that doesn't mean that someone has answered incorrectly just because they wrote it as '22 9 1991' instead.
48
+
```html
60
49
61
-
As much as possible, be flexible with what formats users can use. If an answer is 'good enough' to be unambiguously understood, then accept it. Doing so reduces the likeliness that a user encounters an unnecessary validation error, lowering those barriers I mentioned earlier.
50
+
```
62
51
63
-
## Use the right input type for the answer
52
+
###Use the right input type for the answer
64
53
65
54
HTML comes with a variety of input elements and types. It also comes with a bunch of [`autocomplete` options for autofill functionality](https://developer.mozilla.org/en-US/docs/Web/HTML/Reference/Attributes/autocomplete), `inputmode` hints for virtual keyboards, and you can further utilise visual cues to hint about what kind of answer a user should give.
66
55
@@ -72,7 +61,7 @@ Asking for a payment card's security code? Use the `numberic` input mode, `cc-cs
72
61
73
62
Using these things together allows credential managers to fill things out automatically, mobile devices to display context-specific keyboards, and users to intuit what kind of information they need to provide based on the amount of space provided. Unsurprisingly, that makes filling out forms faster!
74
63
75
-
## Avoid validating values when the user is still providing them
64
+
###Avoid validating values when the user is still providing them
76
65
77
66
A lot of forms frameworks will provide the ability to validate what a user is typing into a field, either whilst typing or after they move on to a different field.
78
67
@@ -91,45 +80,3 @@ Instead, online forms should perform validation at the point the user tries to s
91
80
{% character character='ash', variant='thinking' %}
92
81
You should generally be performing form validation on the server anyway, that's just good security practice. If you really want to do things on the client, you may want to utilise HTML's validation attributes and enhance them with a library like [Vanilla Validation](https://www.npmjs.com/package/@querkmachine/vanilla-validation) (plug, plug, shameless plug).
93
82
{% endcharacter %}
94
-
95
-
## Required or optional?
96
-
97
-
For the love of god, don't do the whole 'required fields are marked with a <abbrtitle="asterisk">\*</abbr>' thing. That entire practice is a relic of paper forms, where space is limited by physical dimensions and questions are unable to be reactive to previously given inputs.
98
-
99
-
On the web nearly every question in a form should be required, as can be determined by previously provided answers, and if it's not required, you have virtually unlimited space to include the word 'optional'.
100
-
101
-
The asterisk approach adds an extra, utterly unnecessary, step to a user understanding your form. Don't do it.
102
-
103
-
## Replay everything for review and amendment
104
-
105
-
If a form is quite long, you probably
106
-
107
-
## Input, label, ID
108
-
109
-
This is a much more technical point than the others, but it's shocking how often [when doing accessibility audits]({{ '/accessibility-for-furries/' | url }}) that I find form inputs that don't have labels, or have labels that aren't programmatically associated to the input.
110
-
111
-
Every `<input>`, `<textarea>` and `<select>` element in a form _needs_ an associated text label, and 99% of the time that's going to be via an `id` attribute and a `<label>` element.
112
-
113
-
If your basic text input doesn't look something like this, there's probably something wrong with it.
114
-
115
-
```html
116
-
<labelfor="display-name">What name should we print on your badge?</label>
117
-
<inputtype="text"id="display-name" />
118
-
```
119
-
120
-
This includes radio buttons and checkboxes. Each of them should have their own, individual `<label>` elements.
0 commit comments