HTMLVoid (Self-Closing) Elements

Void (Self-Closing) Elements

Most HTML elements have an opening tag, some content, and a closing tag: <p>...</p>. Void elements are the exception — they can never have any content or children, so they consist of a single tag with no matching closing tag at all.

The Full List of HTML5 Void Elements

HTML5 defines a fixed set of void elements. There are no others, and you can't create custom ones.

Element

Purpose

<area>

A clickable region inside an image map

<base>

Sets the base URL for relative links in the document

<br>

A line break within text

<col>

A column definition inside a <colgroup>

<embed>

Embeds external content (plugins, media)

<hr>

A thematic break between sections

<img>

An embedded image

<input>

A form control

<link>

Links an external resource, typically a stylesheet

<meta>

Document metadata

<param>

A parameter for an <object> (legacy)

<source>

A media source inside <audio>, <video>, or <picture>

<track>

A text track (captions/subtitles) for <audio>/<video>

<wbr>

A suggested word-break opportunity

Why They Have No Closing Tag

A void element's entire job is expressed through its tag name and attributes — there's nothing for it to "contain." An <img> doesn't wrap other content; the image itself comes from its src attribute. A <br> doesn't wrap text; it just marks a point where a line should break. Since children are meaningless for these elements, HTML5 simply forbids a closing tag.

void-usage.html

HTML
<img src="/logo.png" alt="Company logo">
<br>
<hr>
<input type="text" name="username">
<meta charset="UTF-8">
<link rel="stylesheet" href="/styles.css">
A closing tag is a parse error, not just unnecessary
Writing <br></br> or <img></img> is invalid HTML5. Browsers will usually recover gracefully by ignoring the stray closing tag, but HTML validators flag it, and it signals a misunderstanding of what void elements are for.
XHTML Self-Closing Slash vs HTML5

If you've worked with XHTML or XML-flavored markup, you may be used to writing a trailing slash on void elements, like <br /> or <img src="..." />. XHTML required this because it demanded well-formed XML syntax, where every element must be explicitly closed.

Syntax

HTML5 validity

Notes

<br>

Valid

The standard HTML5 form

<br/>

Valid

Slash is allowed but has no effect in HTML parsing

<br />

Valid

Same as above, just with a space before the slash

<br></br>

Invalid

A closing tag on a void element is a parse error

xhtml-vs-html5.html

HTML
<!-- XHTML-style, still parses fine in HTML5 (slash is cosmetic) -->
<img src="/photo.jpg" alt="A mountain lake" />

<!-- Standard HTML5 form, functionally identical -->
<img src="/photo.jpg" alt="A mountain lake">
Pick one style and be consistent
In an HTML5 document, the trailing slash is purely a style choice — the DOM produced is identical either way. Many teams still include it out of habit from XHTML, or because their JSX-based tooling (like React) requires it. Whatever you choose, apply it consistently across the codebase.
  • Void elements can never have children or a closing tag — their meaning comes entirely from their tag name and attributes.

  • HTML5 defines a fixed list: area, base, br, col, embed, hr, img, input, link, meta, param, source, track, wbr.

  • A trailing slash (<br />) is accepted but has no effect on HTML5 parsing — it's a holdover from XHTML.

  • Writing an explicit closing tag on a void element (<br></br>) is invalid.

Void Elements vs Elements That Are Just Often Empty

Don't confuse "void element" with "element that happens to have no content right now." A <div> or <span> with nothing inside it (<div></div>) is still a normal, non-void element — it's legal for it to be empty, but it still requires a proper closing tag, and it could contain children.

empty-vs-void.html

HTML
<!-- A non-void element that happens to be empty right now — needs a closing tag -->
<div id="modal-root"></div>

<!-- A true void element — can never have a closing tag -->
<hr>

Element

Void?

Can be legally empty?

<div>

No

Yes, with an explicit closing tag

<img>

Yes

N/A — has no closing tag or children at all

<script>

No

Yes (e.g. <script src="...">​</script>), but always needs a closing tag

script is not void, even though src makes it look empty
<script src="app.js"> has no visible text content, which makes it easy to mistake for a void element. It still requires a closing </script> tag — omitting it is invalid HTML, even though many browsers will silently tolerate it.
How JSX Handles Void Elements

If you write React or other JSX-based UI, void elements like <img>, <br>, and <input> must be self-closed in JSX (<img />), unlike plain HTML5 where the slash is optional. This is a JSX/XML syntax requirement, not an HTML rule — the compiled output is still standard HTML with no closing tag.

jsx-void-elements.jsx

JSX
function Avatar({ src, name }) {
  return (
    <div>
      <img src={src} alt={name} />
      <br />
    </div>
  );
}
JSX rules and HTML5 rules are separate
JSX requiring a trailing slash on void elements is a constraint of JSX's own syntax (it must produce well-formed element trees at compile time), not something HTML5 itself requires. Plain .html files never need it.
Void Elements Can Still Have Attributes

Having no content doesn't mean having no attributes — void elements are often the most attribute-heavy tags in a document, since attributes are their only way to carry information.

attribute-heavy-void.html

HTML
<img
  src="/hero.jpg"
  alt="Sunrise over the mountains"
  width="1200"
  height="600"
  loading="lazy"
  decoding="async"
>

<input
  type="email"
  name="email"
  required
  placeholder="you@example.com"
  autocomplete="email"
>
Void Elements in XML/XHTML Documents

If a document is served as actual XML (for example, an XHTML document with an application/xhtml+xml MIME type, or an SVG file), the trailing slash on void elements is not optional — XML requires every element to be explicitly closed, either with a matching closing tag or a self-closing slash. This is the historical reason the self-closing slash convention exists at all.

xhtml-strict.xhtml

XML
<?xml version="1.0" encoding="UTF-8"?>
<html xmlns="http://www.w3.org/1999/xhtml">
  <body>
    <img src="/logo.png" alt="Logo" />
    <br />
  </body>
</html>

Document type

Trailing slash on void elements

HTML5 (text/html)

Optional — has no effect on parsing

XHTML served as XML (application/xhtml+xml)

Required — omitting it is a fatal parse error

SVG (image/svg+xml)

Required for any self-closing element, since SVG is XML

Most sites today are plain HTML5, not XHTML
Unless you specifically know your document is served with an XML MIME type, you're working with ordinary HTML5, where the slash is purely stylistic. Check your server's Content-Type header if you're unsure.