Primitive Components

BasecoatUI primitive components for building modern web applications. Simple, accessible, and fully customizable.

About These Components

These primitive components are based on BasecoatUI, a modern component library built with Tailwind CSS. They provide the building blocks for creating beautiful user interfaces.

All components use semantic HTML and are fully accessible following WAI-ARIA standards. They can be easily customized with Tailwind utility classes.

Accordion

A vertically stacked set of interactive headings that reveal content.

Is it accessible?

Yes. It adheres to the WAI-ARIA design pattern.

Is it styled?

Yes. It comes with default styles that can be customized with Tailwind CSS.

Can I use it in my project?

Yes. Free to use for personal and commercial projects.

<section class="accordion">
  <details class="group border-b">
    <summary>
      <h3>Is it accessible?
        <svg class="rotate-icon">...</svg>
      </h3>
    </summary>
    <section>Yes. It adheres to the WAI-ARIA design pattern.</section>
  </details>
</section>

Alert

Display important messages to users with various severity levels.

Success! Your changes have been saved

This is a success alert with icon, title and description.

Something went wrong!

Your session has expired. Please log in again.
<div class="alert">
  <svg>...</svg>
  <h2>Success! Your changes have been saved</h2>
  <section>This is a success alert.</section>
</div>

<div class="alert-destructive">
  <svg>...</svg>
  <h2>Something went wrong!</h2>
  <section>Your session has expired.</section>
</div>

Alert Dialog

A modal dialog that interrupts the user with important content and expects a response.

Are you absolutely sure?

This action cannot be undone. This will permanently delete your account and remove your data from our servers.

<button onclick="document.getElementById('alert-dialog').showModal()">
  Open Alert Dialog
</button>

<dialog id="alert-dialog" class="dialog">
  <article>
    <header>
      <h2>Are you absolutely sure?</h2>
      <p>This action cannot be undone.</p>
    </header>
    <footer>
      <button onclick="this.closest('dialog').close()">Cancel</button>
      <button onclick="this.closest('dialog').close()">Continue</button>
    </footer>
  </article>
</dialog>

Avatar

Display user profile images in a circular format.

User avatar User avatar User avatar
<img class="size-8 shrink-0 object-cover rounded-full"
     alt="User avatar"
     src="https://github.com/username.png">

<img class="size-12 shrink-0 object-cover rounded-full"
     alt="User avatar"
     src="https://github.com/username.png">

Badge

Small labels for status, categories, and other metadata.

Default Secondary Destructive Outline
<span class="badge">Default</span>
<span class="badge-secondary">Secondary</span>
<span class="badge-destructive">Destructive</span>
<span class="badge-outline">Outline</span>

Button

Clickable button elements with various styles.

<button class="btn">Primary</button>
<button class="btn-secondary">Secondary</button>
<button class="btn-outline">Outline</button>
<button class="btn-ghost">Ghost</button>
<button class="btn-destructive">Destructive</button>

Card

Container for grouping related content.

Card Title

Card Description

This is the card content area. You can add any content here.

<div class="card">
  <header>
    <h2>Card Title</h2>
    <p>Card Description</p>
  </header>
  <section>
    <p>Card content...</p>
  </section>
  <footer>
    <button class="btn">Action</button>
  </footer>
</div>

Checkbox

Select one or multiple options from a list.

<label class="label gap-3">
  <input type="checkbox" class="input">
  Accept terms and conditions
</label>

<label class="label gap-3">
  <input type="checkbox" class="input" checked>
  Subscribe to newsletter
</label>

Dialog

Modal overlay for focused user interaction.

Edit Profile

Make changes to your profile here. Click save when you're done.

<button onclick="document.getElementById('dialog').showModal()">
  Open Dialog
</button>

<dialog id="dialog" class="dialog">
  <article>
    <header>
      <h2>Edit Profile</h2>
      <p>Make changes to your profile here.</p>
    </header>
    <section>...form content...</section>
    <footer>
      <button onclick="this.closest('dialog').close()">Cancel</button>
      <button onclick="this.closest('dialog').close()">Save</button>
    </footer>
  </article>
