43 lines
1.0 KiB
TypeScript
43 lines
1.0 KiB
TypeScript
import { Injectable, signal } from '@angular/core';
|
|
|
|
export type ToastType = 'error' | 'success' | 'info';
|
|
|
|
export interface Toast {
|
|
id: number;
|
|
type: ToastType;
|
|
message: string;
|
|
}
|
|
|
|
/**
|
|
* Lightweight, dependency-free toast/notification store. A single
|
|
* ToastContainerComponent (mounted in the app root) renders whatever this holds.
|
|
*/
|
|
@Injectable({ providedIn: 'root' })
|
|
export class ToastService {
|
|
private counter = 0;
|
|
readonly toasts = signal<Toast[]>([]);
|
|
|
|
error(message: string): void {
|
|
this.show('error', message);
|
|
}
|
|
|
|
success(message: string): void {
|
|
this.show('success', message);
|
|
}
|
|
|
|
info(message: string): void {
|
|
this.show('info', message);
|
|
}
|
|
|
|
dismiss(id: number): void {
|
|
this.toasts.update(list => list.filter(toast => toast.id !== id));
|
|
}
|
|
|
|
private show(type: ToastType, message: string): void {
|
|
const id = ++this.counter;
|
|
this.toasts.update(list => [...list, { id, type, message }]);
|
|
const autoDismissMs = type === 'error' ? 8000 : 4000;
|
|
setTimeout(() => this.dismiss(id), autoDismissMs);
|
|
}
|
|
}
|