{"version":3,"file":"vi5hnuu-ngx-noti.mjs","sources":["../../../projects/ngx-noti/src/lib/utils/util-functions.ts","../../../projects/ngx-noti/src/lib/services/ngx-noti/ngx-noti.service.ts","../../../projects/ngx-noti/src/lib/models/notification.interface.ts","../../../projects/ngx-noti/src/lib/utils/anims.ts","../../../projects/ngx-noti/src/lib/components/notifications-panel/notifications-panel.component.ts","../../../projects/ngx-noti/src/lib/components/notifications-panel/notifications-panel.component.html","../../../projects/ngx-noti/src/public-api.ts","../../../projects/ngx-noti/src/vi5hnuu-ngx-noti.ts"],"sourcesContent":["/** Characters an id may be built from.\n *\n *  Alphanumeric only. The previous alphabet included `!@#$%^&*()-_=+[]{}|;:,.<>?/~\\``, which is\n *  hostile for a value that ends up as an object key, in `trackBy`, and inside DOM attributes —\n *  a `.` or `#` in an id breaks the moment anyone puts it in a selector. */\nconst ID_CHARS = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789';\n\nexport const generateId=({length=32,prefix=''}:{length?:number, prefix?:string})=> {\n  if (length <= prefix.length) {\n    throw new Error('Length must be greater than the prefix length.');\n  }\n\n  const idLength = length - prefix.length;\n  let result = '';\n  for (let i = 0; i < idLength; i++) {\n    result += ID_CHARS[Math.floor(Math.random() * ID_CHARS.length)];\n  }\n\n  return prefix + result;\n}\n","import {Injectable, OnDestroy, TemplateRef} from \"@angular/core\";\nimport {Notification, NotificationPatch, NotificationType} from '../../models/notification.interface';\nimport {generateId} from '../../utils/util-functions';\n\n/** Shortest auto-dismiss delay. Anything quicker cannot be read. */\nconst MIN_VISIBILITY_MS = 1000;\n/** How many notifications may be live at once before the oldest is dropped. */\nconst DEFAULT_MAX_STACK = 5;\n\n/**\n * Holds the live notifications and owns their dismissal timers.\n *\n * `providedIn: 'root'` so the library works with no setup. A consumer that wants notifications\n * scoped to one part of the app still gets that by listing the service in a component's own\n * `providers`, which shadows the root instance — the arrangement every app in this repo uses,\n * and the one the README documents.\n */\n@Injectable({providedIn: 'root'})\nexport class NgxNotiService implements OnDestroy {\n  private notifications: Notification[] = [];\n  /** Dismissal timers by notification id. One `setTimeout` each — the countdown the user sees\n   *  is a CSS animation on the progress bar, so nothing here runs per frame. */\n  private timers: {[key: string]: ReturnType<typeof setTimeout>} = {};\n\n  /** Most notifications to keep on screen; the oldest is dropped past this. */\n  maxStack = DEFAULT_MAX_STACK;\n\n  public get _notifications(): Readonly<Notification[]> {//prop to be used only internally\n    return this.notifications;\n  }\n\n  /**\n   * Show a notification.\n   *\n   * @returns the new notification's id, so the caller can dismiss or {@link update} it later.\n   */\n  addNotification(\n    {title,type,description,visibilityTimeMs,iconSrc,templateRef}:{\n      title: string,\n      type:NotificationType,\n      description?:string,\n      visibilityTimeMs?:number,\n      iconSrc?:string,\n      templateRef?:TemplateRef<any>,\n    }\n  ): string {\n    const timeMs = visibilityTimeMs !== undefined ? Math.max(visibilityTimeMs, MIN_VISIBILITY_MS) : undefined;\n    const notification: Notification = {\n      id: generateId({prefix: 'NOT'}),\n      title,\n      type,\n      description,\n      visibilityTimeMs: timeMs,\n      visibilityTimeMsLeft: timeMs,\n      iconSrc,\n      templateRef,\n      paused: false,\n    };\n    this.notifications.push(notification);\n\n    // Drop the oldest past the cap, so a burst cannot bury the screen or leave a pile of live\n    // timers behind it.\n    while (this.notifications.length > Math.max(1, this.maxStack)) {\n      this.clearNotification(this.notifications[0].id);\n    }\n\n    this.schedule(notification, timeMs);\n    return notification.id;\n  }\n\n  /** Change a live notification in place — for a toast that reports progress. No-op if gone. */\n  update(notificationId: string, patch: NotificationPatch): void {\n    const notification = this.notifications.find(n => n.id === notificationId);\n    if (notification) Object.assign(notification, patch);\n  }\n\n  /**\n   * Hold a notification open while the user is reading it.\n   *\n   * Cancels the dismissal timer and banks the time still to run, so resuming picks up where it\n   * left off rather than restarting the full duration.\n   */\n  pause(notificationId: string): void {\n    const notification = this.notifications.find(n => n.id === notificationId);\n    if (!notification || notification.paused || notification.visibilityTimeMs === undefined) return;\n    const elapsed = Date.now() - (notification.startedAt ?? Date.now());\n    notification.visibilityTimeMsLeft = Math.max(0, (notification.visibilityTimeMsLeft ?? 0) - elapsed);\n    notification.paused = true;\n    this.cancelTimer(notificationId);\n  }\n\n  /** Resume a paused notification for whatever time it had left. */\n  resume(notificationId: string): void {\n    const notification = this.notifications.find(n => n.id === notificationId);\n    if (!notification || !notification.paused) return;\n    notification.paused = false;\n    this.schedule(notification, notification.visibilityTimeMsLeft);\n  }\n\n  clearNotification(notificationId: string): void {\n    this.cancelTimer(notificationId);\n    this.notifications = this.notifications.filter(n => n.id !== notificationId);\n  }\n\n  clearAllNotifications(): void {\n    // Cancel every timer AND drop the handles. Clearing without emptying the map left a dead\n    // entry per notification for the lifetime of the service, growing without bound.\n    Object.keys(this.timers).forEach(id => this.cancelTimer(id));\n    this.notifications = [];\n  }\n\n  ngOnDestroy(): void {\n    this.clearAllNotifications();\n  }\n\n  /** Arm the dismissal timer, unless the notification is meant to stay until dismissed. */\n  private schedule(notification: Notification, timeMs: number | undefined): void {\n    if (timeMs === undefined) return;\n    notification.startedAt = Date.now();\n    notification.visibilityTimeMsLeft = timeMs;\n    this.cancelTimer(notification.id);\n    this.timers[notification.id] = setTimeout(() => this.clearNotification(notification.id), timeMs);\n  }\n\n  private cancelTimer(notificationId: string): void {\n    const timer = this.timers[notificationId];\n    if (timer !== undefined) clearTimeout(timer);\n    delete this.timers[notificationId];\n  }\n}\n","import {TemplateRef} from '@angular/core';\n\nexport interface Notification{\n  id:string,\n  title: string,\n  type:NotificationType,\n  description?:string,\n  /** Auto-dismiss delay. Undefined means the notification stays until dismissed. */\n  visibilityTimeMs?:number,\n  /**\n   * Time still to run, in ms.\n   *\n   * Only meaningful while paused: the countdown itself is a CSS animation on the progress bar,\n   * so nothing writes this every frame. It is stamped when a pause starts so the resumed timer\n   * and the resumed animation agree on how much is left.\n   */\n  visibilityTimeMsLeft?:number,\n  iconSrc?:string,\n  templateRef?:TemplateRef<any>,\n  /** True while a pointer or keyboard focus is holding the notification open. */\n  paused?:boolean,\n  /** When the current run of the timer started, for working out what is left on pause. */\n  startedAt?:number,\n}\n\n/** The fields {@link NgxNotiService.update} may change on a live notification. */\nexport type NotificationPatch = Partial<Pick<Notification, 'title' | 'description' | 'type' | 'iconSrc'>>;\n\nexport enum NotificationType {\n  ERROR,\n  SUCCESS,\n  WARNING,\n  INFO\n}\n\nexport enum NotificationPosition {\n  TOP_LEFT,\n  TOP_RIGHT,\n  BOTTOM_RIGHT,\n  BOTTOM_LEFT,\n  TOP_CENTER,\n  BOTTOM_CENTER\n}\n","import {animate, style, transition, trigger} from '@angular/animations';\n\n/**\n * Enter/leave for a notification card.\n *\n * The starting transform is a parameter rather than a constant, so a card arrives from the edge\n * it is anchored to: a bottom-right panel used to fly in from the left, across the whole screen,\n * and back out the same way.\n *\n * A whole `transform` value rather than an X offset, so the direction is the caller's choice\n * and not baked in here. The panel supplies it from its position; see\n * `NotificationsPanelComponent.slideParams`.\n */\nexport const slideInOut = trigger('slideInOut', [\n  transition(':enter', [\n    style({ transform: '{{transform}}', opacity: 0 }),\n    animate('{{enterDurationMs}}ms cubic-bezier(0.21, 1.02, 0.73, 1)', style({ transform: 'translate(0, 0)', opacity: 1 }))\n  ],{params:{enterDurationMs:300, transform:'translateX(-100%)'}}),\n  transition(':leave', [\n    animate('{{exitDurationMs}}ms cubic-bezier(0.06, 0.71, 0.55, 1)', style({ transform: '{{transform}}', opacity: 0 }))\n  ],{params:{exitDurationMs:200, transform:'translateX(-100%)'}}),\n]);\n","import {\n  Component,\n  EventEmitter,\n  Input,\n  Output,\n  ViewEncapsulation\n} from '@angular/core';\nimport {NgClass, NgForOf, NgIf, NgTemplateOutlet} from \"@angular/common\";\nimport {Notification, NotificationPosition, NotificationType} from '../../models/notification.interface';\nimport {slideInOut} from '../../utils/anims';\nimport {NgxNotiService} from '../../services/ngx-noti/ngx-noti.service';\nimport {MatIcon, MatIconRegistry} from '@angular/material/icon';\nimport {DomSanitizer} from '@angular/platform-browser';\n\n@Component({\n  selector: 'lib-notifications-panel',\n  imports: [\n    NgForOf,\n    NgClass,\n    NgIf,\n    NgTemplateOutlet,\n    MatIcon\n  ],\n  templateUrl: './notifications-panel.component.html',\n  styleUrl: './notifications-panel.component.scss',\n  animations:[slideInOut],\n  encapsulation: ViewEncapsulation.ShadowDom\n})\nexport class NotificationsPanelComponent{\n  @Input() notificationsPosition:NotificationPosition=NotificationPosition.BOTTOM_RIGHT;\n  /** Most notifications on screen at once; the oldest is dropped past this. */\n  @Input() set maxStack(value: number) { this.ngxNotiService.maxStack = value; }\n  /** Hold a notification open while it is hovered or keyboard-focused. */\n  @Input() pauseOnHover = true;\n  /** Show the \"clear all\" control once the stack is deeper than this. */\n  @Input() clearAllThreshold = 2;\n\n  @Output() dismiss=new EventEmitter<string>();\n  @Output() dismissAll=new EventEmitter<void>();\n\n  constructor(private ngxNotiService:NgxNotiService,\n              private matIconRegistry:MatIconRegistry,\n              private domSanitizer:DomSanitizer) {\n    this.initSvgIconsRegistry();\n  }\n\n  initSvgIconsRegistry(){\n    this.matIconRegistry.addSvgIconResolver((name: string, namespace: string) => {\n      if (namespace === 'ngx-noti') {\n        return this.domSanitizer.bypassSecurityTrustResourceUrl(`assets/ngx-noti/${name}.svg`);\n      }\n      return null;\n    });\n  }\n\n  get notifications(){\n    return this.ngxNotiService._notifications;\n  }\n\n  /**\n   * Order the stack so the newest notification sits against the edge the panel is anchored to,\n   * and older ones are pushed away from it — which is how every toast stack behaves.\n   *\n   * `notifications` is oldest-first, and the list renders top to bottom. A top-anchored panel\n   * therefore has to reverse (newest at the top, older pushed down); a bottom-anchored one must\n   * not (newest last, so it sits at the bottom and older ones ride up). This was exactly\n   * inverted, so new notifications appeared at the far end of the stack from where they grew.\n   */\n  get orderedNotifications(): Readonly<Notification[]> {\n    return this.isTopLevelNotification ? this.notifications.slice().reverse() : this.notifications;\n  }\n\n  /**\n   * Identity for the `*ngFor`.\n   *\n   * Without it Angular rebuilt every card on any change, which restarted each one's enter\n   * animation and threw away the running progress-bar animation every time another\n   * notification arrived or left.\n   */\n  trackById = (_: number, notification: Notification) => notification.id;\n\n  /**\n   * Stacking order, so the newest card sits on top of the ones it overlaps.\n   *\n   * The cards deliberately overlap — a nested stack is what this library is for — and which one\n   * wins depends on which end the newest is at, which differs by anchor (see\n   * {@link orderedNotifications}). A top-anchored panel renders newest-first, so z has to count\n   * down; a bottom-anchored one renders newest-last, so it counts up.\n   */\n  stackZ(index: number): number {\n    return this.isTopLevelNotification ? this.notifications.length - index : index;\n  }\n\n  protected readonly NotificationType = NotificationType;\n  protected readonly NotificationPosition = NotificationPosition;\n\n  get isTopLevelNotification(){\n    return [NotificationPosition.TOP_LEFT, NotificationPosition.TOP_CENTER, NotificationPosition.TOP_RIGHT].includes(this.notificationsPosition);\n  }\n\n  /** True for the right-anchored positions, which must slide in from the right. */\n  private get isRightAnchored(){\n    return [NotificationPosition.TOP_RIGHT, NotificationPosition.BOTTOM_RIGHT].includes(this.notificationsPosition);\n  }\n\n  /**\n   * Which edge a card flies in from.\n   *\n   * A card enters from the edge its panel is anchored to, and fades as it travels. Corner\n   * panels come in sideways from their own side; centre panels drop from the top or rise from\n   * the bottom, which is the direction a centred toast belongs to.\n   *\n   * The distances assume the panel does not clip (`overflow: visible`). While it did, a\n   * horizontal card was wiped in from the panel's edge and a vertical one had only the card's\n   * ~50px of height to move through, which is why the vertical version read as a plain fade.\n   */\n  get slideParams(): {transform: string} {\n    switch (this.notificationsPosition) {\n      case NotificationPosition.TOP_CENTER:    return {transform: 'translateY(-140%)'};\n      case NotificationPosition.BOTTOM_CENTER: return {transform: 'translateY(140%)'};\n      default:                                 return {transform: this.isRightAnchored ? 'translateX(110%)' : 'translateX(-110%)'};\n    }\n  }\n\n  /**\n   * Errors interrupt; everything else waits its turn in the screen-reader queue.\n   *\n   * Expressed as the role rather than an `aria-live` attribute. `role=\"alert\"` already *means*\n   * assertive, so pairing it with `aria-live=\"polite\"` — as this did — asks for two different\n   * things at once, and which one wins is down to the screen reader. `status` is the polite\n   * counterpart of `alert` and carries the live semantics on its own.\n   */\n  roleFor(notification: Notification): 'alert' | 'status' {\n    return notification.type === NotificationType.ERROR ? 'alert' : 'status';\n  }\n\n  /**\n   * Duration for the countdown animation — always the notification's *full* time.\n   *\n   * Deliberately not the remaining time. A paused CSS animation keeps its own elapsed time, so\n   * shrinking the duration underneath it re-reads that elapsed time as a larger fraction and\n   * the bar jumps forward the moment you hover. Holding the duration constant and only toggling\n   * `animation-play-state` means the bar simply stops and starts where it was, and it lands at\n   * empty exactly when the service's re-armed timeout fires.\n   */\n  progressDurationMs(notification: Notification): number {\n    return notification.visibilityTimeMs ?? 0;\n  }\n\n  onPointerEnter(notification: Notification) {\n    if (this.pauseOnHover) this.ngxNotiService.pause(notification.id);\n  }\n\n  onPointerLeave(notification: Notification) {\n    if (this.pauseOnHover) this.ngxNotiService.resume(notification.id);\n  }\n\n  /**\n   * Dismiss one notification.\n   *\n   * Removes it here *and* emits, so the panel works whether or not the host wires `(dismiss)`.\n   * Hosts that do wire it call `clearNotification` a second time, which is a no-op for an id\n   * that has already gone.\n   */\n  onDismiss(notificationId: string) {\n    this.ngxNotiService.clearNotification(notificationId);\n    this.dismiss.emit(notificationId);\n  }\n\n  /** Clear the whole stack. Same self-sufficient arrangement as {@link onDismiss}. */\n  onDismissAll() {\n    this.ngxNotiService.clearAllNotifications();\n    this.dismissAll.emit();\n  }\n}\n","<!-- Plain class names, styled entirely by this component's own stylesheet. The template used\n     Tailwind utilities, which meant the component had to `@use` the whole framework plus this\n     repo's private theme — 94 kB of CSS inlined into the shadow root of every consumer, and a\n     published package carrying a theme that is not its own. -->\n<div\n  [ngClass]=\"{\n    'top-left':notificationsPosition===NotificationPosition.TOP_LEFT,\n    'top-center':notificationsPosition===NotificationPosition.TOP_CENTER,\n    'top-right':notificationsPosition===NotificationPosition.TOP_RIGHT,\n    'bottom-right':notificationsPosition===NotificationPosition.BOTTOM_RIGHT,\n    'bottom-center':notificationsPosition===NotificationPosition.BOTTOM_CENTER,\n    'bottom-left':notificationsPosition===NotificationPosition.BOTTOM_LEFT,\n  }\"\n  class=\"noti-panel\"\n  role=\"region\"\n  aria-label=\"Notifications\">\n\n  <!-- Only worth offering once the stack is deep enough to be a nuisance. Its visual position\n       is set by flex `order` (see the stylesheet), which keeps it clear of the host app's\n       chrome at whichever edge the panel is anchored to. -->\n  <button *ngIf=\"notifications.length >= clearAllThreshold\"\n          type=\"button\"\n          class=\"noti-clear-all\"\n          (click)=\"onDismissAll()\">Clear all ({{ notifications.length }})</button>\n\n  <div [@slideInOut]=\"{value:'', params: slideParams}\"\n       class=\"noti-card\"\n       [style.z-index]=\"stackZ(index)\"\n       [ngClass]=\"{'warn':notification.type===NotificationType.WARNING,\n       'error':notification.type===NotificationType.ERROR,\n       'success':notification.type===NotificationType.SUCCESS,\n       'info':notification.type===NotificationType.INFO}\"\n       [attr.role]=\"roleFor(notification)\"\n       aria-atomic=\"true\"\n       (mouseenter)=\"onPointerEnter(notification)\"\n       (mouseleave)=\"onPointerLeave(notification)\"\n       (focusin)=\"onPointerEnter(notification)\"\n       (focusout)=\"onPointerLeave(notification)\"\n       *ngFor=\"let notification of orderedNotifications; let index=index; trackBy: trackById\">\n    <div class=\"noti-body\">\n      <div class=\"noti-icon\">\n        <img alt=\"\" aria-hidden=\"true\" *ngIf=\"notification.iconSrc\" [src]=\"notification.iconSrc\"/>\n        <ng-container *ngIf=\"!notification.iconSrc\">\n          <ng-container *ngIf=\"notification.templateRef;else defaultIcon\">\n            <ng-container *ngTemplateOutlet=\"notification.templateRef\"></ng-container>\n          </ng-container>\n          <ng-template #defaultIcon>\n            <mat-icon aria-hidden=\"true\" *ngIf=\"notification.type===NotificationType.ERROR\" svgIcon=\"ngx-noti:ngx-noti-error_24dp\"></mat-icon>\n            <mat-icon aria-hidden=\"true\" *ngIf=\"notification.type===NotificationType.WARNING\" svgIcon=\"ngx-noti:ngx-noti-warning_24dp\"></mat-icon>\n            <mat-icon aria-hidden=\"true\" *ngIf=\"notification.type===NotificationType.SUCCESS\" svgIcon=\"ngx-noti:ngx-noti-celebration_24dp\"></mat-icon>\n            <mat-icon aria-hidden=\"true\" *ngIf=\"notification.type===NotificationType.INFO\" svgIcon=\"ngx-noti:ngx-noti-lightbulb_24dp\"></mat-icon>\n          </ng-template>\n        </ng-container>\n      </div>\n      <div class=\"noti-text\">\n        <p class=\"noti-title\">{{notification.title}}</p>\n        <p class=\"noti-desc\" *ngIf=\"notification.description\">{{notification.description}}</p>\n      </div>\n      <!-- A real button, not a div: it has to be reachable and operable from the keyboard, and\n           needs a name a screen reader can read out. -->\n      <button type=\"button\"\n              class=\"noti-close\"\n              [attr.aria-label]=\"'Dismiss notification: ' + notification.title\"\n              (click)=\"onDismiss(notification.id)\">\n        <mat-icon aria-hidden=\"true\" svgIcon=\"ngx-noti:ngx-noti-close_24dp\"></mat-icon>\n      </button>\n    </div>\n    <!-- The countdown is a CSS animation, not a per-notification interval writing a width ten\n         times a second. Pausing is animation-play-state; the service banks the remaining time\n         so the timer and the bar resume together. -->\n    <div class=\"noti-progress\" *ngIf=\"notification.visibilityTimeMs\"\n         [style.animation-duration.ms]=\"progressDurationMs(notification)\"\n         [style.animation-play-state]=\"notification.paused ? 'paused' : 'running'\"></div>\n  </div>\n</div>\n","/*\n * Public API Surface of ngx-noti\n */\n\nexport * from './lib/services/ngx-noti/ngx-noti.service';\nexport * from './lib/components/notifications-panel/notifications-panel.component';\nexport * from './lib/models/notification.interface';\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './public-api';\n"],"names":["i1.NgxNotiService"],"mappings":"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"}