Skip to content

Commit ec569e4

Browse files
committed
feat(Toast): progress bar with Progress component
1 parent 1d052ec commit ec569e4

File tree

6 files changed

+311
-58
lines changed

6 files changed

+311
-58
lines changed
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
<script setup lang="ts">
2+
const toast = useToast()
3+
4+
function showToast() {
5+
toast.add({
6+
title: 'Uh oh! Something went wrong.',
7+
description: 'There was a problem with your request.',
8+
icon: 'i-lucide-wifi',
9+
progress: false
10+
})
11+
}
12+
</script>
13+
14+
<template>
15+
<UButton label="Show toast" color="neutral" variant="outline" @click="showToast" />
16+
</template>

‎docs/content/3.components/toast.md

Lines changed: 17 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -107,7 +107,7 @@ name: 'toast-color-example'
107107

108108
### Close
109109

110-
Pass a `close` field to customize or hide the close button (with `false` value).
110+
Pass a `close` field to customize or hide the close [Button](/components/button) (with `false` value).
111111

112112
::component-example
113113
---
@@ -143,7 +143,7 @@ You can customize this icon globally in your `vite.config.ts` under `ui.icons.cl
143143

144144
### Actions
145145

146-
Pass an `actions` field to add some [Button](/components/button) actions to the Alert.
146+
Pass an `actions` field to add some [Button](/components/button) actions to the Toast.
147147

148148
::component-example
149149
---
@@ -155,9 +155,23 @@ name: 'toast-actions-example'
155155
---
156156
::
157157

158+
### Progress :badge{label="Soon" class="align-text-top"}
159+
160+
Pass a `progress` field to customize or hide the [Progress](/components/progress) bar (with `false` value).
161+
162+
::tip
163+
The Progress bar inherits the Toast color by default, but you can override it using the `progress.color` field.
164+
::
165+
166+
::component-example
167+
---
168+
name: 'toast-progress-example'
169+
---
170+
::
171+
158172
### Orientation
159173

160-
Use the `orientation` prop to change the orientation of the Toast.
174+
Pass an `orientation` field to the `toast.add` method to change the orientation of the Toast.
161175

162176
::component-example
163177
---

‎src/runtime/components/Toast.vue

Lines changed: 23 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
import type { ToastRootProps, ToastRootEmits } from 'reka-ui'
33
import type { AppConfig } from '@nuxt/schema'
44
import theme from '#build/ui/toast'
5-
import type { AvatarProps, ButtonProps } from '../types'
5+
import type { AvatarProps, ButtonProps, ProgressProps } from '../types'
66
import type { StringOrVNode, ComponentConfig } from '../types/utils'
77
88
type Toast = ComponentConfig<typeof theme, AppConfig, 'toast'>
@@ -30,10 +30,17 @@ export interface ToastProps extends Pick<ToastRootProps, 'defaultOpen' | 'open'
3030
*/
3131
orientation?: Toast['variants']['orientation']
3232
/**
33-
* Whether to show the progress bar.
33+
* Display a close button to dismiss the toast.
34+
* `{ size: 'md', color: 'neutral', variant: 'link' }`{lang="ts-type"}
3435
* @defaultValue true
3536
*/
36-
progress?: boolean
37+
close?: boolean | Partial<ButtonProps>
38+
/**
39+
* The icon displayed in the close button.
40+
* @defaultValue appConfig.ui.icons.close
41+
* @IconifyIcon
42+
*/
43+
closeIcon?: string
3744
/**
3845
* Display a list of actions:
3946
* - under the title and description when orientation is `vertical`
@@ -42,17 +49,11 @@ export interface ToastProps extends Pick<ToastRootProps, 'defaultOpen' | 'open'
4249
*/
4350
actions?: ButtonProps[]
4451
/**
45-
* Display a close button to dismiss the toast.
46-
* `{ size: 'md', color: 'neutral', variant: 'link' }`{lang="ts-type"}
52+
* Display a progress bar showing the toast's remaining duration.
53+
* `{ size: 'sm' }`{lang="ts-type"}
4754
* @defaultValue true
4855
*/
49-
close?: boolean | Partial<ButtonProps>
50-
/**
51-
* The icon displayed in the close button.
52-
* @defaultValue appConfig.ui.icons.close
53-
* @IconifyIcon
54-
*/
55-
closeIcon?: string
56+
progress?: boolean | Pick<ProgressProps, 'color'>
5657
class?: any
5758
ui?: Toast['slots']
5859
}
@@ -78,10 +79,11 @@ import { tv } from '../utils/tv'
7879
import UIcon from './Icon.vue'
7980
import UAvatar from './Avatar.vue'
8081
import UButton from './Button.vue'
82+
import UProgress from './Progress.vue'
8183
8284
const props = withDefaults(defineProps<ToastProps>(), {
83-
close: true,
8485
orientation: 'vertical',
86+
close: true,
8587
progress: true
8688
})
8789
const emits = defineEmits<ToastEmits>()
@@ -184,6 +186,13 @@ defineExpose({
184186
</ToastClose>
185187
</div>
186188

187-
<div v-if="progress && open && remaining > 0 && duration" :class="ui.progress({ class: props.ui?.progress })" :style="{ width: `${remaining / duration * 100}%` }" />
189+
<UProgress
190+
v-if="progress && open && remaining > 0 && duration"
191+
:model-value="remaining / duration * 100"
192+
:color="color"
193+
v-bind="(typeof progress === 'object' ? progress as Partial<ProgressProps> : {})"
194+
size="sm"
195+
:class="ui.progress({ class: props.ui?.progress })"
196+
/>
188197
</ToastRoot>
189198
</template>

‎src/theme/toast.ts

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -10,20 +10,18 @@ export default (options: Required<ModuleOptions>) => ({
1010
avatar: 'shrink-0',
1111
avatarSize: '2xl',
1212
actions: 'flex gap-1.5 shrink-0',
13-
progress: 'absolute inset-x-0 bottom-0 h-1 z-[-1]',
13+
progress: 'absolute inset-x-0 bottom-0',
1414
close: 'p-0'
1515
},
1616
variants: {
1717
color: {
1818
...Object.fromEntries((options.theme.colors || []).map((color: string) => [color, {
1919
root: `focus-visible:ring-2 focus-visible:ring-inset focus-visible:ring-${color}`,
20-
icon: `text-${color}`,
21-
progress: `bg-${color}`
20+
icon: `text-${color}`
2221
}])),
2322
neutral: {
2423
root: 'focus-visible:ring-2 focus-visible:ring-inset focus-visible:ring-inverted',
25-
icon: 'text-highlighted',
26-
progress: 'bg-inverted'
24+
icon: 'text-highlighted'
2725
}
2826
},
2927
orientation: {

0 commit comments

Comments
 (0)