
Module 10: Final Projects · Lesson 3 of 4
How to Make a Contact Form in HTML (Accessible)
All lessons in Module 10
- Personal Profile Page
- Full Recipe Page
- Contact Page with Form
- One-Page Portfolio
Goal: Build an accessible contact page with a form the browser validates.
Learn
For a small business, the contact page is often the page that counts most, and the one most often broken. A good one is quick for anyone to fill in:
- Every field has a connected label, so a click on the words focuses the field and screen readers announce it (see connecting labels).
- The right input type (
email) brings up the right keyboard on phones and adds free validation. requiredcatches empty fields before anything is sent.- Radio buttons answering one question share a
nameand sit in a<fieldset>whose<legend>asks it. - A plain email link is the backup for people who would sooner use their own mail app.
Submit the empty form in the preview. Built-in validation should stop you and point at the first missing field.
The short version
- Every field needs a
namefor the data that gets sent and a connected<label>for the person filling it in. actionsays where the form data goes, andmethod="post"puts it in the request body, out of the URL.- With
autocomplete="name"andautocomplete="email", browsers fill in known details in one tap. - Browser validation is a convenience for users. The server still has to check the data every time.
Example
<form>
<label for="email">Email</label>
<input type="email" id="email" name="email" required>
<fieldset>
<legend>Best time to call?</legend>
<label><input type="radio" name="time" value="am"> Morning</label>
<label><input type="radio" name="time" value="pm"> Afternoon</label>
</fieldset>
<button type="submit">Send</button>
</form>Your task
Build a contact page for Bright Pixel Studio (or a business you invent). It needs:
- A
<title>that mentions contact, a viewport tag and some CSS (<style>orstyle.css). - A
<header>with a<nav>of at least 2 links. - An
<h1>that mentions contact, and an email link usingmailto:. - A
<form>inside<main>with: a name field, a requiredemailinput, a<select>with at least 3 topics, a<fieldset>with a<legend>and at least 2 radio buttons (same name), and a required<textarea>. - At least 5 labels, so every field is labeled.
- A submit button whose text includes Send.
- A
<footer>.
Ctrl+Enter checks your code. Try Visual edit to change the page directly, DOM tree to see how the browser reads it, and Outline to hear it like a screen reader.
Quick quiz
Common mistakes
Wrong
<label for="email">Email</label>
<input type="email" id="email" required>Right
<label for="email">Email</label>
<input type="email" id="email" name="email" required>The browser skips any field without a name when the form is submitted, so that value never arrives.
Wrong
<form action="mailto:[email protected]">Right
<form action="/contact" method="post">A mailto action relies on the visitor's own mail program and often fails without a sound, so send the form to a server or form service.
Go deeper
Real contact forms handle three things this project skipped. The first is spam. Bots fill in every form they find. A common defense is a hidden extra field that people never see and bots happily fill in, which lets the server reject those submissions.
The second is feedback. After sending, show an obvious confirmation page or message. When the server finds a problem, name the field and explain the fix in words. WCAG 2.2 requires errors to be identified in text (3.3.1, Error Identification (opens in a new tab)) and fields to have labels or instructions (3.3.2).
The third is effort. Ask only for what you need, because every extra field means fewer people finish. Add autocomplete values so browsers can fill in names and addresses. WCAG 2.2 asks for this on fields that collect the user's own details (1.3.5, Identify Input Purpose). A generator such as HTMLinput (opens in a new tab) builds accessible input elements with the right type, autocomplete and validation attributes.
A contact form collects personal data, so in many countries, including the EU under the GDPR (opens in a new tab), you have to say what you do with it, usually by linking to your privacy policy.
Before you call it done, try the form on a real phone. The email field should open the email keyboard, labels should stay visible while you type, and error messages should be hard to miss.
Frequently asked questions
How do I make a contact form in HTML that sends an email?
You can't, with HTML alone. The form only collects the data and sends it to the address in its action attribute. Something on a server has to receive it and send the email. That can be a small script in PHP, Python or Node.js, or a hosted form service that hands you an action URL to paste in. Your HTML is the same in both cases.
What is the difference between GET and POST in HTML forms?
method="get" (the default) adds the form data to the URL, like ?q=pancakes. That suits searches and filters people may bookmark or share. method="post" sends the data inside the body of an HTTP POST request (opens in a new tab), so it stays out of the address bar, the history and server logs. Use post for contact forms, sign-ups and anything that sends personal data or changes something.
How do I make a field required in HTML?
Add the required attribute: <input type="email" name="email" required>. The browser then won't submit the form while that field is empty, and it shows a message pointing at it. Say which fields are required in the label text too, for example Email (required), because plenty of people miss the browser's message or a small asterisk. The lesson on form validation covers the other built-in checks.