Snackbar

Material Design 3 snackbar component for brief messages and notifications

Snackbar

Snackbars provide brief messages about app processes. They appear temporarily at the bottom of the screen and automatically disappear after a timeout.

Basic Usage

Click the button to show a snackbar message.

Basic Snackbar

Message sent

Positions

Bottom Center (Default)

Bottom Center

Bottom center snackbar

Bottom Left

Bottom Left

Bottom left snackbar

Bottom Right

Bottom Right

Bottom right snackbar

Top Center

Top Center

Top center snackbar

Top Left

Top Left

Top left snackbar

Top Right

Top Right

Top right snackbar

With Action

Add an action button for user interaction.

Snackbar with Action

Message archived

With Close Button

Allow users to dismiss the snackbar manually.

Snackbar with Close

This snackbar can be dismissed

With Icon

Add an icon for visual emphasis.

Snackbar with Icon

βœ“ Action completed successfully

Semantic Colors

Success

Success Snackbar

βœ“ Successfully saved!

Error

Error Snackbar

βœ• An error occurred

Warning

Warning Snackbar

⚠ Warning: Check your input

Info

Info Snackbar

β„Ή New updates available

Brand Colors

Primary Snackbar

Primary snackbar

Secondary Snackbar

Secondary snackbar

Tertiary Snackbar

Tertiary snackbar

Dark Snackbar

The traditional Material Design 3 dark snackbar style.

Dark Snackbar

Dark snackbar message

Multiline

For longer messages that need more space.

Multiline Snackbar

This is a longer message that provides more detailed information about the action that was taken.

Complete Example

A snackbar with icon, message, action, and close button.

Complete Snackbar

βœ“ Email sent successfully

JavaScript Integration

Basic Function

function showSnackbar(message, options = {}) {
  const {
    position = 'bottom',
    duration = 3000,
    variant = '',
    action = null,
    showClose = false
  } = options;

  // Create snackbar
  const snackbar = document.createElement('div');
  snackbar.className = `snackbar snackbar-${position} ${variant}`;

  // Build content
  let html = `<span class="snackbar-message">${message}</span>`;

  if (action) {
    html += `<button class="snackbar-action">${action.text}</button>`;
  }

  if (showClose) {
    html += `<button class="snackbar-close" aria-label="Close">Γ—</button>`;
  }

  snackbar.innerHTML = html;
  document.body.appendChild(snackbar);

  // Event listeners
  if (action?.onClick) {
    snackbar.querySelector('.snackbar-action').addEventListener('click', () => {
      action.onClick();
      hideSnackbar(snackbar);
    });
  }

  if (showClose) {
    snackbar.querySelector('.snackbar-close').addEventListener('click', () => {
      hideSnackbar(snackbar);
    });
  }

  // Show with animation
  requestAnimationFrame(() => {
    snackbar.classList.add('snackbar-show');
  });

  // Auto hide
  if (duration > 0) {
    setTimeout(() => hideSnackbar(snackbar), duration);
  }

  return snackbar;
}

function hideSnackbar(snackbar) {
  snackbar.classList.remove('snackbar-show');
  setTimeout(() => snackbar.remove(), 300);
}

// Usage examples
showSnackbar('Message sent');

showSnackbar('File deleted', {
  position: 'bottom-left',
  variant: 'snackbar-warning',
  action: { text: 'Undo', onClick: () => console.log('Undone!') }
});

showSnackbar('Connection restored', {
  variant: 'snackbar-success',
  showClose: true,
  duration: 5000
});

React Example

import { useState, useEffect } from 'react';

interface SnackbarProps {
  message: string;
  isOpen: boolean;
  onClose: () => void;
  variant?: 'success' | 'error' | 'warning' | 'info';
  action?: { text: string; onClick: () => void };
  duration?: number;
}

export function Snackbar({
  message,
  isOpen,
  onClose,
  variant,
  action,
  duration = 3000
}: SnackbarProps) {
  useEffect(() => {
    if (isOpen && duration > 0) {
      const timer = setTimeout(onClose, duration);
      return () => clearTimeout(timer);
    }
  }, [isOpen, duration, onClose]);

  return (
    <div className={`snackbar snackbar-bottom ${variant ? `snackbar-${variant}` : ''} ${isOpen ? 'snackbar-show' : ''}`}>
      <span className="snackbar-message">{message}</span>
      {action && (
        <button className="snackbar-action" onClick={() => { action.onClick(); onClose(); }}>
          {action.text}
        </button>
      )}
      <button className="snackbar-close" onClick={onClose} aria-label="Close">Γ—</button>
    </div>
  );
}

// Usage
function App() {
  const [snackbar, setSnackbar] = useState({ isOpen: false, message: '' });

  return (
    <>
      <button onClick={() => setSnackbar({ isOpen: true, message: 'Hello!' })}>
        Show Snackbar
      </button>
      <Snackbar
        {...snackbar}
        onClose={() => setSnackbar(s => ({ ...s, isOpen: false }))}
      />
    </>
  );
}

API Reference

Class Names

ClassDescription
.snackbarBase snackbar (required)
.snackbar-showShow the snackbar with animation
.snackbar-bottomBottom center position
.snackbar-bottom-leftBottom left position
.snackbar-bottom-rightBottom right position
.snackbar-topTop center position
.snackbar-top-leftTop left position
.snackbar-top-rightTop right position
.snackbar-messageMessage text container
.snackbar-actionAction button
.snackbar-closeClose/dismiss button
.snackbar-iconIcon element
.snackbar-successSuccess color variant
.snackbar-errorError color variant
.snackbar-warningWarning color variant
.snackbar-infoInfo color variant
.snackbar-primaryPrimary color variant
.snackbar-secondarySecondary color variant
.snackbar-tertiaryTertiary color variant
.snackbar-darkDark (inverted) style
.snackbar-multilineMultiline layout

Container Classes (Advanced)

For managing multiple snackbars, use the container approach:

ClassDescription
.snackbar-containerContainer for multiple snackbars
.snackbar-container-bottomContainer at bottom center
.snackbar-container-bottom-leftContainer at bottom left
.snackbar-container-bottom-rightContainer at bottom right
.snackbar-container-topContainer at top center
.snackbar-container-top-leftContainer at top left
.snackbar-container-top-rightContainer at top right

Best Practices

  1. Keep messages brief - Snackbars should contain short, actionable messages
  2. Use appropriate duration - 3-5 seconds for simple messages, longer for messages with actions
  3. One at a time - Avoid showing multiple snackbars simultaneously
  4. Don’t block content - Snackbars should not cover important UI elements
  5. Provide actions when appropriate - Allow users to undo actions or view details
  6. Use semantic colors - Match the snackbar color to the message type (success, error, etc.)
  • Toast - Alternative toast implementation
  • Alert - Prominent inline alerts
  • Dialog - Modal dialogs for important interactions

See Also