Popover API

HTML · Lesson 27 of 44 6 min read Updated

Menus that drop down, little "what is this?" tips and "Saved!" messages all float above the page and disappear again. Building them used to need a lot of JavaScript and careful z-index values. Today the popover attribute does most of the work for you.

In this lesson you will create popovers that open and close from buttons without any script, learn the difference between auto and manual popovers, and control them from JavaScript when you need to.

Your first popover

Two attributes are all you need:

  • popover on the element that should float. It is hidden until opened.
  • popovertarget on a <button>, set to the id of the popover. Clicking the button opens the popover, and clicking it again closes it.
HTMLTry it yourself
<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="utf-8">
  <title>Popover</title>
</head>
<body>
  <h1>Check your ticket</h1>
  <label for="pnr">PNR number</label>
  <input id="pnr" name="pnr" inputmode="numeric">
  <button popovertarget="pnr-help">What is a PNR?</button>

  <div id="pnr-help" popover>
    <p>The PNR is the 10-digit number printed at the top of your train ticket.</p>
  </div>
</body>
</html>

Open the popover, then click anywhere outside it or press Esc. It closes. This is called light dismiss: the popover goes away as soon as the user does something else, just like a native menu.

What the browser does for you

  • Top layer. An open popover is drawn in a special layer above everything else on the page, so you never have to fight with z-index.
  • Hidden by default. Until it is opened, the popover is not displayed at all.
  • Light dismiss. Clicking outside or pressing Esc closes it.
  • One at a time. Opening one popover closes any other open popover, unless one is inside the other (for example, a sub-menu inside a menu).
  • Keyboard support. The trigger is a real <button>, so it works with Tab, Enter and Space.

By default the browser shows a popover in the middle of the window with a thin border. You can style it like any other element, and you can place it next to its button with CSS Anchor Positioning.

Show, hide or toggle

By default a popovertarget button toggles its popover. The popovertargetaction attribute changes that:

  • popovertargetaction="toggle" opens or closes (the default).
  • popovertargetaction="show" only opens.
  • popovertargetaction="hide" only closes.

A "hide" button inside the popover gives touch users an obvious way to close it. The example also styles the popover with the :popover-open pseudo-class, which matches only while the popover is showing.

HTMLTry it yourself
<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="utf-8">
  <title>Language Menu</title>
  <style>
    #lang-menu { border: 1px solid #aaa; border-radius: 8px; padding: 12px 20px; }
    #lang-menu:popover-open { box-shadow: 0 8px 24px rgb(0 0 0 / 0.2); }
  </style>
</head>
<body>
  <button popovertarget="lang-menu" popovertargetaction="show">Language</button>

  <div id="lang-menu" popover>
    <h2>Choose a language</h2>
    <ul>
      <li><a href="#">English</a></li>
      <li><a href="#" lang="hi">हिन्दी</a></li>
      <li><a href="#" lang="ta">தமிழ்</a></li>
    </ul>
    <button popovertarget="lang-menu" popovertargetaction="hide">Close</button>
  </div>
</body>
</html>

auto or manual?

The popover attribute has two main values. Writing popover on its own is the same as popover="auto".

popover="auto"popover="manual"
Light dismiss (click outside, Esc)YesNo
Closes other open popoversYesNo
Several open at onceNo (except nested ones)Yes
How it closesLight dismiss, button or scriptOnly a button or script
Good forMenus, tips, pickersToast messages, persistent panels

Use auto for almost everything the user opens on purpose. Use manual when the popover must stay visible while the user keeps working, such as a "Profile saved" message that your code removes after a few seconds.

Controlling popovers with JavaScript

Every popover element has three methods: showPopover(), hidePopover() and togglePopover(). It also fires a toggle event after it opens or closes; the event's newState property is "open" or "closed".

Here a manual popover works as a toast message. It appears when the user saves and hides itself after three seconds.

HTMLTry it yourself
<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="utf-8">
  <title>Toast</title>
  <style>
    #toast {
      inset: auto 16px 16px auto;
      margin: 0;
      padding: 10px 16px;
      border: none;
      border-radius: 6px;
      background: #1b5e20;
      color: white;
    }
  </style>
</head>
<body>
  <h1>Edit profile</h1>
  <p>Name: Ananya Iyer, Kochi</p>
  <button id="save">Save profile</button>
  <p id="log"></p>

  <div id="toast" popover="manual">Profile saved</div>

  <script>
    const toast = document.querySelector("#toast");
    const log = document.querySelector("#log");

    document.querySelector("#save").addEventListener("click", () => {
      if (!toast.matches(":popover-open")) {
        toast.showPopover();
        setTimeout(() => toast.hidePopover(), 3000);
      }
    });

    toast.addEventListener("toggle", (event) => {
      log.textContent = "Toast is now " + event.newState;
    });
  </script>
</body>
</html>

Click outside the toast while it is showing: it stays, because manual popovers have no light dismiss. The CSS moves it to the bottom-right corner by changing inset and removing the default centring margin.

Popover or dialog?

A popover does not block the page. The user can ignore it and carry on. When the user must answer before continuing, such as confirming a payment, use a modal <dialog> instead, as shown in Details, Summary & Dialog.

Common mistakes

  • Putting popovertarget on a <div> or <a>. It only works on buttons.
  • A trigger button inside a form. A button inside a <form> is a submit button by default and will not open the popover. Add type="button".
  • Misspelt ids. The popovertarget value must match the popover's id exactly.
  • Using manual and forgetting to close it. Manual popovers stay open until your button or code hides them.
  • Using a popover for a required decision. Use a modal dialog when the page must wait for the user.

Key points

  • The popover attribute turns any element into a floating panel that starts hidden.
  • A <button> with popovertarget opens and closes it without JavaScript; popovertargetaction can force show or hide.
  • auto popovers (the default) light dismiss and close each other; manual popovers stay open until closed explicitly.
  • Open popovers sit in the top layer, so z-index is not needed.
  • From script, use showPopover(), hidePopover(), togglePopover() and the toggle event.

Exercise

Build a "Share" button for a recipe page. Clicking it opens an auto popover containing a heading and three links (Email, Copy link, Print), plus a Close button that only hides the popover. Style the open popover with :popover-open so it has rounded corners and some padding.

Show solution
HTML
<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="utf-8">
  <title>Share Recipe</title>
  <style>
    #share:popover-open { border-radius: 10px; padding: 16px; }
  </style>
</head>
<body>
  <h1>Lucknowi dum biryani</h1>
  <button popovertarget="share">Share</button>

  <div id="share" popover>
    <h2>Share this recipe</h2>
    <ul>
      <li><a href="#">Email</a></li>
      <li><a href="#">Copy link</a></li>
      <li><a href="#">Print</a></li>
    </ul>
    <button popovertarget="share" popovertargetaction="hide">Close</button>
  </div>
</body>
</html>

Plain popover means auto, so clicking outside or pressing Esc also closes it. The Close button uses popovertargetaction="hide" so it can never reopen the panel by mistake.

Quick Quiz

1. What does writing popover with no value mean?

2. What is light dismiss?

3. Which popover type should a "Saved" toast use if it must stay while the user keeps clicking?

4. A popovertarget button inside a <form> does nothing. What is the fix?

Learn HTML with a mentor

Free lessons get you started. Our Full Stack Web Development training adds real projects and code reviews from working developers.

  • Project-based learning
  • Mentor code reviews
  • Free counselling call