v2.9.0

Empty

An empty state component.

Usage

No projects found

It looks like you haven't added any projects. Create one to get started.
<script setup lang="ts">
import ProductIcon from '@bitrix24/b24icons-vue/outline/ProductIcon'
import AddProductIcon from '@bitrix24/b24icons-vue/outline/AddProductIcon'
import RefreshIcon from '@bitrix24/b24icons-vue/outline/RefreshIcon'
</script>

<template>
  <B24Empty
    :icon="ProductIcon"
    title="No projects found"
    description="It looks like you haven't added any projects. Create one to get started."
    :actions="[
      {
        label: 'Create new',
        icon: AddProductIcon,
        color: 'air-primary'
      },
      {
        label: 'Refresh',
        icon: RefreshIcon
      }
    ]"
  />
</template>

Title

Use the title prop to set the title of the empty state.

No projects found

<template>
  <B24Empty title="No projects found" />
</template>

Description

Use the description prop to set the description of the empty state.

No projects found

It looks like you haven't added any projects. Create one to get started.
<template>
  <B24Empty
    title="No projects found"
    description="It looks like you haven't added any projects. Create one to get started."
  />
</template>

Icon

Use the icon prop to set the icon of the empty state.

No projects found

It looks like you haven't added any projects. Create one to get started.
<script setup lang="ts">
import RocketIcon from '@bitrix24/b24icons-vue/main/RocketIcon'
</script>

<template>
  <B24Empty
    :icon="RocketIcon"
    title="No projects found"
    description="It looks like you haven't added any projects. Create one to get started."
  />
</template>

Loading

Use the loading prop to show a loading icon in place of the icon. The layout stays identical, so you can toggle between loading and empty states without layout shifts.

Loading projects

Please wait while we fetch your projects.
<template>
  <B24Empty
    loading
    title="Loading projects"
    description="Please wait while we fetch your projects."
  />
</template>

Loading Icon

Use the loading-icon prop to customize the loading icon. Defaults to icons.loading.

Loading projects

Please wait while we fetch your projects.
<script setup lang="ts">
import RocketIcon from '@bitrix24/b24icons-vue/main/RocketIcon'
</script>

<template>
  <B24Empty
    loading
    :loading-icon="RocketIcon"
    title="Loading projects"
    description="Please wait while we fetch your projects."
  />
</template>

Actions

Use the actions prop to add some Button actions to the empty state.

No projects found

It looks like you haven't added any projects. Create one to get started.
<script setup lang="ts">
import RocketIcon from '@bitrix24/b24icons-vue/main/RocketIcon'
</script>

<template>
  <B24Empty
    :icon="RocketIcon"
    title="No projects found"
    description="It looks like you haven't added any projects. Create one to get started."
    :actions="{
      '0': {
        label: 'Create new',
        color: 'air-primary'
      },
      '1': {
        label: 'Refresh'
      }
    }"
  />
</template>

Color

Use the color prop to change the color of the empty state.

No notifications

You're all caught up. New notifications will appear here.
<script setup lang="ts">
import RocketIcon from '@bitrix24/b24icons-vue/main/RocketIcon'
</script>

<template>
  <B24Empty
    color="air-secondary-accent-2"
    :icon="RocketIcon"
    title="No notifications"
    description="You're all caught up. New notifications will appear here."
    :actions="{
      '0': {
        label: 'Refresh'
      }
    }"
  />
</template>

Inverted

Use the inverted prop to invert the color of the empty state.

Only available for air-primary* colors

No notifications

You're all caught up. New notifications will appear here.
<script setup lang="ts">
import RocketIcon from '@bitrix24/b24icons-vue/main/RocketIcon'
</script>

<template>
  <B24Empty
    inverted
    color="air-primary"
    :icon="RocketIcon"
    title="No notifications"
    description="You're all caught up. New notifications will appear here."
    :actions="{
      '0': {
        label: 'Refresh'
      }
    }"
  />
</template>

Size

Use the size prop to change the size of the empty state.

No notifications

You're all caught up. New notifications will appear here.
<script setup lang="ts">
import RocketIcon from '@bitrix24/b24icons-vue/main/RocketIcon'
</script>

<template>
  <B24Empty
    size="xl"
    :icon="RocketIcon"
    title="No notifications"
    description="You're all caught up. New notifications will appear here."
    :actions="{
      '0': {
        label: 'Refresh'
      }
    }"
  />
</template>

Examples

With slots

Use the available slots to create a more complex empty state.

Employee Namebitrix24

No team members

Invite your team to collaborate on this project.
Employee Name

Employee Name

Team employee

Assistant Name

Employee Name

Team assistant

<script setup lang="ts">
import type { UserProps } from '@bitrix24/b24ui-nuxt'
import AddProductIcon from '@bitrix24/b24icons-vue/outline/AddProductIcon'

const members: UserProps[] = [
  {
    name: 'Employee Name',
    description: 'Team employee',
    to: 'https://github.com/bitrix24',
    target: '_blank',
    avatar: {
      src: '/b24ui/avatar/employee.png',
      alt: 'Employee Name',
      loading: 'lazy' as const
    }
  },
  {
    name: 'Employee Name',
    description: 'Team assistant',
    to: 'https://github.com/bitrix24',
    target: '_blank',
    avatar: {
      src: '/b24ui/avatar/assistant.png',
      alt: 'Assistant Name',
      loading: 'lazy' as const
    }
  }
]
</script>

