PhiaUi.Components.Button (phia_ui v0.1.16)

Copy Markdown View Source

Stateless Button component with 6 variants and 7 sizes.

Follows the shadcn/ui Button anatomy adapted for Phoenix LiveView. Classes are built via PhiaUi.ClassMerger.cn/1 so callers can safely override individual utilities using the :class attribute.

Variants

VariantUse case
:defaultPrimary call-to-action
:destructiveDangerous or irreversible actions
:outlineSecondary actions, cancel
:secondaryLower-emphasis actions
:ghostMinimal emphasis, toolbar actions
:linkInline navigation-like actions

Sizes

SizeDimensions
:defaulth-10 px-4 py-2
:xsh-7 px-2 text-xs
:smh-9 px-3
:lgh-11 px-8
:iconh-10 w-10 (square)
:icon_smh-8 w-8 (small square)
:icon_lgh-12 w-12 (large square)

Examples

<.button>Save changes</.button>

<.button variant={:destructive}>Delete account</.button>

<.button variant={:outline}>Cancel</.button>

<.button variant={:secondary}>More options</.button>

<.button variant={:ghost}>Settings</.button>

<.button variant={:link}>View details</.button>

<.button size={:sm}>Compact action</.button>

<.button size={:lg}>Prominent action</.button>

<.button size={:icon} aria-label="Add item">
  <.icon name="hero-plus" />
</.button>

<.button phx-click="save" phx-disable-with="Saving…">
  Save
</.button>

<.button disabled={true}>Unavailable</.button>

<.button class="w-full">Full width</.button>

<.button size={:xs}>Compact</.button>

<.button size={:icon_sm} aria-label="Remove"></.button>

<.button>
  <:left_icon><.icon name="hero-arrow-left" /></:left_icon>
  Back
</.button>

<.button loading={true}>Saving</.button>

Summary

Functions

Renders a <button> element with semantic PhiaUI theming.

Functions

button(assigns)

Renders a <button> element with semantic PhiaUI theming.

Icon slots and gap: when either left_icon or right_icon is provided, gap-2 is automatically added to the button's class list so the icon and label maintain consistent spacing — you do not need to add margin classes inside the slots.

Loading state: when loading={true}, an animated SVG spinner (animate-spin h-4 w-4) is prepended to the button content, aria-busy is set to "true" (announcing the in-progress state to screen readers), and pointer-events-none opacity-50 is applied to prevent duplicate submissions while the operation completes.

Disabled + loading: both :disabled and :loading independently apply pointer-events-none opacity-50. When both are true the button is non-interactive and visually dimmed — this is intentional and safe.

Examples

<%!-- Primary call-to-action --%>
<.button>Save changes</.button>

<%!-- Destructive action  use a confirmation dialog alongside --%>
<.button variant={:destructive}>Delete account</.button>

<%!-- Icon-only toolbar button with accessible label --%>
<.button size={:icon} aria-label="Open menu">
  <.icon name="menu" />
</.button>

<%!-- Left icon adds gap-2 automatically --%>
<.button>
  <:left_icon><.icon name="arrow-left" /></:left_icon>
  Back
</.button>

<%!-- Right icon with a destructive context --%>
<.button variant={:destructive}>
  Delete
  <:right_icon><.icon name="trash-2" /></:right_icon>
</.button>

<%!-- Loading state while an async operation is in progress --%>
<.button loading={@saving}>
  {if @saving, do: "Saving…", else: "Save"}
</.button>

<%!-- LiveView phx-disable-with alternative (server-driven) --%>
<.button phx-click="save" phx-disable-with="Saving…">
  Save
</.button>

<%!-- Full-width block button --%>
<.button class="w-full">Continue</.button>

Attributes

  • variant (:atom) - Visual style variant. Defaults to :default. Must be one of :default, :destructive, :outline, :secondary, :ghost, or :link.
  • size (:atom) - Size variant. Defaults to :default. Must be one of :default, :xs, :sm, :lg, :icon, :icon_sm, or :icon_lg.
  • class (:string) - Additional CSS classes (merged via cn/1, last wins). Defaults to nil.
  • disabled (:boolean) - Disables the button and adds pointer-events-none opacity-50. Defaults to false.
  • loading (:boolean) - Shows a spinner and prevents interaction while true. Defaults to false.
  • Global attributes are accepted. HTML attributes forwarded to the <button> element (phx-click, data-, aria-, etc.).

Slots

  • left_icon - Optional icon rendered to the left of the label.
  • right_icon - Optional icon rendered to the right of the label.
  • inner_block (required) - Button label, text or icon content.