Nuxt UI v3-alpha 已发布!

试用
组件

通知

在您的应用程序中显示一个提示通知。

用法

首先,将 Notifications 组件添加到您的应用程序,最好是在 app.vue 中。

app.vue
<template>
  <div>
    <UContainer>
      <NuxtPage />
    </UContainer>

    <UNotifications />
  </div>
</template>

默认情况下,此组件将在屏幕右下角渲染通知。您可以通过 ui.notificationsapp.config.ts 中配置其行为

app.config.ts
export default defineAppConfig({
  ui: {
    notifications: {
      // Show toasts at the top right of the screen
      position: 'top-0 bottom-[unset]'
    }
  }
})
position 默认值为 bottom-0 end-0bottom-[unset] 类覆盖 bottom-0,因此结果为 top-0 end-0

然后,您可以使用 useToast 可组合函数将通知添加到您的应用程序

<script setup lang="ts">
const toast = useToast()
</script>

<template>
  <UButton label="Show toast" @click="toast.add({ title: 'Hello world!' })" />
</template>

使用 toast.add 时,这将向在 <UNotifications /> 中显示的堆栈中推入一个新的通知。Notification 组件的所有属性都可以传递给 toast.add

<script setup lang="ts">
const toast = useToast()

onMounted(() => {
  toast.add({
    id: 'update_downloaded',
    title: 'Update downloaded.',
    description: 'It will be installed on restart. Restart now?',
    icon: 'i-octicon-desktop-download-24',
    timeout: 0,
    actions: [{
      label: 'Restart',
      click: () => {

      }
    }]
  })
})
</script>

您也可以将 Notification 组件直接用在您的应用程序中,例如作为警报。

标题

title 传递给您的 Notification。

<template>
  <UNotification title="Notification" :id="1" :timeout="0" />
</template>

描述

除了 title 之外,您还可以添加 description

<template>
  <UNotification
    description="This is a notification."
    :id="2"
    :timeout="0"
    title="Notification"
  />
</template>

图标

通过使用此模式设置 icon 属性来使用来自 Iconify 的任何图标:i-{collection_name}-{icon_name},或者在 ui.notification.default.icon 中全局更改它。

<template>
  <UNotification
    icon="i-heroicons-check-circle"
    description="This is a notification."
    :id="3"
    :timeout="0"
    title="Notification"
  />
</template>

头像

使用 avatar 属性作为 object,并使用其任何属性配置它。

<template>
  <UNotification
    description="This is a notification."
    :avatar="{ src: 'https://avatars.githubusercontent.com/u/739984?v=4' }"
    :id="4"
    :timeout="0"
    title="Notification"
  />
</template>

超时

使用 timeout 属性配置 Notification 将保留多长时间。默认值为 5000,将其设置为 0 可禁用超时。

您将在 Notification 底部看到一个进度条,它将指示剩余时间。当您将鼠标悬停在 Notification 上时,进度条将暂停。

<template>
  <UNotification
    :timeout="60000"
    :id="5"
    title="Notification"
    description="This is a notification."
  />
</template>

样式

使用 color 属性更改 Notification 的进度和图标颜色。

<template>
  <UNotification
    icon="i-heroicons-check-badge"
    color="primary"
    :id="6"
    title="Notification"
    description="This is a notification."
    :timeout="600000"
  />
</template>

点击

使用 click 属性在点击 Notification 时执行函数。

<script setup lang="ts">
const toast = useToast()

function onClick() {
  alert('Clicked!')
}
</script>

<template>
  <UButton label="Show toast" @click="toast.add({ title: 'Click me', click: onClick })" />
</template>

回调

使用 callback 属性在 Notification 到期时执行函数。

<script setup lang="ts">
const toast = useToast()

function onCallback() {
  alert('Notification expired!')
}
</script>

<template>
  <UButton label="Show toast" @click="toast.add({ title: 'Expires soon...', timeout: 1000, callback: onCallback })" />
</template>

关闭

使用 close-button 属性隐藏或自定义 Notification 上的关闭按钮。

您可以将 Button 组件的所有属性传递给 close-button 属性,或通过 ui.notification.default.closeButton 全局传递。

<template>
  <UNotification
    :close-button="{ icon: 'i-heroicons-archive-box-x-mark', color: 'primary', variant: 'outline', padded: true, size: '2xs', ui: { rounded: 'rounded-full' } }"
    :id="7"
    title="Notification"
    :timeout="0"
  />
</template>

操作

使用 actions 属性将操作添加到 Notification。

<script setup lang="ts">
const toast = useToast()