</dialog>

Label

Text labels for form inputs.

<label class="label" for="email">Email</label>
<input class="input" id="email" type="email">

Pagination

Navigate through multiple pages of content.

<nav role="navigation" aria-label="pagination">
  <ul class="flex items-center gap-1">
    <li><a href="#" class="btn-ghost">Previous</a></li>
    <li><a href="#" class="btn-ghost">1</a></li>
    <li><a href="#" class="btn-outline">2</a></li>
    <li><a href="#" class="btn-ghost">3</a></li>
    <li><a href="#" class="btn-ghost">Next</a></li>
  </ul>
</nav>

Radio Group

Select a single option from a list.

<fieldset class="grid gap-3">
  <label class="label">
    <input type="radio" name="radio" value="1" class="input">
    Default
  </label>
  <label class="label">
    <input type="radio" name="radio" value="2" class="input" checked>
    Comfortable
  </label>
</fieldset>

Skeleton

Loading placeholder while content is being fetched.

<div class="flex items-center gap-4">
  <div class="bg-gray-200 animate-pulse size-10 rounded-full"></div>
  <div class="grid gap-2">
    <div class="bg-gray-200 animate-pulse rounded-md h-4 w-[150px]"></div>
    <div class="bg-gray-200 animate-pulse rounded-md h-4 w-[100px]"></div>
  </div>
</div>

Slider

Select a value from a continuous range.

<input type="range" class="input" min="0" max="100" value="50">

Switch

Toggle between two states.

<label class="label">
  <input type="checkbox" role="switch" class="input">
  Airplane Mode
</label>

Table

Display tabular data in rows and columns.

Recent Invoices
Invoice Status Method Amount
INV001 Paid Credit Card $250.00
INV002 Pending PayPal $150.00
INV003 Paid Bank Transfer $350.00
Total $750.00
<table class="table">
  <thead>
    <tr>
      <th>Invoice</th>
      <th>Status</th>
      <th>Amount</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td>INV001</td>
      <td>Paid</td>
      <td>$250.00</td>
    </tr>
  </tbody>
</table>

Tabs

Organize content into separate views.

Account settings and profile information.

Change your password and security settings.

General application settings and preferences.

<div class="tabs">
  <nav role="tablist">
    <button role="tab" aria-selected="true">Account</button>
    <button role="tab" aria-selected="false">Password</button>
  </nav>
  <div role="tabpanel">Account content</div>
  <div role="tabpanel" hidden>Password content</div>
</div>

Textarea

Multi-line text input for longer content.

<label for="message" class="label">Message</label>
<textarea id="message" class="textarea"
          placeholder="Type your message here"></textarea>

Toast

Temporary notification messages.

Success

Your changes have been saved.

<div class="toast">
  <svg>...</svg>
  <section>
    <h2>Success</h2>
    <p>Your changes have been saved.</p>
  </section>
  <footer>
    <button>Dismiss</button>
  </footer>
</div>

Tooltip

Contextual information on hover.

<button class="btn-outline" data-tooltip="This is a tooltip">
  Hover me
</button>

<button data-tooltip="Add to library" data-side="right">
  Right tooltip
</button>

Select

Dropdown selection menu.

<select class="select">
  <optgroup label="Fruits">
    <option>Apple</option>
    <option>Banana</option>
    <option>Grapes</option>
  </optgroup>
</select>

Form

Complete form example with multiple input types.

Notification Preferences
<form class="form">
  <div class="grid gap-3">
    <label for="name" class="label">Name</label>
    <input type="text" id="name" class="input">
  </div>

  <div class="grid gap-3">
    <label for="email" class="label">Email</label>
    <input type="email" id="email" class="input">
  </div>

  <button type="submit" class="btn">Submit</button>
</form>