Agents (llms.txt)

Empty State

A friendly placeholder for blank screens and zero-result views

No projects yet

Create your first project to start tracking work across your team.

import { Folder, Plus } from '@untitledui-pro/icons/solid';

import { Button } from '@/components/button';
import { EmptyState } from '@/components/empty-state';

export default function EmptyStatePreview() {
  return (
    <EmptyState>
      <EmptyState.Icon>
        <Folder />
      </EmptyState.Icon>
      <EmptyState.Title>No projects yet</EmptyState.Title>
      <EmptyState.Description>
        Create your first project to start tracking work across your team.
      </EmptyState.Description>
      <EmptyState.Actions>
        <Button>
          <Plus />
          New project
        </Button>
      </EmptyState.Actions>
    </EmptyState>
  );
}

Source Code

import { cn } from '@/lib/utils/classnames';

const EmptyState = ({
  ref,
  className,
  ...rest
}: React.ComponentPropsWithRef<'div'>) => (
  <div
    ref={ref}
    className={cn(
      'mx-auto flex max-w-md flex-col items-center justify-center gap-3 px-6 py-12 text-center',
      className
    )}
    {...rest}
  />
);

const EmptyStateIcon = ({
  ref,
  className,
  ...rest
}: React.ComponentPropsWithRef<'div'>) => (
  <div
    ref={ref}
    aria-hidden
    className={cn(
      'mb-1 inline-flex size-12 items-center justify-center rounded-2xl border border-border bg-surface-sunken text-foreground-secondary [&>svg]:size-6',
      className
    )}
    {...rest}
  />
);

const EmptyStateTitle = ({
  ref,
  className,
  ...rest
}: React.ComponentPropsWithRef<'h3'>) => (
  <h3
    ref={ref}
    className={cn(
      'text-balance font-semibold text-foreground text-lg',
      className
    )}
    {...rest}
  />
);

const EmptyStateDescription = ({
  ref,
  className,
  ...rest
}: React.ComponentPropsWithRef<'p'>) => (
  <p
    ref={ref}
    className={cn(
      'max-w-prose text-pretty text-foreground-secondary text-sm',
      className
    )}
    {...rest}
  />
);

const EmptyStateActions = ({
  ref,
  className,
  ...rest
}: React.ComponentPropsWithRef<'div'>) => (
  <div
    ref={ref}
    className={cn(
      'mt-2 flex flex-wrap items-center justify-center gap-2',
      className
    )}
    {...rest}
  />
);

const CompoundEmptyState = Object.assign(EmptyState, {
  Icon: EmptyStateIcon,
  Title: EmptyStateTitle,
  Description: EmptyStateDescription,
  Actions: EmptyStateActions,
});

export { CompoundEmptyState as EmptyState };

Server component. No 'use client' — static empty-state layout compound; forwards props only.

EmptyState shows up when there is nothing to show — first-run, zero search results, or an empty inbox. It nudges the user toward the next action.

Anatomy


          <EmptyState>
  <EmptyState.Icon>{icon}</EmptyState.Icon>
  <EmptyState.Title>{title}</EmptyState.Title>
  <EmptyState.Description>{description}</EmptyState.Description>
  <EmptyState.Actions>{actions}</EmptyState.Actions>
</EmptyState>
        

API Reference

EmptyState

Extends the div element.

EmptyState.Icon

Extends the div element.

EmptyState.Title

Extends the h3 element.

EmptyState.Description

Extends the p element.

EmptyState.Actions

Extends the div element.

Examples

Default

No projects yet

Create your first project to start tracking work across your team.

import { Folder, Plus } from '@untitledui-pro/icons/solid';

import { Button } from '@/components/button';
import { EmptyState } from '@/components/empty-state';

export default function EmptyStatePreview() {
  return (
    <EmptyState>
      <EmptyState.Icon>
        <Folder />
      </EmptyState.Icon>
      <EmptyState.Title>No projects yet</EmptyState.Title>
      <EmptyState.Description>
        Create your first project to start tracking work across your team.
      </EmptyState.Description>
      <EmptyState.Actions>
        <Button>
          <Plus />
          New project
        </Button>
      </EmptyState.Actions>
    </EmptyState>
  );
}

Previous

Drawer

Next

Field