const actions = ref([{
  label: 'Action 1',
  click: () => alert('Action 1 clicked!')
}, {
  label: 'Action 2',
  click: () => alert('Action 2 clicked!')
}])
</script>

<template>
  <UButton label="Show toast" @click="toast.add({ title: 'With actions', actions })" />
</template>

closeButton 一样,您可以将 Button 组件的所有属性传递到操作中,或通过 ui.notification.default.actionButton 全局传递。

<template>
  <UNotification
    :actions="[{ label: 'Action 1' }, { variant: 'solid', color: 'gray', label: 'Action 2' }]"
    :id="8"
    title="Notification"
    :timeout="0"
  />
</template>

无论是否设置了 description,操作的呈现方式都不同。

<template>
  <UNotification
    :actions="[{ variant: 'solid', color: 'primary', label: 'Action 1' }, { variant: 'outline', color: 'primary', label: 'Action 2' }]"
    :id="9"
    title="Notification"
    description="This is a notification."
    :timeout="0"
  />
</template>

插槽

title / description

使用 #title#description 插槽来自定义 Notification。

当您想显示 HTML 内容时,这将非常方便。要实现这一点,您可以在顶层 <UNotifications /> 组件中定义这些插槽 app.vue,并使用 v-html 指令。

app.vue
<template>
  <UNotifications>
    <template #title="{ title }">
      <span v-html="title" />
    </template>

    <template #description="{ description }">
      <span v-html="description" />
    </template>
  </UNotifications>
</template>

这样,当使用 useToast 时,您可以在 titledescription 属性中使用 HTML 标签。

<script setup lang="ts">
const toast = useToast()
</script>

<template>
  <UButton label="Show toast" @click="toast.add({ title: 'This is an <u>underlined</u> and <b>bold</b> notification.' })" />
</template>
<UNotifications /> 组件中定义的插槽会自动传递给 Notification 子组件。

属性

id必填
string | number
color
string
config.default.color
icon
string
config.default.icon
ui
{ wrapper?: string; container?: string; inner?: string; title?: string; description?: string; actions?: string; background?: string; shadow?: string; rounded?: string; padding?: string; gap?: string; ring?: string; ... 4 more ...; default?: DeepPartial<...>; } & { ...; } & { ...; }
{}
title
string
null
description
string
null
avatar
头像
null
closeButton
按钮
config.default.closeButton as Button
actions
NotificationAction[]
[]
timeout
number
config.default.timeout
callback
Function
null
ui
{ wrapper?: string; position?: string; width?: string; container?: string; } & { [key: string]: any; } & { strategy?: Strategy; }
{}

配置

{
  wrapper: 'w-full pointer-events-auto',
  container: 'relative overflow-hidden',
  inner: 'w-0 flex-1',
  title: 'text-sm font-medium text-gray-900 dark:text-white',
  description: 'mt-1 text-sm leading-4 text-gray-500 dark:text-gray-400',
  actions: 'flex items-center gap-2 mt-3 flex-shrink-0',
  background: 'bg-white dark:bg-gray-900',
  shadow: 'shadow-lg',
  rounded: 'rounded-lg',
  padding: 'p-4',
  gap: 'gap-3',
  ring: 'ring-1 ring-gray-200 dark:ring-gray-800',
  icon: {
    base: 'flex-shrink-0 w-5 h-5',
    color: 'text-{color}-500 dark:text-{color}-400'
  },
  avatar: {
    base: 'flex-shrink-0 self-center',
    size: 'md'
  },
  progress: {
    base: 'absolute bottom-0 end-0 start-0 h-1',
    background: 'bg-{color}-500 dark:bg-{color}-400'
  },
  transition: {
    enterActiveClass: 'transform ease-out duration-300 transition',
    enterFromClass: 'translate-y-2 opacity-0 sm:translate-y-0 sm:translate-x-2',
    enterToClass: 'translate-y-0 opacity-100 sm:translate-x-0',
    leaveActiveClass: 'transition ease-in duration-100',
    leaveFromClass: 'opacity-100',
    leaveToClass: 'opacity-0'
  },
  default: {
    color: 'primary',
    icon: null,
    timeout: 5000,
    closeButton: {
      icon: 'i-heroicons-x-mark-20-solid',
      color: 'gray',
      variant: 'link',
      padded: false
    },
    actionButton: {
      size: 'xs',
      color: 'white'
    }
  }
}
{
  wrapper: 'fixed flex flex-col justify-end z-[55]',
  position: 'bottom-0 end-0',
  width: 'w-full sm:w-96',
  container: 'px-4 sm:px-6 py-6 space-y-3 overflow-y-auto'
}