91 lines
2.2 KiB
TypeScript
91 lines
2.2 KiB
TypeScript
import { ref } from 'vue';
|
|
|
|
export type ToastType = 'green' | 'magenta' | 'blue' | 'gold' | 'red';
|
|
|
|
export interface NotificationData {
|
|
type: ToastType;
|
|
title: string;
|
|
desc: string;
|
|
icon: string;
|
|
}
|
|
|
|
interface Toast extends NotificationData {
|
|
id: number;
|
|
active: boolean;
|
|
flyingOut: boolean;
|
|
progress: number;
|
|
}
|
|
|
|
interface HistoryItem extends NotificationData {
|
|
id: number;
|
|
timestamp: Date;
|
|
read: boolean;
|
|
}
|
|
|
|
const toasts = ref<Toast[]>([]);
|
|
const history = ref<HistoryItem[]>([]);
|
|
const unreadCount = ref(0);
|
|
let toastId = 0;
|
|
|
|
export function useNotifications() {
|
|
const notify = (data: NotificationData) => {
|
|
// Add to toasts (popup)
|
|
const id = toastId++;
|
|
const toast: Toast = { id, ...data, active: false, flyingOut: false, progress: 100 };
|
|
toasts.value.push(toast);
|
|
|
|
// Animation logic for toast
|
|
setTimeout(() => {
|
|
const t = toasts.value.find(x => x.id === id);
|
|
if(t) t.active = true;
|
|
// Trigger lucide icons update if needed in component
|
|
}, 50);
|
|
|
|
const interval = setInterval(() => {
|
|
const t = toasts.value.find(x => x.id === id);
|
|
if (!t) { clearInterval(interval); return; }
|
|
t.progress -= 0.5;
|
|
if (t.progress <= 0) { clearInterval(interval); closeToast(id); }
|
|
}, 40);
|
|
|
|
// Add to history
|
|
history.value.unshift({
|
|
id: Date.now() + Math.random(),
|
|
...data,
|
|
timestamp: new Date(),
|
|
read: false
|
|
});
|
|
unreadCount.value++;
|
|
};
|
|
|
|
const closeToast = (id: number) => {
|
|
const t = toasts.value.find(x => x.id === id);
|
|
if (t) {
|
|
t.flyingOut = true;
|
|
setTimeout(() => {
|
|
toasts.value = toasts.value.filter(x => x.id !== id);
|
|
}, 600);
|
|
}
|
|
};
|
|
|
|
const markAllRead = () => {
|
|
history.value.forEach(n => n.read = true);
|
|
unreadCount.value = 0;
|
|
};
|
|
|
|
const clearAll = () => {
|
|
history.value = [];
|
|
unreadCount.value = 0;
|
|
};
|
|
|
|
return {
|
|
toasts,
|
|
history,
|
|
unreadCount,
|
|
notify,
|
|
closeToast,
|
|
markAllRead,
|
|
clearAll
|
|
};
|
|
}
|