@skysoftware-co/bayan-hr-widgets-ui 2.0.18 → 2.0.20

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.
Files changed (104) hide show
  1. package/ng-package.json +9 -0
  2. package/package.json +3 -15
  3. package/src/assets/i18n/ar.json +166 -0
  4. package/src/assets/i18n/en.json +166 -0
  5. package/src/assets/i18n/fr.json +166 -0
  6. package/src/lib/my-calendar-widget/my-calendar-widget.component.html +25 -0
  7. package/src/lib/my-calendar-widget/my-calendar-widget.component.ts +220 -0
  8. package/src/lib/my-main-details-widget/my-main-details-widget.component.html +157 -0
  9. package/src/lib/my-main-details-widget/my-main-details-widget.component.ts +179 -0
  10. package/src/lib/my-next-week-vacation-insights-widget/components/next-week-vacation-insights-popup/next-week-vacation-insights-popup.component.html +131 -0
  11. package/src/lib/my-next-week-vacation-insights-widget/components/next-week-vacation-insights-popup/next-week-vacation-insights-popup.component.ts +119 -0
  12. package/src/lib/my-next-week-vacation-insights-widget/my-next-week-vacation-insights-widget.component.html +35 -0
  13. package/src/lib/my-next-week-vacation-insights-widget/my-next-week-vacation-insights-widget.component.ts +110 -0
  14. package/src/lib/my-profile/address-widget/my-profile-address-widget.component.html +57 -0
  15. package/src/lib/my-profile/address-widget/my-profile-address-widget.component.ts +70 -0
  16. package/src/lib/my-profile/bank-info-widget/my-profile-bank-info-widget.component.html +101 -0
  17. package/src/lib/my-profile/bank-info-widget/my-profile-bank-info-widget.component.ts +89 -0
  18. package/src/lib/my-profile/contact-widget/my-profile-contact-widget.component.html +89 -0
  19. package/src/lib/my-profile/contact-widget/my-profile-contact-widget.component.ts +78 -0
  20. package/src/lib/my-profile/contract-widget/my-profile-contract-widget.component.html +63 -0
  21. package/src/lib/my-profile/contract-widget/my-profile-contract-widget.component.ts +73 -0
  22. package/src/lib/my-profile/degrees-widget/my-profile-degrees-widget-component.html +86 -0
  23. package/src/lib/my-profile/degrees-widget/my-profile-degrees-widget-component.ts +98 -0
  24. package/src/lib/my-profile/dependents-documents-widget/my-profile-dependents-documents-widget.html +83 -0
  25. package/src/lib/my-profile/dependents-documents-widget/my-profile-dependents-documents-widget.ts +126 -0
  26. package/src/lib/my-profile/documents-widgets/components/document-card/document-card.component.html +53 -0
  27. package/src/lib/my-profile/documents-widgets/components/document-card/document-card.component.ts +50 -0
  28. package/src/lib/my-profile/documents-widgets/components/document-row/document-row.component.html +48 -0
  29. package/src/lib/my-profile/documents-widgets/components/document-row/document-row.component.ts +44 -0
  30. package/src/lib/my-profile/documents-widgets/components/document-tablet-card/document-tablet-card.component.html +46 -0
  31. package/src/lib/my-profile/documents-widgets/components/document-tablet-card/document-tablet-card.component.ts +47 -0
  32. package/src/lib/my-profile/employee-dependents-widget/my-profile-employee-dependents-component.html +50 -0
  33. package/src/lib/my-profile/employee-dependents-widget/my-profile-employee-dependents-component.ts +63 -0
  34. package/src/lib/my-profile/entitlements-others-widget/my-profile-entitlements-others-widget.component.html +26 -0
  35. package/src/lib/my-profile/entitlements-others-widget/my-profile-entitlements-others-widget.component.ts +66 -0
  36. package/src/lib/my-profile/experiences-widget/my-profile-experiences-widget-component.html +93 -0
  37. package/src/lib/my-profile/experiences-widget/my-profile-experiences-widget-component.ts +102 -0
  38. package/src/lib/my-profile/indemnity-widget/my-profile-indemnity-widget.component.html +49 -0
  39. package/src/lib/my-profile/indemnity-widget/my-profile-indemnity-widget.component.ts +79 -0
  40. package/src/lib/my-profile/job-info-widget/my-profile-job-info-widget.component.html +71 -0
  41. package/src/lib/my-profile/job-info-widget/my-profile-job-info-widget.component.ts +73 -0
  42. package/src/lib/my-profile/languages-widget/my-profile-languages-widget.component.html +23 -0
  43. package/src/lib/my-profile/languages-widget/my-profile-languages-widget.component.ts +70 -0
  44. package/src/lib/my-profile/medical-insurance-widget/components/medical-insurance-card/medical-insurance-card.component.html +18 -0
  45. package/src/lib/my-profile/medical-insurance-widget/components/medical-insurance-card/medical-insurance-card.component.ts +29 -0
  46. package/src/lib/my-profile/medical-insurance-widget/my-profile-medical-insurance-widget.component.html +52 -0
  47. package/src/lib/my-profile/medical-insurance-widget/my-profile-medical-insurance-widget.component.ts +103 -0
  48. package/src/lib/my-profile/official-documents-widget/my-profile-official-documents-widget.html +82 -0
  49. package/src/lib/my-profile/official-documents-widget/my-profile-official-documents-widget.ts +119 -0
  50. package/src/lib/my-profile/other-nationalities-widget/my-profile-other-nationalities-widget.component.html +23 -0
  51. package/src/lib/my-profile/other-nationalities-widget/my-profile-other-nationalities-widget.component.ts +70 -0
  52. package/src/lib/my-profile/personal-info-main-widget/my-profile-personal-info-main-widget.component.html +115 -0
  53. package/src/lib/my-profile/personal-info-main-widget/my-profile-personal-info-main-widget.component.ts +75 -0
  54. package/src/lib/my-profile/salary-widget/my-profile-salary-widget.component.html +37 -0
  55. package/src/lib/my-profile/salary-widget/my-profile-salary-widget.component.ts +85 -0
  56. package/src/lib/my-profile/service-charge-widget/my-profile-service-charge-widget.component.html +16 -0
  57. package/src/lib/my-profile/service-charge-widget/my-profile-service-charge-widget.component.ts +101 -0
  58. package/src/lib/my-profile/ticket-widget/components/ticket-card/ticket-card.component.html +23 -0
  59. package/src/lib/my-profile/ticket-widget/components/ticket-card/ticket-card.component.ts +26 -0
  60. package/src/lib/my-profile/ticket-widget/my-profile-ticket-widget.component.html +68 -0
  61. package/src/lib/my-profile/ticket-widget/my-profile-ticket-widget.component.ts +93 -0
  62. package/src/lib/my-profile/vacations-widget/my-profile-vacations-widget.component.html +34 -0
  63. package/src/lib/my-profile/vacations-widget/my-profile-vacations-widget.component.ts +66 -0
  64. package/src/lib/my-team-subordinates-popup-widget/components/employee-main-info-card/employee-information-card.component.ts +65 -0
  65. package/src/lib/my-team-subordinates-popup-widget/components/employee-main-info-card/employee-main-info-card.component.html +57 -0
  66. package/src/lib/my-team-subordinates-popup-widget/components/my-team-subordinates-popup/my-team-popup.component.html +109 -0
  67. package/src/lib/my-team-subordinates-popup-widget/components/my-team-subordinates-popup/my-team-popup.component.ts +297 -0
  68. package/src/lib/my-upcoming-events-widget/components/event-item/event-item.component.html +53 -0
  69. package/src/lib/my-upcoming-events-widget/components/event-item/event-item.component.ts +42 -0
  70. package/src/lib/my-upcoming-events-widget/components/event-tab-bar/event-tab-bar.component.html +21 -0
  71. package/src/lib/my-upcoming-events-widget/components/event-tab-bar/event-tab-bar.component.ts +44 -0
  72. package/src/lib/my-upcoming-events-widget/components/events-popup/events-popup.component.html +67 -0
  73. package/src/lib/my-upcoming-events-widget/components/events-popup/events-popup.component.ts +74 -0
  74. package/src/lib/my-upcoming-events-widget/my-upcoming-events-widget.component.html +74 -0
  75. package/src/lib/my-upcoming-events-widget/my-upcoming-events-widget.component.ts +199 -0
  76. package/src/lib/services/hr-self-widgets.service.ts +624 -0
  77. package/src/lib/shared/components/card-header/card-header.component.html +4 -0
  78. package/src/lib/shared/components/card-header/card-header.component.ts +18 -0
  79. package/src/lib/shared/components/hr-employee-calendar/hr-employee-calendar.component.html +47 -0
  80. package/src/lib/shared/components/hr-employee-calendar/hr-employee-calendar.component.ts +193 -0
  81. package/src/lib/shared/components/info-field/info-field.component.html +2 -0
  82. package/src/lib/shared/components/info-field/info-field.component.ts +20 -0
  83. package/src/lib/shared/components/widget-card/widget-card-component.html +3 -0
  84. package/src/lib/shared/components/widget-card/widget-card-component.ts +17 -0
  85. package/src/lib/shared/pipes/translate.pipe.ts +34 -0
  86. package/src/lib/shared/services/bank-information-cache.service.ts +29 -0
  87. package/src/lib/shared/services/common-methods.service.ts +33 -0
  88. package/src/lib/shared/services/constants.service.ts +12 -0
  89. package/src/lib/shared/services/entitlements-cache.service.ts +94 -0
  90. package/src/lib/shared/services/job-information-cache.service.ts +72 -0
  91. package/src/lib/shared/services/my-team-popup.service.ts +34 -0
  92. package/src/lib/shared/services/personal-information-cache.service.ts +77 -0
  93. package/src/lib/shared/services/profile-documents-cache-service.ts +44 -0
  94. package/src/lib/shared/services/profile-employee-dependents-cach.ts +37 -0
  95. package/src/lib/shared/services/qualifications-cache.service.ts +45 -0
  96. package/src/lib/shared/services/translate.service.ts +35 -0
  97. package/src/lib/shared/types/common.ts +359 -0
  98. package/src/public-api.ts +35 -0
  99. package/tsconfig.lib.json +11 -0
  100. package/tsconfig.lib.prod.json +9 -0
  101. package/tsconfig.spec.json +8 -0
  102. package/fesm2022/skysoftware-co-bayan-hr-widgets-ui.mjs +0 -4785
  103. package/fesm2022/skysoftware-co-bayan-hr-widgets-ui.mjs.map +0 -1
  104. package/types/skysoftware-co-bayan-hr-widgets-ui.d.ts +0 -1305
