mesauth-angular 0.2.3 → 0.2.5
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.
- package/README.md +17 -2
- package/dist/README.md +17 -2
- package/dist/esm2020/ma-user.component.mjs +13 -7
- package/dist/esm2020/notification-panel.component.mjs +88 -28
- package/dist/esm2020/user-profile.component.mjs +1 -1
- package/dist/fesm2015/mesauth-angular.mjs +98 -32
- package/dist/fesm2015/mesauth-angular.mjs.map +1 -1
- package/dist/fesm2020/mesauth-angular.mjs +98 -32
- package/dist/fesm2020/mesauth-angular.mjs.map +1 -1
- package/dist/ma-user.component.d.ts +3 -0
- package/dist/notification-panel.component.d.ts +9 -3
- package/dist/package.json +1 -1
- package/dist/user-profile.component.d.ts +1 -1
- package/package.json +1 -1
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import * as i0 from '@angular/core';
|
|
2
|
-
import { Injectable, NgModule, EventEmitter, Component, Output, HostBinding, HostListener } from '@angular/core';
|
|
2
|
+
import { Injectable, NgModule, EventEmitter, Component, Output, HostBinding, HostListener, ViewChild } from '@angular/core';
|
|
3
3
|
import { HubConnectionBuilder, LogLevel } from '@microsoft/signalr';
|
|
4
4
|
import { BehaviorSubject, Subject, throwError } from 'rxjs';
|
|
5
5
|
import { tap, catchError, takeUntil } from 'rxjs/operators';
|
|
@@ -554,14 +554,25 @@ class NotificationPanelComponent {
|
|
|
554
554
|
this.authService = authService;
|
|
555
555
|
this.toastService = toastService;
|
|
556
556
|
this.themeService = themeService;
|
|
557
|
+
this.notificationRead = new EventEmitter();
|
|
557
558
|
this.isOpen = false;
|
|
558
559
|
this.notifications = [];
|
|
559
560
|
this.currentTheme = 'light';
|
|
561
|
+
this.activeTab = 'unread'; // Default to unread tab
|
|
560
562
|
this.destroy$ = new Subject();
|
|
561
563
|
}
|
|
562
564
|
get themeClass() {
|
|
563
565
|
return `theme-${this.currentTheme}`;
|
|
564
566
|
}
|
|
567
|
+
get unreadNotifications() {
|
|
568
|
+
return this.notifications.filter(n => !n.isRead);
|
|
569
|
+
}
|
|
570
|
+
get readNotifications() {
|
|
571
|
+
return this.notifications.filter(n => n.isRead);
|
|
572
|
+
}
|
|
573
|
+
get currentNotifications() {
|
|
574
|
+
return this.activeTab === 'unread' ? this.unreadNotifications : this.readNotifications;
|
|
575
|
+
}
|
|
565
576
|
ngOnInit() {
|
|
566
577
|
this.themeService.currentTheme$
|
|
567
578
|
.pipe(takeUntil(this.destroy$))
|
|
@@ -584,7 +595,7 @@ class NotificationPanelComponent {
|
|
|
584
595
|
this.destroy$.complete();
|
|
585
596
|
}
|
|
586
597
|
loadNotifications() {
|
|
587
|
-
this.authService.getNotifications(1, 50,
|
|
598
|
+
this.authService.getNotifications(1, 50, true).subscribe({
|
|
588
599
|
next: (response) => {
|
|
589
600
|
this.notifications = response.items || [];
|
|
590
601
|
},
|
|
@@ -593,16 +604,24 @@ class NotificationPanelComponent {
|
|
|
593
604
|
}
|
|
594
605
|
open() {
|
|
595
606
|
this.isOpen = true;
|
|
607
|
+
this.activeTab = 'unread'; // Reset to unread tab when opening
|
|
596
608
|
}
|
|
597
609
|
close() {
|
|
598
610
|
this.isOpen = false;
|
|
599
611
|
}
|
|
600
|
-
|
|
612
|
+
switchTab(tab) {
|
|
613
|
+
this.activeTab = tab;
|
|
614
|
+
}
|
|
615
|
+
markAsRead(notificationId, event) {
|
|
616
|
+
if (event) {
|
|
617
|
+
event.stopPropagation();
|
|
618
|
+
}
|
|
601
619
|
this.authService.markAsRead(notificationId).subscribe({
|
|
602
620
|
next: () => {
|
|
603
621
|
const notification = this.notifications.find(n => n.id === notificationId);
|
|
604
622
|
if (notification) {
|
|
605
623
|
notification.isRead = true;
|
|
624
|
+
this.notificationRead.emit();
|
|
606
625
|
}
|
|
607
626
|
},
|
|
608
627
|
error: (err) => { }
|
|
@@ -612,6 +631,7 @@ class NotificationPanelComponent {
|
|
|
612
631
|
this.authService.markAllAsRead().subscribe({
|
|
613
632
|
next: () => {
|
|
614
633
|
this.notifications.forEach(n => n.isRead = true);
|
|
634
|
+
this.notificationRead.emit();
|
|
615
635
|
},
|
|
616
636
|
error: (err) => { }
|
|
617
637
|
});
|
|
@@ -644,7 +664,7 @@ class NotificationPanelComponent {
|
|
|
644
664
|
}
|
|
645
665
|
}
|
|
646
666
|
NotificationPanelComponent.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.3.0", ngImport: i0, type: NotificationPanelComponent, deps: [{ token: MesAuthService }, { token: ToastService }, { token: ThemeService }], target: i0.ɵɵFactoryTarget.Component });
|
|
647
|
-
NotificationPanelComponent.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "14.3.0", type: NotificationPanelComponent, isStandalone: true, selector: "ma-notification-panel", host: { properties: { "class": "this.themeClass" } }, ngImport: i0, template: `
|
|
667
|
+
NotificationPanelComponent.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "14.3.0", type: NotificationPanelComponent, isStandalone: true, selector: "ma-notification-panel", outputs: { notificationRead: "notificationRead" }, host: { properties: { "class": "this.themeClass" } }, ngImport: i0, template: `
|
|
648
668
|
<div class="notification-panel" [class.open]="isOpen">
|
|
649
669
|
<!-- Header -->
|
|
650
670
|
<div class="panel-header">
|
|
@@ -652,11 +672,29 @@ NotificationPanelComponent.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0
|
|
|
652
672
|
<button class="close-btn" (click)="close()" title="Close">✕</button>
|
|
653
673
|
</div>
|
|
654
674
|
|
|
675
|
+
<!-- Tabs -->
|
|
676
|
+
<div class="tabs">
|
|
677
|
+
<button
|
|
678
|
+
class="tab-btn"
|
|
679
|
+
[class.active]="activeTab === 'unread'"
|
|
680
|
+
(click)="switchTab('unread')"
|
|
681
|
+
>
|
|
682
|
+
Unread ({{ unreadNotifications.length }})
|
|
683
|
+
</button>
|
|
684
|
+
<button
|
|
685
|
+
class="tab-btn"
|
|
686
|
+
[class.active]="activeTab === 'read'"
|
|
687
|
+
(click)="switchTab('read')"
|
|
688
|
+
>
|
|
689
|
+
Read ({{ readNotifications.length }})
|
|
690
|
+
</button>
|
|
691
|
+
</div>
|
|
692
|
+
|
|
655
693
|
<!-- Notifications List -->
|
|
656
694
|
<div class="notifications-list">
|
|
657
|
-
<ng-container *ngIf="
|
|
695
|
+
<ng-container *ngIf="currentNotifications.length > 0">
|
|
658
696
|
<div
|
|
659
|
-
*ngFor="let notification of
|
|
697
|
+
*ngFor="let notification of currentNotifications"
|
|
660
698
|
class="notification-item"
|
|
661
699
|
[class.unread]="!notification.isRead"
|
|
662
700
|
(click)="markAsRead(notification.id)"
|
|
@@ -670,30 +708,31 @@ NotificationPanelComponent.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0
|
|
|
670
708
|
</div>
|
|
671
709
|
</div>
|
|
672
710
|
<button
|
|
673
|
-
class="
|
|
674
|
-
(click)="
|
|
675
|
-
title="
|
|
711
|
+
class="read-btn"
|
|
712
|
+
(click)="markAsRead(notification.id, $event)"
|
|
713
|
+
title="Mark as read"
|
|
714
|
+
*ngIf="!notification.isRead"
|
|
676
715
|
>
|
|
677
|
-
|
|
716
|
+
✓
|
|
678
717
|
</button>
|
|
679
718
|
</div>
|
|
680
719
|
</ng-container>
|
|
681
720
|
|
|
682
|
-
<ng-container *ngIf="
|
|
721
|
+
<ng-container *ngIf="currentNotifications.length === 0">
|
|
683
722
|
<div class="empty-state">
|
|
684
|
-
No notifications
|
|
723
|
+
No {{ activeTab }} notifications
|
|
685
724
|
</div>
|
|
686
725
|
</ng-container>
|
|
687
726
|
</div>
|
|
688
727
|
|
|
689
728
|
<!-- Footer Actions -->
|
|
690
|
-
<div class="panel-footer" *ngIf="
|
|
691
|
-
<button class="action-btn" (click)="markAllAsRead()">
|
|
729
|
+
<div class="panel-footer" *ngIf="currentNotifications.length > 0">
|
|
730
|
+
<button class="action-btn" (click)="markAllAsRead()" *ngIf="activeTab === 'unread' && unreadNotifications.length > 0">
|
|
692
731
|
Mark all as read
|
|
693
732
|
</button>
|
|
694
733
|
</div>
|
|
695
734
|
</div>
|
|
696
|
-
`, isInline: true, styles: [":host{--primary-color: #1976d2;--primary-hover: #1565c0;--error-color: #f44336;--text-primary: #333;--text-secondary: #666;--text-muted: #999;--bg-primary: white;--bg-secondary: #f5f5f5;--bg-tertiary: #fafafa;--bg-hover: #f5f5f5;--bg-unread: #e3f2fd;--border-color: #e0e0e0;--border-light: #f0f0f0;--shadow: rgba(0, 0, 0, .1)}:host(.theme-dark){--primary-color: #90caf9;--primary-hover: #64b5f6;--error-color: #ef5350;--text-primary: #e0e0e0;--text-secondary: #b0b0b0;--text-muted: #888;--bg-primary: #1e1e1e;--bg-secondary: #2d2d2d;--bg-tertiary: #252525;--bg-hover: #333;--bg-unread: rgba(144, 202, 249, .1);--border-color: #404040;--border-light: #333;--shadow: rgba(0, 0, 0, .3)}.notification-panel{position:fixed;top:0;right:-350px;width:350px;height:100vh;background:var(--bg-primary);box-shadow:-2px 0 8px var(--shadow);display:flex;flex-direction:column;z-index:1000;transition:right .3s ease}.notification-panel.open{right:0}.panel-header{display:flex;justify-content:space-between;align-items:center;padding:16px;border-bottom:1px solid var(--border-color);background-color:var(--bg-secondary)}.panel-header h3{margin:0;font-size:18px;color:var(--text-primary)}.close-btn{background:none;border:none;font-size:20px;cursor:pointer;color:var(--text-secondary);padding:0;width:32px;height:32px;display:flex;align-items:center;justify-content:center;transition:color .2s}.close-btn:hover{color:var(--text-primary)}.notifications-list{flex:1;overflow-y:auto}.notification-item{display:flex;gap:12px;padding:12px 16px;border-bottom:1px solid var(--border-light);cursor:pointer;background-color:var(--bg-tertiary);transition:background-color .2s}.notification-item:hover{background-color:var(--bg-hover)}.notification-item.unread{background-color:var(--bg-unread)}.notification-content{flex:1;min-width:0}.notification-title{font-weight:600;color:var(--text-primary);font-size:14px;margin-bottom:4px}.notification-message{color:var(--text-secondary);font-size:13px;line-height:1.4;margin-bottom:6px;display:-webkit-box;-webkit-line-clamp:2;-webkit-box-orient:vertical;overflow:hidden}.notification-meta{display:flex;justify-content:space-between;font-size:12px;color:var(--text-muted)}.app-name{font-weight:500;color:var(--primary-color)}.
|
|
735
|
+
`, isInline: true, styles: [":host{--primary-color: #1976d2;--primary-hover: #1565c0;--success-color: #4caf50;--error-color: #f44336;--text-primary: #333;--text-secondary: #666;--text-muted: #999;--bg-primary: white;--bg-secondary: #f5f5f5;--bg-tertiary: #fafafa;--bg-hover: #f5f5f5;--bg-unread: #e3f2fd;--border-color: #e0e0e0;--border-light: #f0f0f0;--shadow: rgba(0, 0, 0, .1)}:host(.theme-dark){--primary-color: #90caf9;--primary-hover: #64b5f6;--success-color: #81c784;--error-color: #ef5350;--text-primary: #e0e0e0;--text-secondary: #b0b0b0;--text-muted: #888;--bg-primary: #1e1e1e;--bg-secondary: #2d2d2d;--bg-tertiary: #252525;--bg-hover: #333;--bg-unread: rgba(144, 202, 249, .1);--border-color: #404040;--border-light: #333;--shadow: rgba(0, 0, 0, .3)}.notification-panel{position:fixed;top:0;right:-350px;width:350px;height:100vh;background:var(--bg-primary);box-shadow:-2px 0 8px var(--shadow);display:flex;flex-direction:column;z-index:1000;transition:right .3s ease}.notification-panel.open{right:0}.panel-header{display:flex;justify-content:space-between;align-items:center;padding:16px;border-bottom:1px solid var(--border-color);background-color:var(--bg-secondary)}.panel-header h3{margin:0;font-size:18px;color:var(--text-primary)}.close-btn{background:none;border:none;font-size:20px;cursor:pointer;color:var(--text-secondary);padding:0;width:32px;height:32px;display:flex;align-items:center;justify-content:center;transition:color .2s}.close-btn:hover{color:var(--text-primary)}.tabs{display:flex;border-bottom:1px solid var(--border-color);background-color:var(--bg-secondary)}.tab-btn{flex:1;padding:12px 16px;background:none;border:none;color:var(--text-secondary);cursor:pointer;font-size:14px;font-weight:500;transition:all .2s;border-bottom:2px solid transparent}.tab-btn:hover{background-color:var(--bg-hover);color:var(--text-primary)}.tab-btn.active{color:var(--primary-color);border-bottom-color:var(--primary-color);background-color:var(--bg-primary)}.notifications-list{flex:1;overflow-y:auto}.notification-item{display:flex;gap:12px;padding:12px 16px;border-bottom:1px solid var(--border-light);cursor:pointer;background-color:var(--bg-tertiary);transition:background-color .2s}.notification-item:hover{background-color:var(--bg-hover)}.notification-item.unread{background-color:var(--bg-unread)}.notification-content{flex:1;min-width:0}.notification-title{font-weight:600;color:var(--text-primary);font-size:14px;margin-bottom:4px}.notification-message{color:var(--text-secondary);font-size:13px;line-height:1.4;margin-bottom:6px;display:-webkit-box;-webkit-line-clamp:2;-webkit-box-orient:vertical;overflow:hidden}.notification-meta{display:flex;justify-content:space-between;font-size:12px;color:var(--text-muted)}.app-name{font-weight:500;color:var(--primary-color)}.read-btn{background:none;border:none;color:var(--text-muted);cursor:pointer;font-size:14px;padding:0;width:24px;height:24px;display:flex;align-items:center;justify-content:center;flex-shrink:0;transition:color .2s}.read-btn:hover{color:var(--success-color)}.empty-state{display:flex;align-items:center;justify-content:center;height:100%;color:var(--text-muted);font-size:14px}.panel-footer{padding:12px 16px;border-top:1px solid var(--border-color);background-color:var(--bg-secondary)}.action-btn{width:100%;padding:8px;background-color:var(--primary-color);color:#fff;border:none;border-radius:4px;cursor:pointer;font-weight:500;transition:background-color .2s}.action-btn:hover{background-color:var(--primary-hover)}@media (max-width: 600px){.notification-panel{width:100%;right:-100%}}\n"], dependencies: [{ kind: "directive", type: NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "directive", type: NgFor, selector: "[ngFor][ngForOf]", inputs: ["ngForOf", "ngForTrackBy", "ngForTemplate"] }] });
|
|
697
736
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.3.0", ngImport: i0, type: NotificationPanelComponent, decorators: [{
|
|
698
737
|
type: Component,
|
|
699
738
|
args: [{ selector: 'ma-notification-panel', standalone: true, imports: [NgIf, NgFor], template: `
|
|
@@ -704,11 +743,29 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.3.0", ngImpor
|
|
|
704
743
|
<button class="close-btn" (click)="close()" title="Close">✕</button>
|
|
705
744
|
</div>
|
|
706
745
|
|
|
746
|
+
<!-- Tabs -->
|
|
747
|
+
<div class="tabs">
|
|
748
|
+
<button
|
|
749
|
+
class="tab-btn"
|
|
750
|
+
[class.active]="activeTab === 'unread'"
|
|
751
|
+
(click)="switchTab('unread')"
|
|
752
|
+
>
|
|
753
|
+
Unread ({{ unreadNotifications.length }})
|
|
754
|
+
</button>
|
|
755
|
+
<button
|
|
756
|
+
class="tab-btn"
|
|
757
|
+
[class.active]="activeTab === 'read'"
|
|
758
|
+
(click)="switchTab('read')"
|
|
759
|
+
>
|
|
760
|
+
Read ({{ readNotifications.length }})
|
|
761
|
+
</button>
|
|
762
|
+
</div>
|
|
763
|
+
|
|
707
764
|
<!-- Notifications List -->
|
|
708
765
|
<div class="notifications-list">
|
|
709
|
-
<ng-container *ngIf="
|
|
766
|
+
<ng-container *ngIf="currentNotifications.length > 0">
|
|
710
767
|
<div
|
|
711
|
-
*ngFor="let notification of
|
|
768
|
+
*ngFor="let notification of currentNotifications"
|
|
712
769
|
class="notification-item"
|
|
713
770
|
[class.unread]="!notification.isRead"
|
|
714
771
|
(click)="markAsRead(notification.id)"
|
|
@@ -722,45 +779,51 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.3.0", ngImpor
|
|
|
722
779
|
</div>
|
|
723
780
|
</div>
|
|
724
781
|
<button
|
|
725
|
-
class="
|
|
726
|
-
(click)="
|
|
727
|
-
title="
|
|
782
|
+
class="read-btn"
|
|
783
|
+
(click)="markAsRead(notification.id, $event)"
|
|
784
|
+
title="Mark as read"
|
|
785
|
+
*ngIf="!notification.isRead"
|
|
728
786
|
>
|
|
729
|
-
|
|
787
|
+
✓
|
|
730
788
|
</button>
|
|
731
789
|
</div>
|
|
732
790
|
</ng-container>
|
|
733
791
|
|
|
734
|
-
<ng-container *ngIf="
|
|
792
|
+
<ng-container *ngIf="currentNotifications.length === 0">
|
|
735
793
|
<div class="empty-state">
|
|
736
|
-
No notifications
|
|
794
|
+
No {{ activeTab }} notifications
|
|
737
795
|
</div>
|
|
738
796
|
</ng-container>
|
|
739
797
|
</div>
|
|
740
798
|
|
|
741
799
|
<!-- Footer Actions -->
|
|
742
|
-
<div class="panel-footer" *ngIf="
|
|
743
|
-
<button class="action-btn" (click)="markAllAsRead()">
|
|
800
|
+
<div class="panel-footer" *ngIf="currentNotifications.length > 0">
|
|
801
|
+
<button class="action-btn" (click)="markAllAsRead()" *ngIf="activeTab === 'unread' && unreadNotifications.length > 0">
|
|
744
802
|
Mark all as read
|
|
745
803
|
</button>
|
|
746
804
|
</div>
|
|
747
805
|
</div>
|
|
748
|
-
`, styles: [":host{--primary-color: #1976d2;--primary-hover: #1565c0;--error-color: #f44336;--text-primary: #333;--text-secondary: #666;--text-muted: #999;--bg-primary: white;--bg-secondary: #f5f5f5;--bg-tertiary: #fafafa;--bg-hover: #f5f5f5;--bg-unread: #e3f2fd;--border-color: #e0e0e0;--border-light: #f0f0f0;--shadow: rgba(0, 0, 0, .1)}:host(.theme-dark){--primary-color: #90caf9;--primary-hover: #64b5f6;--error-color: #ef5350;--text-primary: #e0e0e0;--text-secondary: #b0b0b0;--text-muted: #888;--bg-primary: #1e1e1e;--bg-secondary: #2d2d2d;--bg-tertiary: #252525;--bg-hover: #333;--bg-unread: rgba(144, 202, 249, .1);--border-color: #404040;--border-light: #333;--shadow: rgba(0, 0, 0, .3)}.notification-panel{position:fixed;top:0;right:-350px;width:350px;height:100vh;background:var(--bg-primary);box-shadow:-2px 0 8px var(--shadow);display:flex;flex-direction:column;z-index:1000;transition:right .3s ease}.notification-panel.open{right:0}.panel-header{display:flex;justify-content:space-between;align-items:center;padding:16px;border-bottom:1px solid var(--border-color);background-color:var(--bg-secondary)}.panel-header h3{margin:0;font-size:18px;color:var(--text-primary)}.close-btn{background:none;border:none;font-size:20px;cursor:pointer;color:var(--text-secondary);padding:0;width:32px;height:32px;display:flex;align-items:center;justify-content:center;transition:color .2s}.close-btn:hover{color:var(--text-primary)}.notifications-list{flex:1;overflow-y:auto}.notification-item{display:flex;gap:12px;padding:12px 16px;border-bottom:1px solid var(--border-light);cursor:pointer;background-color:var(--bg-tertiary);transition:background-color .2s}.notification-item:hover{background-color:var(--bg-hover)}.notification-item.unread{background-color:var(--bg-unread)}.notification-content{flex:1;min-width:0}.notification-title{font-weight:600;color:var(--text-primary);font-size:14px;margin-bottom:4px}.notification-message{color:var(--text-secondary);font-size:13px;line-height:1.4;margin-bottom:6px;display:-webkit-box;-webkit-line-clamp:2;-webkit-box-orient:vertical;overflow:hidden}.notification-meta{display:flex;justify-content:space-between;font-size:12px;color:var(--text-muted)}.app-name{font-weight:500;color:var(--primary-color)}.
|
|
749
|
-
}], ctorParameters: function () { return [{ type: MesAuthService }, { type: ToastService }, { type: ThemeService }]; }, propDecorators: {
|
|
806
|
+
`, styles: [":host{--primary-color: #1976d2;--primary-hover: #1565c0;--success-color: #4caf50;--error-color: #f44336;--text-primary: #333;--text-secondary: #666;--text-muted: #999;--bg-primary: white;--bg-secondary: #f5f5f5;--bg-tertiary: #fafafa;--bg-hover: #f5f5f5;--bg-unread: #e3f2fd;--border-color: #e0e0e0;--border-light: #f0f0f0;--shadow: rgba(0, 0, 0, .1)}:host(.theme-dark){--primary-color: #90caf9;--primary-hover: #64b5f6;--success-color: #81c784;--error-color: #ef5350;--text-primary: #e0e0e0;--text-secondary: #b0b0b0;--text-muted: #888;--bg-primary: #1e1e1e;--bg-secondary: #2d2d2d;--bg-tertiary: #252525;--bg-hover: #333;--bg-unread: rgba(144, 202, 249, .1);--border-color: #404040;--border-light: #333;--shadow: rgba(0, 0, 0, .3)}.notification-panel{position:fixed;top:0;right:-350px;width:350px;height:100vh;background:var(--bg-primary);box-shadow:-2px 0 8px var(--shadow);display:flex;flex-direction:column;z-index:1000;transition:right .3s ease}.notification-panel.open{right:0}.panel-header{display:flex;justify-content:space-between;align-items:center;padding:16px;border-bottom:1px solid var(--border-color);background-color:var(--bg-secondary)}.panel-header h3{margin:0;font-size:18px;color:var(--text-primary)}.close-btn{background:none;border:none;font-size:20px;cursor:pointer;color:var(--text-secondary);padding:0;width:32px;height:32px;display:flex;align-items:center;justify-content:center;transition:color .2s}.close-btn:hover{color:var(--text-primary)}.tabs{display:flex;border-bottom:1px solid var(--border-color);background-color:var(--bg-secondary)}.tab-btn{flex:1;padding:12px 16px;background:none;border:none;color:var(--text-secondary);cursor:pointer;font-size:14px;font-weight:500;transition:all .2s;border-bottom:2px solid transparent}.tab-btn:hover{background-color:var(--bg-hover);color:var(--text-primary)}.tab-btn.active{color:var(--primary-color);border-bottom-color:var(--primary-color);background-color:var(--bg-primary)}.notifications-list{flex:1;overflow-y:auto}.notification-item{display:flex;gap:12px;padding:12px 16px;border-bottom:1px solid var(--border-light);cursor:pointer;background-color:var(--bg-tertiary);transition:background-color .2s}.notification-item:hover{background-color:var(--bg-hover)}.notification-item.unread{background-color:var(--bg-unread)}.notification-content{flex:1;min-width:0}.notification-title{font-weight:600;color:var(--text-primary);font-size:14px;margin-bottom:4px}.notification-message{color:var(--text-secondary);font-size:13px;line-height:1.4;margin-bottom:6px;display:-webkit-box;-webkit-line-clamp:2;-webkit-box-orient:vertical;overflow:hidden}.notification-meta{display:flex;justify-content:space-between;font-size:12px;color:var(--text-muted)}.app-name{font-weight:500;color:var(--primary-color)}.read-btn{background:none;border:none;color:var(--text-muted);cursor:pointer;font-size:14px;padding:0;width:24px;height:24px;display:flex;align-items:center;justify-content:center;flex-shrink:0;transition:color .2s}.read-btn:hover{color:var(--success-color)}.empty-state{display:flex;align-items:center;justify-content:center;height:100%;color:var(--text-muted);font-size:14px}.panel-footer{padding:12px 16px;border-top:1px solid var(--border-color);background-color:var(--bg-secondary)}.action-btn{width:100%;padding:8px;background-color:var(--primary-color);color:#fff;border:none;border-radius:4px;cursor:pointer;font-weight:500;transition:background-color .2s}.action-btn:hover{background-color:var(--primary-hover)}@media (max-width: 600px){.notification-panel{width:100%;right:-100%}}\n"] }]
|
|
807
|
+
}], ctorParameters: function () { return [{ type: MesAuthService }, { type: ToastService }, { type: ThemeService }]; }, propDecorators: { notificationRead: [{
|
|
808
|
+
type: Output
|
|
809
|
+
}], themeClass: [{
|
|
750
810
|
type: HostBinding,
|
|
751
811
|
args: ['class']
|
|
752
812
|
}] } });
|
|
753
813
|
|
|
754
814
|
class MaUserComponent {
|
|
815
|
+
onNotificationRead() {
|
|
816
|
+
this.userProfile.loadUnreadCount();
|
|
817
|
+
}
|
|
755
818
|
}
|
|
756
819
|
MaUserComponent.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.3.0", ngImport: i0, type: MaUserComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
757
|
-
MaUserComponent.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "14.3.0", type: MaUserComponent, isStandalone: true, selector: "ma-user", ngImport: i0, template: `
|
|
820
|
+
MaUserComponent.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "14.3.0", type: MaUserComponent, isStandalone: true, selector: "ma-user", viewQueries: [{ propertyName: "userProfile", first: true, predicate: UserProfileComponent, descendants: true }], ngImport: i0, template: `
|
|
758
821
|
<ma-toast-container></ma-toast-container>
|
|
759
822
|
<div class="user-header">
|
|
760
823
|
<ma-user-profile (notificationClick)="notificationPanel.open()"></ma-user-profile>
|
|
761
824
|
</div>
|
|
762
|
-
<ma-notification-panel #notificationPanel></ma-notification-panel>
|
|
763
|
-
`, isInline: true, styles: [".user-header{display:flex;justify-content:flex-end}\n"], dependencies: [{ kind: "component", type: ToastContainerComponent, selector: "ma-toast-container" }, { kind: "component", type: UserProfileComponent, selector: "ma-user-profile", outputs: ["notificationClick"] }, { kind: "component", type: NotificationPanelComponent, selector: "ma-notification-panel" }] });
|
|
825
|
+
<ma-notification-panel #notificationPanel (notificationRead)="onNotificationRead()"></ma-notification-panel>
|
|
826
|
+
`, isInline: true, styles: [".user-header{display:flex;justify-content:flex-end}\n"], dependencies: [{ kind: "component", type: ToastContainerComponent, selector: "ma-toast-container" }, { kind: "component", type: UserProfileComponent, selector: "ma-user-profile", outputs: ["notificationClick"] }, { kind: "component", type: NotificationPanelComponent, selector: "ma-notification-panel", outputs: ["notificationRead"] }] });
|
|
764
827
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.3.0", ngImport: i0, type: MaUserComponent, decorators: [{
|
|
765
828
|
type: Component,
|
|
766
829
|
args: [{ selector: 'ma-user', standalone: true, imports: [ToastContainerComponent, UserProfileComponent, NotificationPanelComponent], template: `
|
|
@@ -768,9 +831,12 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.3.0", ngImpor
|
|
|
768
831
|
<div class="user-header">
|
|
769
832
|
<ma-user-profile (notificationClick)="notificationPanel.open()"></ma-user-profile>
|
|
770
833
|
</div>
|
|
771
|
-
<ma-notification-panel #notificationPanel></ma-notification-panel>
|
|
834
|
+
<ma-notification-panel #notificationPanel (notificationRead)="onNotificationRead()"></ma-notification-panel>
|
|
772
835
|
`, styles: [".user-header{display:flex;justify-content:flex-end}\n"] }]
|
|
773
|
-
}]
|
|
836
|
+
}], propDecorators: { userProfile: [{
|
|
837
|
+
type: ViewChild,
|
|
838
|
+
args: [UserProfileComponent]
|
|
839
|
+
}] } });
|
|
774
840
|
|
|
775
841
|
class NotificationBadgeComponent {
|
|
776
842
|
constructor(authService, themeService) {
|