<template>
  <B24Empty
    title="No team members"
    description="Invite your team to collaborate on this project."
    :actions="[{
      label: 'Invite members',
      icon: AddProductIcon
    }]"
  >
    <template #leading>
      <B24AvatarGroup size="xl">
        <B24Avatar src="/b24ui/avatar/employee.png" alt="Employee Name" loading="lazy" />
        <B24Avatar src="https://github.com/bitrix24.png" alt="bitrix24" loading="lazy" />
      </B24AvatarGroup>
    </template>

    <template #footer>
      <B24Separator class="my-4" />

      <div class="grid grid-cols-2 gap-4">
        <B24Card
          v-for="(member, index) in members"
          :key="index"
          :b24ui="{ body: 'p-4 sm:p-4' }"
        >
          <B24User
            :avatar="member.avatar"
            :name="member.name"
            :description="member.description"
            :b24ui="{ name: 'truncate' }"
          />
          <div class="mt-2 w-full flex flex-row justify-end">
            <B24Link
              class="text-xs"
              is-action
              :to="member.to"
              :target="member.target"
            >
              Invite
            </B24Link>
          </div>
        </B24Card>
      </div>
    </template>
  </B24Empty>
</template>

API

Props

Prop Default Type
as'div'any

The element or component this component should render as.

iconIconComponent

The icon displayed above the title.

loadingboolean

When true, the loading icon will be displayed.

loadingIconicons.loadingIconComponent

The icon when the loading prop is true.

title string
description string
actions ButtonProps[]

Display a list of Button in the body.

color'air-secondary-accent'"air-primary" | "air-primary-success" | "air-primary-alert" | "air-primary-warning" | "air-primary-copilot" | "air-secondary" | "air-secondary-alert" | "air-secondary-accent" | "air-secondary-accent-1" | "air-secondary-accent-2" | "air-tertiary"
invertedfalseboolean

If set to true the color is inverted. Used for 'air-primary', 'air-primary-success', 'air-primary-alert', 'air-primary-copilot' and 'air-primary-warning' colors.

size'md' "md" | "xs" | "sm" | "lg" | "xl"
b24ui { root?: SlotClass; header?: SlotClass; indicator?: SlotClass; icon?: SlotClass; title?: SlotClass; description?: SlotClass; body?: SlotClass; actions?: SlotClass; footer?: SlotClass; }

Slots

Slot Type
header{}
leading{ b24ui: object; }
title{}
description{}
body{}
actions{}
footer{}

Theme

https://github.com/bitrix24/b24ui/tree/main/src/theme/empty.ts
export default {
  slots: {
    root: 'relative flex flex-col items-center justify-center gap-4 rounded-lg p-4 sm:p-6 lg:p-8 min-w-0 bg-(--b24ui-background) ring ring-(--b24ui-border-color) ring-(length:--b24ui-border-width)',
    header: 'flex flex-col items-center gap-2 max-w-[384px] text-center',
    indicator: 'rounded-full text-(--b24ui-color) bg-(--b24ui-background-active) flex items-center justify-center mb-2',
    icon: 'shrink-0',
    title: 'text-(--b24ui-color) text-pretty font-(--ui-font-weight-medium)',
    description: 'text-balance text-center text-(--b24ui-color)',
    body: 'flex flex-col items-center gap-4 max-w-[384px]',
    actions: 'flex flex-wrap justify-center gap-2 shrink-0',
    footer: 'flex flex-col items-center gap-2 max-w-[384px]'
  },
  variants: {
    size: {
      xs: {
        icon: 'size-[26px]',
        title: 'text-(length:--ui-font-size-sm)/(--ui-font-line-height-lg)',
        description: 'text-(length:--ui-font-size-xs)'
      },
      sm: {
        icon: 'size-[28px]',
        title: 'text-(length:--ui-font-size-sm)/(--ui-font-line-height-lg)',
        description: 'text-(length:--ui-font-size-xs)'
      },
      md: {
        icon: 'size-[38px]',
        title: 'text-base',
        description: 'text-(length:--ui-font-size-sm)/(--ui-font-line-height-lg)'
      },
      lg: {
        icon: 'size-[44px]',
        title: 'text-base',
        description: 'text-(length:--ui-font-size-sm)/(--ui-font-line-height-lg)'
      },
      xl: {
        icon: 'size-[56px]',
        title: 'text-(length:--ui-font-size-xl)/(--ui-font-line-height-3xs)',
        description: 'text-(length:--ui-font-size-lg)/(--ui-font-line-height-3xs)'
      }
    },
    color: {
      'air-primary': {
        root: 'style-filled'
      },
      'air-primary-success': {
        root: 'style-filled-success'
      },
      'air-primary-alert': {
        root: 'style-filled-alert'
      },
      'air-primary-copilot': {
        root: 'style-filled-copilot'
      },
      'air-primary-warning': {
        root: 'style-filled-warning'
      },
      'air-secondary': {
        root: 'style-tinted'
      },
      'air-secondary-alert': {
        root: 'style-tinted-alert'
      },
      'air-secondary-accent': {
        root: 'style-outline'
      },
      'air-secondary-accent-1': {
        root: 'style-outline-accent-1'
      },
      'air-secondary-accent-2': {
        root: 'style-outline-accent-2'
      },
      'air-tertiary': {
        root: 'style-outline-no-accent'
      }
    },
    inverted: {
      true: '',
      false: ''
    },
    loading: {
      true: {
        icon: 'animate-spin'
      }
    }
  },
  compoundVariants: [
    {
      inverted: true,
      color: 'air-primary',
      class: {
        root: 'style-filled-inverted'
      }
    }
  ],
  defaultVariants: {
    color: 'air-secondary-accent',
    size: 'md',
    inverted: false
  }
}
Some colors in compoundVariants are omitted for readability. Check out the source code on GitHub.