sapenlinea-components 0.12.98 → 0.13.99
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import * as i0 from '@angular/core';
|
|
2
|
-
import { model, input, signal, computed, Component, Injectable, inject, ElementRef, NgZone, output, HostListener, ViewChild, ViewChildren, forwardRef, effect, booleanAttribute, DestroyRef, EventEmitter, Output, Input as Input$1, untracked, viewChildren, ChangeDetectionStrategy, ChangeDetectorRef } from '@angular/core';
|
|
2
|
+
import { model, input, signal, computed, Component, Injectable, inject, ElementRef, NgZone, output, HostListener, ViewChild, ViewChildren, forwardRef, effect, booleanAttribute, DestroyRef, EventEmitter, Output, Input as Input$1, untracked, viewChildren, ChangeDetectionStrategy, ChangeDetectorRef, viewChild } from '@angular/core';
|
|
3
3
|
import * as i1$2 from '@angular/common';
|
|
4
4
|
import { CommonModule, DOCUMENT, NgStyle, UpperCasePipe, NgClass, DatePipe } from '@angular/common';
|
|
5
5
|
import * as i1 from 'lucide-angular';
|
|
@@ -8556,6 +8556,237 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImpo
|
|
|
8556
8556
|
}]
|
|
8557
8557
|
}] });
|
|
8558
8558
|
|
|
8559
|
+
class BellWithBadge {
|
|
8560
|
+
count = input(0, ...(ngDevMode ? [{ debugName: "count" }] : []));
|
|
8561
|
+
active = input(false, ...(ngDevMode ? [{ debugName: "active", transform: booleanAttribute }] : [{ transform: booleanAttribute }]));
|
|
8562
|
+
ariaLabel = input('Notificaciones', ...(ngDevMode ? [{ debugName: "ariaLabel" }] : []));
|
|
8563
|
+
bellClick = output();
|
|
8564
|
+
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: BellWithBadge, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
8565
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.16", type: BellWithBadge, isStandalone: true, selector: "lib-bell-with-badge", inputs: { count: { classPropertyName: "count", publicName: "count", isSignal: true, isRequired: false, transformFunction: null }, active: { classPropertyName: "active", publicName: "active", isSignal: true, isRequired: false, transformFunction: null }, ariaLabel: { classPropertyName: "ariaLabel", publicName: "ariaLabel", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { bellClick: "bellClick" }, ngImport: i0, template: "<button\n class=\"lib-bell__btn\"\n [class.lib-bell__btn--active]=\"active()\"\n type=\"button\"\n [attr.aria-label]=\"ariaLabel()\"\n (click)=\"bellClick.emit()\"\n>\n <svg class=\"lib-bell__icon\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\">\n <path d=\"M6 8a6 6 0 0 1 12 0c0 7 3 9 3 9H3s3-2 3-9\"/>\n <path d=\"M10.3 21a1.94 1.94 0 0 0 3.4 0\"/>\n </svg>\n @if (count() > 0) {\n <span class=\"lib-bell__badge\">{{ count() > 99 ? '99+' : count() }}</span>\n }\n</button>\n", styles: [":host{--lib-bell-icon: #1c1c12;--lib-bell-badge-bg: #bfd100;--lib-bell-badge-text: #1c1c12}.lib-bell__btn{position:relative;background:none;border:none;cursor:pointer;padding:10px;width:44px;height:44px;border-radius:50%;color:var(--lib-bell-icon);transition:background-color .2s ease;display:inline-flex;align-items:center;justify-content:center}.lib-bell__btn:hover{background-color:#00000014}.lib-bell__btn--active{background-color:#0000001f}.lib-bell__icon{width:24px;height:24px}.lib-bell__badge{position:absolute;top:3px;right:3px;min-width:18px;height:18px;padding:0 4px;box-sizing:border-box;border-radius:9px;background-color:var(--lib-bell-badge-bg);color:var(--lib-bell-badge-text);font-family:Inter,sans-serif;font-size:12px;font-weight:600;line-height:1;display:inline-flex;align-items:center;justify-content:center}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }] });
|
|
8566
|
+
}
|
|
8567
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: BellWithBadge, decorators: [{
|
|
8568
|
+
type: Component,
|
|
8569
|
+
args: [{ selector: 'lib-bell-with-badge', standalone: true, imports: [CommonModule], template: "<button\n class=\"lib-bell__btn\"\n [class.lib-bell__btn--active]=\"active()\"\n type=\"button\"\n [attr.aria-label]=\"ariaLabel()\"\n (click)=\"bellClick.emit()\"\n>\n <svg class=\"lib-bell__icon\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\">\n <path d=\"M6 8a6 6 0 0 1 12 0c0 7 3 9 3 9H3s3-2 3-9\"/>\n <path d=\"M10.3 21a1.94 1.94 0 0 0 3.4 0\"/>\n </svg>\n @if (count() > 0) {\n <span class=\"lib-bell__badge\">{{ count() > 99 ? '99+' : count() }}</span>\n }\n</button>\n", styles: [":host{--lib-bell-icon: #1c1c12;--lib-bell-badge-bg: #bfd100;--lib-bell-badge-text: #1c1c12}.lib-bell__btn{position:relative;background:none;border:none;cursor:pointer;padding:10px;width:44px;height:44px;border-radius:50%;color:var(--lib-bell-icon);transition:background-color .2s ease;display:inline-flex;align-items:center;justify-content:center}.lib-bell__btn:hover{background-color:#00000014}.lib-bell__btn--active{background-color:#0000001f}.lib-bell__icon{width:24px;height:24px}.lib-bell__badge{position:absolute;top:3px;right:3px;min-width:18px;height:18px;padding:0 4px;box-sizing:border-box;border-radius:9px;background-color:var(--lib-bell-badge-bg);color:var(--lib-bell-badge-text);font-family:Inter,sans-serif;font-size:12px;font-weight:600;line-height:1;display:inline-flex;align-items:center;justify-content:center}\n"] }]
|
|
8570
|
+
}], propDecorators: { count: [{ type: i0.Input, args: [{ isSignal: true, alias: "count", required: false }] }], active: [{ type: i0.Input, args: [{ isSignal: true, alias: "active", required: false }] }], ariaLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "ariaLabel", required: false }] }], bellClick: [{ type: i0.Output, args: ["bellClick"] }] } });
|
|
8571
|
+
|
|
8572
|
+
class NotificationCenter {
|
|
8573
|
+
notifications = input([], ...(ngDevMode ? [{ debugName: "notifications" }] : []));
|
|
8574
|
+
isOpen = input(false, ...(ngDevMode ? [{ debugName: "isOpen" }] : []));
|
|
8575
|
+
/** Indica si hay una página de notificaciones cargándose en este momento. */
|
|
8576
|
+
loading = input(false, ...(ngDevMode ? [{ debugName: "loading" }] : []));
|
|
8577
|
+
/** Indica si quedan más notificaciones por cargar desde el origen. */
|
|
8578
|
+
hasMore = input(false, ...(ngDevMode ? [{ debugName: "hasMore" }] : []));
|
|
8579
|
+
markAllRead = output();
|
|
8580
|
+
notificationClick = output();
|
|
8581
|
+
close = output();
|
|
8582
|
+
/** Se emite cuando el usuario se acerca al final de la lista y debe cargarse la siguiente página. */
|
|
8583
|
+
loadMore = output();
|
|
8584
|
+
scrollContainer = viewChild('scrollContainer', ...(ngDevMode ? [{ debugName: "scrollContainer" }] : []));
|
|
8585
|
+
sentinel = viewChild('sentinel', ...(ngDevMode ? [{ debugName: "sentinel" }] : []));
|
|
8586
|
+
selectedCategory = signal('Todas', ...(ngDevMode ? [{ debugName: "selectedCategory" }] : []));
|
|
8587
|
+
categories = computed(() => {
|
|
8588
|
+
const cats = new Set(this.notifications().map((n) => n.category));
|
|
8589
|
+
return ['Todas', ...Array.from(cats)];
|
|
8590
|
+
}, ...(ngDevMode ? [{ debugName: "categories" }] : []));
|
|
8591
|
+
filteredNotifications = computed(() => {
|
|
8592
|
+
const cat = this.selectedCategory();
|
|
8593
|
+
if (cat === 'Todas')
|
|
8594
|
+
return this.notifications();
|
|
8595
|
+
return this.notifications().filter((n) => n.category === cat);
|
|
8596
|
+
}, ...(ngDevMode ? [{ debugName: "filteredNotifications" }] : []));
|
|
8597
|
+
unreadCount = computed(() => this.notifications().filter((n) => !n.isRead).length, ...(ngDevMode ? [{ debugName: "unreadCount" }] : []));
|
|
8598
|
+
lightColors = {
|
|
8599
|
+
acuerdos: '#9DAFD8',
|
|
8600
|
+
financiero: '#9ED89D',
|
|
8601
|
+
infracciones: '#D89D9D',
|
|
8602
|
+
sistema: '#BAC2BB',
|
|
8603
|
+
default: '#C7C7AD',
|
|
8604
|
+
};
|
|
8605
|
+
darkColors = {
|
|
8606
|
+
acuerdos: '#0746CF',
|
|
8607
|
+
financiero: '#006D2F',
|
|
8608
|
+
infracciones: '#CF0707',
|
|
8609
|
+
sistema: '#40484C',
|
|
8610
|
+
default: '#454733',
|
|
8611
|
+
};
|
|
8612
|
+
constructor() {
|
|
8613
|
+
// Carga progresiva: observamos un sentinel al final de la lista y pedimos
|
|
8614
|
+
// la siguiente página cuando entra en pantalla, evitando cargar todo de golpe.
|
|
8615
|
+
effect((onCleanup) => {
|
|
8616
|
+
const sentinel = this.sentinel();
|
|
8617
|
+
const root = this.scrollContainer();
|
|
8618
|
+
if (!sentinel || !root || typeof IntersectionObserver === 'undefined')
|
|
8619
|
+
return;
|
|
8620
|
+
const observer = new IntersectionObserver((entries) => {
|
|
8621
|
+
if (entries[0].isIntersecting &&
|
|
8622
|
+
this.isOpen() &&
|
|
8623
|
+
this.hasMore() &&
|
|
8624
|
+
!this.loading()) {
|
|
8625
|
+
this.loadMore.emit();
|
|
8626
|
+
}
|
|
8627
|
+
}, { root: root.nativeElement, rootMargin: '120px', threshold: 0 });
|
|
8628
|
+
observer.observe(sentinel.nativeElement);
|
|
8629
|
+
onCleanup(() => observer.disconnect());
|
|
8630
|
+
});
|
|
8631
|
+
}
|
|
8632
|
+
selectCategory(cat) {
|
|
8633
|
+
this.selectedCategory.set(cat);
|
|
8634
|
+
}
|
|
8635
|
+
onMarkAllRead() {
|
|
8636
|
+
if (this.unreadCount() === 0)
|
|
8637
|
+
return;
|
|
8638
|
+
this.markAllRead.emit();
|
|
8639
|
+
}
|
|
8640
|
+
onNotificationClick(n) {
|
|
8641
|
+
this.notificationClick.emit(n);
|
|
8642
|
+
}
|
|
8643
|
+
/** Etiqueta legible para una pestaña de categoría (ej. "ACUERDOS DE PAGO" -> "Acuerdos de pago"). */
|
|
8644
|
+
tabLabel(category) {
|
|
8645
|
+
if (category === 'Todas')
|
|
8646
|
+
return category;
|
|
8647
|
+
return category.charAt(0).toUpperCase() + category.slice(1).toLowerCase();
|
|
8648
|
+
}
|
|
8649
|
+
/** Normaliza una categoría a una de las claves conocidas para color e icono. */
|
|
8650
|
+
categoryKey(category) {
|
|
8651
|
+
const c = (category || '').toUpperCase();
|
|
8652
|
+
if (c.includes('ACUERDO'))
|
|
8653
|
+
return 'acuerdos';
|
|
8654
|
+
if (c.includes('FINAN'))
|
|
8655
|
+
return 'financiero';
|
|
8656
|
+
if (c.includes('INFRAC'))
|
|
8657
|
+
return 'infracciones';
|
|
8658
|
+
if (c.includes('SISTEMA'))
|
|
8659
|
+
return 'sistema';
|
|
8660
|
+
return 'default';
|
|
8661
|
+
}
|
|
8662
|
+
getCategoryLight(category) {
|
|
8663
|
+
return this.lightColors[this.categoryKey(category)];
|
|
8664
|
+
}
|
|
8665
|
+
getCategoryDark(category) {
|
|
8666
|
+
return this.darkColors[this.categoryKey(category)];
|
|
8667
|
+
}
|
|
8668
|
+
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: NotificationCenter, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
8669
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.16", type: NotificationCenter, isStandalone: true, selector: "lib-notification-center", inputs: { notifications: { classPropertyName: "notifications", publicName: "notifications", isSignal: true, isRequired: false, transformFunction: null }, isOpen: { classPropertyName: "isOpen", publicName: "isOpen", isSignal: true, isRequired: false, transformFunction: null }, loading: { classPropertyName: "loading", publicName: "loading", isSignal: true, isRequired: false, transformFunction: null }, hasMore: { classPropertyName: "hasMore", publicName: "hasMore", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { markAllRead: "markAllRead", notificationClick: "notificationClick", close: "close", loadMore: "loadMore" }, viewQueries: [{ propertyName: "scrollContainer", first: true, predicate: ["scrollContainer"], descendants: true, isSignal: true }, { propertyName: "sentinel", first: true, predicate: ["sentinel"], descendants: true, isSignal: true }], ngImport: i0, template: "@if (isOpen()) {\n<div class=\"lib-nc__overlay\" (click)=\"close.emit()\"></div>\n}\n\n<div class=\"lib-nc__panel\" [class.lib-nc__panel--open]=\"isOpen()\">\n <div class=\"lib-nc__header\">\n <div class=\"lib-nc__title-group\">\n <span class=\"lib-nc__title\">Notificaciones</span>\n <span class=\"lib-nc__counter\">({{ unreadCount() }} nuevas)</span>\n </div>\n <button\n class=\"lib-nc__mark-all\"\n type=\"button\"\n [disabled]=\"unreadCount() === 0\"\n (click)=\"onMarkAllRead()\"\n >\n Marcar todas como le\u00EDdas\n </button>\n </div>\n\n @if (notifications().length > 0) {\n <div class=\"lib-nc__tabs\">\n @for (cat of categories(); track cat) {\n <button\n class=\"lib-nc__tab\"\n [class.lib-nc__tab--active]=\"selectedCategory() === cat\"\n type=\"button\"\n (click)=\"selectCategory(cat)\"\n >\n {{ tabLabel(cat) }}\n </button>\n }\n </div>\n\n <div class=\"lib-nc__list\" #scrollContainer>\n @for (notification of filteredNotifications(); track notification.id) {\n <div class=\"lib-nc__item\" (click)=\"onNotificationClick(notification)\">\n <div\n class=\"lib-nc__item-icon\"\n [style.background-color]=\"getCategoryLight(notification.category)\"\n [style.color]=\"getCategoryDark(notification.category)\"\n >\n <svg class=\"lib-nc__item-icon-svg\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\">\n @switch (categoryKey(notification.category)) {\n @case ('acuerdos') {\n <path d=\"m11 17 2 2a1 1 0 1 0 3-3\"/>\n <path d=\"m14 14 2.5 2.5a1 1 0 1 0 3-3l-3.88-3.88a3 3 0 0 0-4.24 0l-.88.88a1 1 0 1 1-3-3l2.81-2.81a5.79 5.79 0 0 1 7.06-.87l.47.28a2 2 0 0 0 1.42.25L21 4\"/>\n <path d=\"m21 3 1 11h-2\"/>\n <path d=\"M3 3 2 14l6.5 6.5a1 1 0 1 0 3-3\"/>\n <path d=\"M3 4h8\"/>\n }\n @case ('financiero') {\n <line x1=\"12\" x2=\"12\" y1=\"2\" y2=\"22\"/>\n <path d=\"M17 5H9.5a3.5 3.5 0 0 0 0 7h5a3.5 3.5 0 0 1 0 7H6\"/>\n }\n @case ('infracciones') {\n <path d=\"m21.73 18-8-14a2 2 0 0 0-3.48 0l-8 14A2 2 0 0 0 4 21h16a2 2 0 0 0 1.73-3\"/>\n <path d=\"M12 9v4\"/>\n <path d=\"M12 17h.01\"/>\n }\n @case ('sistema') {\n <rect width=\"20\" height=\"8\" x=\"2\" y=\"2\" rx=\"2\" ry=\"2\"/>\n <rect width=\"20\" height=\"8\" x=\"2\" y=\"14\" rx=\"2\" ry=\"2\"/>\n <line x1=\"6\" x2=\"6.01\" y1=\"6\" y2=\"6\"/>\n <line x1=\"6\" x2=\"6.01\" y1=\"18\" y2=\"18\"/>\n }\n @default {\n <path d=\"M6 8a6 6 0 0 1 12 0c0 7 3 9 3 9H3s3-2 3-9\"/>\n <path d=\"M10.3 21a1.94 1.94 0 0 0 3.4 0\"/>\n }\n }\n </svg>\n </div>\n\n <div class=\"lib-nc__item-content\">\n <div class=\"lib-nc__item-top\">\n <span class=\"lib-nc__item-title\">{{ notification.title }}</span>\n <span class=\"lib-nc__item-time\">{{ notification.timeAgo }}</span>\n </div>\n <p class=\"lib-nc__item-message\">{{ notification.description }}</p>\n <span\n class=\"lib-nc__item-chip\"\n [style.background-color]=\"getCategoryLight(notification.category)\"\n [style.color]=\"getCategoryDark(notification.category)\"\n >\n {{ notification.category }}\n </span>\n </div>\n\n @if (!notification.isRead) {\n <span class=\"lib-nc__item-dot\"></span>\n }\n </div>\n }\n\n @if (loading()) {\n <div class=\"lib-nc__loading\">\n <span class=\"lib-nc__spinner\" aria-label=\"Cargando notificaciones\"></span>\n </div>\n }\n\n <div class=\"lib-nc__sentinel\" #sentinel aria-hidden=\"true\"></div>\n </div>\n } @else {\n <div class=\"lib-nc__empty\">\n <svg class=\"lib-nc__empty-icon\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\">\n <path d=\"M8.7 3A6 6 0 0 1 18 8a21.3 21.3 0 0 0 .6 5\"/>\n <path d=\"M17 17H3s3-2 3-9a4.67 4.67 0 0 1 .3-1.7\"/>\n <path d=\"M10.3 21a1.94 1.94 0 0 0 3.4 0\"/>\n <path d=\"m2 2 20 20\"/>\n </svg>\n <p class=\"lib-nc__empty-title\">Est\u00E1s al d\u00EDa</p>\n <p class=\"lib-nc__empty-message\">No tienes notificaciones por ahora.</p>\n </div>\n }\n</div>\n", styles: [":host{--lib-nc-width: 420px;--lib-nc-max-height: 560px;--lib-nc-bg: #f0f0db;--lib-nc-border: #d8d8c8;--lib-nc-text-strong: #1c1c12;--lib-nc-text: #454733;--lib-nc-text-muted: #7a7f52;--lib-nc-accent: #bfd100;--lib-nc-link: #596300}.lib-nc__overlay{position:fixed;inset:0;z-index:1090}.lib-nc__panel{position:absolute;top:calc(100% + 10px);right:0;width:var(--lib-nc-width);max-height:var(--lib-nc-max-height);max-width:calc(100vw - 24px);background:var(--lib-nc-bg);border:1px solid var(--lib-nc-border);border-radius:12px;box-shadow:5px 6px 5px -3px #0000005c;display:flex;flex-direction:column;z-index:1100;overflow:hidden;opacity:0;visibility:hidden;transform:translateY(-8px);transition:opacity .2s ease,transform .2s ease,visibility .2s ease;pointer-events:none;font-family:Inter,sans-serif}.lib-nc__panel--open{opacity:1;visibility:visible;transform:translateY(0);pointer-events:auto}.lib-nc__header{display:flex;align-items:center;justify-content:space-between;gap:12px;padding:16px 20px;border-bottom:1px solid var(--lib-nc-border);flex-shrink:0}.lib-nc__title-group{display:flex;align-items:center;gap:6px}.lib-nc__title{font-size:16px;font-weight:600;color:var(--lib-nc-text-strong);line-height:1.4}.lib-nc__counter{font-size:12px;color:var(--lib-nc-text);line-height:1.4}.lib-nc__mark-all{background:none;border:none;padding:0;color:var(--lib-nc-link);font-size:14px;font-weight:600;cursor:pointer;white-space:nowrap;line-height:1.4}.lib-nc__mark-all:hover:not(:disabled){text-decoration:underline}.lib-nc__mark-all:disabled{color:var(--lib-nc-text-muted);cursor:default}.lib-nc__tabs{display:flex;align-items:flex-end;gap:4px;padding:0 16px;border-bottom:1px solid var(--lib-nc-border);overflow-x:auto;flex-shrink:0;scrollbar-width:none}.lib-nc__tabs::-webkit-scrollbar{display:none}.lib-nc__tab{background:none;border:none;border-bottom:2px solid transparent;padding:10px 8px;font-size:12px;font-weight:500;letter-spacing:.2px;line-height:1.4;color:var(--lib-nc-text-muted);cursor:pointer;white-space:nowrap;transition:color .15s ease,border-color .15s ease}.lib-nc__tab:hover{color:var(--lib-nc-text-strong)}.lib-nc__tab--active{color:var(--lib-nc-text-strong);font-weight:600;border-bottom-color:var(--lib-nc-accent)}.lib-nc__list{flex:1;overflow-y:auto;overscroll-behavior:contain;scrollbar-width:thin;scrollbar-color:#c4c4a8 transparent}.lib-nc__list::-webkit-scrollbar{width:10px}.lib-nc__list::-webkit-scrollbar-track{background:transparent}.lib-nc__list::-webkit-scrollbar-thumb{background-color:#c4c4a8;border-radius:999px;border:3px solid transparent;background-clip:padding-box}.lib-nc__list::-webkit-scrollbar-thumb:hover{background-color:#aeae90}.lib-nc__loading{display:flex;align-items:center;justify-content:center;padding:16px}.lib-nc__spinner{width:22px;height:22px;border-radius:50%;border:2.5px solid #d8d8c8;border-top-color:var(--lib-nc-accent);animation:lib-nc-spin .7s linear infinite}@keyframes lib-nc-spin{to{transform:rotate(360deg)}}.lib-nc__sentinel{width:100%;height:1px}.lib-nc__item{display:flex;align-items:center;gap:12px;padding:12px 20px;border-bottom:1px solid var(--lib-nc-border);cursor:pointer;transition:background-color .15s ease}.lib-nc__item:hover{background-color:#00000008}.lib-nc__item-icon{width:36px;height:36px;border-radius:50%;display:inline-flex;align-items:center;justify-content:center;flex-shrink:0}.lib-nc__item-icon-svg{width:18px;height:18px}.lib-nc__item-content{flex:1;min-width:0;display:flex;flex-direction:column;gap:4px}.lib-nc__item-top{display:flex;align-items:flex-start;justify-content:space-between;gap:8px}.lib-nc__item-title{font-size:14px;font-weight:600;color:var(--lib-nc-text-strong);line-height:1.4}.lib-nc__item-time{font-size:12px;color:var(--lib-nc-text);line-height:1.4;white-space:nowrap;flex-shrink:0}.lib-nc__item-message{margin:0;font-size:14px;color:var(--lib-nc-text);line-height:1.4}.lib-nc__item-chip{align-self:flex-start;display:inline-flex;align-items:center;border-radius:12px;padding:4px 10px;font-size:11px;font-weight:600;letter-spacing:.4px;line-height:1.2;margin-top:2px}.lib-nc__item-dot{width:8px;height:8px;border-radius:50%;background-color:var(--lib-nc-accent);flex-shrink:0}.lib-nc__empty{flex:1;display:flex;flex-direction:column;align-items:center;justify-content:center;gap:8px;padding:24px;text-align:center}.lib-nc__empty-icon{width:64px;height:64px;color:#c7c7ad;margin-bottom:4px}.lib-nc__empty-title{margin:0;font-size:16px;font-weight:600;color:var(--lib-nc-text);line-height:1.4}.lib-nc__empty-message{margin:0;font-size:14px;color:var(--lib-nc-text-muted);line-height:1.4}@media (max-width: 480px){.lib-nc__panel{width:calc(100vw - 16px);right:-8px;max-height:calc(100vh - 90px)}}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }] });
|
|
8670
|
+
}
|
|
8671
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: NotificationCenter, decorators: [{
|
|
8672
|
+
type: Component,
|
|
8673
|
+
args: [{ selector: 'lib-notification-center', standalone: true, imports: [CommonModule], template: "@if (isOpen()) {\n<div class=\"lib-nc__overlay\" (click)=\"close.emit()\"></div>\n}\n\n<div class=\"lib-nc__panel\" [class.lib-nc__panel--open]=\"isOpen()\">\n <div class=\"lib-nc__header\">\n <div class=\"lib-nc__title-group\">\n <span class=\"lib-nc__title\">Notificaciones</span>\n <span class=\"lib-nc__counter\">({{ unreadCount() }} nuevas)</span>\n </div>\n <button\n class=\"lib-nc__mark-all\"\n type=\"button\"\n [disabled]=\"unreadCount() === 0\"\n (click)=\"onMarkAllRead()\"\n >\n Marcar todas como le\u00EDdas\n </button>\n </div>\n\n @if (notifications().length > 0) {\n <div class=\"lib-nc__tabs\">\n @for (cat of categories(); track cat) {\n <button\n class=\"lib-nc__tab\"\n [class.lib-nc__tab--active]=\"selectedCategory() === cat\"\n type=\"button\"\n (click)=\"selectCategory(cat)\"\n >\n {{ tabLabel(cat) }}\n </button>\n }\n </div>\n\n <div class=\"lib-nc__list\" #scrollContainer>\n @for (notification of filteredNotifications(); track notification.id) {\n <div class=\"lib-nc__item\" (click)=\"onNotificationClick(notification)\">\n <div\n class=\"lib-nc__item-icon\"\n [style.background-color]=\"getCategoryLight(notification.category)\"\n [style.color]=\"getCategoryDark(notification.category)\"\n >\n <svg class=\"lib-nc__item-icon-svg\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\">\n @switch (categoryKey(notification.category)) {\n @case ('acuerdos') {\n <path d=\"m11 17 2 2a1 1 0 1 0 3-3\"/>\n <path d=\"m14 14 2.5 2.5a1 1 0 1 0 3-3l-3.88-3.88a3 3 0 0 0-4.24 0l-.88.88a1 1 0 1 1-3-3l2.81-2.81a5.79 5.79 0 0 1 7.06-.87l.47.28a2 2 0 0 0 1.42.25L21 4\"/>\n <path d=\"m21 3 1 11h-2\"/>\n <path d=\"M3 3 2 14l6.5 6.5a1 1 0 1 0 3-3\"/>\n <path d=\"M3 4h8\"/>\n }\n @case ('financiero') {\n <line x1=\"12\" x2=\"12\" y1=\"2\" y2=\"22\"/>\n <path d=\"M17 5H9.5a3.5 3.5 0 0 0 0 7h5a3.5 3.5 0 0 1 0 7H6\"/>\n }\n @case ('infracciones') {\n <path d=\"m21.73 18-8-14a2 2 0 0 0-3.48 0l-8 14A2 2 0 0 0 4 21h16a2 2 0 0 0 1.73-3\"/>\n <path d=\"M12 9v4\"/>\n <path d=\"M12 17h.01\"/>\n }\n @case ('sistema') {\n <rect width=\"20\" height=\"8\" x=\"2\" y=\"2\" rx=\"2\" ry=\"2\"/>\n <rect width=\"20\" height=\"8\" x=\"2\" y=\"14\" rx=\"2\" ry=\"2\"/>\n <line x1=\"6\" x2=\"6.01\" y1=\"6\" y2=\"6\"/>\n <line x1=\"6\" x2=\"6.01\" y1=\"18\" y2=\"18\"/>\n }\n @default {\n <path d=\"M6 8a6 6 0 0 1 12 0c0 7 3 9 3 9H3s3-2 3-9\"/>\n <path d=\"M10.3 21a1.94 1.94 0 0 0 3.4 0\"/>\n }\n }\n </svg>\n </div>\n\n <div class=\"lib-nc__item-content\">\n <div class=\"lib-nc__item-top\">\n <span class=\"lib-nc__item-title\">{{ notification.title }}</span>\n <span class=\"lib-nc__item-time\">{{ notification.timeAgo }}</span>\n </div>\n <p class=\"lib-nc__item-message\">{{ notification.description }}</p>\n <span\n class=\"lib-nc__item-chip\"\n [style.background-color]=\"getCategoryLight(notification.category)\"\n [style.color]=\"getCategoryDark(notification.category)\"\n >\n {{ notification.category }}\n </span>\n </div>\n\n @if (!notification.isRead) {\n <span class=\"lib-nc__item-dot\"></span>\n }\n </div>\n }\n\n @if (loading()) {\n <div class=\"lib-nc__loading\">\n <span class=\"lib-nc__spinner\" aria-label=\"Cargando notificaciones\"></span>\n </div>\n }\n\n <div class=\"lib-nc__sentinel\" #sentinel aria-hidden=\"true\"></div>\n </div>\n } @else {\n <div class=\"lib-nc__empty\">\n <svg class=\"lib-nc__empty-icon\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\">\n <path d=\"M8.7 3A6 6 0 0 1 18 8a21.3 21.3 0 0 0 .6 5\"/>\n <path d=\"M17 17H3s3-2 3-9a4.67 4.67 0 0 1 .3-1.7\"/>\n <path d=\"M10.3 21a1.94 1.94 0 0 0 3.4 0\"/>\n <path d=\"m2 2 20 20\"/>\n </svg>\n <p class=\"lib-nc__empty-title\">Est\u00E1s al d\u00EDa</p>\n <p class=\"lib-nc__empty-message\">No tienes notificaciones por ahora.</p>\n </div>\n }\n</div>\n", styles: [":host{--lib-nc-width: 420px;--lib-nc-max-height: 560px;--lib-nc-bg: #f0f0db;--lib-nc-border: #d8d8c8;--lib-nc-text-strong: #1c1c12;--lib-nc-text: #454733;--lib-nc-text-muted: #7a7f52;--lib-nc-accent: #bfd100;--lib-nc-link: #596300}.lib-nc__overlay{position:fixed;inset:0;z-index:1090}.lib-nc__panel{position:absolute;top:calc(100% + 10px);right:0;width:var(--lib-nc-width);max-height:var(--lib-nc-max-height);max-width:calc(100vw - 24px);background:var(--lib-nc-bg);border:1px solid var(--lib-nc-border);border-radius:12px;box-shadow:5px 6px 5px -3px #0000005c;display:flex;flex-direction:column;z-index:1100;overflow:hidden;opacity:0;visibility:hidden;transform:translateY(-8px);transition:opacity .2s ease,transform .2s ease,visibility .2s ease;pointer-events:none;font-family:Inter,sans-serif}.lib-nc__panel--open{opacity:1;visibility:visible;transform:translateY(0);pointer-events:auto}.lib-nc__header{display:flex;align-items:center;justify-content:space-between;gap:12px;padding:16px 20px;border-bottom:1px solid var(--lib-nc-border);flex-shrink:0}.lib-nc__title-group{display:flex;align-items:center;gap:6px}.lib-nc__title{font-size:16px;font-weight:600;color:var(--lib-nc-text-strong);line-height:1.4}.lib-nc__counter{font-size:12px;color:var(--lib-nc-text);line-height:1.4}.lib-nc__mark-all{background:none;border:none;padding:0;color:var(--lib-nc-link);font-size:14px;font-weight:600;cursor:pointer;white-space:nowrap;line-height:1.4}.lib-nc__mark-all:hover:not(:disabled){text-decoration:underline}.lib-nc__mark-all:disabled{color:var(--lib-nc-text-muted);cursor:default}.lib-nc__tabs{display:flex;align-items:flex-end;gap:4px;padding:0 16px;border-bottom:1px solid var(--lib-nc-border);overflow-x:auto;flex-shrink:0;scrollbar-width:none}.lib-nc__tabs::-webkit-scrollbar{display:none}.lib-nc__tab{background:none;border:none;border-bottom:2px solid transparent;padding:10px 8px;font-size:12px;font-weight:500;letter-spacing:.2px;line-height:1.4;color:var(--lib-nc-text-muted);cursor:pointer;white-space:nowrap;transition:color .15s ease,border-color .15s ease}.lib-nc__tab:hover{color:var(--lib-nc-text-strong)}.lib-nc__tab--active{color:var(--lib-nc-text-strong);font-weight:600;border-bottom-color:var(--lib-nc-accent)}.lib-nc__list{flex:1;overflow-y:auto;overscroll-behavior:contain;scrollbar-width:thin;scrollbar-color:#c4c4a8 transparent}.lib-nc__list::-webkit-scrollbar{width:10px}.lib-nc__list::-webkit-scrollbar-track{background:transparent}.lib-nc__list::-webkit-scrollbar-thumb{background-color:#c4c4a8;border-radius:999px;border:3px solid transparent;background-clip:padding-box}.lib-nc__list::-webkit-scrollbar-thumb:hover{background-color:#aeae90}.lib-nc__loading{display:flex;align-items:center;justify-content:center;padding:16px}.lib-nc__spinner{width:22px;height:22px;border-radius:50%;border:2.5px solid #d8d8c8;border-top-color:var(--lib-nc-accent);animation:lib-nc-spin .7s linear infinite}@keyframes lib-nc-spin{to{transform:rotate(360deg)}}.lib-nc__sentinel{width:100%;height:1px}.lib-nc__item{display:flex;align-items:center;gap:12px;padding:12px 20px;border-bottom:1px solid var(--lib-nc-border);cursor:pointer;transition:background-color .15s ease}.lib-nc__item:hover{background-color:#00000008}.lib-nc__item-icon{width:36px;height:36px;border-radius:50%;display:inline-flex;align-items:center;justify-content:center;flex-shrink:0}.lib-nc__item-icon-svg{width:18px;height:18px}.lib-nc__item-content{flex:1;min-width:0;display:flex;flex-direction:column;gap:4px}.lib-nc__item-top{display:flex;align-items:flex-start;justify-content:space-between;gap:8px}.lib-nc__item-title{font-size:14px;font-weight:600;color:var(--lib-nc-text-strong);line-height:1.4}.lib-nc__item-time{font-size:12px;color:var(--lib-nc-text);line-height:1.4;white-space:nowrap;flex-shrink:0}.lib-nc__item-message{margin:0;font-size:14px;color:var(--lib-nc-text);line-height:1.4}.lib-nc__item-chip{align-self:flex-start;display:inline-flex;align-items:center;border-radius:12px;padding:4px 10px;font-size:11px;font-weight:600;letter-spacing:.4px;line-height:1.2;margin-top:2px}.lib-nc__item-dot{width:8px;height:8px;border-radius:50%;background-color:var(--lib-nc-accent);flex-shrink:0}.lib-nc__empty{flex:1;display:flex;flex-direction:column;align-items:center;justify-content:center;gap:8px;padding:24px;text-align:center}.lib-nc__empty-icon{width:64px;height:64px;color:#c7c7ad;margin-bottom:4px}.lib-nc__empty-title{margin:0;font-size:16px;font-weight:600;color:var(--lib-nc-text);line-height:1.4}.lib-nc__empty-message{margin:0;font-size:14px;color:var(--lib-nc-text-muted);line-height:1.4}@media (max-width: 480px){.lib-nc__panel{width:calc(100vw - 16px);right:-8px;max-height:calc(100vh - 90px)}}\n"] }]
|
|
8674
|
+
}], ctorParameters: () => [], propDecorators: { notifications: [{ type: i0.Input, args: [{ isSignal: true, alias: "notifications", required: false }] }], isOpen: [{ type: i0.Input, args: [{ isSignal: true, alias: "isOpen", required: false }] }], loading: [{ type: i0.Input, args: [{ isSignal: true, alias: "loading", required: false }] }], hasMore: [{ type: i0.Input, args: [{ isSignal: true, alias: "hasMore", required: false }] }], markAllRead: [{ type: i0.Output, args: ["markAllRead"] }], notificationClick: [{ type: i0.Output, args: ["notificationClick"] }], close: [{ type: i0.Output, args: ["close"] }], loadMore: [{ type: i0.Output, args: ["loadMore"] }], scrollContainer: [{ type: i0.ViewChild, args: ['scrollContainer', { isSignal: true }] }], sentinel: [{ type: i0.ViewChild, args: ['sentinel', { isSignal: true }] }] } });
|
|
8675
|
+
|
|
8676
|
+
class Header {
|
|
8677
|
+
/**
|
|
8678
|
+
* Todas las entradas son opcionales para que el header funcione igual
|
|
8679
|
+
* como custom element, microfrontend con module-federation o dentro del
|
|
8680
|
+
* monolito, sin que el consumidor esté obligado a enlazar cada propiedad.
|
|
8681
|
+
*/
|
|
8682
|
+
isExpanded = input(false, ...(ngDevMode ? [{ debugName: "isExpanded" }] : []));
|
|
8683
|
+
activeTitle = input('', ...(ngDevMode ? [{ debugName: "activeTitle" }] : []));
|
|
8684
|
+
mfId = input('', ...(ngDevMode ? [{ debugName: "mfId" }] : []));
|
|
8685
|
+
isMfFailed = input(false, ...(ngDevMode ? [{ debugName: "isMfFailed" }] : []));
|
|
8686
|
+
userRole = input('Administrador', ...(ngDevMode ? [{ debugName: "userRole" }] : []));
|
|
8687
|
+
/** Lista de notificaciones a mostrar en el centro de notificaciones. */
|
|
8688
|
+
notifications = input([], ...(ngDevMode ? [{ debugName: "notifications" }] : []));
|
|
8689
|
+
/** Indica si se está cargando una página de notificaciones. */
|
|
8690
|
+
notificationsLoading = input(false, ...(ngDevMode ? [{ debugName: "notificationsLoading" }] : []));
|
|
8691
|
+
/** Indica si quedan más notificaciones por cargar desde el origen. */
|
|
8692
|
+
notificationsHasMore = input(false, ...(ngDevMode ? [{ debugName: "notificationsHasMore" }] : []));
|
|
8693
|
+
navigateTo = output();
|
|
8694
|
+
menuClick = output();
|
|
8695
|
+
profileClick = output();
|
|
8696
|
+
logoutClick = output();
|
|
8697
|
+
actionClick = output();
|
|
8698
|
+
/** Eventos reenviados desde el centro de notificaciones. */
|
|
8699
|
+
markAllRead = output();
|
|
8700
|
+
notificationClick = output();
|
|
8701
|
+
/** Se emite cuando debe cargarse la siguiente página de notificaciones. */
|
|
8702
|
+
loadMoreNotifications = output();
|
|
8703
|
+
isDropdownOpen = signal(false, ...(ngDevMode ? [{ debugName: "isDropdownOpen" }] : []));
|
|
8704
|
+
isNotifOpen = signal(false, ...(ngDevMode ? [{ debugName: "isNotifOpen" }] : []));
|
|
8705
|
+
/** Cantidad de notificaciones no leídas, derivada de la lista. */
|
|
8706
|
+
unreadCount = computed(() => this.notifications().filter((n) => !n.isRead).length, ...(ngDevMode ? [{ debugName: "unreadCount" }] : []));
|
|
8707
|
+
onMenuClick() {
|
|
8708
|
+
this.menuClick.emit();
|
|
8709
|
+
}
|
|
8710
|
+
toggleDropdown() {
|
|
8711
|
+
this.isNotifOpen.set(false);
|
|
8712
|
+
this.isDropdownOpen.update((open) => !open);
|
|
8713
|
+
}
|
|
8714
|
+
toggleNotifications() {
|
|
8715
|
+
this.isDropdownOpen.set(false);
|
|
8716
|
+
this.isNotifOpen.update((open) => !open);
|
|
8717
|
+
}
|
|
8718
|
+
closeNotifications() {
|
|
8719
|
+
this.isNotifOpen.set(false);
|
|
8720
|
+
}
|
|
8721
|
+
userProfile() {
|
|
8722
|
+
this.isDropdownOpen.set(false);
|
|
8723
|
+
this.profileClick.emit();
|
|
8724
|
+
}
|
|
8725
|
+
logout() {
|
|
8726
|
+
this.isDropdownOpen.set(false);
|
|
8727
|
+
this.logoutClick.emit();
|
|
8728
|
+
}
|
|
8729
|
+
getMenuIcon() {
|
|
8730
|
+
return this.isExpanded() ? '✕' : '☰';
|
|
8731
|
+
}
|
|
8732
|
+
goToHome() {
|
|
8733
|
+
this.navigateTo.emit('/home');
|
|
8734
|
+
}
|
|
8735
|
+
onActionClick() {
|
|
8736
|
+
const id = this.mfId();
|
|
8737
|
+
const routeMap = {
|
|
8738
|
+
'infractions': '/child/infractions/register',
|
|
8739
|
+
'paymentAgreements': '/child/paymentAgreements/register',
|
|
8740
|
+
'trainingCourses-programar': '/child/trainingCourses/programacion',
|
|
8741
|
+
};
|
|
8742
|
+
const eventMap = {
|
|
8743
|
+
'paymentAgreementParameters': 'mf-action-register-parameter',
|
|
8744
|
+
'trainingCourses-administrar': 'mf-action-training-course-nuevo',
|
|
8745
|
+
'trainingCourses-catalogos-cia': 'mf-action-catalogo-cia-nuevo',
|
|
8746
|
+
'trainingCourses-catalogos-salones': 'mf-action-catalogo-salon-nuevo',
|
|
8747
|
+
'trainingCourses-catalogos-instructores': 'mf-action-catalogo-instructor-nuevo',
|
|
8748
|
+
};
|
|
8749
|
+
if (routeMap[id]) {
|
|
8750
|
+
this.navigateTo.emit(routeMap[id]);
|
|
8751
|
+
}
|
|
8752
|
+
else if (eventMap[id]) {
|
|
8753
|
+
window.dispatchEvent(new CustomEvent(eventMap[id]));
|
|
8754
|
+
}
|
|
8755
|
+
this.actionClick.emit(id);
|
|
8756
|
+
}
|
|
8757
|
+
getActionLabel() {
|
|
8758
|
+
const labels = {
|
|
8759
|
+
'infractions': 'Nueva Infracción',
|
|
8760
|
+
'paymentAgreements': 'Nuevo Acuerdo',
|
|
8761
|
+
'paymentAgreementParameters': 'Nuevo Parámetro',
|
|
8762
|
+
'trainingCourses-administrar': 'Nuevo Curso',
|
|
8763
|
+
'trainingCourses-programar': 'Programar Curso',
|
|
8764
|
+
'trainingCourses-catalogos-cia': 'Nueva CIA',
|
|
8765
|
+
'trainingCourses-catalogos-salones': 'Nuevo salón',
|
|
8766
|
+
'trainingCourses-catalogos-instructores': 'Nuevo instructor',
|
|
8767
|
+
};
|
|
8768
|
+
return labels[this.mfId()] || '';
|
|
8769
|
+
}
|
|
8770
|
+
hasAction() {
|
|
8771
|
+
return !!this.getActionLabel() && !this.isMfFailed();
|
|
8772
|
+
}
|
|
8773
|
+
onMarkAllRead() {
|
|
8774
|
+
this.markAllRead.emit();
|
|
8775
|
+
}
|
|
8776
|
+
onNotificationItemClick(notification) {
|
|
8777
|
+
this.notificationClick.emit(notification);
|
|
8778
|
+
}
|
|
8779
|
+
onLoadMoreNotifications() {
|
|
8780
|
+
this.loadMoreNotifications.emit();
|
|
8781
|
+
}
|
|
8782
|
+
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: Header, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
8783
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.16", type: Header, isStandalone: true, selector: "lib-header", inputs: { isExpanded: { classPropertyName: "isExpanded", publicName: "isExpanded", isSignal: true, isRequired: false, transformFunction: null }, activeTitle: { classPropertyName: "activeTitle", publicName: "activeTitle", isSignal: true, isRequired: false, transformFunction: null }, mfId: { classPropertyName: "mfId", publicName: "mfId", isSignal: true, isRequired: false, transformFunction: null }, isMfFailed: { classPropertyName: "isMfFailed", publicName: "isMfFailed", isSignal: true, isRequired: false, transformFunction: null }, userRole: { classPropertyName: "userRole", publicName: "userRole", isSignal: true, isRequired: false, transformFunction: null }, notifications: { classPropertyName: "notifications", publicName: "notifications", isSignal: true, isRequired: false, transformFunction: null }, notificationsLoading: { classPropertyName: "notificationsLoading", publicName: "notificationsLoading", isSignal: true, isRequired: false, transformFunction: null }, notificationsHasMore: { classPropertyName: "notificationsHasMore", publicName: "notificationsHasMore", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { navigateTo: "navigateTo", menuClick: "menuClick", profileClick: "profileClick", logoutClick: "logoutClick", actionClick: "actionClick", markAllRead: "markAllRead", notificationClick: "notificationClick", loadMoreNotifications: "loadMoreNotifications" }, ngImport: i0, template: "<header class=\"lib-header\">\n <div class=\"lib-header__left\" (click)=\"goToHome()\">\n <button class=\"lib-header__menu-btn\" type=\"button\" (click)=\"$event.stopPropagation(); onMenuClick()\">\n <span class=\"lib-header__menu-icon\">{{ getMenuIcon() }}</span>\n </button>\n <div class=\"lib-header__section-icons\">\n <div class=\"lib-header__icon lib-header__icon--first\"></div>\n <div class=\"lib-header__divider\"></div>\n <div class=\"lib-header__icon lib-header__icon--second\"></div>\n </div>\n </div>\n\n <div class=\"lib-header__title-container\">\n <div class=\"lib-header__title\">{{ activeTitle() }}</div>\n </div>\n\n <div class=\"lib-header__right\">\n @if (hasAction()) {\n <button class=\"lib-header__action-btn\" type=\"button\" (click)=\"onActionClick()\">\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"20\" height=\"20\" viewBox=\"0 0 24 24\" fill=\"currentColor\">\n <path stroke=\"none\" d=\"M0 0h24v24H0z\" fill=\"none\"/>\n <path d=\"M12 4a1 1 0 0 1 1 1v6h6a1 1 0 0 1 0 2h-6v6a1 1 0 0 1 -2 0v-6h-6a1 1 0 0 1 0 -2h6v-6a1 1 0 0 1 1 -1\"/>\n </svg>\n {{ getActionLabel() }}\n </button>\n }\n\n <div class=\"lib-header__notif-wrapper\">\n <lib-bell-with-badge\n [count]=\"unreadCount()\"\n [active]=\"isNotifOpen()\"\n (bellClick)=\"toggleNotifications()\"\n />\n\n <lib-notification-center\n [isOpen]=\"isNotifOpen()\"\n [notifications]=\"notifications()\"\n [loading]=\"notificationsLoading()\"\n [hasMore]=\"notificationsHasMore()\"\n (markAllRead)=\"onMarkAllRead()\"\n (notificationClick)=\"onNotificationItemClick($event)\"\n (loadMore)=\"onLoadMoreNotifications()\"\n (close)=\"closeNotifications()\"\n />\n </div>\n\n <div class=\"lib-header__user-info\" [class.lib-header__user-info--open]=\"isDropdownOpen()\" (click)=\"toggleDropdown()\">\n <div class=\"lib-header__user-avatar\">{{ userRole().charAt(0) }}</div>\n <svg class=\"lib-header__dropdown-arrow\" viewBox=\"0 0 16 16\" fill=\"currentColor\">\n <path d=\"M4 6l4 4 4-4H4z\"/>\n </svg>\n\n <div class=\"lib-header__dropdown-menu\" [class.lib-header__dropdown-menu--show]=\"isDropdownOpen()\" (click)=\"$event.stopPropagation()\">\n <div class=\"lib-header__dropdown-header\">\n <div class=\"lib-header__dropdown-avatar\">{{ userRole().charAt(0) }}</div>\n <div class=\"lib-header__dropdown-user-info\">\n <div class=\"lib-header__dropdown-user-name\">{{ userRole() }}</div>\n <div class=\"lib-header__dropdown-user-role\">Administrador</div>\n </div>\n </div>\n <div class=\"lib-header__dropdown-item\" (click)=\"userProfile()\">\n <svg class=\"lib-header__dropdown-item-icon\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\">\n <path d=\"M20 21v-2a4 4 0 0 0-4-4H8a4 4 0 0 0-4 4v2\"/>\n <circle cx=\"12\" cy=\"7\" r=\"4\"/>\n </svg>\n Perfil\n </div>\n <div class=\"lib-header__dropdown-item lib-header__dropdown-item--danger\" (click)=\"logout()\">\n <svg class=\"lib-header__dropdown-item-icon\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\">\n <path d=\"M9 21H5a2 2 0 0 1-2-2V5a2 2 0 0 1 2-2h4\"/>\n <polyline points=\"16,17 21,12 16,7\"/>\n <line x1=\"21\" y1=\"12\" x2=\"9\" y2=\"12\"/>\n </svg>\n Cerrar sesi\u00F3n\n </div>\n </div>\n </div>\n </div>\n</header>\n", styles: [":host{--lib-header-height: 75px;--lib-header-bg: #fafae8;--lib-header-text: #171c1f;--lib-header-accent: #bfd100;--lib-header-avatar-bg: #bfd100;--lib-header-user-chip-bg: #e3e3d1;--lib-header-divider: #d6d5d2}.lib-header{background-color:var(--lib-header-bg);height:var(--lib-header-height);display:flex;align-items:center;justify-content:space-between;padding:0 10px;position:fixed;top:0;left:0;right:0;z-index:200}.lib-header__left{display:flex;align-items:center;flex:1;justify-content:flex-start;cursor:pointer;gap:0}.lib-header__menu-btn{display:none;background:none;border:none;cursor:pointer;padding:8px;color:var(--lib-header-text);border-radius:4px;transition:background-color .2s ease}.lib-header__menu-btn:hover{background-color:#0000001a}.lib-header__menu-icon{width:30px;height:30px;display:inline-flex;align-items:center;justify-content:center}.lib-header__section-icons{display:flex;align-items:center;gap:3px}.lib-header__icon{background-size:contain;background-repeat:no-repeat;background-position:center;flex-shrink:0}.lib-header__icon--first{width:54px;height:44px;border-radius:8px;margin-right:6px;background-image:url(/logo.png)}.lib-header__icon--second{width:140px;height:60px;margin-left:10px;background-image:url(/logos-secretaria-alcaldia.svg)}.lib-header__divider{width:1px;height:30px;background-color:var(--lib-header-divider);border-radius:1px;flex-shrink:0}.lib-header__title-container{display:flex;align-items:center;justify-content:center}.lib-header__title{font-size:26px;font-weight:600;color:var(--lib-header-text)}.lib-header__right{display:flex;align-items:center;gap:15px;flex:1;justify-content:flex-end}.lib-header__action-btn{display:inline-flex;align-items:center;gap:8px;background-color:#596300;color:#fff;border:none;border-radius:6px;padding:8px 16px;font-size:14px;font-weight:500;cursor:pointer;transition:background-color .2s ease}.lib-header__action-btn:hover{background-color:#4a5200}.lib-header__notif-wrapper{position:relative;display:inline-flex;align-items:center}.lib-header__user-info{display:flex;align-items:center;gap:8px;background-color:var(--lib-header-user-chip-bg);padding:5px;border-radius:24px;cursor:pointer;transition:background-color .2s ease;position:relative;justify-content:space-between;width:80px}.lib-header__user-info:hover:not(.lib-header__user-info--open){background-color:#d4d8dc}.lib-header__user-info--open{background-color:#eaeef2}.lib-header__user-avatar,.lib-header__dropdown-avatar{width:40px;height:40px;background-color:var(--lib-header-avatar-bg);border-radius:50%;display:flex;align-items:center;justify-content:center;color:#111827;font-weight:600;font-size:16px;flex-shrink:0}.lib-header__dropdown-arrow{width:16px;height:16px;color:#666;flex-shrink:0;transition:transform .2s ease}.lib-header__user-info--open .lib-header__dropdown-arrow{transform:rotate(180deg)}.lib-header__dropdown-menu{position:absolute;top:100%;right:0;margin-top:8px;background-color:#fff;border-radius:12px;min-width:240px;overflow:hidden;opacity:0;visibility:hidden;transform:translateY(-10px);transition:all .2s ease;z-index:1001;box-shadow:5px 6px 5px -3px #0000005c}.lib-header__dropdown-menu--show{opacity:1;visibility:visible;transform:translateY(0)}.lib-header__dropdown-header{padding:16px 20px;border-bottom:2px solid #f0f0f0;display:flex;align-items:center;gap:12px}.lib-header__dropdown-user-info{flex:1}.lib-header__dropdown-user-name{font-size:16px;font-weight:600;color:var(--lib-header-text);margin-bottom:2px}.lib-header__dropdown-user-role{font-size:14px;color:#666}.lib-header__dropdown-item{display:flex;align-items:center;gap:12px;padding:12px 20px;color:var(--lib-header-text);font-size:14px;transition:background-color .2s ease;cursor:pointer}.lib-header__dropdown-item:hover{background-color:#f8f9fa}.lib-header__dropdown-item--danger{color:#dc3545}.lib-header__dropdown-item--danger:hover{background-color:#fff5f5;color:#a02834}.lib-header__dropdown-item-icon{width:15px;height:15px;flex-shrink:0}@media (max-width: 921px){.lib-header__title{display:none}}@media (max-width: 640px){.lib-header__section-icons{display:none}.lib-header__menu-btn{display:block}}@media (max-width: 480px){.lib-header{padding:0 8px}.lib-header__right{gap:10px}}@media (max-width: 360px){.lib-header{padding:0 6px}.lib-header__right{gap:8px}.lib-header__user-avatar{width:36px;height:36px;font-size:12px}}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "component", type: BellWithBadge, selector: "lib-bell-with-badge", inputs: ["count", "active", "ariaLabel"], outputs: ["bellClick"] }, { kind: "component", type: NotificationCenter, selector: "lib-notification-center", inputs: ["notifications", "isOpen", "loading", "hasMore"], outputs: ["markAllRead", "notificationClick", "close", "loadMore"] }] });
|
|
8784
|
+
}
|
|
8785
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: Header, decorators: [{
|
|
8786
|
+
type: Component,
|
|
8787
|
+
args: [{ selector: 'lib-header', standalone: true, imports: [CommonModule, BellWithBadge, NotificationCenter], template: "<header class=\"lib-header\">\n <div class=\"lib-header__left\" (click)=\"goToHome()\">\n <button class=\"lib-header__menu-btn\" type=\"button\" (click)=\"$event.stopPropagation(); onMenuClick()\">\n <span class=\"lib-header__menu-icon\">{{ getMenuIcon() }}</span>\n </button>\n <div class=\"lib-header__section-icons\">\n <div class=\"lib-header__icon lib-header__icon--first\"></div>\n <div class=\"lib-header__divider\"></div>\n <div class=\"lib-header__icon lib-header__icon--second\"></div>\n </div>\n </div>\n\n <div class=\"lib-header__title-container\">\n <div class=\"lib-header__title\">{{ activeTitle() }}</div>\n </div>\n\n <div class=\"lib-header__right\">\n @if (hasAction()) {\n <button class=\"lib-header__action-btn\" type=\"button\" (click)=\"onActionClick()\">\n <svg xmlns=\"http://www.w3.org/2000/svg\" width=\"20\" height=\"20\" viewBox=\"0 0 24 24\" fill=\"currentColor\">\n <path stroke=\"none\" d=\"M0 0h24v24H0z\" fill=\"none\"/>\n <path d=\"M12 4a1 1 0 0 1 1 1v6h6a1 1 0 0 1 0 2h-6v6a1 1 0 0 1 -2 0v-6h-6a1 1 0 0 1 0 -2h6v-6a1 1 0 0 1 1 -1\"/>\n </svg>\n {{ getActionLabel() }}\n </button>\n }\n\n <div class=\"lib-header__notif-wrapper\">\n <lib-bell-with-badge\n [count]=\"unreadCount()\"\n [active]=\"isNotifOpen()\"\n (bellClick)=\"toggleNotifications()\"\n />\n\n <lib-notification-center\n [isOpen]=\"isNotifOpen()\"\n [notifications]=\"notifications()\"\n [loading]=\"notificationsLoading()\"\n [hasMore]=\"notificationsHasMore()\"\n (markAllRead)=\"onMarkAllRead()\"\n (notificationClick)=\"onNotificationItemClick($event)\"\n (loadMore)=\"onLoadMoreNotifications()\"\n (close)=\"closeNotifications()\"\n />\n </div>\n\n <div class=\"lib-header__user-info\" [class.lib-header__user-info--open]=\"isDropdownOpen()\" (click)=\"toggleDropdown()\">\n <div class=\"lib-header__user-avatar\">{{ userRole().charAt(0) }}</div>\n <svg class=\"lib-header__dropdown-arrow\" viewBox=\"0 0 16 16\" fill=\"currentColor\">\n <path d=\"M4 6l4 4 4-4H4z\"/>\n </svg>\n\n <div class=\"lib-header__dropdown-menu\" [class.lib-header__dropdown-menu--show]=\"isDropdownOpen()\" (click)=\"$event.stopPropagation()\">\n <div class=\"lib-header__dropdown-header\">\n <div class=\"lib-header__dropdown-avatar\">{{ userRole().charAt(0) }}</div>\n <div class=\"lib-header__dropdown-user-info\">\n <div class=\"lib-header__dropdown-user-name\">{{ userRole() }}</div>\n <div class=\"lib-header__dropdown-user-role\">Administrador</div>\n </div>\n </div>\n <div class=\"lib-header__dropdown-item\" (click)=\"userProfile()\">\n <svg class=\"lib-header__dropdown-item-icon\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\">\n <path d=\"M20 21v-2a4 4 0 0 0-4-4H8a4 4 0 0 0-4 4v2\"/>\n <circle cx=\"12\" cy=\"7\" r=\"4\"/>\n </svg>\n Perfil\n </div>\n <div class=\"lib-header__dropdown-item lib-header__dropdown-item--danger\" (click)=\"logout()\">\n <svg class=\"lib-header__dropdown-item-icon\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\">\n <path d=\"M9 21H5a2 2 0 0 1-2-2V5a2 2 0 0 1 2-2h4\"/>\n <polyline points=\"16,17 21,12 16,7\"/>\n <line x1=\"21\" y1=\"12\" x2=\"9\" y2=\"12\"/>\n </svg>\n Cerrar sesi\u00F3n\n </div>\n </div>\n </div>\n </div>\n</header>\n", styles: [":host{--lib-header-height: 75px;--lib-header-bg: #fafae8;--lib-header-text: #171c1f;--lib-header-accent: #bfd100;--lib-header-avatar-bg: #bfd100;--lib-header-user-chip-bg: #e3e3d1;--lib-header-divider: #d6d5d2}.lib-header{background-color:var(--lib-header-bg);height:var(--lib-header-height);display:flex;align-items:center;justify-content:space-between;padding:0 10px;position:fixed;top:0;left:0;right:0;z-index:200}.lib-header__left{display:flex;align-items:center;flex:1;justify-content:flex-start;cursor:pointer;gap:0}.lib-header__menu-btn{display:none;background:none;border:none;cursor:pointer;padding:8px;color:var(--lib-header-text);border-radius:4px;transition:background-color .2s ease}.lib-header__menu-btn:hover{background-color:#0000001a}.lib-header__menu-icon{width:30px;height:30px;display:inline-flex;align-items:center;justify-content:center}.lib-header__section-icons{display:flex;align-items:center;gap:3px}.lib-header__icon{background-size:contain;background-repeat:no-repeat;background-position:center;flex-shrink:0}.lib-header__icon--first{width:54px;height:44px;border-radius:8px;margin-right:6px;background-image:url(/logo.png)}.lib-header__icon--second{width:140px;height:60px;margin-left:10px;background-image:url(/logos-secretaria-alcaldia.svg)}.lib-header__divider{width:1px;height:30px;background-color:var(--lib-header-divider);border-radius:1px;flex-shrink:0}.lib-header__title-container{display:flex;align-items:center;justify-content:center}.lib-header__title{font-size:26px;font-weight:600;color:var(--lib-header-text)}.lib-header__right{display:flex;align-items:center;gap:15px;flex:1;justify-content:flex-end}.lib-header__action-btn{display:inline-flex;align-items:center;gap:8px;background-color:#596300;color:#fff;border:none;border-radius:6px;padding:8px 16px;font-size:14px;font-weight:500;cursor:pointer;transition:background-color .2s ease}.lib-header__action-btn:hover{background-color:#4a5200}.lib-header__notif-wrapper{position:relative;display:inline-flex;align-items:center}.lib-header__user-info{display:flex;align-items:center;gap:8px;background-color:var(--lib-header-user-chip-bg);padding:5px;border-radius:24px;cursor:pointer;transition:background-color .2s ease;position:relative;justify-content:space-between;width:80px}.lib-header__user-info:hover:not(.lib-header__user-info--open){background-color:#d4d8dc}.lib-header__user-info--open{background-color:#eaeef2}.lib-header__user-avatar,.lib-header__dropdown-avatar{width:40px;height:40px;background-color:var(--lib-header-avatar-bg);border-radius:50%;display:flex;align-items:center;justify-content:center;color:#111827;font-weight:600;font-size:16px;flex-shrink:0}.lib-header__dropdown-arrow{width:16px;height:16px;color:#666;flex-shrink:0;transition:transform .2s ease}.lib-header__user-info--open .lib-header__dropdown-arrow{transform:rotate(180deg)}.lib-header__dropdown-menu{position:absolute;top:100%;right:0;margin-top:8px;background-color:#fff;border-radius:12px;min-width:240px;overflow:hidden;opacity:0;visibility:hidden;transform:translateY(-10px);transition:all .2s ease;z-index:1001;box-shadow:5px 6px 5px -3px #0000005c}.lib-header__dropdown-menu--show{opacity:1;visibility:visible;transform:translateY(0)}.lib-header__dropdown-header{padding:16px 20px;border-bottom:2px solid #f0f0f0;display:flex;align-items:center;gap:12px}.lib-header__dropdown-user-info{flex:1}.lib-header__dropdown-user-name{font-size:16px;font-weight:600;color:var(--lib-header-text);margin-bottom:2px}.lib-header__dropdown-user-role{font-size:14px;color:#666}.lib-header__dropdown-item{display:flex;align-items:center;gap:12px;padding:12px 20px;color:var(--lib-header-text);font-size:14px;transition:background-color .2s ease;cursor:pointer}.lib-header__dropdown-item:hover{background-color:#f8f9fa}.lib-header__dropdown-item--danger{color:#dc3545}.lib-header__dropdown-item--danger:hover{background-color:#fff5f5;color:#a02834}.lib-header__dropdown-item-icon{width:15px;height:15px;flex-shrink:0}@media (max-width: 921px){.lib-header__title{display:none}}@media (max-width: 640px){.lib-header__section-icons{display:none}.lib-header__menu-btn{display:block}}@media (max-width: 480px){.lib-header{padding:0 8px}.lib-header__right{gap:10px}}@media (max-width: 360px){.lib-header{padding:0 6px}.lib-header__right{gap:8px}.lib-header__user-avatar{width:36px;height:36px;font-size:12px}}\n"] }]
|
|
8788
|
+
}], propDecorators: { isExpanded: [{ type: i0.Input, args: [{ isSignal: true, alias: "isExpanded", required: false }] }], activeTitle: [{ type: i0.Input, args: [{ isSignal: true, alias: "activeTitle", required: false }] }], mfId: [{ type: i0.Input, args: [{ isSignal: true, alias: "mfId", required: false }] }], isMfFailed: [{ type: i0.Input, args: [{ isSignal: true, alias: "isMfFailed", required: false }] }], userRole: [{ type: i0.Input, args: [{ isSignal: true, alias: "userRole", required: false }] }], notifications: [{ type: i0.Input, args: [{ isSignal: true, alias: "notifications", required: false }] }], notificationsLoading: [{ type: i0.Input, args: [{ isSignal: true, alias: "notificationsLoading", required: false }] }], notificationsHasMore: [{ type: i0.Input, args: [{ isSignal: true, alias: "notificationsHasMore", required: false }] }], navigateTo: [{ type: i0.Output, args: ["navigateTo"] }], menuClick: [{ type: i0.Output, args: ["menuClick"] }], profileClick: [{ type: i0.Output, args: ["profileClick"] }], logoutClick: [{ type: i0.Output, args: ["logoutClick"] }], actionClick: [{ type: i0.Output, args: ["actionClick"] }], markAllRead: [{ type: i0.Output, args: ["markAllRead"] }], notificationClick: [{ type: i0.Output, args: ["notificationClick"] }], loadMoreNotifications: [{ type: i0.Output, args: ["loadMoreNotifications"] }] } });
|
|
8789
|
+
|
|
8559
8790
|
// src/app/components/public-api.ts
|
|
8560
8791
|
// Exportar los componentes
|
|
8561
8792
|
|
|
@@ -8563,5 +8794,5 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImpo
|
|
|
8563
8794
|
* Generated bundle index. Do not edit.
|
|
8564
8795
|
*/
|
|
8565
8796
|
|
|
8566
|
-
export { BarChart, BaseChart, Button, ButtonCards, CARD_BG, CSS_ICON_CATALOG, CardContent, CardHistory, ColorPicker, Colors, DEFAULT_ICON_PICKER_ICONS, DEFAULT_MODULE_ICONS, DEFAULT_ROLE_COLORS, DateTimeFilter, DateTimePicker, DevicesCarousel, DialogAlertComponent, DialogConfirmation, DocumentItem, DocumentUpload, DonutChart, DynamicFormFields, FeatureCard, Footer, GeoAPIMaps, Heatmap, IconPicker, InfoGroup, Input, InputNumberFilter, InputSelectFilter, InputTextFilter, InputTimeFilter, KpiCard, LUCIDE_ICON_CATALOG, LineChart, LoadImage, Loader, MapGeo, ModalForm, ModuleCard, ModuleCardList, NotFoundModal, NotFoundSection, NotificationModal, OptionCard, PaginationComponent, PdfViewer, PdfViewerService, ProcessingOverlay, ProgressBar, ProgressFormService, QuickAccessCards, RolCard, SelectCustomSearch, SideCard, SideCardDetail, Sidebar, SidebarService, Signature, TOAST_EVENTS, Table, TableChart, Tabs, TitleFilters, Toast, ToastHelper, ToastService, ToggleCustom, UI_CHART_TOKENS, WizardForm, buildChildGridTemplateColumns, filterVisibleSidebarItems, getCssIconClass, getIconPickerOptionLabel, getInitialOpenState, getLucideIconName, getModuleChildOrder, getTableMinWidth, isLucideIconValue, isMultilineHeaderLabel, mapModuleDataToSidebarItems, markActiveSidebarItems, parseIconPickerValue, resolveIconKind, resolveModuleChildren, resolveTableColumnLayout, submoduleOpenKey, toIconPickerStoredValue, toLucidePascalCase };
|
|
8797
|
+
export { BarChart, BaseChart, BellWithBadge, Button, ButtonCards, CARD_BG, CSS_ICON_CATALOG, CardContent, CardHistory, ColorPicker, Colors, DEFAULT_ICON_PICKER_ICONS, DEFAULT_MODULE_ICONS, DEFAULT_ROLE_COLORS, DateTimeFilter, DateTimePicker, DevicesCarousel, DialogAlertComponent, DialogConfirmation, DocumentItem, DocumentUpload, DonutChart, DynamicFormFields, FeatureCard, Footer, GeoAPIMaps, Header, Heatmap, IconPicker, InfoGroup, Input, InputNumberFilter, InputSelectFilter, InputTextFilter, InputTimeFilter, KpiCard, LUCIDE_ICON_CATALOG, LineChart, LoadImage, Loader, MapGeo, ModalForm, ModuleCard, ModuleCardList, NotFoundModal, NotFoundSection, NotificationCenter, NotificationModal, OptionCard, PaginationComponent, PdfViewer, PdfViewerService, ProcessingOverlay, ProgressBar, ProgressFormService, QuickAccessCards, RolCard, SelectCustomSearch, SideCard, SideCardDetail, Sidebar, SidebarService, Signature, TOAST_EVENTS, Table, TableChart, Tabs, TitleFilters, Toast, ToastHelper, ToastService, ToggleCustom, UI_CHART_TOKENS, WizardForm, buildChildGridTemplateColumns, filterVisibleSidebarItems, getCssIconClass, getIconPickerOptionLabel, getInitialOpenState, getLucideIconName, getModuleChildOrder, getTableMinWidth, isLucideIconValue, isMultilineHeaderLabel, mapModuleDataToSidebarItems, markActiveSidebarItems, parseIconPickerValue, resolveIconKind, resolveModuleChildren, resolveTableColumnLayout, submoduleOpenKey, toIconPickerStoredValue, toLucidePascalCase };
|
|
8567
8798
|
//# sourceMappingURL=sapenlinea-components.mjs.map
|