@@ -0,0 +1,78 @@
1
+ import { CommonModule } from '@angular/common';
2
+ import { ChangeDetectionStrategy, Component, OnInit, inject, input, output, signal } from '@angular/core';
3
+ import { FontAwesomeModule } from '@fortawesome/angular-fontawesome';
4
+ import { faBolt, faPhone } from '@fortawesome/pro-light-svg-icons';
5
+ import { HRTranslatePipe } from '../../shared/pipes/translate.pipe';
6
+ import { SkyEmptyDesignCardComponent, SkySectionDividerComponent } from '@skysoftware-co/sky-components-ui';
7
+ import { PersonalInfoContactDetails } from '../../shared/types/common';
8
+ import { HRSelfWidgetsService } from '../../services/hr-self-widgets.service';
9
+ import { HRInfoFieldComponent } from '../../shared/components/info-field/info-field.component';
10
+
11
+ @Component({
12
+ selector: 'hr-my-profile-contact-widget',
13
+ standalone: true,
14
+ imports: [
15
+ CommonModule,
16
+ FontAwesomeModule,
17
+ HRTranslatePipe,
18
+ SkySectionDividerComponent,
19
+ SkyEmptyDesignCardComponent,
20
+ HRInfoFieldComponent,
21
+ ],
22
+ templateUrl: './my-profile-contact-widget.component.html',
23
+ changeDetection: ChangeDetectionStrategy.OnPush,
24
+ })
25
+ export class MyProfileContactWidgetComponent implements OnInit {
26
+ readonly employeePersonalInfoContactDetails = signal<PersonalInfoContactDetails | null>(null);
27
+ readonly isLoading = signal(true);
28
+ readonly baseUrl = input.required<string>();
29
+ readonly headerIconClass = input<string>('primary-icon-xl');
30
+ readonly headerTextClass = input<string>('mt-2 field-secondary-label-lg');
31
+ readonly headerDividerClass = input<string>('flex-grow-1 ms-2');
32
+ readonly rowClass = input<string>('row mt-4');
33
+ readonly columnClass = input<string>('col-4');
34
+ readonly responsiveTopSpacingColumnClass = input<string>('col-6 mt-4');
35
+ readonly topSpacingBottomMdSpacingColumnClass = input<string>('col-md-4 col-6 mt-4 mb-md-5');
36
+ readonly topSpacingBottomSpacingColumnClass = input<string>('col-md-4 col-6 mt-4 mb-5');
37
+ readonly labelClass = input<string>('field-secondary-label-sm');
38
+ readonly valueClass = input<string>('fs-14 fw-medium text-ellipsis-one-line');
39
+ readonly emergencyContactLabelClass = input<string>('fs-14 fw-semibold');
40
+ readonly emergencyContactColumnClass = input<string>('col-md-4 col-6');
41
+ readonly emergencyContactResponsiveColumnClass = input<string>('col-md-4 col-6 mt-md-0 mt-4');
42
+ readonly emptyStateContainerClass = input<string>(
43
+ 'd-flex flex-column justify-content-center align-items-center my-5',
44
+ );
45
+ readonly emptyStateTextClass = input<string>('field-secondary-label-md');
46
+
47
+ readonly contactIcon = input(faPhone);
48
+ readonly emergencyContactIcon = input(faBolt);
49
+ readonly sectionTitle = input('contact');
50
+ readonly showEmergencyContact = input(true);
51
+ readonly emergencyContactRowClass = input('row mt-3 mb-4');
52
+ readonly isLoadingChanged = output<boolean>();
53
+ readonly errorOccurred = output<string>();
54
+
55
+ private readonly hrSelfWidgetsService = inject(HRSelfWidgetsService);
56
+
57
+ ngOnInit(): void {
58
+ if (!this.baseUrl()) {
59
+ this.isLoading.set(false);
60
+ return;
61
+ }
62
+ this.isLoadingChanged.emit(true);
63
+
64
+ this.hrSelfWidgetsService.getPersonalInfoContactDetails(this.baseUrl()).subscribe({
65
+ next: response => {
66
+ this.isLoading.set(false);
67
+ this.isLoadingChanged.emit(false);
68
+ this.employeePersonalInfoContactDetails.set(response);
69
+ },
70
+ error: error => {
71
+ this.isLoading.set(false);
72
+ this.isLoadingChanged.emit(false);
73
+ this.employeePersonalInfoContactDetails.set(null);
74
+ this.errorOccurred.emit(error.error.ResponseData.Errors[0].Message);
75
+ },
76
+ });
77
+ }
78
+ }
@@ -0,0 +1,63 @@
1
+ <sky-section-divider
2
+ [fontAwesomeIcon]="contractIcon()"
3
+ [text]="sectionTitle() | translate | uppercase"
4
+ [iconClass]="headerIconClass()"
5
+ [textClass]="headerTextClass()"
6
+ [dividerClass]="headerDividerClass()"
7
+ ></sky-section-divider>
8
+
9
+ @if (jobInformationContract()) {
10
+ <div [ngClass]="rowClass()">
11
+ <div [ngClass]="columnClass()">
12
+ <hr-info-field
13
+ [labelKey]="'ContractType'"
14
+ [value]="jobInformationContract()!.ContractTypeName"
15
+ [labelClass]="labelClass()"
16
+ [valueClass]="valueClass()"
17
+ ></hr-info-field>
18
+ </div>
19
+ <div [ngClass]="columnClass()">
20
+ <hr-info-field
21
+ [labelKey]="'ContractStartDate'"
22
+ [value]="jobInformationContract()!.ContractStartDate ? (jobInformationContract()!.ContractStartDate | date: 'dd/MM/yyyy') : null"
23
+ [labelClass]="labelClass()"
24
+ [valueClass]="valueClass()"
25
+ ></hr-info-field>
26
+ </div>
27
+ <div [ngClass]="responsiveTopSpacingColumnClass()">
28
+ <hr-info-field
29
+ [labelKey]="'ContractEndDate'"
30
+ [value]="jobInformationContract()!.ContractEndDate ? (jobInformationContract()!.ContractEndDate | date: 'dd/MM/yyyy') : null"
31
+ [labelClass]="labelClass()"
32
+ [valueClass]="valueClass()"
33
+ ></hr-info-field>
34
+ </div>
35
+
36
+ <div [ngClass]="topSpacingBottomMdSpacingColumnClass()">
37
+ <hr-info-field
38
+ [labelKey]="'ContractMaritalStatus'"
39
+ [value]="jobInformationContract()!.ContractMaritalStateName"
40
+ [labelClass]="labelClass()"
41
+ [valueClass]="valueClass()"
42
+ ></hr-info-field>
43
+ </div>
44
+ <div [ngClass]="topSpacingBottomSpacingColumnClass()">
45
+ <hr-info-field
46
+ [labelKey]="'ContractDependentsCount'"
47
+ [value]="jobInformationContract()!.ContractDependentsCount?.toString()"
48
+ [labelClass]="labelClass()"
49
+ [valueClass]="valueClass()"
50
+ ></hr-info-field>
51
+ </div>
52
+ </div>
53
+ } @else {
54
+ <sky-empty-design-card
55
+ [visibleIcon]="false"
56
+ [visibleQuickAction]="false"
57
+ [containerClass]="emptyStateContainerClass()"
58
+ [cardBodyClass]="''"
59
+ [cardBodyContainerClass]="''"
60
+ [emptyTextClass]="emptyStateTextClass()"
61
+ [emptyText]="isLoading() ? (sectionTitle() | translate) + ' ' + ('IsLoading' | translate) : ('ThereIsNoJobContractYet' | translate)"
62
+ ></sky-empty-design-card>
63
+ }
@@ -0,0 +1,73 @@
1
+ import { CommonModule } from '@angular/common';
2
+ import { ChangeDetectionStrategy, Component, OnInit, inject, input, output, signal } from '@angular/core';
3
+ import { faFileSignature } from '@fortawesome/pro-light-svg-icons';
4
+ import { SkyEmptyDesignCardComponent, SkySectionDividerComponent } from '@skysoftware-co/sky-components-ui';
5
+ import { HRSelfWidgetsService } from '../../services/hr-self-widgets.service';
6
+ import { HRTranslatePipe } from '../../shared/pipes/translate.pipe';
7
+ import { JobInformationContract } from '../../shared/types/common';
8
+ import { HRInfoFieldComponent } from '../../shared/components/info-field/info-field.component';
9
+
10
+ @Component({
11
+ selector: 'hr-my-profile-contract-widget',
12
+ standalone: true,
13
+ imports: [
14
+ CommonModule,
15
+ HRTranslatePipe,
16
+ SkySectionDividerComponent,
17
+ SkyEmptyDesignCardComponent,
18
+ HRInfoFieldComponent,
19
+ ],
20
+ templateUrl: './my-profile-contract-widget.component.html',
21
+ changeDetection: ChangeDetectionStrategy.OnPush,
22
+ })
23
+ export class MyProfileContractWidgetComponent implements OnInit {
24
+ readonly jobInformationContract = signal<JobInformationContract | null>(null);
25
+ readonly isLoading = signal(true);
26
+
27
+ readonly baseUrl = input.required<string>();
28
+ readonly headerIconClass = input<string>('primary-icon-xl');
29
+ readonly headerTextClass = input<string>('mt-2 field-secondary-label-lg');
30
+ readonly headerDividerClass = input<string>('flex-grow-1 ms-2');
31
+ readonly rowClass = input<string>('row mt-4');
32
+ readonly columnClass = input<string>('col-md-4 col-6');
33
+ readonly responsiveTopSpacingColumnClass = input<string>('col-md-4 col-6 mt-md-0 mt-4');
34
+ readonly topSpacingBottomMdSpacingColumnClass = input<string>('col-md-4 col-6 mt-4 mb-md-5');
35
+ readonly topSpacingBottomSpacingColumnClass = input<string>('col-md-4 col-6 mt-4 mb-5');
36
+ readonly labelClass = input<string>('field-secondary-label-sm');
37
+ readonly valueClass = input<string>('fs-14 fw-medium text-ellipsis-one-line');
38
+ readonly emptyStateContainerClass = input<string>(
39
+ 'd-flex flex-column justify-content-center align-items-center my-5',
40
+ );
41
+ readonly emptyStateTextClass = input<string>('field-secondary-label-md');
42
+
43
+ readonly contractIcon = input(faFileSignature);
44
+ readonly sectionTitle = input('Contract');
45
+
46
+ readonly isLoadingChanged = output<boolean>();
47
+ readonly errorOccurred = output<string>();
48
+
49
+ private readonly hrSelfWidgetsService = inject(HRSelfWidgetsService);
50
+
51
+ ngOnInit(): void {
52
+ if (!this.baseUrl()) {
53
+ this.isLoading.set(false);
54
+ return;
55
+ }
56
+
57
+ this.isLoadingChanged.emit(true);
58
+
59
+ this.hrSelfWidgetsService.getJobInformationContract(this.baseUrl()).subscribe({
60
+ next: response => {
61
+ this.isLoading.set(false);
62
+ this.jobInformationContract.set(response);
63
+ this.isLoadingChanged.emit(false);
64
+ },
65
+ error: error => {
66
+ this.isLoading.set(false);
67
+ this.jobInformationContract.set(null);
68
+ this.isLoadingChanged.emit(false);
69
+ this.errorOccurred.emit(error.error.ResponseData.Errors[0].Message);
70
+ },
71
+ });
72
+ }
73
+ }
@@ -0,0 +1,86 @@
1
+ <sky-section-divider
2
+ [fontAwesomeIcon]="degreesIcon()"
3
+ [text]="sectionTitle() | translate | uppercase"
4
+ [iconClass]="headerIconClass()"
5
+ [textClass]="headerTextClass()"
6
+ [dividerClass]="headerDividerClass()"
7
+ ></sky-section-divider>
8
+
9
+ <div [class]="wrapperClass">
10
+ @if (degrees().length > 0) {
11
+ <div class="row">
12
+ <div [class]="headerRowClass()">
13
+ <div [class]="itemColumnClass()">
14
+ <p [class]="labelClass()">{{ 'Degree/Year' | translate }}</p>
15
+ </div>
16
+
17
+ <div [class]="itemColumnClass()">
18
+ <p [class]="labelClass()">{{ 'Country' | translate }}</p>
19
+ </div>
20
+
21
+ <div [class]="itemColumnClass()">
22
+ <p [class]="labelClass()">{{ 'Specialty' | translate }}</p>
23
+ </div>
24
+
25
+ <div [class]="itemColumnClass()">
26
+ <p [class]="labelClass()">{{ 'Institute' | translate }}</p>
27
+ </div>
28
+ </div>
29
+
30
+ <div [class]="actionsSpacerClass()"></div>
31
+
32
+ @for (qualification of degrees(); track qualification) {
33
+ <div [class]="itemColumnsWrapperClass()">
34
+ <div [class]="itemColumnClass()">
35
+ <p [class]="valueClass()" [title]="qualification.DegreeName + ' / ' + qualification.DegreeYear">
36
+ {{ qualification.DegreeName + ' / ' + qualification.DegreeYear }}
37
+ </p>
38
+ </div>
39
+
40
+ <div [class]="itemColumnClass()">
41
+ <p [class]="valueClass()" [title]="qualification.CountryName ? qualification.CountryName : ''">
42
+ {{ qualification.CountryName }}
43
+ </p>
44
+ </div>
45
+
46
+ <div [class]="itemColumnClass()">
47
+ <p [class]="valueClass()" [title]="qualification.Specialty ? qualification.Specialty : ''">
48
+ @if (qualification.Specialty) {
49
+ {{ qualification.Specialty }}
50
+ } @else {
51
+ {{ '—' }}
52
+ }
53
+ </p>
54
+ </div>
55
+
56
+ <div [class]="itemColumnClass()">
57
+ <p [class]="valueClass()" [title]="qualification.Institute ? qualification.Institute : ''">
58
+ @if (qualification.Institute) {
59
+ {{ qualification.Institute }}
60
+ } @else {
61
+ {{ '—' }}
62
+ }
63
+ </p>
64
+ </div>
65
+ </div>
66
+
67
+ @if (qualification.Document) {
68
+ <div [class]="actionsColumnClass()">
69
+ <fa-icon [icon]="viewIcon()" [class]="viewIconClass()" (click)="onAttachmentView(qualification.Document)"></fa-icon>
70
+ <fa-icon [icon]="downloadIcon()" [class]="downloadIconClass()" (click)="onAttachmentDownload(qualification.Document)"></fa-icon>
71
+ </div>
72
+ }
73
+ }
74
+ </div>
75
+ } @else {
76
+ <sky-empty-design-card
77
+ [containerClass]="emptyStateContainerClass()"
78
+ [cardBodyClass]="''"
79
+ [cardBodyContainerClass]="''"
80
+ [visibleIcon]="false"
81
+ [visibleQuickAction]="false"
82
+ [emptyTextClass]="emptyStateTextClass()"
83
+ [emptyText]="isLoading() ? (sectionTitle() | translate) + ' ' + ('IsLoading' | translate) : ('ThereIsNoDegreesYet' | translate)"
84
+ ></sky-empty-design-card>
85
+ }
86
+ </div>
@@ -0,0 +1,98 @@
1
+ import { CommonModule } from '@angular/common';
2
+ import { ChangeDetectionStrategy, Component, OnInit, inject, input, output, signal } from '@angular/core';
3
+ import { SkyEmptyDesignCardComponent, SkySectionDividerComponent } from '@skysoftware-co/sky-components-ui';
4
+ import { faFileCertificate, faFolderArrowDown } from '@fortawesome/pro-light-svg-icons';
5
+ import { faEye } from '@fortawesome/pro-regular-svg-icons';
6
+ import { HRTranslatePipe } from '../../shared/pipes/translate.pipe';
7
+ import { HRSelfWidgetsService } from '../../services/hr-self-widgets.service';
8
+ import { IconDefinition } from '@fortawesome/angular-fontawesome';
9
+ import { FontAwesomeModule } from '@fortawesome/angular-fontawesome';
10
+ import { Degree } from '../../shared/types/common';
11
+
12
+ @Component({
13
+ selector: 'hr-my-profile-degrees-widget',
14
+ standalone: true,
15
+ imports: [CommonModule, SkySectionDividerComponent, HRTranslatePipe, SkyEmptyDesignCardComponent, FontAwesomeModule],
16
+ templateUrl: './my-profile-degrees-widget-component.html',
17
+ changeDetection: ChangeDetectionStrategy.OnPush,
18
+ })
19
+ export class MyProfileDegreesWidgetComponent implements OnInit {
20
+ readonly degrees = signal<Degree[]>([]);
21
+ readonly isLoading = signal(true);
22
+
23
+ readonly baseUrl = input<string>('');
24
+ readonly sectionTitle = input<string>('Degrees');
25
+
26
+ readonly degreesIcon = input(faFileCertificate);
27
+ readonly viewIcon = input<IconDefinition>(faEye);
28
+ readonly downloadIcon = input(faFolderArrowDown);
29
+
30
+ readonly headerIconClass = input<string>('primary-icon-xl');
31
+ readonly headerTextClass = input<string>('fs-16 mt-2 text-secondary');
32
+ readonly headerDividerClass = input<string>('flex-grow-1 ms-2');
33
+ readonly rowClass = input<string>('mt-4');
34
+ readonly rowMarginBottomClass = input<string>('mb-5');
35
+ readonly rowMarginBottomEmptyClass = input<string>('mb-4');
36
+ readonly headerRowClass = input<string>('row col-10');
37
+ readonly actionsSpacerClass = input<string>('col-2');
38
+ readonly labelClass = input<string>('field-secondary-label-sm text-ellipsis-one-line');
39
+ readonly valueClass = input<string>('text-dark-gray fs-14 text-ellipsis-one-line');
40
+ readonly viewIconClass = input<string>('fs-15 text-dark cursor-pointer');
41
+ readonly downloadIconClass = input<string>('fs-15 mx-3 text-dark cursor-pointer');
42
+ readonly emptyStateContainerClass = input<string>(
43
+ 'd-flex flex-column justify-content-center align-items-center my-5',
44
+ );
45
+ readonly emptyStateTextClass = input<string>('field-secondary-label-md');
46
+
47
+ readonly itemRowClass = input<string>('row');
48
+ readonly itemColumnsWrapperClass = input<string>('row col-10 mt-3');
49
+ readonly itemColumnClass = input<string>('col-3');
50
+ readonly actionsColumnClass = input<string>('col-2 align-items-end mt-3');
51
+
52
+ readonly isLoadingChanged = output<boolean>();
53
+ readonly attachmentViewed = output<any>();
54
+ readonly attachmentDownloaded = output<any>();
55
+ readonly errorOccurred = output<string>();
56
+ private readonly service = inject(HRSelfWidgetsService);
57
+
58
+ ngOnInit(): void {
59
+ if (!this.baseUrl()) {
60
+ this.isLoading.set(false);
61
+ return;
62
+ }
63
+
64
+ this.isLoadingChanged.emit(true);
65
+
66
+ this.service.getEmployeeDegrees(this.baseUrl()).subscribe({
67
+ next: res => {
68
+ this.degrees.set(res ?? []);
69
+ this.isLoading.set(false);
70
+ this.isLoadingChanged.emit(false);
71
+ },
72
+ error: error => {
73
+ this.degrees.set([]);
74
+ this.isLoading.set(false);
75
+ this.errorOccurred.emit(error.error.ResponseData.Errors[0].Message);
76
+ this.isLoadingChanged.emit(false);
77
+ },
78
+ });
79
+ }
80
+
81
+ get wrapperClass(): string {
82
+ const classes = [this.rowClass()];
83
+ if (this.degrees().length > 0) {
84
+ classes.push(this.rowMarginBottomClass());
85
+ } else {
86
+ classes.push(this.rowMarginBottomEmptyClass());
87
+ }
88
+ return classes.join(' ');
89
+ }
90
+
91
+ onAttachmentView(file: any) {
92
+ this.attachmentViewed.emit(file);
93
+ }
94
+
95
+ onAttachmentDownload(file: any) {
96
+ this.attachmentDownloaded.emit(file);
97
+ }
98
+ }
@@ -0,0 +1,83 @@
1
+ <sky-section-divider
2
+ [fontAwesomeIcon]="icon()"
3
+ [text]="sectionTitle() | translate | uppercase"
4
+ [iconClass]="headerIconClass()"
5
+ [textClass]="headerTextClass()"
6
+ [dividerClass]="headerDividerClass()"
7
+ ></sky-section-divider>
8
+
9
+ <div class="mt-4">
10
+ @if (groups().length) {
11
+ @for (group of groups(); track group; let first = $first) {
12
+ <div [class]="!(isTablet() || isMobile()) ? cardClass() : ''" [class.mt-3]="!first">
13
+ @if (!(isTablet() || isMobile())) {
14
+ <hr-document-card
15
+ [title]="group.DependentName + ' (' + group.DependentTypeName + ')'"
16
+ [documents]="group.Documents"
17
+ [valueClass]="valueClass()"
18
+ [viewIcon]="viewIcon()"
19
+ [downloadIcon]="downloadIcon()"
20
+ [viewIconClass]="viewIconClass()"
21
+ [downloadIconClass]="downloadIconClass()"
22
+ [titleContainerClass]="titleContainerClass()"
23
+ [titleClass]="titleClass()"
24
+ [labelClass]="labelClass()"
25
+ [rowClass]="rowClass()"
26
+ [dataColClass]="dataColClass()"
27
+ [dataColSpacingClass]="dataColSpacingClass()"
28
+ [dataRowClass]="dataRowClass()"
29
+ [typeColClass]="typeColClass()"
30
+ [numberColClass]="numberColClass()"
31
+ [issueDateColClass]="issueDateColClass()"
32
+ [expiryDateColClass]="expiryDateColClass()"
33
+ [actionsColClass]="actionsColClass()"
34
+ [actionsWrapperClass]="actionsWrapperClass()"
35
+ [downloadContainerClass]="downloadContainerClass()"
36
+ (attachmentView)="onAttachmentView($event)"
37
+ (download)="onDownload($event)"
38
+ ></hr-document-card>
39
+ } @else {
40
+ <div [class]="titleContainerClass()">
41
+ <p [class]="titleClass()">{{ group.DependentName }} ({{ group.DependentTypeName }})</p>
42
+ </div>
43
+ <div class="row mx-1">
44
+ @for (doc of group.Documents; track doc; let odd = $odd) {
45
+ <div class="col-6 mb-2">
46
+ <hr-document-tablet-card
47
+ [doc]="doc"
48
+ [isOdd]="odd"
49
+ [viewIcon]="viewIcon()"
50
+ [downloadIcon]="downloadIcon()"
51
+ [labelClass]="labelClass()"
52
+ [valueClass]="valueClass()"
53
+ [downloadIconClass]="downloadIconClass()"
54
+ [downloadContainerClass]="downloadContainerClass()"
55
+ [downloadCountClass]="tabletDownloadCountClass()"
56
+ [tabletContainerClass]="tabletContainerClass()"
57
+ [tabletCardClass]="tabletCardClass()"
58
+ [cardHeight]="tabletCardHeight()"
59
+ [tabletColWithAttachmentClass]="tabletColWithAttachmentClass()"
60
+ [tabletColWithoutAttachmentClass]="tabletColWithoutAttachmentClass()"
61
+ [tabletActionsColClass]="tabletActionsColClass()"
62
+ [tabletBottomRowSpacingClass]="tabletBottomRowSpacingClass()"
63
+ (view)="onAttachmentView(doc)"
64
+ (download)="onDownload(doc)"
65
+ ></hr-document-tablet-card>
66
+ </div>
67
+ }
68
+ </div>
69
+ }
70
+ </div>
71
+ }
72
+ } @else {
73
+ <sky-empty-design-card
74
+ [visibleIcon]="false"
75
+ [visibleQuickAction]="false"
76
+ [containerClass]="emptyStateContainerClass()"
77
+ [emptyTextClass]="emptyStateTextClass()"
78
+ [emptyText]="
79
+ isLoading() ? (sectionTitle() | translate) + ' ' + ('IsLoading' | translate) : ('ThereAreNoDependentsDocumentsYet' | translate)
80
+ "
81
+ ></sky-empty-design-card>
82
+ }
83
+ </div>
@@ -0,0 +1,126 @@
1
+ import { CommonModule } from '@angular/common';
2
+ import { ChangeDetectionStrategy, Component, OnInit, inject, input, output, signal } from '@angular/core';
3
+ import { SkyEmptyDesignCardComponent, SkySectionDividerComponent } from '@skysoftware-co/sky-components-ui';
4
+ import { faFileLines, faFolderArrowDown } from '@fortawesome/pro-light-svg-icons';
5
+ import { faEye } from '@fortawesome/pro-regular-svg-icons';
6
+ import { HRSelfWidgetsService } from '../../services/hr-self-widgets.service';
7
+ import { FontAwesomeModule } from '@fortawesome/angular-fontawesome';
8
+ import { IconDefinition } from '@fortawesome/angular-fontawesome';
9
+ import { HRDocumentCardComponent } from '../documents-widgets/components/document-card/document-card.component';
10
+ import { HrDocumentTabletCardComponent } from '../documents-widgets/components/document-tablet-card/document-tablet-card.component';
11
+ import { HRTranslatePipe } from '../../shared/pipes/translate.pipe';
12
+ import { DependentDocumentGroup } from '../../shared/types/common';
13
+
14
+ @Component({
15
+ selector: 'hr-my-profile-dependents-documents-widget',
16
+ standalone: true,
17
+ imports: [
18
+ CommonModule,
19
+ SkySectionDividerComponent,
20
+ HRTranslatePipe,
21
+ SkyEmptyDesignCardComponent,
22
+ FontAwesomeModule,
23
+ HRDocumentCardComponent,
24
+ HrDocumentTabletCardComponent,
25
+ ],
26
+ templateUrl: './my-profile-dependents-documents-widget.html',
27
+ changeDetection: ChangeDetectionStrategy.OnPush,
28
+ })
29
+ export class MyProfileDependentsDocumentsWidgetComponent implements OnInit {
30
+ documents: DependentDocumentGroup[] = [];
31
+ groupedDocuments: DependentDocumentGroup[] = [];
32
+ readonly isLoading = signal(true);
33
+
34
+ readonly baseUrl = input<string>('');
35
+ readonly sectionTitle = input<string>('DependentsDocuments');
36
+ readonly icon = input(faFileLines);
37
+ readonly viewIcon = input<IconDefinition>(faEye);
38
+ readonly downloadIcon = input(faFolderArrowDown);
39
+ readonly headerIconClass = input<string>('primary-icon-xl');
40
+ readonly headerTextClass = input<string>('fs-16 mt-2 text-secondary');
41
+ readonly headerDividerClass = input<string>('flex-grow-1 ms-2');
42
+ readonly valueClass = input<string>('text-dark-gray fs-14 text-break');
43
+ readonly viewIconClass = input<string>('fs-15 text-dark cursor-pointer');
44
+ readonly downloadIconClass = input<string>('fs-15 text-dark cursor-pointer');
45
+ readonly emptyStateContainerClass = input<string>(
46
+ 'd-flex flex-column justify-content-center align-items-center my-5',
47
+ );
48
+ readonly emptyStateTextClass = input<string>('field-secondary-label-md');
49
+ readonly cardClass = input<string>('mt-4 card-shadow position-relative p-4');
50
+ readonly topSpacingColClass = input<string>('col-md-3 col-6 mt-4');
51
+ readonly titleContainerClass = input<string>('mb-3');
52
+ readonly titleClass = input<string>('text-dark fs-16 mb-0');
53
+ readonly labelClass = input<string>('field-secondary-label-sm mb-1');
54
+ readonly actionsColumnClass = input<string>('col-2 d-flex flex-column mt-3');
55
+ readonly rowClass = input<string>('row');
56
+ readonly dataColClass = input<string>('col-10');
57
+ readonly dataColSpacingClass = input<string>('mt-2');
58
+ readonly dataRowClass = input<string>('row align-items-center py-1 gx-0');
59
+ readonly typeColClass = input<string>('col-3');
60
+ readonly numberColClass = input<string>('col-3');
61
+ readonly issueDateColClass = input<string>('col-3');
62
+ readonly expiryDateColClass = input<string>('col-3');
63
+ readonly actionsColClass = input<string>('col-2 d-flex align-items-center');
64
+ readonly actionsWrapperClass = input<string>('d-flex align-items-center gap-2');
65
+ readonly downloadContainerClass = input<string>(
66
+ 'bg-light-gray rounded-3 d-flex align-items-center justify-content-center px-1 cursor-pointer',
67
+ );
68
+
69
+ readonly tabletContainerClass = input<string>('mt-3');
70
+ readonly tabletCardClass = input<string>('row px-4 py-3 card-shadow');
71
+ readonly tabletCardHeight = input<string>('175px');
72
+ readonly tabletColWithAttachmentClass = input<string>('col-5');
73
+ readonly tabletColWithoutAttachmentClass = input<string>('col-6');
74
+ readonly tabletActionsColClass = input<string>('col-1 d-flex align-items-center');
75
+ readonly tabletBottomRowSpacingClass = input<string>('mt-4');
76
+ readonly tabletDownloadCountClass = input<string>('text-dark fs-12 fw-bold ps-2');
77
+
78
+ readonly isMobile = input<boolean>(false);
79
+ readonly isTablet = input<boolean>(false);
80
+
81
+ readonly isLoadingChanged = output<boolean>();
82
+ readonly attachmentViewed = output<any>();
83
+ readonly attachmentDownloaded = output<any>();
84
+ readonly errorOccurred = output<string>();
85
+
86
+ private readonly service = inject(HRSelfWidgetsService);
87
+
88
+ readonly groups = signal<any[]>([]);
89
+
90
+ ngOnInit(): void {
91
+ if (!this.baseUrl()) {
92
+ this.isLoading.set(false);
93
+ return;
94
+ }
95
+
96
+ this.isLoadingChanged.emit(true);
97
+
98
+ this.service.getDependentDocuments(this.baseUrl()).subscribe({
99
+ next: (res: any) => {
100
+ this.groups.set(res ?? []);
101
+ this.isLoading.set(false);
102
+ this.isLoadingChanged.emit(false);
103
+ },
104
+ error: (error: any) => {
105
+ this.groups.set([]);
106
+ this.isLoading.set(false);
107
+ this.errorOccurred.emit(error.error.ResponseData.Errors[0].Message);
108
+ this.isLoadingChanged.emit(false);
109
+ },
110
+ });
111
+ }
112
+
113
+ onAttachmentView(doc: any): void {
114
+ if (doc.Attachments?.length) {
115
+ this.attachmentViewed.emit(doc.Attachments[0]);
116
+ }
117
+ }
118
+
119
+ onDownload(group: any): void {
120
+ const attachments = group.Attachments;
121
+
122
+ if (!attachments.length) return;
123
+
124
+ this.attachmentDownloaded.emit(attachments);
125
+ }
126
+ }
@@ -0,0 +1,53 @@
1
+ @if (title) {
2
+ <div [class]="titleContainerClass">
3
+ <p [class]="titleClass">{{ title }}</p>
4
+ </div>
5
+ }
6
+
7
+ <div [class]="rowClass">
8
+ <div [class]="dataColClass">
9
+ <div class="row g-1">
10
+ <div [class]="typeColClass">
11
+ <p [class]="labelClass">{{ 'Type' | translate }}</p>
12
+ </div>
13
+
14
+ <div [class]="numberColClass">
15
+ <p [class]="labelClass">{{ 'DocumentNumber' | translate }}</p>
16
+ </div>
17
+
18
+ <div [class]="issueDateColClass">
19
+ <p [class]="labelClass">{{ 'IssueDate' | translate }}</p>
20
+ </div>
21
+
22
+ <div [class]="expiryDateColClass">
23
+ <p [class]="labelClass">{{ 'ExpiryDate' | translate }}</p>
24
+ </div>
25
+ </div>
26
+ </div>
27
+
28
+ <div [class]="actionsColClass"></div>
29
+ </div>
30
+
31
+ @for (doc of documents; track doc) {
32
+ <hr-document-row
33
+ [doc]="doc"
34
+ [valueClass]="valueClass"
35
+ [viewIcon]="viewIcon"
36
+ [downloadIcon]="downloadIcon"
37
+ [viewIconClass]="viewIconClass"
38
+ [downloadIconClass]="downloadIconClass"
39
+ [rowClass]="rowClass"
40
+ [dataColClass]="dataColClass"
41
+ [dataColSpacingClass]="dataColSpacingClass"
42
+ [dataRowClass]="dataRowClass"
43
+ [typeColClass]="typeColClass"
44
+ [numberColClass]="numberColClass"
45
+ [issueDateColClass]="issueDateColClass"
46
+ [expiryDateColClass]="expiryDateColClass"
47
+ [actionsColClass]="actionsColClass"
48
+ [actionsWrapperClass]="actionsWrapperClass"
49
+ [downloadContainerClass]="downloadContainerClass"
50
+ (attachmentView)="onAttachmentView($event)"
51
+ (download)="onDownload($event)"
52
+ ></hr-document-row>
53
+ }