@gloww/gloww 20.0.0-beta.4 → 20.0.0-beta.41

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,6 +1,6 @@
1
1
  import * as i0 from '@angular/core';
2
- import { InjectionToken, Injectable, HostListener, Input, Directive, Pipe, Inject, Component, EventEmitter, Output, HostBinding, ViewChild, ContentChildren, PLATFORM_ID, Optional, ContentChild, ViewEncapsulation, NgModule, SecurityContext, forwardRef } from '@angular/core';
3
- import { Subject, firstValueFrom, BehaviorSubject, Subscription, of, combineLatest, forkJoin, throwError } from 'rxjs';
2
+ import { InjectionToken, Injectable, HostListener, Input, Directive, Pipe, Inject, Component, EventEmitter, Output, HostBinding, ViewChild, ContentChildren, Optional, PLATFORM_ID, ContentChild, ViewEncapsulation, makeEnvironmentProviders, NgModule, SecurityContext, forwardRef } from '@angular/core';
3
+ import { Subject, firstValueFrom, BehaviorSubject, of, combineLatest, forkJoin, throwError } from 'rxjs';
4
4
  import * as i1 from '@angular/common/http';
5
5
  import { HttpClient, HttpParams, HttpEventType, HTTP_INTERCEPTORS, provideHttpClient, withInterceptorsFromDi, HttpResponse } from '@angular/common/http';
6
6
  import * as i3 from '@angular/common';
@@ -12,12 +12,11 @@ import * as i2 from '@angular/router';
12
12
  import { NavigationEnd, RouterLink, RouterModule } from '@angular/router';
13
13
  import { MatButton, MatButtonModule } from '@angular/material/button';
14
14
  import * as i1$1 from '@angular/platform-browser';
15
- import { BrowserModule } from '@angular/platform-browser';
16
15
  import * as i5 from '@kolkov/angular-editor';
17
16
  import { AngularEditorModule } from '@kolkov/angular-editor';
18
17
  import { switchMap, map, tap, filter, catchError, take, mergeMap, retryWhen, scan, delay, first, distinctUntilChanged, debounceTime } from 'rxjs/operators';
19
18
  import { MatSort, MatSortModule } from '@angular/material/sort';
20
- import { MatPaginator, MatPaginatorModule } from '@angular/material/paginator';
19
+ import { MatPaginator, MatPaginatorIntl, MatPaginatorModule } from '@angular/material/paginator';
21
20
  import { MatColumnDef, MatTableDataSource, MatTable, MatHeaderCellDef, MatHeaderCell, MatCellDef, MatCell, MatHeaderRowDef, MatHeaderRow, MatRowDef, MatRow, MatTableModule } from '@angular/material/table';
22
21
  import { MatProgressSpinner, MatProgressSpinnerModule } from '@angular/material/progress-spinner';
23
22
  import { MatCard, MatCardContent, MatCardActions, MatCardHeader, MatCardTitle, MatCardModule } from '@angular/material/card';
@@ -26,27 +25,27 @@ import { MatError, MatFormField, MatInput, MatLabel, MatInputModule, MatSuffix }
26
25
  import * as i4 from '@ctrl/ngx-codemirror';
27
26
  import { CodemirrorModule, CodemirrorComponent } from '@ctrl/ngx-codemirror';
28
27
  import * as i1$3 from '@angular/forms';
29
- import { NG_VALUE_ACCESSOR, FormsModule, UntypedFormControl, ReactiveFormsModule, Validators } from '@angular/forms';
28
+ import { NG_VALUE_ACCESSOR, FormsModule, UntypedFormControl, ReactiveFormsModule, Validators, FormControl } from '@angular/forms';
30
29
  import { MatProgressBar, MatProgressBarModule } from '@angular/material/progress-bar';
31
30
  import { MatDatepickerInput, MatDatepickerToggle, MatDatepicker, MatDatepickerModule } from '@angular/material/datepicker';
32
- import * as i2$1 from 'ngx-mat-datetime-picker-v2';
33
31
  import { NgxMatDatetimePickerModule, NgxMatTimepickerComponent, NgxMatNativeDateModule } from 'ngx-mat-datetime-picker-v2';
32
+ import moment from 'moment';
33
+ import * as i1$4 from '@ngx-translate/core';
34
+ import { TranslateDefaultParser } from '@ngx-translate/core';
34
35
  import { MatSelect, MatOption, MatSelectModule } from '@angular/material/select';
35
36
  import { trigger, state, style, transition, animate } from '@angular/animations';
36
- import prettier from 'node_modules/prettier/esm/standalone.mjs';
37
- import parserTypescript from 'node_modules/prettier/esm/parser-typescript.mjs';
38
- import parserBabel from 'node_modules/prettier/esm/parser-babel.mjs';
39
- import { BrowserAnimationsModule } from '@angular/platform-browser/animations';
37
+ import { MatListItem, MatListItemIcon, MatListItemTitle } from '@angular/material/list';
38
+ import * as prettier from 'prettier/standalone';
39
+ import * as parserTypescript from 'prettier/plugins/typescript';
40
+ import * as parserBabel from 'prettier/plugins/babel';
40
41
  import { MatToolbarModule } from '@angular/material/toolbar';
41
42
  import { MatSidenavModule } from '@angular/material/sidenav';
42
- import { MatFormFieldModule } from '@angular/material/form-field';
43
+ import { MatFormFieldModule, MatFormField as MatFormField$1, MatLabel as MatLabel$1 } from '@angular/material/form-field';
43
44
  import { jwtDecode } from 'jwt-decode';
44
45
  import { CdkDrag, CdkDragHandle, DragDropModule } from '@angular/cdk/drag-drop';
45
46
  import FileSaver from 'file-saver';
46
47
  import JSZip from 'jszip';
47
- import { TranslateDefaultParser } from '@ngx-translate/core';
48
48
  import { MatAutocompleteTrigger, MatAutocomplete, MatAutocompleteModule } from '@angular/material/autocomplete';
49
- import moment from 'moment';
50
49
  import { MAT_DATE_LOCALE } from '@angular/material/core';
51
50
  import { AngularResizeEventModule } from 'angular-resize-event';
52
51
 
@@ -223,7 +222,10 @@ class RouteDirective {
223
222
  }
224
223
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: RouteDirective, decorators: [{
225
224
  type: Directive,
226
- args: [{ selector: '[glowwRoute]' }]
225
+ args: [{
226
+ selector: '[glowwRoute]',
227
+ standalone: true
228
+ }]
227
229
  }], ctorParameters: () => [{ type: i0.ElementRef }, { type: i2.Router }], propDecorators: { dlg: [{
228
230
  type: Input
229
231
  }], onClick: [{
@@ -245,7 +247,10 @@ class SafeHtmlPipe {
245
247
  }
246
248
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: SafeHtmlPipe, decorators: [{
247
249
  type: Pipe,
248
- args: [{ name: 'safeHtml' }]
250
+ args: [{
251
+ name: 'safeHtml',
252
+ standalone: true
253
+ }]
249
254
  }], ctorParameters: () => [{ type: i1$1.DomSanitizer }] });
250
255
 
251
256
  class ConfirmationComponent {
@@ -455,7 +460,10 @@ class FileSinkDirective {
455
460
  }
456
461
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: FileSinkDirective, decorators: [{
457
462
  type: Directive,
458
- args: [{ selector: '[glowwFileSink]' }]
463
+ args: [{
464
+ selector: '[glowwFileSink]',
465
+ standalone: true
466
+ }]
459
467
  }], propDecorators: { fileOver: [{
460
468
  type: HostBinding,
461
469
  args: ['class.fileover']
@@ -739,8 +747,33 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImpo
739
747
  args: [MatColumnDef]
740
748
  }] } });
741
749
 
750
+ class GlowwI18nService {
751
+ constructor(translate) {
752
+ this.translate = translate;
753
+ }
754
+ get langChanges$() {
755
+ return this.translate?.onLangChange ?? of(null);
756
+ }
757
+ instant(key, fallback) {
758
+ if (!this.translate) {
759
+ return fallback;
760
+ }
761
+ const translated = this.translate.instant(key);
762
+ return translated && translated !== key ? translated : fallback;
763
+ }
764
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: GlowwI18nService, deps: [{ token: i1$4.TranslateService, optional: true }], target: i0.ɵɵFactoryTarget.Injectable }); }
765
+ static { this.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: GlowwI18nService, providedIn: 'root' }); }
766
+ }
767
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: GlowwI18nService, decorators: [{
768
+ type: Injectable,
769
+ args: [{ providedIn: 'root' }]
770
+ }], ctorParameters: () => [{ type: i1$4.TranslateService, decorators: [{
771
+ type: Optional
772
+ }] }] });
773
+
742
774
  class FilterFormComponent {
743
- constructor() {
775
+ constructor(i18n) {
776
+ this.i18n = i18n;
744
777
  this.filter = new EventEmitter();
745
778
  }
746
779
  ngOnInit() {
@@ -748,13 +781,16 @@ class FilterFormComponent {
748
781
  onFilter() {
749
782
  this.filter.emit("xxx");
750
783
  }
751
- static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: FilterFormComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
752
- static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "20.3.18", type: FilterFormComponent, isStandalone: true, selector: "glw-filter-form", outputs: { filter: "filter" }, ngImport: i0, template: "<mat-card appearance=\"outlined\">\r\n <mat-card-content>\r\n <ng-content></ng-content>\r\n </mat-card-content>\r\n <mat-card-actions align=\"end\">\r\n <button mat-stroked-button color=\"accent\" (click)=\"onFilter()\">\r\n <mat-icon>search</mat-icon>\r\n Filter\r\n </button>\r\n </mat-card-actions>\r\n</mat-card>", styles: [""], dependencies: [{ kind: "component", type: MatCard, selector: "mat-card", inputs: ["appearance"], exportAs: ["matCard"] }, { kind: "directive", type: MatCardContent, selector: "mat-card-content" }, { kind: "directive", type: MatCardActions, selector: "mat-card-actions", inputs: ["align"], exportAs: ["matCardActions"] }, { kind: "component", type: MatButton, selector: " button[matButton], a[matButton], button[mat-button], button[mat-raised-button], button[mat-flat-button], button[mat-stroked-button], a[mat-button], a[mat-raised-button], a[mat-flat-button], a[mat-stroked-button] ", inputs: ["matButton"], exportAs: ["matButton", "matAnchor"] }, { kind: "component", type: MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }] }); }
784
+ get filterLabel() {
785
+ return this.i18n.instant('COMMON.FILTER', 'Filter');
786
+ }
787
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: FilterFormComponent, deps: [{ token: GlowwI18nService }], target: i0.ɵɵFactoryTarget.Component }); }
788
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "20.3.18", type: FilterFormComponent, isStandalone: true, selector: "glw-filter-form", outputs: { filter: "filter" }, ngImport: i0, template: "<mat-card appearance=\"outlined\">\r\n <mat-card-content>\r\n <ng-content></ng-content>\r\n </mat-card-content>\r\n <mat-card-actions align=\"end\">\n <button mat-stroked-button color=\"accent\" (click)=\"onFilter()\">\n <mat-icon>search</mat-icon>\n {{ filterLabel }}\n </button>\n </mat-card-actions>\n</mat-card>\n", styles: [""], dependencies: [{ kind: "component", type: MatCard, selector: "mat-card", inputs: ["appearance"], exportAs: ["matCard"] }, { kind: "directive", type: MatCardContent, selector: "mat-card-content" }, { kind: "directive", type: MatCardActions, selector: "mat-card-actions", inputs: ["align"], exportAs: ["matCardActions"] }, { kind: "component", type: MatButton, selector: " button[matButton], a[matButton], button[mat-button], button[mat-raised-button], button[mat-flat-button], button[mat-stroked-button], a[mat-button], a[mat-raised-button], a[mat-flat-button], a[mat-stroked-button] ", inputs: ["matButton"], exportAs: ["matButton", "matAnchor"] }, { kind: "component", type: MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }] }); }
753
789
  }
754
790
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: FilterFormComponent, decorators: [{
755
791
  type: Component,
756
- args: [{ selector: 'glw-filter-form', imports: [MatCard, MatCardContent, MatCardActions, MatButton, MatIcon], template: "<mat-card appearance=\"outlined\">\r\n <mat-card-content>\r\n <ng-content></ng-content>\r\n </mat-card-content>\r\n <mat-card-actions align=\"end\">\r\n <button mat-stroked-button color=\"accent\" (click)=\"onFilter()\">\r\n <mat-icon>search</mat-icon>\r\n Filter\r\n </button>\r\n </mat-card-actions>\r\n</mat-card>" }]
757
- }], ctorParameters: () => [], propDecorators: { filter: [{
792
+ args: [{ selector: 'glw-filter-form', imports: [MatCard, MatCardContent, MatCardActions, MatButton, MatIcon], template: "<mat-card appearance=\"outlined\">\r\n <mat-card-content>\r\n <ng-content></ng-content>\r\n </mat-card-content>\r\n <mat-card-actions align=\"end\">\n <button mat-stroked-button color=\"accent\" (click)=\"onFilter()\">\n <mat-icon>search</mat-icon>\n {{ filterLabel }}\n </button>\n </mat-card-actions>\n</mat-card>\n" }]
793
+ }], ctorParameters: () => [{ type: GlowwI18nService }], propDecorators: { filter: [{
758
794
  type: Output
759
795
  }] } });
760
796
 
@@ -985,7 +1021,11 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImpo
985
1021
 
986
1022
  ;
987
1023
  class DisplayObjectsComponent {
988
- constructor(glowwService, changeDetectorRef, dialog, router, location, authenticationService, formBuilder, route) {
1024
+ static { this.DISPLAY_PARAM = '__display'; }
1025
+ static { this.DISPLAY_FORM = 'form'; }
1026
+ static { this.DISPLAY_RESULT = 'result'; }
1027
+ static { this.INTERNAL_QUERY_KEYS = new Set(['__guid', DisplayObjectsComponent.DISPLAY_PARAM]); }
1028
+ constructor(glowwService, changeDetectorRef, dialog, router, location, authenticationService, formBuilder, route, i18n) {
989
1029
  this.changeDetectorRef = changeDetectorRef;
990
1030
  this.dialog = dialog;
991
1031
  this.router = router;
@@ -993,6 +1033,7 @@ class DisplayObjectsComponent {
993
1033
  this.authenticationService = authenticationService;
994
1034
  this.formBuilder = formBuilder;
995
1035
  this.route = route;
1036
+ this.i18n = i18n;
996
1037
  this.canDisplayObj = false;
997
1038
  this.canEdit = true;
998
1039
  this.canDelete = true;
@@ -1004,7 +1045,7 @@ class DisplayObjectsComponent {
1004
1045
  this.displayform = true;
1005
1046
  this.displayresult = false;
1006
1047
  this.queryParams = {};
1007
- this.navSubscription = new Subscription();
1048
+ this.viewInitialized = false;
1008
1049
  this.currentFilter = null;
1009
1050
  this.glowwService = glowwService;
1010
1051
  const component = this;
@@ -1017,8 +1058,15 @@ class DisplayObjectsComponent {
1017
1058
  this.routeParams = this.route.snapshot.params;
1018
1059
  route.params.subscribe(routeParams => {
1019
1060
  this.routeParams = routeParams;
1020
- if (this.displayresult)
1021
- this.Search();
1061
+ if (this.viewInitialized) {
1062
+ this.applyRouteState(this.route.snapshot.queryParams);
1063
+ }
1064
+ });
1065
+ route.queryParams.subscribe(queryParams => {
1066
+ this.queryParams = { ...queryParams };
1067
+ if (this.viewInitialized) {
1068
+ this.applyRouteState(queryParams);
1069
+ }
1022
1070
  });
1023
1071
  }
1024
1072
  ngOnChanges(changes) {
@@ -1091,61 +1139,49 @@ class DisplayObjectsComponent {
1091
1139
  }
1092
1140
  //debugger;
1093
1141
  console.log(`INIT : formLayout:${this.searchFormLayout}-displayform:${this.displayform}`);
1094
- if (!this.searchFormLayout && this.resultLayout) {
1095
- this.displayform = false;
1096
- this.displayresult = true;
1097
- }
1098
- if (Object.keys(this.data).length > 0 && (this.data["__mode"] !== "edit")) {
1099
- this.displayform = false;
1100
- this.displayresult = true;
1101
- }
1102
- if (Object.keys(this.route.snapshot.params).length > 0 && (this.data["__mode"] !== "edit")) {
1103
- this.displayform = false;
1104
- this.displayresult = true;
1105
- }
1106
1142
  this.glowwService.basePathChange.subscribe(newUrl => {
1107
1143
  console.log(`basePathChange ${newUrl}: fromLayout:${this.searchFormLayout}-displayform:${this.displayform}`);
1108
1144
  this.parent.form?.reset();
1109
- if (!this.searchFormLayout && this.resultLayout) {
1110
- this.displayform = false;
1111
- this.displayresult = true;
1112
- }
1113
- if (this.displayresult) {
1114
- this.Search();
1115
- }
1145
+ this.applyRouteState(this.route.snapshot.queryParams);
1116
1146
  });
1117
- if (this.displayresult) {
1118
- this.Search();
1119
- }
1147
+ this.viewInitialized = true;
1148
+ this.applyRouteState(this.route.snapshot.queryParams);
1120
1149
  }
1121
1150
  ngAfterContentInit() {
1122
1151
  }
1123
1152
  ngOnInit() {
1124
- this.navSubscription = this.router.events.subscribe((e) => {
1125
- if (e instanceof NavigationEnd) {
1126
- this.parent.form?.reset();
1127
- this.displayform = true;
1128
- this.displayresult = false;
1129
- this.changeDetectorRef.detectChanges();
1130
- this.dataSource = null;
1131
- if (!this.searchFormLayout && this.resultLayout) {
1132
- this.displayform = false;
1133
- this.displayresult = true;
1134
- }
1135
- if (this.displayresult) {
1136
- this.Search();
1137
- }
1138
- }
1139
- });
1140
1153
  }
1141
1154
  ngOnDestroy() {
1142
- this.navSubscription?.unsubscribe(); // this prevents a memory leak
1155
+ }
1156
+ t(key, fallback) {
1157
+ return this.i18n.instant(key, fallback);
1143
1158
  }
1144
1159
  Init(data) {
1145
1160
  if ((data && Object.keys(data).length > 0) || this.displayresult) {
1146
1161
  this.Search(data);
1147
1162
  }
1148
1163
  }
1164
+ hasSearchState() {
1165
+ return this.displayresult || this.hasSearchQueryParams(this.route.snapshot.queryParams);
1166
+ }
1167
+ onBack() {
1168
+ const searchQuery = this.buildSearchQueryParams();
1169
+ if (!Object.keys(searchQuery).length) {
1170
+ this.showForm();
1171
+ this.syncFormWithQueryParams({});
1172
+ return;
1173
+ }
1174
+ this.router.navigate([], {
1175
+ relativeTo: this.route,
1176
+ queryParams: {
1177
+ ...searchQuery,
1178
+ [DisplayObjectsComponent.DISPLAY_PARAM]: DisplayObjectsComponent.DISPLAY_FORM
1179
+ }
1180
+ });
1181
+ }
1182
+ onRefresh() {
1183
+ this.Search();
1184
+ }
1149
1185
  SetFilterPredicate() {
1150
1186
  this.dataSource.filterPredicate = function (record, filterString) {
1151
1187
  console.log(filterString);
@@ -1199,9 +1235,9 @@ class DisplayObjectsComponent {
1199
1235
  console.log(`Search ${this.glowwService.InternalBasePath}`);
1200
1236
  if (data)
1201
1237
  this.data = data;
1202
- this.displayresult = true;
1203
- this.displayform = false;
1238
+ this.showResult();
1204
1239
  this.resultException = null;
1240
+ this.queryParams = {};
1205
1241
  if (this.data) {
1206
1242
  Object.keys(this.data).forEach(name => {
1207
1243
  this.queryParams[name] = this.data[name];
@@ -1212,11 +1248,20 @@ class DisplayObjectsComponent {
1212
1248
  this.queryParams[name] = this.routeParams[name];
1213
1249
  });
1214
1250
  }
1251
+ const routeQueryParams = this.route.snapshot.queryParams ?? {};
1252
+ Object.keys(routeQueryParams).forEach(name => {
1253
+ if (!DisplayObjectsComponent.INTERNAL_QUERY_KEYS.has(name)) {
1254
+ this.queryParams[name] = routeQueryParams[name];
1255
+ }
1256
+ });
1215
1257
  if (this.mandatoryParams) {
1216
1258
  Object.keys(this.mandatoryParams).forEach(name => {
1217
- this.queryParams[name] = this.queryParams[name];
1259
+ this.queryParams[name] = this.mandatoryParams[name];
1218
1260
  });
1219
1261
  }
1262
+ Object.keys(this.queryParams).forEach(name => {
1263
+ this.queryParams[name] = this.serializeQueryParamValue(this.queryParams[name]);
1264
+ });
1220
1265
  this.queryParams['__guid'] = (Math.random().toString()).substring(2);
1221
1266
  console.log("Before searchRequest");
1222
1267
  //debugger;
@@ -1233,9 +1278,8 @@ class DisplayObjectsComponent {
1233
1278
  this.changeDetectorRef.detectChanges();
1234
1279
  this.UpdateTable();
1235
1280
  }, error => {
1236
- this.displayresult = false;
1237
- this.displayform = true;
1238
- this.resultException = error;
1281
+ this.showForm();
1282
+ this.resultException = this.toErrorMessage(error);
1239
1283
  });
1240
1284
  }
1241
1285
  clean(obj) {
@@ -1246,22 +1290,25 @@ class DisplayObjectsComponent {
1246
1290
  }
1247
1291
  }
1248
1292
  onSearch() {
1249
- this.queryParams = {};
1250
- const searchData = this.parent.form.value.searchData;
1251
- if (searchData) {
1252
- Object.keys(searchData).forEach(name => {
1253
- const val = searchData[name];
1254
- this.queryParams[name] = val;
1255
- });
1293
+ this.router.navigate([], {
1294
+ relativeTo: this.route,
1295
+ queryParams: {
1296
+ ...this.buildSearchQueryParams(),
1297
+ [DisplayObjectsComponent.DISPLAY_PARAM]: DisplayObjectsComponent.DISPLAY_RESULT
1298
+ }
1299
+ });
1300
+ }
1301
+ serializeQueryParamValue(value) {
1302
+ if (value === undefined || value === null || value === '') {
1303
+ return value;
1256
1304
  }
1257
- if (this.form2.value._MaxRow_) {
1258
- this.queryParams._MaxRow_ = this.form2.value._MaxRow_;
1305
+ if (value instanceof Date) {
1306
+ return Number.isNaN(value.getTime()) ? null : moment(value).format('YYYY-MM-DD HH:mm:ss');
1259
1307
  }
1260
- this.clean(this.queryParams);
1261
- const params = new HttpParams({ fromObject: this.queryParams });
1262
- const currentstate = this.location.getState();
1263
- this.location.replaceState(this.router.url, params.toString());
1264
- this.Search();
1308
+ if (moment.isMoment(value)) {
1309
+ return value.isValid() ? value.format('YYYY-MM-DD HH:mm:ss') : null;
1310
+ }
1311
+ return value;
1265
1312
  }
1266
1313
  onFilter() {
1267
1314
  }
@@ -1418,9 +1465,10 @@ class DisplayObjectsComponent {
1418
1465
  dialogConfig.disableClose = true;
1419
1466
  dialogConfig.autoFocus = true;
1420
1467
  dialogConfig.closeOnNavigation = false;
1421
- dialogConfig.maxHeight = "95%";
1422
- dialogConfig.maxWidth = "95%";
1423
- dialogConfig.height = "100%";
1468
+ dialogConfig.panelClass = 'gw-resizable-dialog-panel';
1469
+ dialogConfig.width = '900px';
1470
+ dialogConfig.maxWidth = '100vw';
1471
+ dialogConfig.maxHeight = '100vh';
1424
1472
  if (this.dialogConfig) {
1425
1473
  Object.keys(this.dialogConfig).forEach(name => {
1426
1474
  dialogConfig[name] = this.dialogConfig[name];
@@ -1476,14 +1524,14 @@ class DisplayObjectsComponent {
1476
1524
  });
1477
1525
  }
1478
1526
  DeleteObj(obj) {
1479
- if (confirm('Are you sure you want to delete this objet ? ')) {
1527
+ if (confirm(this.t('GLOWW.CONFIRM_DELETE', 'Are you sure you want to delete this object ?'))) {
1480
1528
  this.deleteRequest.apply(this.glowwService, this.getPrimaryKey(obj)).subscribe(p => {
1481
1529
  const i = this.dataSource.data.indexOf(obj);
1482
1530
  const tmp = this.dataSource.data;
1483
1531
  tmp.splice(i, 1);
1484
1532
  this.dataSource.data = tmp;
1485
1533
  }, error => {
1486
- alert(`Unable to delete Object ${error.status} ${error.statusText}\n${error.Message}\n${error.error}`);
1534
+ alert(`${this.t('GLOWW.UNABLE_TO_DELETE_OBJECT', 'Unable to delete object')} ${error.status} ${error.statusText}\n${error.Message}\n${error.error}`);
1487
1535
  });
1488
1536
  }
1489
1537
  }
@@ -1508,9 +1556,10 @@ class DisplayObjectsComponent {
1508
1556
  dialogConfig.disableClose = true;
1509
1557
  dialogConfig.autoFocus = true;
1510
1558
  dialogConfig.closeOnNavigation = false;
1511
- dialogConfig.maxHeight = "95%";
1512
- dialogConfig.maxWidth = "95%";
1513
- dialogConfig.height = "100%";
1559
+ dialogConfig.panelClass = 'gw-resizable-dialog-panel';
1560
+ dialogConfig.width = '900px';
1561
+ dialogConfig.maxWidth = '100vw';
1562
+ dialogConfig.maxHeight = '100vh';
1514
1563
  if (this.dialogConfig) {
1515
1564
  Object.keys(this.dialogConfig).forEach(name => {
1516
1565
  dialogConfig[name] = this.dialogConfig[name];
@@ -1559,16 +1608,113 @@ class DisplayObjectsComponent {
1559
1608
  }
1560
1609
  });
1561
1610
  }
1562
- static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: DisplayObjectsComponent, deps: [{ token: 'glowwService' }, { token: i0.ChangeDetectorRef }, { token: i1$2.MatDialog }, { token: i2.Router }, { token: i3.Location }, { token: AuthenticationService }, { token: i1$3.UntypedFormBuilder }, { token: i2.ActivatedRoute }], target: i0.ɵɵFactoryTarget.Component }); }
1563
- static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.18", type: DisplayObjectsComponent, isStandalone: true, selector: "glw-display-objects", inputs: { configuration: "configuration", displayObjLink: "displayObjLink", canDisplayObj: "canDisplayObj", canEdit: "canEdit", canDelete: "canDelete", canAdd: "canAdd", form: "form", SearchForm: "SearchForm", searchRequest: "searchRequest", postRequest: "postRequest", deleteRequest: "deleteRequest", putRequest: "putRequest", maxrows: "maxrows", mandatoryParams: "mandatoryParams", actions: "actions", dialogConfig: "dialogConfig", parent: "parent", columns: "columns", objectName: "objectName", primaryKey: "primaryKey", Editor: "Editor", AddEditor: "AddEditor" }, queries: [{ propertyName: "header", first: true, predicate: HeaderComponent, descendants: true }, { propertyName: "searchFormLayout", first: true, predicate: SearchFormComponent, descendants: true }, { propertyName: "filterFormLayout", first: true, predicate: FilterFormComponent, descendants: true }, { propertyName: "resultLayout", first: true, predicate: ResultTableComponent, descendants: true }], viewQueries: [{ propertyName: "table", first: true, predicate: MatTable, descendants: true }, { propertyName: "paginator", first: true, predicate: MatPaginator, descendants: true }, { propertyName: "sort", first: true, predicate: MatSort, descendants: true }], usesOnChanges: true, ngImport: i0, template: "<div>\n <ng-content select=\"glw-header\"></ng-content>\n</div>\n\n@if (displayform) {\n <div>\n <mat-card appearance=\"outlined\">\n <mat-card-content>\n @if (resultException) {\n <mat-error>\n Unable to query : {{resultException}}\n </mat-error>\n }\n <ng-content select=\"glw-search-form\"></ng-content>\n <!--<ng-container *ngComponentOutlet=\"SearchForm; injector: objInjector\"></ng-container>-->\n @if (maxrows) {\n <div [formGroup]=\"form2\">\n <br />\n <mat-form-field>\n <mat-select placeholder=\"MaxRow\" formControlName=\"_MaxRow_\">\n @for (maxrow of maxrows; track maxrow) {\n <mat-option [value]=\"maxrow\">\n @if (maxrow) {\n <span>{{maxrow}} objects</span>\n }\n @if (!maxrow) {\n <span> Default</span>\n }\n </mat-option>\n }\n </mat-select>\n </mat-form-field>\n </div>\n }\n </mat-card-content>\n <mat-card-actions>\n <button mat-stroked-button color=\"accent\" (click)=\"onSearch()\">\n <mat-icon>search</mat-icon>\n Search\n </button>\n </mat-card-actions>\n </mat-card>\n </div>\n}\n\n<div [hidden]=\"!displayresult\">\n <!--*ngIf=\"displayresult\"-->\n <div class=\"mat-elevation-z8\" [hidden]=\"!dataSource\">\n <ng-content select=\"[filter]\"></ng-content>\n\n <!--*ngIf=\"dataSource; else Spinner\"-->\n <table mat-table [dataSource]=\"dataSource\" matSort>\n <ng-container matColumnDef=\"action\">\n <th mat-header-cell *matHeaderCellDef>\n @if (canAddThis()) {\n <i class=\"fal fa-plus\" (click)=\"AddObj()\">\n </i>\n }\n </th>\n <td mat-cell *matCellDef=\"let obj\">\n @if (canDisplayObjThis(obj)) {\n <i class=\"fal fa-eye\" [routerLink]=\"displayObjLinkThis(obj)\">\n </i>\n }\n @for (action of actions; track action) {\n @if (action.icon.icon && (!action.display || action.display(obj, action.name))) {\n <i [ngClass]=\"action.icon\" [routerLink]=\"action.routerLinkFct(obj)\">\n </i>\n }\n @if (!action.icon.icon && (!action.display || action.display(obj, action.name))) {\n <i [ngClass]=\"action.icon\" [routerLink]=\"action.routerLinkFct(obj)\"></i>\n }\n }\n @if (canDeleteThis(obj)) {\n <i class=\"fal fa-trash-alt\" (click)=\"DeleteObj(obj)\">\n </i>\n }\n @if (canEditThis(obj)) {\n <i class=\"fal fa-pencil\" (click)=\"EditObj(obj)\">\n </i>\n }\n </td>\n </ng-container>\n <ng-content select=\"glw-result-table\"></ng-content>\n <tr mat-header-row *matHeaderRowDef=\"columnsToDisplay\"></tr>\n <tr mat-row *matRowDef=\"let myRowData; columns: columnsToDisplay\"></tr>\n </table>\n <mat-paginator pageSize=\"10\"></mat-paginator>\n </div>\n <div #Spinner [hidden]=\"dataSource\">\n <mat-spinner></mat-spinner>\n </div>\n</div>\n", styles: ["table{width:100%}i{cursor:pointer;padding:5px}\n"], dependencies: [{ kind: "component", type: MatCard, selector: "mat-card", inputs: ["appearance"], exportAs: ["matCard"] }, { kind: "directive", type: MatCardContent, selector: "mat-card-content" }, { kind: "directive", type: MatError, selector: "mat-error, [matError]", inputs: ["id"] }, { kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1$3.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1$3.NgControlStatusGroup, selector: "[formGroupName],[formArrayName],[ngModelGroup],[formGroup],form:not([ngNoForm]),[ngForm]" }, { kind: "ngmodule", type: ReactiveFormsModule }, { kind: "directive", type: i1$3.FormGroupDirective, selector: "[formGroup]", inputs: ["formGroup"], outputs: ["ngSubmit"], exportAs: ["ngForm"] }, { kind: "directive", type: i1$3.FormControlName, selector: "[formControlName]", inputs: ["formControlName", "disabled", "ngModel"], outputs: ["ngModelChange"] }, { kind: "component", type: MatFormField, selector: "mat-form-field", inputs: ["hideRequiredMarker", "color", "floatLabel", "appearance", "subscriptSizing", "hintLabel"], exportAs: ["matFormField"] }, { kind: "component", type: MatSelect, selector: "mat-select", inputs: ["aria-describedby", "panelClass", "disabled", "disableRipple", "tabIndex", "hideSingleSelectionIndicator", "placeholder", "required", "multiple", "disableOptionCentering", "compareWith", "value", "aria-label", "aria-labelledby", "errorStateMatcher", "typeaheadDebounceInterval", "sortComparator", "id", "panelWidth", "canSelectNullableOptions"], outputs: ["openedChange", "opened", "closed", "selectionChange", "valueChange"], exportAs: ["matSelect"] }, { kind: "component", type: MatOption, selector: "mat-option", inputs: ["value", "id", "disabled"], outputs: ["onSelectionChange"], exportAs: ["matOption"] }, { kind: "directive", type: MatCardActions, selector: "mat-card-actions", inputs: ["align"], exportAs: ["matCardActions"] }, { kind: "component", type: MatButton, selector: " button[matButton], a[matButton], button[mat-button], button[mat-raised-button], button[mat-flat-button], button[mat-stroked-button], a[mat-button], a[mat-raised-button], a[mat-flat-button], a[mat-stroked-button] ", inputs: ["matButton"], exportAs: ["matButton", "matAnchor"] }, { kind: "component", type: MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: MatTable, selector: "mat-table, table[mat-table]", exportAs: ["matTable"] }, { kind: "directive", type: MatSort, selector: "[matSort]", inputs: ["matSortActive", "matSortStart", "matSortDirection", "matSortDisableClear", "matSortDisabled"], outputs: ["matSortChange"], exportAs: ["matSort"] }, { kind: "directive", type: MatColumnDef, selector: "[matColumnDef]", inputs: ["matColumnDef"] }, { kind: "directive", type: MatHeaderCellDef, selector: "[matHeaderCellDef]" }, { kind: "directive", type: MatHeaderCell, selector: "mat-header-cell, th[mat-header-cell]" }, { kind: "directive", type: MatCellDef, selector: "[matCellDef]" }, { kind: "directive", type: MatCell, selector: "mat-cell, td[mat-cell]" }, { kind: "directive", type: RouterLink, selector: "[routerLink]", inputs: ["target", "queryParams", "fragment", "queryParamsHandling", "state", "info", "relativeTo", "preserveFragment", "skipLocationChange", "replaceUrl", "routerLink"] }, { kind: "directive", type: NgClass, selector: "[ngClass]", inputs: ["class", "ngClass"] }, { kind: "directive", type: MatHeaderRowDef, selector: "[matHeaderRowDef]", inputs: ["matHeaderRowDef", "matHeaderRowDefSticky"] }, { kind: "component", type: MatHeaderRow, selector: "mat-header-row, tr[mat-header-row]", exportAs: ["matHeaderRow"] }, { kind: "directive", type: MatRowDef, selector: "[matRowDef]", inputs: ["matRowDefColumns", "matRowDefWhen"] }, { kind: "component", type: MatRow, selector: "mat-row, tr[mat-row]", exportAs: ["matRow"] }, { kind: "component", type: MatPaginator, selector: "mat-paginator", inputs: ["color", "pageIndex", "length", "pageSize", "pageSizeOptions", "hidePageSize", "showFirstLastButtons", "selectConfig", "disabled"], outputs: ["page"], exportAs: ["matPaginator"] }, { kind: "component", type: MatProgressSpinner, selector: "mat-progress-spinner, mat-spinner", inputs: ["color", "mode", "value", "diameter", "strokeWidth"], exportAs: ["matProgressSpinner"] }] }); }
1611
+ toErrorMessage(error) {
1612
+ if (!error) {
1613
+ return '';
1614
+ }
1615
+ const details = error.error?.message || error.error || error.message || error.statusText || `${error}`;
1616
+ return `${this.t('GLOWW.UNABLE_TO_QUERY', 'Unable to query')} : ${details}`;
1617
+ }
1618
+ applyRouteState(queryParams) {
1619
+ this.dataSource = null;
1620
+ this.resultException = null;
1621
+ this.queryParams = { ...(queryParams ?? {}) };
1622
+ this.syncFormWithQueryParams(this.queryParams);
1623
+ if (this.shouldDisplayForm(this.queryParams)) {
1624
+ this.showForm();
1625
+ this.changeDetectorRef.detectChanges();
1626
+ return;
1627
+ }
1628
+ if (this.shouldDisplayResult(this.queryParams)) {
1629
+ this.showResult();
1630
+ this.changeDetectorRef.detectChanges();
1631
+ this.Search();
1632
+ return;
1633
+ }
1634
+ this.showForm();
1635
+ this.changeDetectorRef.detectChanges();
1636
+ }
1637
+ shouldDisplayForm(queryParams) {
1638
+ if (!this.searchFormLayout) {
1639
+ return false;
1640
+ }
1641
+ return queryParams?.[DisplayObjectsComponent.DISPLAY_PARAM] === DisplayObjectsComponent.DISPLAY_FORM;
1642
+ }
1643
+ shouldDisplayResult(queryParams) {
1644
+ if (!this.searchFormLayout && this.resultLayout) {
1645
+ return true;
1646
+ }
1647
+ if (Object.keys(this.data ?? {}).length > 0 && (this.data["__mode"] !== "edit")) {
1648
+ return true;
1649
+ }
1650
+ if (Object.keys(this.routeParams ?? {}).length > 0 && (this.data["__mode"] !== "edit")) {
1651
+ return true;
1652
+ }
1653
+ return queryParams?.[DisplayObjectsComponent.DISPLAY_PARAM] === DisplayObjectsComponent.DISPLAY_RESULT
1654
+ || this.hasSearchQueryParams(queryParams);
1655
+ }
1656
+ hasSearchQueryParams(queryParams) {
1657
+ if (!queryParams) {
1658
+ return false;
1659
+ }
1660
+ return Object.keys(queryParams).some(key => !DisplayObjectsComponent.INTERNAL_QUERY_KEYS.has(key) &&
1661
+ queryParams[key] !== null &&
1662
+ queryParams[key] !== undefined &&
1663
+ queryParams[key] !== '');
1664
+ }
1665
+ syncFormWithQueryParams(queryParams) {
1666
+ const searchData = {};
1667
+ Object.keys(queryParams ?? {}).forEach(key => {
1668
+ if (DisplayObjectsComponent.INTERNAL_QUERY_KEYS.has(key) || key === '_MaxRow_') {
1669
+ return;
1670
+ }
1671
+ searchData[key] = queryParams[key];
1672
+ });
1673
+ const parentForm = this.parent?.form;
1674
+ if (parentForm?.contains('searchData')) {
1675
+ parentForm.patchValue({
1676
+ searchData: Object.keys(searchData).length ? searchData : null
1677
+ }, { emitEvent: false });
1678
+ }
1679
+ if (this.form2?.contains('_MaxRow_')) {
1680
+ this.form2.patchValue({
1681
+ _MaxRow_: queryParams?._MaxRow_ ?? null
1682
+ }, { emitEvent: false });
1683
+ }
1684
+ }
1685
+ buildSearchQueryParams() {
1686
+ const nextQueryParams = {};
1687
+ const searchData = this.parent?.form?.value?.searchData;
1688
+ const form2Value = this.form2.value;
1689
+ if (searchData) {
1690
+ Object.keys(searchData).forEach(name => {
1691
+ nextQueryParams[name] = this.serializeQueryParamValue(searchData[name]);
1692
+ });
1693
+ }
1694
+ if (form2Value._MaxRow_) {
1695
+ nextQueryParams._MaxRow_ = form2Value._MaxRow_;
1696
+ }
1697
+ this.clean(nextQueryParams);
1698
+ return nextQueryParams;
1699
+ }
1700
+ showForm() {
1701
+ this.displayform = true;
1702
+ this.displayresult = false;
1703
+ }
1704
+ showResult() {
1705
+ this.displayform = false;
1706
+ this.displayresult = true;
1707
+ }
1708
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: DisplayObjectsComponent, deps: [{ token: 'glowwService' }, { token: i0.ChangeDetectorRef }, { token: i1$2.MatDialog }, { token: i2.Router }, { token: i3.Location }, { token: AuthenticationService }, { token: i1$3.UntypedFormBuilder }, { token: i2.ActivatedRoute }, { token: GlowwI18nService }], target: i0.ɵɵFactoryTarget.Component }); }
1709
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.18", type: DisplayObjectsComponent, isStandalone: true, selector: "glw-display-objects", inputs: { configuration: "configuration", displayObjLink: "displayObjLink", canDisplayObj: "canDisplayObj", canEdit: "canEdit", canDelete: "canDelete", canAdd: "canAdd", form: "form", SearchForm: "SearchForm", searchRequest: "searchRequest", postRequest: "postRequest", deleteRequest: "deleteRequest", putRequest: "putRequest", maxrows: "maxrows", mandatoryParams: "mandatoryParams", actions: "actions", dialogConfig: "dialogConfig", parent: "parent", columns: "columns", objectName: "objectName", primaryKey: "primaryKey", Editor: "Editor", AddEditor: "AddEditor" }, queries: [{ propertyName: "header", first: true, predicate: HeaderComponent, descendants: true }, { propertyName: "searchFormLayout", first: true, predicate: SearchFormComponent, descendants: true }, { propertyName: "filterFormLayout", first: true, predicate: FilterFormComponent, descendants: true }, { propertyName: "resultLayout", first: true, predicate: ResultTableComponent, descendants: true }], viewQueries: [{ propertyName: "table", first: true, predicate: MatTable, descendants: true }, { propertyName: "paginator", first: true, predicate: MatPaginator, descendants: true }, { propertyName: "sort", first: true, predicate: MatSort, descendants: true }], usesOnChanges: true, ngImport: i0, template: "<div>\n <ng-content select=\"glw-header\"></ng-content>\n</div>\n\n@if (displayform) {\n <div>\n <mat-card appearance=\"outlined\">\n <mat-card-content>\n @if (resultException) {\n <mat-error>\n {{ resultException }}\n </mat-error>\n }\n <ng-content select=\"glw-search-form\"></ng-content>\n <!--<ng-container *ngComponentOutlet=\"SearchForm; injector: objInjector\"></ng-container>-->\n @if (maxrows) {\n <div [formGroup]=\"form2\">\n <br />\n <mat-form-field>\n <mat-select [placeholder]=\"t('COMMON.MAX_ROW', 'MaxRow')\" formControlName=\"_MaxRow_\">\n @for (maxrow of maxrows; track maxrow) {\n <mat-option [value]=\"maxrow\">\n @if (maxrow) {\n <span>{{maxrow}} {{ t('COMMON.OBJECTS_SUFFIX', 'objects') }}</span>\n }\n @if (!maxrow) {\n <span>{{ t('COMMON.DEFAULT', 'Default') }}</span>\n }\n </mat-option>\n }\n </mat-select>\n </mat-form-field>\n </div>\n }\n </mat-card-content>\n <mat-card-actions>\n <button mat-stroked-button color=\"accent\" (click)=\"onSearch()\">\n <mat-icon>search</mat-icon>\n {{ t('COMMON.SEARCH', 'Search') }}\n </button>\n </mat-card-actions>\n </mat-card>\n </div>\n}\n\n<div [hidden]=\"!displayresult\">\n <!--*ngIf=\"displayresult\"-->\n <div class=\"mat-elevation-z8\" [hidden]=\"!dataSource\">\n <ng-content select=\"[filter]\"></ng-content>\n\n <!--*ngIf=\"dataSource; else Spinner\"-->\n <table mat-table [dataSource]=\"dataSource\" matSort>\n <ng-container matColumnDef=\"action\">\n <th mat-header-cell *matHeaderCellDef>\n @if (hasSearchState()) {\n <i class=\"fal fa-arrow-left\" (click)=\"onBack()\" [attr.title]=\"t('COMMON.BACK', 'Back')\">\n </i>\n <i class=\"fal fa-rotate-right\" (click)=\"onRefresh()\" [attr.title]=\"t('COMMON.REFRESH', 'Refresh')\">\n </i>\n }\n @if (canAddThis()) {\n <i class=\"fal fa-plus\" (click)=\"AddObj()\">\n </i>\n }\n </th>\n <td mat-cell *matCellDef=\"let obj\">\n @if (canDisplayObjThis(obj)) {\n <i class=\"fal fa-eye\" [routerLink]=\"displayObjLinkThis(obj)\">\n </i>\n }\n @for (action of actions; track action) {\n @if (action.icon.icon && (!action.display || action.display(obj, action.name))) {\n <i [ngClass]=\"action.icon\" [routerLink]=\"action.routerLinkFct(obj)\">\n </i>\n }\n @if (!action.icon.icon && (!action.display || action.display(obj, action.name))) {\n <i [ngClass]=\"action.icon\" [routerLink]=\"action.routerLinkFct(obj)\"></i>\n }\n }\n @if (canDeleteThis(obj)) {\n <i class=\"fal fa-trash-alt\" (click)=\"DeleteObj(obj)\">\n </i>\n }\n @if (canEditThis(obj)) {\n <i class=\"fal fa-pencil\" (click)=\"EditObj(obj)\">\n </i>\n }\n </td>\n </ng-container>\n <ng-content select=\"glw-result-table\"></ng-content>\n <tr mat-header-row *matHeaderRowDef=\"columnsToDisplay\"></tr>\n <tr mat-row *matRowDef=\"let myRowData; columns: columnsToDisplay\"></tr>\n </table>\n <mat-paginator [pageSize]=\"10\" [pageSizeOptions]=\"[10, 20, 50, 100]\" [showFirstLastButtons]=\"true\"></mat-paginator>\n </div>\n <div #Spinner [hidden]=\"dataSource\">\n <mat-spinner></mat-spinner>\n </div>\n</div>\n", styles: ["table{width:100%}i{cursor:pointer;padding:5px}\n"], dependencies: [{ kind: "component", type: MatCard, selector: "mat-card", inputs: ["appearance"], exportAs: ["matCard"] }, { kind: "directive", type: MatCardContent, selector: "mat-card-content" }, { kind: "directive", type: MatError, selector: "mat-error, [matError]", inputs: ["id"] }, { kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1$3.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1$3.NgControlStatusGroup, selector: "[formGroupName],[formArrayName],[ngModelGroup],[formGroup],form:not([ngNoForm]),[ngForm]" }, { kind: "ngmodule", type: ReactiveFormsModule }, { kind: "directive", type: i1$3.FormGroupDirective, selector: "[formGroup]", inputs: ["formGroup"], outputs: ["ngSubmit"], exportAs: ["ngForm"] }, { kind: "directive", type: i1$3.FormControlName, selector: "[formControlName]", inputs: ["formControlName", "disabled", "ngModel"], outputs: ["ngModelChange"] }, { kind: "component", type: MatFormField, selector: "mat-form-field", inputs: ["hideRequiredMarker", "color", "floatLabel", "appearance", "subscriptSizing", "hintLabel"], exportAs: ["matFormField"] }, { kind: "component", type: MatSelect, selector: "mat-select", inputs: ["aria-describedby", "panelClass", "disabled", "disableRipple", "tabIndex", "hideSingleSelectionIndicator", "placeholder", "required", "multiple", "disableOptionCentering", "compareWith", "value", "aria-label", "aria-labelledby", "errorStateMatcher", "typeaheadDebounceInterval", "sortComparator", "id", "panelWidth", "canSelectNullableOptions"], outputs: ["openedChange", "opened", "closed", "selectionChange", "valueChange"], exportAs: ["matSelect"] }, { kind: "component", type: MatOption, selector: "mat-option", inputs: ["value", "id", "disabled"], outputs: ["onSelectionChange"], exportAs: ["matOption"] }, { kind: "directive", type: MatCardActions, selector: "mat-card-actions", inputs: ["align"], exportAs: ["matCardActions"] }, { kind: "component", type: MatButton, selector: " button[matButton], a[matButton], button[mat-button], button[mat-raised-button], button[mat-flat-button], button[mat-stroked-button], a[mat-button], a[mat-raised-button], a[mat-flat-button], a[mat-stroked-button] ", inputs: ["matButton"], exportAs: ["matButton", "matAnchor"] }, { kind: "component", type: MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: MatTable, selector: "mat-table, table[mat-table]", exportAs: ["matTable"] }, { kind: "directive", type: MatSort, selector: "[matSort]", inputs: ["matSortActive", "matSortStart", "matSortDirection", "matSortDisableClear", "matSortDisabled"], outputs: ["matSortChange"], exportAs: ["matSort"] }, { kind: "directive", type: MatColumnDef, selector: "[matColumnDef]", inputs: ["matColumnDef"] }, { kind: "directive", type: MatHeaderCellDef, selector: "[matHeaderCellDef]" }, { kind: "directive", type: MatHeaderCell, selector: "mat-header-cell, th[mat-header-cell]" }, { kind: "directive", type: MatCellDef, selector: "[matCellDef]" }, { kind: "directive", type: MatCell, selector: "mat-cell, td[mat-cell]" }, { kind: "directive", type: RouterLink, selector: "[routerLink]", inputs: ["target", "queryParams", "fragment", "queryParamsHandling", "state", "info", "relativeTo", "preserveFragment", "skipLocationChange", "replaceUrl", "routerLink"] }, { kind: "directive", type: NgClass, selector: "[ngClass]", inputs: ["class", "ngClass"] }, { kind: "directive", type: MatHeaderRowDef, selector: "[matHeaderRowDef]", inputs: ["matHeaderRowDef", "matHeaderRowDefSticky"] }, { kind: "component", type: MatHeaderRow, selector: "mat-header-row, tr[mat-header-row]", exportAs: ["matHeaderRow"] }, { kind: "directive", type: MatRowDef, selector: "[matRowDef]", inputs: ["matRowDefColumns", "matRowDefWhen"] }, { kind: "component", type: MatRow, selector: "mat-row, tr[mat-row]", exportAs: ["matRow"] }, { kind: "component", type: MatPaginator, selector: "mat-paginator", inputs: ["color", "pageIndex", "length", "pageSize", "pageSizeOptions", "hidePageSize", "showFirstLastButtons", "selectConfig", "disabled"], outputs: ["page"], exportAs: ["matPaginator"] }, { kind: "component", type: MatProgressSpinner, selector: "mat-progress-spinner, mat-spinner", inputs: ["color", "mode", "value", "diameter", "strokeWidth"], exportAs: ["matProgressSpinner"] }, { kind: "ngmodule", type: MatDialogModule }] }); }
1564
1710
  }
1565
1711
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: DisplayObjectsComponent, decorators: [{
1566
1712
  type: Component,
1567
- args: [{ selector: 'glw-display-objects', imports: [MatCard, MatCardContent, MatError, FormsModule, ReactiveFormsModule, MatFormField, MatSelect, MatOption, MatCardActions, MatButton, MatIcon, MatTable, MatSort, MatColumnDef, MatHeaderCellDef, MatHeaderCell, MatCellDef, MatCell, RouterLink, NgClass, MatHeaderRowDef, MatHeaderRow, MatRowDef, MatRow, MatPaginator, MatProgressSpinner], template: "<div>\n <ng-content select=\"glw-header\"></ng-content>\n</div>\n\n@if (displayform) {\n <div>\n <mat-card appearance=\"outlined\">\n <mat-card-content>\n @if (resultException) {\n <mat-error>\n Unable to query : {{resultException}}\n </mat-error>\n }\n <ng-content select=\"glw-search-form\"></ng-content>\n <!--<ng-container *ngComponentOutlet=\"SearchForm; injector: objInjector\"></ng-container>-->\n @if (maxrows) {\n <div [formGroup]=\"form2\">\n <br />\n <mat-form-field>\n <mat-select placeholder=\"MaxRow\" formControlName=\"_MaxRow_\">\n @for (maxrow of maxrows; track maxrow) {\n <mat-option [value]=\"maxrow\">\n @if (maxrow) {\n <span>{{maxrow}} objects</span>\n }\n @if (!maxrow) {\n <span> Default</span>\n }\n </mat-option>\n }\n </mat-select>\n </mat-form-field>\n </div>\n }\n </mat-card-content>\n <mat-card-actions>\n <button mat-stroked-button color=\"accent\" (click)=\"onSearch()\">\n <mat-icon>search</mat-icon>\n Search\n </button>\n </mat-card-actions>\n </mat-card>\n </div>\n}\n\n<div [hidden]=\"!displayresult\">\n <!--*ngIf=\"displayresult\"-->\n <div class=\"mat-elevation-z8\" [hidden]=\"!dataSource\">\n <ng-content select=\"[filter]\"></ng-content>\n\n <!--*ngIf=\"dataSource; else Spinner\"-->\n <table mat-table [dataSource]=\"dataSource\" matSort>\n <ng-container matColumnDef=\"action\">\n <th mat-header-cell *matHeaderCellDef>\n @if (canAddThis()) {\n <i class=\"fal fa-plus\" (click)=\"AddObj()\">\n </i>\n }\n </th>\n <td mat-cell *matCellDef=\"let obj\">\n @if (canDisplayObjThis(obj)) {\n <i class=\"fal fa-eye\" [routerLink]=\"displayObjLinkThis(obj)\">\n </i>\n }\n @for (action of actions; track action) {\n @if (action.icon.icon && (!action.display || action.display(obj, action.name))) {\n <i [ngClass]=\"action.icon\" [routerLink]=\"action.routerLinkFct(obj)\">\n </i>\n }\n @if (!action.icon.icon && (!action.display || action.display(obj, action.name))) {\n <i [ngClass]=\"action.icon\" [routerLink]=\"action.routerLinkFct(obj)\"></i>\n }\n }\n @if (canDeleteThis(obj)) {\n <i class=\"fal fa-trash-alt\" (click)=\"DeleteObj(obj)\">\n </i>\n }\n @if (canEditThis(obj)) {\n <i class=\"fal fa-pencil\" (click)=\"EditObj(obj)\">\n </i>\n }\n </td>\n </ng-container>\n <ng-content select=\"glw-result-table\"></ng-content>\n <tr mat-header-row *matHeaderRowDef=\"columnsToDisplay\"></tr>\n <tr mat-row *matRowDef=\"let myRowData; columns: columnsToDisplay\"></tr>\n </table>\n <mat-paginator pageSize=\"10\"></mat-paginator>\n </div>\n <div #Spinner [hidden]=\"dataSource\">\n <mat-spinner></mat-spinner>\n </div>\n</div>\n", styles: ["table{width:100%}i{cursor:pointer;padding:5px}\n"] }]
1713
+ args: [{ selector: 'glw-display-objects', imports: [MatCard, MatCardContent, MatError, FormsModule, ReactiveFormsModule, MatFormField, MatSelect, MatOption, MatCardActions, MatButton, MatIcon, MatTable, MatSort, MatColumnDef, MatHeaderCellDef, MatHeaderCell, MatCellDef, MatCell, RouterLink, NgClass, MatHeaderRowDef, MatHeaderRow, MatRowDef, MatRow, MatPaginator, MatProgressSpinner, MatDialogModule], template: "<div>\n <ng-content select=\"glw-header\"></ng-content>\n</div>\n\n@if (displayform) {\n <div>\n <mat-card appearance=\"outlined\">\n <mat-card-content>\n @if (resultException) {\n <mat-error>\n {{ resultException }}\n </mat-error>\n }\n <ng-content select=\"glw-search-form\"></ng-content>\n <!--<ng-container *ngComponentOutlet=\"SearchForm; injector: objInjector\"></ng-container>-->\n @if (maxrows) {\n <div [formGroup]=\"form2\">\n <br />\n <mat-form-field>\n <mat-select [placeholder]=\"t('COMMON.MAX_ROW', 'MaxRow')\" formControlName=\"_MaxRow_\">\n @for (maxrow of maxrows; track maxrow) {\n <mat-option [value]=\"maxrow\">\n @if (maxrow) {\n <span>{{maxrow}} {{ t('COMMON.OBJECTS_SUFFIX', 'objects') }}</span>\n }\n @if (!maxrow) {\n <span>{{ t('COMMON.DEFAULT', 'Default') }}</span>\n }\n </mat-option>\n }\n </mat-select>\n </mat-form-field>\n </div>\n }\n </mat-card-content>\n <mat-card-actions>\n <button mat-stroked-button color=\"accent\" (click)=\"onSearch()\">\n <mat-icon>search</mat-icon>\n {{ t('COMMON.SEARCH', 'Search') }}\n </button>\n </mat-card-actions>\n </mat-card>\n </div>\n}\n\n<div [hidden]=\"!displayresult\">\n <!--*ngIf=\"displayresult\"-->\n <div class=\"mat-elevation-z8\" [hidden]=\"!dataSource\">\n <ng-content select=\"[filter]\"></ng-content>\n\n <!--*ngIf=\"dataSource; else Spinner\"-->\n <table mat-table [dataSource]=\"dataSource\" matSort>\n <ng-container matColumnDef=\"action\">\n <th mat-header-cell *matHeaderCellDef>\n @if (hasSearchState()) {\n <i class=\"fal fa-arrow-left\" (click)=\"onBack()\" [attr.title]=\"t('COMMON.BACK', 'Back')\">\n </i>\n <i class=\"fal fa-rotate-right\" (click)=\"onRefresh()\" [attr.title]=\"t('COMMON.REFRESH', 'Refresh')\">\n </i>\n }\n @if (canAddThis()) {\n <i class=\"fal fa-plus\" (click)=\"AddObj()\">\n </i>\n }\n </th>\n <td mat-cell *matCellDef=\"let obj\">\n @if (canDisplayObjThis(obj)) {\n <i class=\"fal fa-eye\" [routerLink]=\"displayObjLinkThis(obj)\">\n </i>\n }\n @for (action of actions; track action) {\n @if (action.icon.icon && (!action.display || action.display(obj, action.name))) {\n <i [ngClass]=\"action.icon\" [routerLink]=\"action.routerLinkFct(obj)\">\n </i>\n }\n @if (!action.icon.icon && (!action.display || action.display(obj, action.name))) {\n <i [ngClass]=\"action.icon\" [routerLink]=\"action.routerLinkFct(obj)\"></i>\n }\n }\n @if (canDeleteThis(obj)) {\n <i class=\"fal fa-trash-alt\" (click)=\"DeleteObj(obj)\">\n </i>\n }\n @if (canEditThis(obj)) {\n <i class=\"fal fa-pencil\" (click)=\"EditObj(obj)\">\n </i>\n }\n </td>\n </ng-container>\n <ng-content select=\"glw-result-table\"></ng-content>\n <tr mat-header-row *matHeaderRowDef=\"columnsToDisplay\"></tr>\n <tr mat-row *matRowDef=\"let myRowData; columns: columnsToDisplay\"></tr>\n </table>\n <mat-paginator [pageSize]=\"10\" [pageSizeOptions]=\"[10, 20, 50, 100]\" [showFirstLastButtons]=\"true\"></mat-paginator>\n </div>\n <div #Spinner [hidden]=\"dataSource\">\n <mat-spinner></mat-spinner>\n </div>\n</div>\n", styles: ["table{width:100%}i{cursor:pointer;padding:5px}\n"] }]
1568
1714
  }], ctorParameters: () => [{ type: GlowwService, decorators: [{
1569
1715
  type: Inject,
1570
1716
  args: ['glowwService']
1571
- }] }, { type: i0.ChangeDetectorRef }, { type: i1$2.MatDialog }, { type: i2.Router }, { type: i3.Location }, { type: AuthenticationService }, { type: i1$3.UntypedFormBuilder }, { type: i2.ActivatedRoute }], propDecorators: { header: [{
1717
+ }] }, { type: i0.ChangeDetectorRef }, { type: i1$2.MatDialog }, { type: i2.Router }, { type: i3.Location }, { type: AuthenticationService }, { type: i1$3.UntypedFormBuilder }, { type: i2.ActivatedRoute }, { type: GlowwI18nService }], propDecorators: { header: [{
1572
1718
  type: ContentChild,
1573
1719
  args: [HeaderComponent]
1574
1720
  }], searchFormLayout: [{
@@ -1711,7 +1857,10 @@ class SecurePipe {
1711
1857
  }
1712
1858
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: SecurePipe, decorators: [{
1713
1859
  type: Pipe,
1714
- args: [{ name: 'secure' }]
1860
+ args: [{
1861
+ name: 'secure',
1862
+ standalone: true
1863
+ }]
1715
1864
  }], ctorParameters: () => [{ type: i1.HttpClient }, { type: i1$1.DomSanitizer }] });
1716
1865
 
1717
1866
  class MenuListItemComponent {
@@ -1722,9 +1871,10 @@ class MenuListItemComponent {
1722
1871
  console.log("change expanded");
1723
1872
  this._expanded = value;
1724
1873
  }
1725
- constructor(glowwService, navService, router) {
1874
+ constructor(glowwService, navService, router, i18n) {
1726
1875
  this.navService = navService;
1727
1876
  this.router = router;
1877
+ this.i18n = i18n;
1728
1878
  this._expanded = false;
1729
1879
  this.ariaExpanded = this.expanded;
1730
1880
  this.falsePromise = new Promise((resolve, reject) => {
@@ -1768,6 +1918,9 @@ class MenuListItemComponent {
1768
1918
  }
1769
1919
  return route;
1770
1920
  }
1921
+ displayName(item) {
1922
+ return this.i18n.instant(item.displayName, item.displayName);
1923
+ }
1771
1924
  getDisabledPromise() {
1772
1925
  //console.log(`isdisable item ${item.displayName} ${item.disabled}`);
1773
1926
  if (!this.item.disabled) {
@@ -1781,8 +1934,8 @@ class MenuListItemComponent {
1781
1934
  }
1782
1935
  return this.item.hidden();
1783
1936
  }
1784
- static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: MenuListItemComponent, deps: [{ token: 'glowwService' }, { token: NavService }, { token: i2.Router }], target: i0.ɵɵFactoryTarget.Component }); }
1785
- static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.18", type: MenuListItemComponent, isStandalone: true, selector: "gloww-menu-list-item", inputs: { item: "item", depth: "depth" }, host: { properties: { "attr.aria-expanded": "this.ariaExpanded" } }, ngImport: i0, template: "@if (item) {\n @if (!(_hidden | async)) {\n <div class=\"thisMenu\" (click)=\"onItemSelected(item)\" [class.disabled]=\"(_disabled | async)\">\n <a mat-list-item\n [ngStyle]=\"{'padding-left': (depth * 12) + 'px'}\"\n [ngClass]=\"{'active': isActive(item) && !(_disabled | async), 'expanded': expanded}\"\n class=\"menu-list-item\"\n [routerLink]=\"routerLink(item)\">\n <mat-icon class=\"routeIcon\">\n <i [ngClass]=\"item.icon\" [ngStyle]=\"item.iconStyle\"></i>\n </mat-icon>\n <span class=\"menu-label\">{{item.displayName}}</span>\n </a>\n @if (item.children?.length && !(_disabled | async)) {\n <div class=\"expand-container\">\n <mat-icon [@indicatorRotate]=\"expanded ? 'expanded': 'collapsed'\" class=\"expandIcon\">\n expand_more\n </mat-icon>\n </div>\n }\n </div>\n }\n @if (expanded && !(_disabled | async)) {\n <div>\n @for (child of item.children; track child) {\n <gloww-menu-list-item [item]=\"child\" [depth]=\"depth+1\">\n </gloww-menu-list-item>\n }\n </div>\n }\n}", styles: [".thisMenu{display:flex;flex-direction:row;align-items:center;outline:none;width:calc(100% - 20px);margin:10px;cursor:pointer}.menu-list-item{display:flex;align-items:center;flex:1;padding:8px 0;text-decoration:none;color:inherit;min-width:0}.menu-list-item .routeIcon{margin-right:20px;flex-shrink:0}.menu-list-item .menu-label{white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.expand-container{display:flex;align-items:center;justify-content:center;flex-shrink:0}mat-icon{height:32px;width:40px;display:flex;align-items:center;justify-content:center}.expandIcon{cursor:pointer}:disabled,.disabled{color:#d3d3d3!important;pointer-events:none}:disabled mat-icon i,.disabled mat-icon i{color:#d3d3d3!important}\n"], dependencies: [{ kind: "component", type: MenuListItemComponent, selector: "gloww-menu-list-item", inputs: ["item", "depth"] }, { kind: "directive", type: NgStyle, selector: "[ngStyle]", inputs: ["ngStyle"] }, { kind: "directive", type: NgClass, selector: "[ngClass]", inputs: ["class", "ngClass"] }, { kind: "directive", type: RouterLink, selector: "[routerLink]", inputs: ["target", "queryParams", "fragment", "queryParamsHandling", "state", "info", "relativeTo", "preserveFragment", "skipLocationChange", "replaceUrl", "routerLink"] }, { kind: "component", type: MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "ngmodule", type: GlowwModule }, { kind: "pipe", type: AsyncPipe, name: "async" }], animations: [
1937
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: MenuListItemComponent, deps: [{ token: 'glowwService' }, { token: NavService }, { token: i2.Router }, { token: GlowwI18nService }], target: i0.ɵɵFactoryTarget.Component }); }
1938
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.18", type: MenuListItemComponent, isStandalone: true, selector: "gloww-menu-list-item", inputs: { item: "item", depth: "depth" }, host: { properties: { "attr.aria-expanded": "this.ariaExpanded" } }, ngImport: i0, template: "@if (item) {\n @if (!(_hidden | async)) {\n <div class=\"thisMenu\" (click)=\"onItemSelected(item)\" [class.disabled]=\"(_disabled | async)\">\n <a mat-list-item lines=\"1\"\n [ngStyle]=\"{'padding-left': (depth * 12) + 'px'}\"\n [ngClass]=\"{'active': isActive(item) && !(_disabled | async), 'expanded': expanded}\"\n class=\"menu-list-item\"\n [routerLink]=\"routerLink(item)\">\n <span matListItemIcon class=\"routeIcon\">\n <i [ngClass]=\"item.icon\" [ngStyle]=\"item.iconStyle\"></i>\n </span>\n <span matListItemTitle class=\"menu-label\">{{ displayName(item) }}</span>\n </a>\n @if (item.children?.length && !(_disabled | async)) {\n <div class=\"expand-container\">\n <mat-icon [@indicatorRotate]=\"expanded ? 'expanded': 'collapsed'\" class=\"expandIcon\">\n expand_more\n </mat-icon>\n </div>\n }\n </div>\n }\n @if (expanded && !(_disabled | async)) {\n <div>\n @for (child of item.children; track child) {\n <gloww-menu-list-item [item]=\"child\" [depth]=\"depth+1\">\n </gloww-menu-list-item>\n }\n </div>\n }\n}\n", styles: [".thisMenu{display:flex;flex-direction:row;align-items:center;outline:none;width:calc(100% - 20px);margin:10px;cursor:pointer}.menu-list-item{display:flex;align-items:center;flex:1;padding:8px 0;text-decoration:none;color:inherit;min-width:0}.menu-list-item .menu-label{white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.expand-container{display:flex;align-items:center;justify-content:center;flex-shrink:0}.routeIcon{display:inline-flex;align-items:center;justify-content:center;width:40px;min-width:40px;height:32px;margin-right:20px;flex-shrink:0;overflow:visible}.routeIcon i{display:inline-block;line-height:1}mat-icon{height:32px;width:40px;display:flex;align-items:center;justify-content:center}.expandIcon{cursor:pointer}:disabled,.disabled{color:#d3d3d3!important;pointer-events:none}:disabled .routeIcon i,:disabled mat-icon i,.disabled .routeIcon i,.disabled mat-icon i{color:#d3d3d3!important}\n"], dependencies: [{ kind: "component", type: MenuListItemComponent, selector: "gloww-menu-list-item", inputs: ["item", "depth"] }, { kind: "directive", type: NgStyle, selector: "[ngStyle]", inputs: ["ngStyle"] }, { kind: "directive", type: NgClass, selector: "[ngClass]", inputs: ["class", "ngClass"] }, { kind: "directive", type: RouterLink, selector: "[routerLink]", inputs: ["target", "queryParams", "fragment", "queryParamsHandling", "state", "info", "relativeTo", "preserveFragment", "skipLocationChange", "replaceUrl", "routerLink"] }, { kind: "component", type: MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: MatListItem, selector: "mat-list-item, a[mat-list-item], button[mat-list-item]", inputs: ["activated"], exportAs: ["matListItem"] }, { kind: "directive", type: MatListItemIcon, selector: "[matListItemIcon]" }, { kind: "directive", type: MatListItemTitle, selector: "[matListItemTitle]" }, { kind: "pipe", type: AsyncPipe, name: "async" }], animations: [
1786
1939
  trigger('indicatorRotate', [
1787
1940
  state('collapsed', style({ transform: 'rotate(0deg)' })),
1788
1941
  state('expanded', style({ transform: 'rotate(180deg)' })),
@@ -1798,11 +1951,11 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImpo
1798
1951
  state('expanded', style({ transform: 'rotate(180deg)' })),
1799
1952
  transition('expanded <=> collapsed', animate('225ms cubic-bezier(0.4,0.0,0.2,1)'))
1800
1953
  ])
1801
- ], imports: [NgStyle, NgClass, RouterLink, MatIcon, GlowwModule, AsyncPipe], template: "@if (item) {\n @if (!(_hidden | async)) {\n <div class=\"thisMenu\" (click)=\"onItemSelected(item)\" [class.disabled]=\"(_disabled | async)\">\n <a mat-list-item\n [ngStyle]=\"{'padding-left': (depth * 12) + 'px'}\"\n [ngClass]=\"{'active': isActive(item) && !(_disabled | async), 'expanded': expanded}\"\n class=\"menu-list-item\"\n [routerLink]=\"routerLink(item)\">\n <mat-icon class=\"routeIcon\">\n <i [ngClass]=\"item.icon\" [ngStyle]=\"item.iconStyle\"></i>\n </mat-icon>\n <span class=\"menu-label\">{{item.displayName}}</span>\n </a>\n @if (item.children?.length && !(_disabled | async)) {\n <div class=\"expand-container\">\n <mat-icon [@indicatorRotate]=\"expanded ? 'expanded': 'collapsed'\" class=\"expandIcon\">\n expand_more\n </mat-icon>\n </div>\n }\n </div>\n }\n @if (expanded && !(_disabled | async)) {\n <div>\n @for (child of item.children; track child) {\n <gloww-menu-list-item [item]=\"child\" [depth]=\"depth+1\">\n </gloww-menu-list-item>\n }\n </div>\n }\n}", styles: [".thisMenu{display:flex;flex-direction:row;align-items:center;outline:none;width:calc(100% - 20px);margin:10px;cursor:pointer}.menu-list-item{display:flex;align-items:center;flex:1;padding:8px 0;text-decoration:none;color:inherit;min-width:0}.menu-list-item .routeIcon{margin-right:20px;flex-shrink:0}.menu-list-item .menu-label{white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.expand-container{display:flex;align-items:center;justify-content:center;flex-shrink:0}mat-icon{height:32px;width:40px;display:flex;align-items:center;justify-content:center}.expandIcon{cursor:pointer}:disabled,.disabled{color:#d3d3d3!important;pointer-events:none}:disabled mat-icon i,.disabled mat-icon i{color:#d3d3d3!important}\n"] }]
1954
+ ], imports: [NgStyle, NgClass, RouterLink, MatIcon, MatListItem, MatListItemIcon, MatListItemTitle, AsyncPipe], template: "@if (item) {\n @if (!(_hidden | async)) {\n <div class=\"thisMenu\" (click)=\"onItemSelected(item)\" [class.disabled]=\"(_disabled | async)\">\n <a mat-list-item lines=\"1\"\n [ngStyle]=\"{'padding-left': (depth * 12) + 'px'}\"\n [ngClass]=\"{'active': isActive(item) && !(_disabled | async), 'expanded': expanded}\"\n class=\"menu-list-item\"\n [routerLink]=\"routerLink(item)\">\n <span matListItemIcon class=\"routeIcon\">\n <i [ngClass]=\"item.icon\" [ngStyle]=\"item.iconStyle\"></i>\n </span>\n <span matListItemTitle class=\"menu-label\">{{ displayName(item) }}</span>\n </a>\n @if (item.children?.length && !(_disabled | async)) {\n <div class=\"expand-container\">\n <mat-icon [@indicatorRotate]=\"expanded ? 'expanded': 'collapsed'\" class=\"expandIcon\">\n expand_more\n </mat-icon>\n </div>\n }\n </div>\n }\n @if (expanded && !(_disabled | async)) {\n <div>\n @for (child of item.children; track child) {\n <gloww-menu-list-item [item]=\"child\" [depth]=\"depth+1\">\n </gloww-menu-list-item>\n }\n </div>\n }\n}\n", styles: [".thisMenu{display:flex;flex-direction:row;align-items:center;outline:none;width:calc(100% - 20px);margin:10px;cursor:pointer}.menu-list-item{display:flex;align-items:center;flex:1;padding:8px 0;text-decoration:none;color:inherit;min-width:0}.menu-list-item .menu-label{white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.expand-container{display:flex;align-items:center;justify-content:center;flex-shrink:0}.routeIcon{display:inline-flex;align-items:center;justify-content:center;width:40px;min-width:40px;height:32px;margin-right:20px;flex-shrink:0;overflow:visible}.routeIcon i{display:inline-block;line-height:1}mat-icon{height:32px;width:40px;display:flex;align-items:center;justify-content:center}.expandIcon{cursor:pointer}:disabled,.disabled{color:#d3d3d3!important;pointer-events:none}:disabled .routeIcon i,:disabled mat-icon i,.disabled .routeIcon i,.disabled mat-icon i{color:#d3d3d3!important}\n"] }]
1802
1955
  }], ctorParameters: () => [{ type: GlowwService, decorators: [{
1803
1956
  type: Inject,
1804
1957
  args: ['glowwService']
1805
- }] }, { type: NavService }, { type: i2.Router }], propDecorators: { ariaExpanded: [{
1958
+ }] }, { type: NavService }, { type: i2.Router }, { type: GlowwI18nService }], propDecorators: { ariaExpanded: [{
1806
1959
  type: HostBinding,
1807
1960
  args: ['attr.aria-expanded']
1808
1961
  }], item: [{
@@ -1986,7 +2139,10 @@ class HtmlFormatPipe {
1986
2139
  }
1987
2140
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: HtmlFormatPipe, decorators: [{
1988
2141
  type: Pipe,
1989
- args: [{ name: 'htmlFormat' }]
2142
+ args: [{
2143
+ name: 'htmlFormat',
2144
+ standalone: true
2145
+ }]
1990
2146
  }], ctorParameters: () => [{ type: i1$1.DomSanitizer }] });
1991
2147
 
1992
2148
  class SocialNetworkComponent {
@@ -2048,15 +2204,10 @@ class LoginComponent {
2048
2204
  if (config && config.showDomain) {
2049
2205
  this.showDomain = config.showDomain;
2050
2206
  }
2207
+ this.initializeForms();
2051
2208
  this.authenticationService.getOAuthProviders().subscribe(oap => this.oAuthProviders = oap);
2052
2209
  }
2053
- MatchPassword(fg) {
2054
- if (!fg) {
2055
- return;
2056
- }
2057
- return fg.get('newpassword')?.value === fg.get('confirmationPassword')?.value;
2058
- }
2059
- ngOnInit() {
2210
+ initializeForms() {
2060
2211
  const grp = {
2061
2212
  username: ['', Validators.required],
2062
2213
  password: ['', Validators.required]
@@ -2079,6 +2230,14 @@ class LoginComponent {
2079
2230
  this.loginForm = this.formBuilder.group(grp);
2080
2231
  this.lostPasswordForm = this.formBuilder.group(lostPwd);
2081
2232
  this.resetPasswordForm = this.formBuilder.group(resetPwd, { validator: this.MatchPassword });
2233
+ }
2234
+ MatchPassword(fg) {
2235
+ if (!fg) {
2236
+ return;
2237
+ }
2238
+ return fg.get('newpassword')?.value === fg.get('confirmationPassword')?.value;
2239
+ }
2240
+ ngOnInit() {
2082
2241
  // get return url from route parameters or default to '/'
2083
2242
  this.returnUrl = this.route.snapshot.queryParams.returnUrl; //|| window.location.search;
2084
2243
  this.application = this.route.snapshot.queryParams.application; //|| window.location.pathname;
@@ -2499,6 +2658,30 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImpo
2499
2658
  }]
2500
2659
  }], ctorParameters: () => [{ type: i2.Router }, { type: AuthenticationService }, { type: i3.PlatformLocation }] });
2501
2660
 
2661
+ const GLOWW_SECURITY_STANDALONE_DECLARATIONS = [
2662
+ LoginComponent,
2663
+ ChangePasswordDlgComponent,
2664
+ UserMenuComponent,
2665
+ SocialNetworkDlgComponent,
2666
+ SocialNetworkComponent
2667
+ ];
2668
+ function getGlowwSecurityProviders(authenticationServiceConfig) {
2669
+ return [
2670
+ AuthenticationService,
2671
+ AuthenticationServiceConfig,
2672
+ { provide: AuthenticationServiceConfig, useValue: authenticationServiceConfig },
2673
+ { provide: HTTP_INTERCEPTORS, useClass: JwtInterceptor, multi: true },
2674
+ { provide: HTTP_INTERCEPTORS, useClass: ErrorInterceptor, multi: true },
2675
+ //{ provide: HTTP_INTERCEPTORS, useClass: StagingInterceptor, multi: true },
2676
+ //socialLoginProviders
2677
+ ];
2678
+ }
2679
+ function provideGlowwSecurity(authenticationServiceConfig) {
2680
+ return makeEnvironmentProviders([
2681
+ provideHttpClient(withInterceptorsFromDi()),
2682
+ ...getGlowwSecurityProviders(authenticationServiceConfig)
2683
+ ]);
2684
+ }
2502
2685
  class GlowwSecurityModule {
2503
2686
  static forRoot(authenticationServiceConfig) {
2504
2687
  /*
@@ -2557,23 +2740,13 @@ class GlowwSecurityModule {
2557
2740
  */
2558
2741
  return {
2559
2742
  ngModule: GlowwSecurityModule,
2560
- providers: [
2561
- AuthenticationService,
2562
- AuthenticationServiceConfig,
2563
- { provide: AuthenticationServiceConfig, useValue: authenticationServiceConfig },
2564
- { provide: HTTP_INTERCEPTORS, useClass: JwtInterceptor, multi: true },
2565
- { provide: HTTP_INTERCEPTORS, useClass: ErrorInterceptor, multi: true },
2566
- //{ provide: HTTP_INTERCEPTORS, useClass: StagingInterceptor, multi: true },
2567
- //socialLoginProviders
2568
- ]
2743
+ providers: getGlowwSecurityProviders(authenticationServiceConfig)
2569
2744
  };
2570
2745
  }
2571
2746
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: GlowwSecurityModule, deps: [], target: i0.ɵɵFactoryTarget.NgModule }); }
2572
2747
  static { this.ɵmod = i0.ɵɵngDeclareNgModule({ minVersion: "14.0.0", version: "20.3.18", ngImport: i0, type: GlowwSecurityModule, imports: [CommonModule,
2573
2748
  FormsModule,
2574
2749
  ReactiveFormsModule,
2575
- BrowserModule,
2576
- BrowserAnimationsModule,
2577
2750
  MatToolbarModule,
2578
2751
  MatButtonModule,
2579
2752
  MatSidenavModule,
@@ -2585,12 +2758,14 @@ class GlowwSecurityModule {
2585
2758
  ChangePasswordDlgComponent,
2586
2759
  UserMenuComponent,
2587
2760
  SocialNetworkDlgComponent,
2588
- SocialNetworkComponent], exports: [LoginComponent, RouterModule, UserMenuComponent] }); }
2761
+ SocialNetworkComponent], exports: [LoginComponent,
2762
+ ChangePasswordDlgComponent,
2763
+ UserMenuComponent,
2764
+ SocialNetworkDlgComponent,
2765
+ SocialNetworkComponent, RouterModule] }); }
2589
2766
  static { this.ɵinj = i0.ɵɵngDeclareInjector({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: GlowwSecurityModule, providers: [provideHttpClient(withInterceptorsFromDi())], imports: [CommonModule,
2590
2767
  FormsModule,
2591
2768
  ReactiveFormsModule,
2592
- BrowserModule,
2593
- BrowserAnimationsModule,
2594
2769
  MatToolbarModule,
2595
2770
  MatButtonModule,
2596
2771
  MatSidenavModule,
@@ -2605,11 +2780,9 @@ class GlowwSecurityModule {
2605
2780
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: GlowwSecurityModule, decorators: [{
2606
2781
  type: NgModule,
2607
2782
  args: [{
2608
- exports: [LoginComponent, RouterModule, UserMenuComponent], imports: [CommonModule,
2783
+ exports: [...GLOWW_SECURITY_STANDALONE_DECLARATIONS, RouterModule], imports: [CommonModule,
2609
2784
  FormsModule,
2610
2785
  ReactiveFormsModule,
2611
- BrowserModule,
2612
- BrowserAnimationsModule,
2613
2786
  MatToolbarModule,
2614
2787
  MatButtonModule,
2615
2788
  MatSidenavModule,
@@ -2617,11 +2790,8 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImpo
2617
2790
  MatFormFieldModule,
2618
2791
  MatCardModule,
2619
2792
  MatDialogModule,
2620
- RouterModule, LoginComponent,
2621
- ChangePasswordDlgComponent,
2622
- UserMenuComponent,
2623
- SocialNetworkDlgComponent,
2624
- SocialNetworkComponent], providers: [provideHttpClient(withInterceptorsFromDi())]
2793
+ RouterModule,
2794
+ ...GLOWW_SECURITY_STANDALONE_DECLARATIONS], providers: [provideHttpClient(withInterceptorsFromDi())]
2625
2795
  }]
2626
2796
  }] });
2627
2797
 
@@ -3402,6 +3572,7 @@ class AutoCompleteComponent {
3402
3572
  this.onTouched = () => { };
3403
3573
  this.items = [];
3404
3574
  this.parser = new TranslateDefaultParser();
3575
+ this.pendingExternalValue = undefined;
3405
3576
  this.options = []; //Observable<unknown>;
3406
3577
  this.propagateChange = (_) => { };
3407
3578
  this.glowwService = glowwService;
@@ -3435,9 +3606,21 @@ class AutoCompleteComponent {
3435
3606
  },
3436
3607
  error: (error) => { this.error = error; }
3437
3608
  });
3609
+ if (this.pendingExternalValue !== undefined) {
3610
+ this.applyExternalValue(this.pendingExternalValue);
3611
+ this.pendingExternalValue = undefined;
3612
+ }
3438
3613
  }
3439
3614
  writeValue(val) {
3440
- val && this.form.setValue({ __result: val }, { emitEvent: false });
3615
+ if (val === undefined || val === null || val === '') {
3616
+ this.form.setValue({ __result: null }, { emitEvent: false });
3617
+ return;
3618
+ }
3619
+ if (!this.searchRequest) {
3620
+ this.pendingExternalValue = val;
3621
+ return;
3622
+ }
3623
+ this.applyExternalValue(val);
3441
3624
  }
3442
3625
  registerOnChange(fn) {
3443
3626
  this.onChange = fn;
@@ -3460,6 +3643,9 @@ class AutoCompleteComponent {
3460
3643
  displayObj(item) {
3461
3644
  if (!item)
3462
3645
  return null;
3646
+ if (typeof item !== 'object') {
3647
+ return item;
3648
+ }
3463
3649
  console.log("displayOf");
3464
3650
  if (this.displayField) {
3465
3651
  return item[this.displayField];
@@ -3472,6 +3658,30 @@ class AutoCompleteComponent {
3472
3658
  return this.displayFct(item);
3473
3659
  }
3474
3660
  }
3661
+ applyExternalValue(val) {
3662
+ if (typeof val === 'object') {
3663
+ this.form.setValue({ __result: val }, { emitEvent: false });
3664
+ this.ref.markForCheck();
3665
+ return;
3666
+ }
3667
+ if (!this.returnField || !this.searchRequest) {
3668
+ this.form.setValue({ __result: val }, { emitEvent: false });
3669
+ this.ref.markForCheck();
3670
+ return;
3671
+ }
3672
+ const searchObj = {};
3673
+ if (this.data) {
3674
+ Object.keys(this.data).forEach(k => {
3675
+ searchObj[k] = this.data[k];
3676
+ });
3677
+ }
3678
+ searchObj[this.returnField] = val;
3679
+ this.searchRequest.call(this.glowwService, searchObj).pipe(catchError(() => of([]))).subscribe((results) => {
3680
+ const match = results.find(item => item?.[this.returnField] == val) ?? results[0] ?? val;
3681
+ this.form.setValue({ __result: match }, { emitEvent: false });
3682
+ this.ref.markForCheck();
3683
+ });
3684
+ }
3475
3685
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: AutoCompleteComponent, deps: [{ token: 'glowwService' }, { token: i1$3.UntypedFormBuilder }, { token: i0.ChangeDetectorRef }], target: i0.ɵɵFactoryTarget.Component }); }
3476
3686
  static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.18", type: AutoCompleteComponent, isStandalone: true, selector: "gloww-auto-complete", inputs: { _value: ["value", "_value"], objectName: "objectName", searchField: "searchField", returnField: "returnField", displayField: "displayField", displayExpr: "displayExpr", displayFct: "displayFct", placeHolder: "placeHolder", data: "data", searchRequest: "searchRequest" }, providers: [
3477
3687
  {
@@ -3525,31 +3735,64 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImpo
3525
3735
  }] } });
3526
3736
 
3527
3737
  class DatetimeComponent {
3528
- constructor() {
3738
+ static { this.DATE_FORMATS = [
3739
+ moment.ISO_8601,
3740
+ 'DD/MM/YYYY HH:mm:ss',
3741
+ 'DD/MM/YYYY HH:mm',
3742
+ 'DD/MM/YYYY',
3743
+ 'MM/DD/YYYY HH:mm:ss',
3744
+ 'MM/DD/YYYY HH:mm',
3745
+ 'MM/DD/YYYY',
3746
+ 'YYYY-MM-DD HH:mm:ss',
3747
+ 'YYYY-MM-DD HH:mm',
3748
+ 'YYYY-MM-DD',
3749
+ 'YYYY-MM-DDTHH:mm:ss',
3750
+ 'YYYY-MM-DDTHH:mm'
3751
+ ]; }
3752
+ static { this.CLOCK_CENTER = 50; }
3753
+ static { this.CLOCK_OUTER_RADIUS = 36; }
3754
+ static { this.CLOCK_INNER_RADIUS = 25; }
3755
+ static { this.CLOCK_TICK_OUTER_RADIUS = 48; }
3756
+ static { this.CLOCK_TICK_INNER_RADIUS = 41; }
3757
+ static { this.CLOCK_TICK_LABEL_RADIUS = 34; }
3758
+ static { this.CLOCK_OUTER_HAND_HEIGHT = '34%'; }
3759
+ static { this.CLOCK_INNER_HAND_HEIGHT = '23%'; }
3760
+ static { this.CLOCK_MINUTE_HAND_HEIGHT = '48%'; }
3761
+ constructor(locale) {
3762
+ this.locale = locale;
3529
3763
  this._value = null;
3530
3764
  this.display = null;
3531
3765
  this.placeHolder = null;
3532
3766
  this.mode = 'date';
3533
- this.showSpinners = true;
3534
3767
  this.showSeconds = false;
3535
- this.disableMinute = false;
3768
+ this.dateControl = new FormControl(null);
3769
+ this.hourControl = new FormControl('00', { nonNullable: true });
3770
+ this.minuteControl = new FormControl('00', { nonNullable: true });
3771
+ this.secondControl = new FormControl('00', { nonNullable: true });
3772
+ this.hourMarkers = this.buildHourMarkers();
3773
+ this.minuteTicks = this.buildUnitTicks();
3774
+ this.secondTicks = this.buildUnitTicks();
3775
+ this.isDisabled = false;
3776
+ this.isClockOpen = false;
3777
+ this.clockStep = 'hour';
3536
3778
  this.onChange = () => { };
3537
3779
  this.onTouched = () => { };
3780
+ this.dateControl.valueChanges.subscribe(() => this.emitCurrentValue());
3781
+ this.hourControl.valueChanges.subscribe(() => this.emitCurrentValue());
3782
+ this.minuteControl.valueChanges.subscribe(() => this.emitCurrentValue());
3783
+ this.secondControl.valueChanges.subscribe(() => this.emitCurrentValue());
3784
+ }
3785
+ get isDateTime() {
3786
+ return this.mode === 'datetime';
3538
3787
  }
3539
3788
  get value() {
3540
3789
  return this._value;
3541
3790
  }
3542
3791
  set value(val) {
3543
- this._value = val;
3544
- let dt = this._value;
3545
- if (typeof (this._value) === 'string') {
3546
- dt = moment(this._value).toISOString();
3547
- }
3548
- this.onChange(dt);
3549
- this.onTouched();
3792
+ this.setValueFromOutside(val, true);
3550
3793
  }
3551
3794
  writeValue(obj) {
3552
- this.value = obj;
3795
+ this.setValueFromOutside(obj, false);
3553
3796
  }
3554
3797
  registerOnChange(fn) {
3555
3798
  this.onChange = fn;
@@ -3558,27 +3801,308 @@ class DatetimeComponent {
3558
3801
  this.onTouched = fn;
3559
3802
  }
3560
3803
  setDisabledState(isDisabled) {
3561
- //throw new Error('Method not implemented.');
3804
+ this.isDisabled = isDisabled;
3805
+ const action = isDisabled ? 'disable' : 'enable';
3806
+ this.dateControl[action]({ emitEvent: false });
3807
+ this.hourControl[action]({ emitEvent: false });
3808
+ this.minuteControl[action]({ emitEvent: false });
3809
+ this.secondControl[action]({ emitEvent: false });
3810
+ }
3811
+ clear() {
3812
+ this._value = null;
3813
+ this.isClockOpen = false;
3814
+ this.dateControl.setValue(null, { emitEvent: false });
3815
+ this.hourControl.setValue('00', { emitEvent: false });
3816
+ this.minuteControl.setValue('00', { emitEvent: false });
3817
+ this.secondControl.setValue('00', { emitEvent: false });
3818
+ this.onChange(null);
3819
+ this.onTouched();
3820
+ }
3821
+ markTouched() {
3822
+ this.onTouched();
3823
+ }
3824
+ get timeSummary() {
3825
+ return this.showSeconds
3826
+ ? `${this.normalizeTimePartValue(this.hourControl.value, 23, true)}:${this.normalizeTimePartValue(this.minuteControl.value, 59, true)}:${this.normalizeTimePartValue(this.secondControl.value, 59, true)}`
3827
+ : `${this.normalizeTimePartValue(this.hourControl.value, 23, true)}:${this.normalizeTimePartValue(this.minuteControl.value, 59, true)}`;
3828
+ }
3829
+ get clockTitle() {
3830
+ switch (this.clockStep) {
3831
+ case 'hour':
3832
+ return 'Hours';
3833
+ case 'minute':
3834
+ return 'Minutes';
3835
+ default:
3836
+ return 'Seconds';
3837
+ }
3838
+ }
3839
+ openClock() {
3840
+ if (this.isDisabled) {
3841
+ return;
3842
+ }
3843
+ this.isClockOpen = true;
3844
+ this.clockStep = 'hour';
3845
+ this.onTouched();
3846
+ }
3847
+ closeClock() {
3848
+ this.isClockOpen = false;
3849
+ this.onTouched();
3850
+ }
3851
+ onTimePartInput(part) {
3852
+ const control = this.getTimeControl(part);
3853
+ const max = this.getTimePartMax(part);
3854
+ control.setValue(this.normalizeTimePartValue(control.value, max, false), { emitEvent: false });
3855
+ this.emitCurrentValue();
3856
+ }
3857
+ onTimePartBlur(part) {
3858
+ const control = this.getTimeControl(part);
3859
+ const max = this.getTimePartMax(part);
3860
+ control.setValue(this.normalizeTimePartValue(control.value, max, true), { emitEvent: false });
3861
+ this.emitCurrentValue();
3862
+ this.onTouched();
3863
+ }
3864
+ selectClockHour(value, event) {
3865
+ event?.stopPropagation();
3866
+ this.hourControl.setValue(value.toString().padStart(2, '0'), { emitEvent: false });
3867
+ this.emitCurrentValue();
3868
+ this.clockStep = 'minute';
3869
+ this.onTouched();
3870
+ }
3871
+ selectClockMinute(value, event) {
3872
+ event?.stopPropagation();
3873
+ this.minuteControl.setValue(value.toString().padStart(2, '0'), { emitEvent: false });
3874
+ this.emitCurrentValue();
3875
+ if (this.showSeconds) {
3876
+ this.clockStep = 'second';
3877
+ }
3878
+ else {
3879
+ this.closeClock();
3880
+ }
3881
+ this.onTouched();
3882
+ }
3883
+ selectClockSecond(value, event) {
3884
+ event?.stopPropagation();
3885
+ this.secondControl.setValue(value.toString().padStart(2, '0'), { emitEvent: false });
3886
+ this.emitCurrentValue();
3887
+ this.closeClock();
3888
+ this.onTouched();
3889
+ }
3890
+ selectClockTick(value, event) {
3891
+ if (this.clockStep === 'minute') {
3892
+ this.selectClockMinute(value, event);
3893
+ return;
3894
+ }
3895
+ if (this.clockStep === 'second') {
3896
+ this.selectClockSecond(value, event);
3897
+ }
3898
+ }
3899
+ goToClockStep(step) {
3900
+ this.clockStep = step;
3901
+ }
3902
+ onClockFaceClick(event) {
3903
+ if (this.clockStep === 'hour') {
3904
+ return;
3905
+ }
3906
+ const target = event.currentTarget;
3907
+ if (!target) {
3908
+ return;
3909
+ }
3910
+ const rect = target.getBoundingClientRect();
3911
+ const centerX = rect.left + (rect.width / 2);
3912
+ const centerY = rect.top + (rect.height / 2);
3913
+ const dx = event.clientX - centerX;
3914
+ const dy = event.clientY - centerY;
3915
+ const angle = Math.atan2(dy, dx) + (Math.PI / 2);
3916
+ const normalized = angle < 0 ? angle + (Math.PI * 2) : angle;
3917
+ const rawValue = Math.round((normalized / (Math.PI * 2)) * 60) % 60;
3918
+ if (this.clockStep === 'minute') {
3919
+ this.selectClockMinute(rawValue);
3920
+ return;
3921
+ }
3922
+ this.selectClockSecond(rawValue);
3923
+ }
3924
+ isHourSelected(value) {
3925
+ return this.toNumber(this.hourControl.value) === value;
3926
+ }
3927
+ isMinuteSelected(value) {
3928
+ return this.toNumber(this.minuteControl.value) === value;
3929
+ }
3930
+ isSecondSelected(value) {
3931
+ return this.toNumber(this.secondControl.value) === value;
3932
+ }
3933
+ get clockHandTransform() {
3934
+ if (this.clockStep === 'hour') {
3935
+ const hour = this.toNumber(this.hourControl.value) % 12;
3936
+ return `translate(-50%, -100%) rotate(${(hour / 12) * 360}deg)`;
3937
+ }
3938
+ if (this.clockStep === 'minute') {
3939
+ const minute = this.toNumber(this.minuteControl.value) % 60;
3940
+ return `translate(-50%, -100%) rotate(${(minute / 60) * 360}deg)`;
3941
+ }
3942
+ const second = this.toNumber(this.secondControl.value) % 60;
3943
+ return `translate(-50%, -100%) rotate(${(second / 60) * 360}deg)`;
3944
+ }
3945
+ get clockHandHeight() {
3946
+ if (this.clockStep === 'hour') {
3947
+ const hour = this.toNumber(this.hourControl.value);
3948
+ return hour < 12 ? '38%' : '25%';
3949
+ }
3950
+ return '45%';
3951
+ }
3952
+ get hourHandTransform() {
3953
+ const hour = this.toNumber(this.hourControl.value) % 12;
3954
+ return `translate(-50%, -100%) rotate(${(hour / 12) * 360}deg)`;
3955
+ }
3956
+ get hourHandHeight() {
3957
+ const hour = this.toNumber(this.hourControl.value);
3958
+ return hour < 12 ? DatetimeComponent.CLOCK_OUTER_HAND_HEIGHT : DatetimeComponent.CLOCK_INNER_HAND_HEIGHT;
3959
+ }
3960
+ get minuteHandTransform() {
3961
+ const minute = (this.toNumber(this.minuteControl.value) % 60) + (this.toNumber(this.secondControl.value) / 60);
3962
+ return `translate(-50%, -100%) rotate(${(minute / 60) * 360}deg)`;
3963
+ }
3964
+ get minuteHandHeight() {
3965
+ return DatetimeComponent.CLOCK_MINUTE_HAND_HEIGHT;
3966
+ }
3967
+ get selectedHourMarker() {
3968
+ const hour = this.toNumber(this.hourControl.value);
3969
+ return this.buildClockMarker(hour, hour < 12 ? DatetimeComponent.CLOCK_OUTER_RADIUS : DatetimeComponent.CLOCK_INNER_RADIUS, hour.toString().padStart(2, '0'));
3970
+ }
3971
+ setValueFromOutside(value, emit) {
3972
+ const normalized = this.normalizeDateValue(value);
3973
+ this._value = normalized;
3974
+ this.dateControl.setValue(normalized ? new Date(normalized.getTime()) : null, { emitEvent: false });
3975
+ this.hourControl.setValue(normalized ? normalized.getHours().toString().padStart(2, '0') : '00', { emitEvent: false });
3976
+ this.minuteControl.setValue(normalized ? normalized.getMinutes().toString().padStart(2, '0') : '00', { emitEvent: false });
3977
+ this.secondControl.setValue(normalized ? normalized.getSeconds().toString().padStart(2, '0') : '00', { emitEvent: false });
3978
+ if (emit) {
3979
+ this.onChange(normalized);
3980
+ this.onTouched();
3981
+ }
3982
+ }
3983
+ emitCurrentValue() {
3984
+ const date = this.normalizeDateValue(this.dateControl.value);
3985
+ if (!date) {
3986
+ this._value = null;
3987
+ this.onChange(null);
3988
+ return;
3989
+ }
3990
+ const next = new Date(date.getTime());
3991
+ next.setHours(this.toNumber(this.hourControl.value), this.toNumber(this.minuteControl.value), this.showSeconds ? this.toNumber(this.secondControl.value) : 0, 0);
3992
+ this._value = next;
3993
+ this.onChange(next);
3994
+ }
3995
+ toNumber(value) {
3996
+ const parsed = Number.parseInt(value ?? '0', 10);
3997
+ return Number.isNaN(parsed) ? 0 : parsed;
3998
+ }
3999
+ getTimeControl(part) {
4000
+ switch (part) {
4001
+ case 'hour':
4002
+ return this.hourControl;
4003
+ case 'minute':
4004
+ return this.minuteControl;
4005
+ default:
4006
+ return this.secondControl;
4007
+ }
4008
+ }
4009
+ getTimePartMax(part) {
4010
+ return part === 'hour' ? 23 : 59;
4011
+ }
4012
+ normalizeTimePartValue(value, max, pad) {
4013
+ const digits = `${value ?? ''}`.replace(/\D/g, '').slice(-2);
4014
+ if (!digits) {
4015
+ return pad ? '00' : '';
4016
+ }
4017
+ const parsed = Number.parseInt(digits, 10);
4018
+ const clamped = Number.isNaN(parsed) ? 0 : Math.min(max, Math.max(0, parsed));
4019
+ return pad || digits.length > 1 ? clamped.toString().padStart(2, '0') : clamped.toString();
4020
+ }
4021
+ normalizeDateValue(value) {
4022
+ if (value === undefined || value === null || value === '') {
4023
+ return null;
4024
+ }
4025
+ if (value instanceof Date) {
4026
+ return Number.isNaN(value.getTime()) ? null : new Date(value.getTime());
4027
+ }
4028
+ if (moment.isMoment(value)) {
4029
+ const date = value.toDate();
4030
+ return Number.isNaN(date.getTime()) ? null : date;
4031
+ }
4032
+ if (typeof value === 'string' || typeof value === 'number') {
4033
+ const strictMoment = moment(value, DatetimeComponent.DATE_FORMATS, this.locale ?? undefined, true);
4034
+ if (strictMoment.isValid()) {
4035
+ return strictMoment.toDate();
4036
+ }
4037
+ const lenientMoment = moment(value, DatetimeComponent.DATE_FORMATS, this.locale ?? undefined, false);
4038
+ if (lenientMoment.isValid()) {
4039
+ return lenientMoment.toDate();
4040
+ }
4041
+ const date = new Date(value);
4042
+ return Number.isNaN(date.getTime()) ? null : date;
4043
+ }
4044
+ return null;
4045
+ }
4046
+ buildHourMarkers() {
4047
+ return Array.from({ length: 24 }, (_, index) => this.buildClockMarker(index, index < 12 ? DatetimeComponent.CLOCK_OUTER_RADIUS : DatetimeComponent.CLOCK_INNER_RADIUS, index.toString().padStart(2, '0')));
4048
+ }
4049
+ buildUnitTicks() {
4050
+ return Array.from({ length: 12 }, (_, index) => {
4051
+ const value = index * 5;
4052
+ const angle = (index / 12) * (Math.PI * 2) - (Math.PI / 2);
4053
+ const x1 = DatetimeComponent.CLOCK_CENTER + Math.cos(angle) * DatetimeComponent.CLOCK_TICK_INNER_RADIUS;
4054
+ const y1 = DatetimeComponent.CLOCK_CENTER + Math.sin(angle) * DatetimeComponent.CLOCK_TICK_INNER_RADIUS;
4055
+ const x2 = DatetimeComponent.CLOCK_CENTER + Math.cos(angle) * DatetimeComponent.CLOCK_TICK_OUTER_RADIUS;
4056
+ const y2 = DatetimeComponent.CLOCK_CENTER + Math.sin(angle) * DatetimeComponent.CLOCK_TICK_OUTER_RADIUS;
4057
+ const labelX = DatetimeComponent.CLOCK_CENTER + Math.cos(angle) * DatetimeComponent.CLOCK_TICK_LABEL_RADIUS;
4058
+ const labelY = DatetimeComponent.CLOCK_CENTER + Math.sin(angle) * DatetimeComponent.CLOCK_TICK_LABEL_RADIUS;
4059
+ return {
4060
+ value,
4061
+ label: value.toString().padStart(2, '0'),
4062
+ x1: `${x1}%`,
4063
+ y1: `${y1}%`,
4064
+ x2: `${x2}%`,
4065
+ y2: `${y2}%`,
4066
+ labelLeft: `${labelX}%`,
4067
+ labelTop: `${labelY}%`,
4068
+ };
4069
+ });
4070
+ }
4071
+ buildClockMarker(index, radius, label) {
4072
+ const angle = ((index % 12) / 12) * (Math.PI * 2) - (Math.PI / 2);
4073
+ const x = DatetimeComponent.CLOCK_CENTER + Math.cos(angle) * radius;
4074
+ const y = DatetimeComponent.CLOCK_CENTER + Math.sin(angle) * radius;
4075
+ return {
4076
+ value: index,
4077
+ label,
4078
+ left: `${x}%`,
4079
+ top: `${y}%`
4080
+ };
3562
4081
  }
3563
- static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: DatetimeComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
3564
- static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.18", type: DatetimeComponent, isStandalone: true, selector: "gloww-datetime", inputs: { _value: ["value", "_value"], display: "display", placeHolder: "placeHolder", mode: "mode", showSpinners: "showSpinners", showSeconds: "showSeconds", disableMinute: "disableMinute" }, providers: [
4082
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: DatetimeComponent, deps: [{ token: MAT_DATE_LOCALE, optional: true }], target: i0.ɵɵFactoryTarget.Component }); }
4083
+ static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.18", type: DatetimeComponent, isStandalone: true, selector: "gloww-datetime", inputs: { _value: ["value", "_value"], display: "display", placeHolder: "placeHolder", mode: "mode", showSeconds: "showSeconds" }, providers: [
3565
4084
  {
3566
4085
  provide: NG_VALUE_ACCESSOR,
3567
4086
  multi: true,
3568
- useExisting: DatetimeComponent
4087
+ useExisting: forwardRef(() => DatetimeComponent)
3569
4088
  }
3570
- ], ngImport: i0, template: "<div style=\"width:100%\">\n @if (mode==='date') {\n <mat-form-field>\n <mat-label>{{display}}</mat-label>\n <input matInput [matDatepicker]=\"picker\" [placeholder]=\"placeHolder\" [(ngModel)]=\"value\">\n <mat-datepicker-toggle matSuffix [for]=\"picker\"></mat-datepicker-toggle>\n <mat-datepicker #picker></mat-datepicker>\n </mat-form-field>\n }\n\n @if (mode==='datetime') {\n <mat-form-field>\n <mat-label>{{display}}</mat-label>\n <input matInput [ngxMatDatetimePicker]=\"pickerDT\" [placeholder]=\"placeHolder\" [(ngModel)]=\"value\">\n <mat-datepicker-toggle matSuffix [for]=\"$any(pickerDT)\"></mat-datepicker-toggle>\n <ngx-mat-datetime-picker #pickerDT [showSpinners]=\"showSpinners\" [showSeconds]=\"showSeconds\" [touchUi]=\"true\" [disableMinute]=\"disableMinute\">\n </ngx-mat-datetime-picker>\n </mat-form-field>\n }\n</div>\n", styles: [""], dependencies: [{ kind: "component", type: MatFormField, selector: "mat-form-field", inputs: ["hideRequiredMarker", "color", "floatLabel", "appearance", "subscriptSizing", "hintLabel"], exportAs: ["matFormField"] }, { kind: "directive", type: MatLabel, selector: "mat-label" }, { kind: "directive", type: MatInput, selector: "input[matInput], textarea[matInput], select[matNativeControl], input[matNativeControl], textarea[matNativeControl]", inputs: ["disabled", "id", "placeholder", "name", "required", "type", "errorStateMatcher", "aria-describedby", "value", "readonly", "disabledInteractive"], exportAs: ["matInput"] }, { kind: "directive", type: MatDatepickerInput, selector: "input[matDatepicker]", inputs: ["matDatepicker", "min", "max", "matDatepickerFilter"], exportAs: ["matDatepickerInput"] }, { kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1$3.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1$3.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1$3.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }, { kind: "component", type: MatDatepickerToggle, selector: "mat-datepicker-toggle", inputs: ["for", "tabIndex", "aria-label", "disabled", "disableRipple"], exportAs: ["matDatepickerToggle"] }, { kind: "directive", type: MatSuffix, selector: "[matSuffix], [matIconSuffix], [matTextSuffix]", inputs: ["matTextSuffix"] }, { kind: "component", type: MatDatepicker, selector: "mat-datepicker", exportAs: ["matDatepicker"] }, { kind: "ngmodule", type: NgxMatDatetimePickerModule }, { kind: "component", type: i2$1.NgxMatDatetimepicker, selector: "ngx-mat-datetime-picker", exportAs: ["ngxMatDatetimePicker"] }, { kind: "directive", type: i2$1.NgxMatDatepickerInput, selector: "input[ngxMatDatetimePicker]", inputs: ["ngxMatDatetimePicker", "min", "max", "matDatepickerFilter"], exportAs: ["ngxMatDatepickerInput"] }] }); }
4089
+ ], ngImport: i0, template: "<div class=\"datetime-wrapper\" [class.datetime-mode]=\"isDateTime\" [class.has-seconds]=\"showSeconds\">\n <mat-form-field class=\"date-field\">\n @if (display) {\n <mat-label>{{ display }}</mat-label>\n }\n <input\n matInput\n [matDatepicker]=\"picker\"\n [placeholder]=\"placeHolder\"\n [formControl]=\"dateControl\"\n [disabled]=\"isDisabled\"\n (dateChange)=\"markTouched()\"\n (blur)=\"markTouched()\">\n <mat-datepicker-toggle matSuffix [for]=\"picker\"></mat-datepicker-toggle>\n <mat-datepicker #picker></mat-datepicker>\n </mat-form-field>\n\n @if (isDateTime) {\n <div class=\"middle-actions\">\n <button\n mat-icon-button\n type=\"button\"\n class=\"icon-action\"\n [disabled]=\"isDisabled\"\n title=\"Clear date and time\"\n aria-label=\"Clear date and time\"\n (click)=\"clear()\">\n <i class=\"fal fa-eraser\"></i>\n </button>\n\n <button\n mat-icon-button\n type=\"button\"\n class=\"icon-action\"\n [disabled]=\"isDisabled\"\n title=\"Open time clock\"\n aria-label=\"Open time clock\"\n (click)=\"openClock()\">\n <i class=\"fal fa-clock\"></i>\n </button>\n </div>\n\n <div class=\"time-row\">\n <mat-form-field class=\"time-field\">\n <mat-label>HH</mat-label>\n <input\n matInput\n type=\"number\"\n min=\"0\"\n max=\"23\"\n inputmode=\"numeric\"\n [formControl]=\"hourControl\"\n [disabled]=\"isDisabled\"\n (input)=\"onTimePartInput('hour')\"\n (blur)=\"onTimePartBlur('hour')\">\n </mat-form-field>\n\n <mat-form-field class=\"time-field\">\n <mat-label>MM</mat-label>\n <input\n matInput\n type=\"number\"\n min=\"0\"\n max=\"59\"\n inputmode=\"numeric\"\n [formControl]=\"minuteControl\"\n [disabled]=\"isDisabled\"\n (input)=\"onTimePartInput('minute')\"\n (blur)=\"onTimePartBlur('minute')\">\n </mat-form-field>\n\n @if (showSeconds) {\n <mat-form-field class=\"time-field\">\n <mat-label>SS</mat-label>\n <input\n matInput\n type=\"number\"\n min=\"0\"\n max=\"59\"\n inputmode=\"numeric\"\n [formControl]=\"secondControl\"\n [disabled]=\"isDisabled\"\n (input)=\"onTimePartInput('second')\"\n (blur)=\"onTimePartBlur('second')\">\n </mat-form-field>\n }\n </div>\n\n @if (isClockOpen) {\n <div class=\"clock-backdrop\" (click)=\"closeClock()\"></div>\n\n <div class=\"clock-dialog\" (click)=\"$event.stopPropagation()\">\n <div class=\"clock-panel\">\n <div class=\"clock-panel-header\">\n <div class=\"clock-panel-title\">{{ clockTitle }}</div>\n <button\n mat-button\n type=\"button\"\n class=\"clock-close\"\n [disabled]=\"isDisabled\"\n (click)=\"closeClock()\">\n Close\n </button>\n </div>\n\n <div class=\"clock-summary\">\n <button mat-button type=\"button\" class=\"clock-step\" [class.active]=\"clockStep === 'hour'\" (click)=\"goToClockStep('hour')\">\n {{ hourControl.value || '00' }}\n </button>\n <span>:</span>\n <button mat-button type=\"button\" class=\"clock-step\" [class.active]=\"clockStep === 'minute'\" (click)=\"goToClockStep('minute')\">\n {{ minuteControl.value || '00' }}\n </button>\n @if (showSeconds) {\n <span>:</span>\n <button mat-button type=\"button\" class=\"clock-step\" [class.active]=\"clockStep === 'second'\" (click)=\"goToClockStep('second')\">\n {{ secondControl.value || '00' }}\n </button>\n }\n </div>\n\n <div class=\"clock-face\" [class.clickable-face]=\"clockStep !== 'hour'\" [class.hour-face]=\"clockStep === 'hour'\" (click)=\"onClockFaceClick($event)\">\n <div class=\"clock-hand clock-hour-hand\" [style.transform]=\"hourHandTransform\" [style.height]=\"hourHandHeight\"></div>\n <div class=\"clock-hand clock-minute-hand\" [style.transform]=\"minuteHandTransform\" [style.height]=\"minuteHandHeight\"></div>\n\n @if (clockStep === 'hour') {\n @for (marker of hourMarkers; track marker.value) {\n <button\n type=\"button\"\n class=\"clock-hour-label\"\n [class.selected]=\"isHourSelected(marker.value)\"\n [class.inner-ring]=\"marker.value >= 12\"\n [style.left]=\"marker.left\"\n [style.top]=\"marker.top\"\n (click)=\"selectClockHour(marker.value, $event)\">\n {{ marker.label }}\n </button>\n }\n }\n\n @if (clockStep !== 'hour') {\n <div\n class=\"clock-hour-indicator\"\n [class.inner-ring]=\"selectedHourMarker.value >= 12\"\n [style.left]=\"selectedHourMarker.left\"\n [style.top]=\"selectedHourMarker.top\">\n {{ selectedHourMarker.label }}\n </div>\n }\n\n @if (clockStep === 'minute') {\n <svg class=\"clock-ticks-svg\" viewBox=\"0 0 100 100\" preserveAspectRatio=\"none\" aria-hidden=\"true\">\n @for (tick of minuteTicks; track tick.value) {\n <line\n class=\"clock-tick-line\"\n [class.selected]=\"isMinuteSelected(tick.value)\"\n [attr.x1]=\"tick.x1\"\n [attr.y1]=\"tick.y1\"\n [attr.x2]=\"tick.x2\"\n [attr.y2]=\"tick.y2\"\n (click)=\"selectClockTick(tick.value, $event)\"></line>\n }\n </svg>\n @for (tick of minuteTicks; track tick.value) {\n <div\n class=\"clock-tick-label\"\n [class.selected]=\"isMinuteSelected(tick.value)\"\n [style.left]=\"tick.labelLeft\"\n [style.top]=\"tick.labelTop\"\n (click)=\"selectClockTick(tick.value, $event)\">\n {{ tick.label }}\n </div>\n }\n }\n\n @if (clockStep === 'second') {\n <svg class=\"clock-ticks-svg\" viewBox=\"0 0 100 100\" preserveAspectRatio=\"none\" aria-hidden=\"true\">\n @for (tick of secondTicks; track tick.value) {\n <line\n class=\"clock-tick-line\"\n [class.selected]=\"isSecondSelected(tick.value)\"\n [attr.x1]=\"tick.x1\"\n [attr.y1]=\"tick.y1\"\n [attr.x2]=\"tick.x2\"\n [attr.y2]=\"tick.y2\"\n (click)=\"selectClockTick(tick.value, $event)\"></line>\n }\n </svg>\n @for (tick of secondTicks; track tick.value) {\n <div\n class=\"clock-tick-label\"\n [class.selected]=\"isSecondSelected(tick.value)\"\n [style.left]=\"tick.labelLeft\"\n [style.top]=\"tick.labelTop\"\n (click)=\"selectClockTick(tick.value, $event)\">\n {{ tick.label }}\n </div>\n }\n }\n\n <div class=\"clock-center-dot\"></div>\n </div>\n\n <div class=\"clock-help\">\n @if (clockStep === 'hour') {\n <span>Outer ring 00-11, inner ring 12-23.</span>\n }\n @if (clockStep === 'minute') {\n <span>Click the dial. The nearest minute will be selected.</span>\n }\n @if (clockStep === 'second') {\n <span>Click the dial. The nearest second will be selected.</span>\n }\n </div>\n\n <div class=\"clock-footer\">\n <span>{{ timeSummary }}</span>\n </div>\n </div>\n </div>\n }\n }\n</div>\n", styles: [":host{display:block;width:100%;container-type:inline-size}.datetime-wrapper{display:flex;flex-direction:column;gap:8px;width:100%}.date-field,.time-field{width:100%}.middle-actions{display:flex;align-items:center;gap:4px;justify-content:flex-start}.icon-action{flex:0 0 auto}.icon-action i{font-size:1rem;line-height:1}.time-row{display:grid;gap:8px;grid-template-columns:repeat(2,minmax(0,1fr))}.clock-backdrop{position:fixed;inset:0;z-index:1000;background:#0000002e}.clock-dialog{position:fixed;z-index:1001;top:50%;left:50%;width:min(92vw,360px);transform:translate(-50%,-50%)}.clock-panel{display:flex;flex-direction:column;gap:10px;padding:12px;border:1px solid rgba(0,0,0,.12);border-radius:16px;background:#fff;box-shadow:0 18px 36px #0003}.clock-panel-header,.clock-summary,.clock-footer{display:flex;align-items:center;justify-content:space-between;gap:8px}.clock-panel-title{font-size:.95rem;font-weight:600}.clock-summary{justify-content:center;font-size:1.1rem}.clock-step{min-width:52px;font-weight:600}.clock-step.active{background:#1976d21f}.clock-face{position:relative;align-self:center;width:min(100%,280px);aspect-ratio:1;border-radius:50%;overflow:hidden;background:radial-gradient(circle at center,rgba(25,118,210,.08) 0 16%,transparent 16% 100%),radial-gradient(circle at center,transparent 0 61%,rgba(25,118,210,.08) 61% 62%,transparent 62% 100%),radial-gradient(circle at center,#0000000a 0 100%)}.clock-face.clickable-face{cursor:crosshair}.clock-hand{position:absolute;top:50%;left:50%;width:2px;transform-origin:center bottom;background:#1976d2;border-radius:999px;z-index:1}.clock-hour-hand{background:#1976d2b8;width:4px}.clock-minute-hand{background:#1976d2;width:2px}.clock-hour-label{position:absolute;transform:translate(-50%,-50%);border:0;padding:0;margin:0;min-width:0;width:auto;height:auto;font-size:.72rem;line-height:1;background:transparent;box-shadow:none;color:#000000d1;cursor:pointer}.clock-hour-label.inner-ring{font-size:.68rem}.clock-hour-label.selected{color:#1976d2;font-weight:700}.clock-hour-indicator{position:absolute;transform:translate(-50%,-50%);font-size:.76rem;line-height:1;font-weight:800;color:#1976d2;z-index:2}.clock-hour-indicator.inner-ring{font-size:.7rem}.clock-ticks-svg{position:absolute;inset:0;width:100%;height:100%;overflow:visible}.clock-tick-line{stroke:#00000057;stroke-width:1.5;stroke-linecap:round;cursor:pointer}.clock-tick-line.selected{stroke:#1976d2;stroke-width:2.5}.clock-tick-label{position:absolute;transform:translate(-50%,-50%);font-size:.68rem;line-height:1;color:#000000b8}.clock-tick-label.selected{color:#1976d2;font-weight:700}.clock-center-dot{position:absolute;top:50%;left:50%;width:12px;height:12px;border-radius:50%;transform:translate(-50%,-50%);background:#1976d2;z-index:2}.hour-face .clock-hour-label:hover,.hour-face .clock-hour-label:focus-visible{color:#1976d2;outline:none}.clock-help,.clock-footer{font-size:.78rem;color:#000000ad}@container (min-width: 420px){.time-row{grid-template-columns:repeat(3,minmax(0,1fr))}}@container (min-width: 760px){.datetime-wrapper.datetime-mode{display:grid;align-items:start;gap:8px;grid-template-columns:minmax(220px,2fr) auto repeat(2,minmax(74px,88px))}.datetime-wrapper.datetime-mode.has-seconds{grid-template-columns:minmax(220px,2fr) auto repeat(3,minmax(74px,88px))}.datetime-wrapper.datetime-mode .date-field{margin-bottom:0}.datetime-wrapper.datetime-mode .middle-actions{align-self:start;padding-top:4px}.datetime-wrapper.datetime-mode .time-row{display:contents}.datetime-wrapper.datetime-mode .clock-panel{grid-column:1/-1}}\n"], dependencies: [{ kind: "ngmodule", type: ReactiveFormsModule }, { kind: "directive", type: i1$3.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1$3.NumberValueAccessor, selector: "input[type=number][formControlName],input[type=number][formControl],input[type=number][ngModel]" }, { kind: "directive", type: i1$3.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1$3.MinValidator, selector: "input[type=number][min][formControlName],input[type=number][min][formControl],input[type=number][min][ngModel]", inputs: ["min"] }, { kind: "directive", type: i1$3.MaxValidator, selector: "input[type=number][max][formControlName],input[type=number][max][formControl],input[type=number][max][ngModel]", inputs: ["max"] }, { kind: "directive", type: i1$3.FormControlDirective, selector: "[formControl]", inputs: ["formControl", "disabled", "ngModel"], outputs: ["ngModelChange"], exportAs: ["ngForm"] }, { kind: "component", type: MatFormField$1, selector: "mat-form-field", inputs: ["hideRequiredMarker", "color", "floatLabel", "appearance", "subscriptSizing", "hintLabel"], exportAs: ["matFormField"] }, { kind: "directive", type: MatLabel$1, selector: "mat-label" }, { kind: "directive", type: MatInput, selector: "input[matInput], textarea[matInput], select[matNativeControl], input[matNativeControl], textarea[matNativeControl]", inputs: ["disabled", "id", "placeholder", "name", "required", "type", "errorStateMatcher", "aria-describedby", "value", "readonly", "disabledInteractive"], exportAs: ["matInput"] }, { kind: "directive", type: MatDatepickerInput, selector: "input[matDatepicker]", inputs: ["matDatepicker", "min", "max", "matDatepickerFilter"], exportAs: ["matDatepickerInput"] }, { kind: "component", type: MatDatepickerToggle, selector: "mat-datepicker-toggle", inputs: ["for", "tabIndex", "aria-label", "disabled", "disableRipple"], exportAs: ["matDatepickerToggle"] }, { kind: "component", type: MatDatepicker, selector: "mat-datepicker", exportAs: ["matDatepicker"] }, { kind: "directive", type: MatSuffix, selector: "[matSuffix], [matIconSuffix], [matTextSuffix]", inputs: ["matTextSuffix"] }, { kind: "component", type: MatButton, selector: " button[matButton], a[matButton], button[mat-button], button[mat-raised-button], button[mat-flat-button], button[mat-stroked-button], a[mat-button], a[mat-raised-button], a[mat-flat-button], a[mat-stroked-button] ", inputs: ["matButton"], exportAs: ["matButton", "matAnchor"] }] }); }
3571
4090
  }
3572
4091
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: DatetimeComponent, decorators: [{
3573
4092
  type: Component,
3574
- args: [{ selector: 'gloww-datetime', providers: [
4093
+ args: [{ selector: 'gloww-datetime', standalone: true, providers: [
3575
4094
  {
3576
4095
  provide: NG_VALUE_ACCESSOR,
3577
4096
  multi: true,
3578
- useExisting: DatetimeComponent
4097
+ useExisting: forwardRef(() => DatetimeComponent)
3579
4098
  }
3580
- ], imports: [MatFormField, MatLabel, MatInput, MatDatepickerInput, FormsModule, MatDatepickerToggle, MatSuffix, MatDatepicker, NgxMatDatetimePickerModule], template: "<div style=\"width:100%\">\n @if (mode==='date') {\n <mat-form-field>\n <mat-label>{{display}}</mat-label>\n <input matInput [matDatepicker]=\"picker\" [placeholder]=\"placeHolder\" [(ngModel)]=\"value\">\n <mat-datepicker-toggle matSuffix [for]=\"picker\"></mat-datepicker-toggle>\n <mat-datepicker #picker></mat-datepicker>\n </mat-form-field>\n }\n\n @if (mode==='datetime') {\n <mat-form-field>\n <mat-label>{{display}}</mat-label>\n <input matInput [ngxMatDatetimePicker]=\"pickerDT\" [placeholder]=\"placeHolder\" [(ngModel)]=\"value\">\n <mat-datepicker-toggle matSuffix [for]=\"$any(pickerDT)\"></mat-datepicker-toggle>\n <ngx-mat-datetime-picker #pickerDT [showSpinners]=\"showSpinners\" [showSeconds]=\"showSeconds\" [touchUi]=\"true\" [disableMinute]=\"disableMinute\">\n </ngx-mat-datetime-picker>\n </mat-form-field>\n }\n</div>\n" }]
3581
- }], ctorParameters: () => [], propDecorators: { _value: [{
4099
+ ], imports: [ReactiveFormsModule, MatFormField$1, MatLabel$1, MatInput, MatDatepickerInput, MatDatepickerToggle, MatDatepicker, MatSuffix, MatButton], template: "<div class=\"datetime-wrapper\" [class.datetime-mode]=\"isDateTime\" [class.has-seconds]=\"showSeconds\">\n <mat-form-field class=\"date-field\">\n @if (display) {\n <mat-label>{{ display }}</mat-label>\n }\n <input\n matInput\n [matDatepicker]=\"picker\"\n [placeholder]=\"placeHolder\"\n [formControl]=\"dateControl\"\n [disabled]=\"isDisabled\"\n (dateChange)=\"markTouched()\"\n (blur)=\"markTouched()\">\n <mat-datepicker-toggle matSuffix [for]=\"picker\"></mat-datepicker-toggle>\n <mat-datepicker #picker></mat-datepicker>\n </mat-form-field>\n\n @if (isDateTime) {\n <div class=\"middle-actions\">\n <button\n mat-icon-button\n type=\"button\"\n class=\"icon-action\"\n [disabled]=\"isDisabled\"\n title=\"Clear date and time\"\n aria-label=\"Clear date and time\"\n (click)=\"clear()\">\n <i class=\"fal fa-eraser\"></i>\n </button>\n\n <button\n mat-icon-button\n type=\"button\"\n class=\"icon-action\"\n [disabled]=\"isDisabled\"\n title=\"Open time clock\"\n aria-label=\"Open time clock\"\n (click)=\"openClock()\">\n <i class=\"fal fa-clock\"></i>\n </button>\n </div>\n\n <div class=\"time-row\">\n <mat-form-field class=\"time-field\">\n <mat-label>HH</mat-label>\n <input\n matInput\n type=\"number\"\n min=\"0\"\n max=\"23\"\n inputmode=\"numeric\"\n [formControl]=\"hourControl\"\n [disabled]=\"isDisabled\"\n (input)=\"onTimePartInput('hour')\"\n (blur)=\"onTimePartBlur('hour')\">\n </mat-form-field>\n\n <mat-form-field class=\"time-field\">\n <mat-label>MM</mat-label>\n <input\n matInput\n type=\"number\"\n min=\"0\"\n max=\"59\"\n inputmode=\"numeric\"\n [formControl]=\"minuteControl\"\n [disabled]=\"isDisabled\"\n (input)=\"onTimePartInput('minute')\"\n (blur)=\"onTimePartBlur('minute')\">\n </mat-form-field>\n\n @if (showSeconds) {\n <mat-form-field class=\"time-field\">\n <mat-label>SS</mat-label>\n <input\n matInput\n type=\"number\"\n min=\"0\"\n max=\"59\"\n inputmode=\"numeric\"\n [formControl]=\"secondControl\"\n [disabled]=\"isDisabled\"\n (input)=\"onTimePartInput('second')\"\n (blur)=\"onTimePartBlur('second')\">\n </mat-form-field>\n }\n </div>\n\n @if (isClockOpen) {\n <div class=\"clock-backdrop\" (click)=\"closeClock()\"></div>\n\n <div class=\"clock-dialog\" (click)=\"$event.stopPropagation()\">\n <div class=\"clock-panel\">\n <div class=\"clock-panel-header\">\n <div class=\"clock-panel-title\">{{ clockTitle }}</div>\n <button\n mat-button\n type=\"button\"\n class=\"clock-close\"\n [disabled]=\"isDisabled\"\n (click)=\"closeClock()\">\n Close\n </button>\n </div>\n\n <div class=\"clock-summary\">\n <button mat-button type=\"button\" class=\"clock-step\" [class.active]=\"clockStep === 'hour'\" (click)=\"goToClockStep('hour')\">\n {{ hourControl.value || '00' }}\n </button>\n <span>:</span>\n <button mat-button type=\"button\" class=\"clock-step\" [class.active]=\"clockStep === 'minute'\" (click)=\"goToClockStep('minute')\">\n {{ minuteControl.value || '00' }}\n </button>\n @if (showSeconds) {\n <span>:</span>\n <button mat-button type=\"button\" class=\"clock-step\" [class.active]=\"clockStep === 'second'\" (click)=\"goToClockStep('second')\">\n {{ secondControl.value || '00' }}\n </button>\n }\n </div>\n\n <div class=\"clock-face\" [class.clickable-face]=\"clockStep !== 'hour'\" [class.hour-face]=\"clockStep === 'hour'\" (click)=\"onClockFaceClick($event)\">\n <div class=\"clock-hand clock-hour-hand\" [style.transform]=\"hourHandTransform\" [style.height]=\"hourHandHeight\"></div>\n <div class=\"clock-hand clock-minute-hand\" [style.transform]=\"minuteHandTransform\" [style.height]=\"minuteHandHeight\"></div>\n\n @if (clockStep === 'hour') {\n @for (marker of hourMarkers; track marker.value) {\n <button\n type=\"button\"\n class=\"clock-hour-label\"\n [class.selected]=\"isHourSelected(marker.value)\"\n [class.inner-ring]=\"marker.value >= 12\"\n [style.left]=\"marker.left\"\n [style.top]=\"marker.top\"\n (click)=\"selectClockHour(marker.value, $event)\">\n {{ marker.label }}\n </button>\n }\n }\n\n @if (clockStep !== 'hour') {\n <div\n class=\"clock-hour-indicator\"\n [class.inner-ring]=\"selectedHourMarker.value >= 12\"\n [style.left]=\"selectedHourMarker.left\"\n [style.top]=\"selectedHourMarker.top\">\n {{ selectedHourMarker.label }}\n </div>\n }\n\n @if (clockStep === 'minute') {\n <svg class=\"clock-ticks-svg\" viewBox=\"0 0 100 100\" preserveAspectRatio=\"none\" aria-hidden=\"true\">\n @for (tick of minuteTicks; track tick.value) {\n <line\n class=\"clock-tick-line\"\n [class.selected]=\"isMinuteSelected(tick.value)\"\n [attr.x1]=\"tick.x1\"\n [attr.y1]=\"tick.y1\"\n [attr.x2]=\"tick.x2\"\n [attr.y2]=\"tick.y2\"\n (click)=\"selectClockTick(tick.value, $event)\"></line>\n }\n </svg>\n @for (tick of minuteTicks; track tick.value) {\n <div\n class=\"clock-tick-label\"\n [class.selected]=\"isMinuteSelected(tick.value)\"\n [style.left]=\"tick.labelLeft\"\n [style.top]=\"tick.labelTop\"\n (click)=\"selectClockTick(tick.value, $event)\">\n {{ tick.label }}\n </div>\n }\n }\n\n @if (clockStep === 'second') {\n <svg class=\"clock-ticks-svg\" viewBox=\"0 0 100 100\" preserveAspectRatio=\"none\" aria-hidden=\"true\">\n @for (tick of secondTicks; track tick.value) {\n <line\n class=\"clock-tick-line\"\n [class.selected]=\"isSecondSelected(tick.value)\"\n [attr.x1]=\"tick.x1\"\n [attr.y1]=\"tick.y1\"\n [attr.x2]=\"tick.x2\"\n [attr.y2]=\"tick.y2\"\n (click)=\"selectClockTick(tick.value, $event)\"></line>\n }\n </svg>\n @for (tick of secondTicks; track tick.value) {\n <div\n class=\"clock-tick-label\"\n [class.selected]=\"isSecondSelected(tick.value)\"\n [style.left]=\"tick.labelLeft\"\n [style.top]=\"tick.labelTop\"\n (click)=\"selectClockTick(tick.value, $event)\">\n {{ tick.label }}\n </div>\n }\n }\n\n <div class=\"clock-center-dot\"></div>\n </div>\n\n <div class=\"clock-help\">\n @if (clockStep === 'hour') {\n <span>Outer ring 00-11, inner ring 12-23.</span>\n }\n @if (clockStep === 'minute') {\n <span>Click the dial. The nearest minute will be selected.</span>\n }\n @if (clockStep === 'second') {\n <span>Click the dial. The nearest second will be selected.</span>\n }\n </div>\n\n <div class=\"clock-footer\">\n <span>{{ timeSummary }}</span>\n </div>\n </div>\n </div>\n }\n }\n</div>\n", styles: [":host{display:block;width:100%;container-type:inline-size}.datetime-wrapper{display:flex;flex-direction:column;gap:8px;width:100%}.date-field,.time-field{width:100%}.middle-actions{display:flex;align-items:center;gap:4px;justify-content:flex-start}.icon-action{flex:0 0 auto}.icon-action i{font-size:1rem;line-height:1}.time-row{display:grid;gap:8px;grid-template-columns:repeat(2,minmax(0,1fr))}.clock-backdrop{position:fixed;inset:0;z-index:1000;background:#0000002e}.clock-dialog{position:fixed;z-index:1001;top:50%;left:50%;width:min(92vw,360px);transform:translate(-50%,-50%)}.clock-panel{display:flex;flex-direction:column;gap:10px;padding:12px;border:1px solid rgba(0,0,0,.12);border-radius:16px;background:#fff;box-shadow:0 18px 36px #0003}.clock-panel-header,.clock-summary,.clock-footer{display:flex;align-items:center;justify-content:space-between;gap:8px}.clock-panel-title{font-size:.95rem;font-weight:600}.clock-summary{justify-content:center;font-size:1.1rem}.clock-step{min-width:52px;font-weight:600}.clock-step.active{background:#1976d21f}.clock-face{position:relative;align-self:center;width:min(100%,280px);aspect-ratio:1;border-radius:50%;overflow:hidden;background:radial-gradient(circle at center,rgba(25,118,210,.08) 0 16%,transparent 16% 100%),radial-gradient(circle at center,transparent 0 61%,rgba(25,118,210,.08) 61% 62%,transparent 62% 100%),radial-gradient(circle at center,#0000000a 0 100%)}.clock-face.clickable-face{cursor:crosshair}.clock-hand{position:absolute;top:50%;left:50%;width:2px;transform-origin:center bottom;background:#1976d2;border-radius:999px;z-index:1}.clock-hour-hand{background:#1976d2b8;width:4px}.clock-minute-hand{background:#1976d2;width:2px}.clock-hour-label{position:absolute;transform:translate(-50%,-50%);border:0;padding:0;margin:0;min-width:0;width:auto;height:auto;font-size:.72rem;line-height:1;background:transparent;box-shadow:none;color:#000000d1;cursor:pointer}.clock-hour-label.inner-ring{font-size:.68rem}.clock-hour-label.selected{color:#1976d2;font-weight:700}.clock-hour-indicator{position:absolute;transform:translate(-50%,-50%);font-size:.76rem;line-height:1;font-weight:800;color:#1976d2;z-index:2}.clock-hour-indicator.inner-ring{font-size:.7rem}.clock-ticks-svg{position:absolute;inset:0;width:100%;height:100%;overflow:visible}.clock-tick-line{stroke:#00000057;stroke-width:1.5;stroke-linecap:round;cursor:pointer}.clock-tick-line.selected{stroke:#1976d2;stroke-width:2.5}.clock-tick-label{position:absolute;transform:translate(-50%,-50%);font-size:.68rem;line-height:1;color:#000000b8}.clock-tick-label.selected{color:#1976d2;font-weight:700}.clock-center-dot{position:absolute;top:50%;left:50%;width:12px;height:12px;border-radius:50%;transform:translate(-50%,-50%);background:#1976d2;z-index:2}.hour-face .clock-hour-label:hover,.hour-face .clock-hour-label:focus-visible{color:#1976d2;outline:none}.clock-help,.clock-footer{font-size:.78rem;color:#000000ad}@container (min-width: 420px){.time-row{grid-template-columns:repeat(3,minmax(0,1fr))}}@container (min-width: 760px){.datetime-wrapper.datetime-mode{display:grid;align-items:start;gap:8px;grid-template-columns:minmax(220px,2fr) auto repeat(2,minmax(74px,88px))}.datetime-wrapper.datetime-mode.has-seconds{grid-template-columns:minmax(220px,2fr) auto repeat(3,minmax(74px,88px))}.datetime-wrapper.datetime-mode .date-field{margin-bottom:0}.datetime-wrapper.datetime-mode .middle-actions{align-self:start;padding-top:4px}.datetime-wrapper.datetime-mode .time-row{display:contents}.datetime-wrapper.datetime-mode .clock-panel{grid-column:1/-1}}\n"] }]
4100
+ }], ctorParameters: () => [{ type: undefined, decorators: [{
4101
+ type: Optional
4102
+ }, {
4103
+ type: Inject,
4104
+ args: [MAT_DATE_LOCALE]
4105
+ }] }], propDecorators: { _value: [{
3582
4106
  type: Input,
3583
4107
  args: ['value']
3584
4108
  }], display: [{
@@ -3590,14 +4114,56 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImpo
3590
4114
  }], mode: [{
3591
4115
  type: Input,
3592
4116
  args: ['mode']
3593
- }], showSpinners: [{
3594
- type: Input
3595
4117
  }], showSeconds: [{
3596
4118
  type: Input
3597
- }], disableMinute: [{
3598
- type: Input
3599
4119
  }] } });
3600
4120
 
4121
+ class CallbackDirective {
4122
+ constructor() { }
4123
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: CallbackDirective, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
4124
+ static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "20.3.18", type: CallbackDirective, isStandalone: true, selector: "[glowwCallback]", ngImport: i0 }); }
4125
+ }
4126
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: CallbackDirective, decorators: [{
4127
+ type: Directive,
4128
+ args: [{
4129
+ selector: '[glowwCallback]',
4130
+ standalone: true
4131
+ }]
4132
+ }], ctorParameters: () => [] });
4133
+
4134
+ class GlowwMatPaginatorIntlService extends MatPaginatorIntl {
4135
+ constructor(i18n) {
4136
+ super();
4137
+ this.i18n = i18n;
4138
+ this.getRangeLabel = (page, pageSize, length) => {
4139
+ if (length === 0 || pageSize === 0) {
4140
+ return `0 ${this.i18n.instant('PAGINATOR.OF', 'of')} ${length}`;
4141
+ }
4142
+ const startIndex = page * pageSize;
4143
+ const endIndex = Math.min(startIndex + pageSize, length);
4144
+ return `${startIndex + 1}-${endIndex} ${this.i18n.instant('PAGINATOR.OF', 'of')} ${length}`;
4145
+ };
4146
+ this.subscription = this.i18n.langChanges$.subscribe(() => this.translateLabels());
4147
+ this.translateLabels();
4148
+ }
4149
+ ngOnDestroy() {
4150
+ this.subscription.unsubscribe();
4151
+ }
4152
+ translateLabels() {
4153
+ this.itemsPerPageLabel = this.i18n.instant('PAGINATOR.ITEMS_PER_PAGE', 'Items per page');
4154
+ this.nextPageLabel = this.i18n.instant('PAGINATOR.NEXT_PAGE', 'Next page');
4155
+ this.previousPageLabel = this.i18n.instant('PAGINATOR.PREVIOUS_PAGE', 'Previous page');
4156
+ this.firstPageLabel = this.i18n.instant('PAGINATOR.FIRST_PAGE', 'First page');
4157
+ this.lastPageLabel = this.i18n.instant('PAGINATOR.LAST_PAGE', 'Last page');
4158
+ this.changes.next();
4159
+ }
4160
+ static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: GlowwMatPaginatorIntlService, deps: [{ token: GlowwI18nService }], target: i0.ɵɵFactoryTarget.Injectable }); }
4161
+ static { this.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: GlowwMatPaginatorIntlService }); }
4162
+ }
4163
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: GlowwMatPaginatorIntlService, decorators: [{
4164
+ type: Injectable
4165
+ }], ctorParameters: () => [{ type: GlowwI18nService }] });
4166
+
3601
4167
  class BaseCollectionComponent {
3602
4168
  constructor(_formBuilder) {
3603
4169
  this._formBuilder = _formBuilder;
@@ -3639,26 +4205,67 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImpo
3639
4205
  type: Injectable
3640
4206
  }] });
3641
4207
 
4208
+ const GLOWW_STANDALONE_DECLARATIONS = [
4209
+ UploadDocComponent,
4210
+ SafeHtmlPipe,
4211
+ DisplayObjectsComponent,
4212
+ HeaderComponent,
4213
+ ResultTableComponent,
4214
+ SearchFormComponent,
4215
+ ConfirmationComponent,
4216
+ PromptComponent,
4217
+ SecurePipe,
4218
+ SecureImgComponent,
4219
+ MenuListItemComponent,
4220
+ CodeEditorComponent,
4221
+ HtmlEditorComponent,
4222
+ HtmlFormatPipe,
4223
+ UploadFileComponent,
4224
+ FileSinkDirective,
4225
+ FileEditComponent,
4226
+ FoldersComponent,
4227
+ DownloadProgressComponent,
4228
+ SecureAComponent,
4229
+ DummyComponent,
4230
+ SelectComponent,
4231
+ AutoCompleteComponent,
4232
+ DatetimeComponent,
4233
+ RouteDirective,
4234
+ CallbackDirective,
4235
+ FilterFormComponent
4236
+ ];
4237
+ const GLOWW_MODULE_EXPORTS = [
4238
+ ...GLOWW_STANDALONE_DECLARATIONS,
4239
+ MatDatepickerModule,
4240
+ NgxMatDatetimePickerModule,
4241
+ NgxMatTimepickerComponent,
4242
+ NgxMatNativeDateModule
4243
+ ];
4244
+ function getGlowwProviders(folderServiceConfig) {
4245
+ return [
4246
+ VersionCheckService,
4247
+ NavService,
4248
+ VoiceRecognitionService,
4249
+ {
4250
+ provide: FolderServiceConfig,
4251
+ useValue: folderServiceConfig
4252
+ },
4253
+ { provide: MAT_DATE_LOCALE, useValue: 'fr' }
4254
+ ];
4255
+ }
4256
+ function provideGloww(folderServiceConfig) {
4257
+ return makeEnvironmentProviders(getGlowwProviders(folderServiceConfig));
4258
+ }
3642
4259
  class GlowwModule {
3643
4260
  static forRoot(folderServiceConfig) {
3644
4261
  console.log(`forRoot ${folderServiceConfig}`);
3645
4262
  return {
3646
4263
  ngModule: GlowwModule,
3647
- providers: [
3648
- VersionCheckService,
3649
- NavService,
3650
- VoiceRecognitionService,
3651
- {
3652
- provide: FolderServiceConfig,
3653
- useValue: folderServiceConfig
3654
- },
3655
- { provide: MAT_DATE_LOCALE, useValue: 'fr' }
3656
- ]
4264
+ providers: getGlowwProviders(folderServiceConfig)
3657
4265
  };
3658
4266
  }
3659
4267
  static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: GlowwModule, deps: [], target: i0.ɵɵFactoryTarget.NgModule }); }
3660
4268
  static { this.ɵmod = i0.ɵɵngDeclareNgModule({ minVersion: "14.0.0", version: "20.3.18", ngImport: i0, type: GlowwModule, imports: [CommonModule,
3661
- BrowserModule,
3662
4269
  RouterModule,
3663
4270
  FormsModule,
3664
4271
  ReactiveFormsModule,
@@ -3683,8 +4290,7 @@ class GlowwModule {
3683
4290
  NgxMatNativeDateModule, // Existe selon ta liste
3684
4291
  //NgxMatMomentModule,
3685
4292
  DragDropModule,
3686
- AngularResizeEventModule,
3687
- UploadDocComponent,
4293
+ AngularResizeEventModule, UploadDocComponent,
3688
4294
  SafeHtmlPipe,
3689
4295
  DisplayObjectsComponent,
3690
4296
  HeaderComponent,
@@ -3709,9 +4315,9 @@ class GlowwModule {
3709
4315
  AutoCompleteComponent,
3710
4316
  DatetimeComponent,
3711
4317
  RouteDirective,
3712
- FilterFormComponent], exports: [SafeHtmlPipe,
3713
- UploadDocComponent,
3714
- UploadFileComponent,
4318
+ CallbackDirective,
4319
+ FilterFormComponent], exports: [UploadDocComponent,
4320
+ SafeHtmlPipe,
3715
4321
  DisplayObjectsComponent,
3716
4322
  HeaderComponent,
3717
4323
  ResultTableComponent,
@@ -3724,6 +4330,9 @@ class GlowwModule {
3724
4330
  CodeEditorComponent,
3725
4331
  HtmlEditorComponent,
3726
4332
  HtmlFormatPipe,
4333
+ UploadFileComponent,
4334
+ FileSinkDirective,
4335
+ FileEditComponent,
3727
4336
  FoldersComponent,
3728
4337
  DownloadProgressComponent,
3729
4338
  SecureAComponent,
@@ -3731,14 +4340,13 @@ class GlowwModule {
3731
4340
  SelectComponent,
3732
4341
  AutoCompleteComponent,
3733
4342
  DatetimeComponent,
3734
- MatDatepickerModule,
3735
- NgxMatDatetimePickerModule, // Existe selon ta liste
3736
- NgxMatTimepickerComponent, // Attention : ta liste dit "NgxMatTimepickerComponent"
3737
- NgxMatNativeDateModule, // Existe selon ta liste
3738
- //NgxMatMomentModule,
3739
- FilterFormComponent] }); }
3740
- static { this.ɵinj = i0.ɵɵngDeclareInjector({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: GlowwModule, imports: [CommonModule,
3741
- BrowserModule,
4343
+ RouteDirective,
4344
+ CallbackDirective,
4345
+ FilterFormComponent, MatDatepickerModule,
4346
+ NgxMatDatetimePickerModule,
4347
+ NgxMatTimepickerComponent,
4348
+ NgxMatNativeDateModule] }); }
4349
+ static { this.ɵinj = i0.ɵɵngDeclareInjector({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: GlowwModule, providers: [{ provide: MatPaginatorIntl, useClass: GlowwMatPaginatorIntlService }], imports: [CommonModule,
3742
4350
  RouterModule,
3743
4351
  FormsModule,
3744
4352
  ReactiveFormsModule,
@@ -3763,8 +4371,7 @@ class GlowwModule {
3763
4371
  NgxMatNativeDateModule, // Existe selon ta liste
3764
4372
  //NgxMatMomentModule,
3765
4373
  DragDropModule,
3766
- AngularResizeEventModule,
3767
- UploadDocComponent,
4374
+ AngularResizeEventModule, UploadDocComponent,
3768
4375
  DisplayObjectsComponent,
3769
4376
  ConfirmationComponent,
3770
4377
  PromptComponent,
@@ -3779,7 +4386,7 @@ class GlowwModule {
3779
4386
  AutoCompleteComponent,
3780
4387
  DatetimeComponent,
3781
4388
  FilterFormComponent, MatDatepickerModule,
3782
- NgxMatDatetimePickerModule, // Attention : ta liste dit "NgxMatTimepickerComponent"
4389
+ NgxMatDatetimePickerModule,
3783
4390
  NgxMatNativeDateModule] }); }
3784
4391
  }
3785
4392
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImport: i0, type: GlowwModule, decorators: [{
@@ -3787,7 +4394,6 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImpo
3787
4394
  args: [{
3788
4395
  imports: [
3789
4396
  CommonModule,
3790
- BrowserModule,
3791
4397
  RouterModule,
3792
4398
  FormsModule,
3793
4399
  ReactiveFormsModule,
@@ -3813,64 +4419,10 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.18", ngImpo
3813
4419
  //NgxMatMomentModule,
3814
4420
  DragDropModule,
3815
4421
  AngularResizeEventModule,
3816
- UploadDocComponent,
3817
- SafeHtmlPipe,
3818
- DisplayObjectsComponent,
3819
- HeaderComponent,
3820
- ResultTableComponent,
3821
- SearchFormComponent,
3822
- ConfirmationComponent,
3823
- PromptComponent,
3824
- SecurePipe,
3825
- SecureImgComponent,
3826
- MenuListItemComponent,
3827
- CodeEditorComponent,
3828
- HtmlEditorComponent,
3829
- HtmlFormatPipe,
3830
- UploadFileComponent,
3831
- FileSinkDirective,
3832
- FileEditComponent,
3833
- FoldersComponent,
3834
- DownloadProgressComponent,
3835
- SecureAComponent,
3836
- DummyComponent,
3837
- SelectComponent,
3838
- AutoCompleteComponent,
3839
- DatetimeComponent,
3840
- RouteDirective,
3841
- FilterFormComponent
4422
+ ...GLOWW_STANDALONE_DECLARATIONS
3842
4423
  ],
3843
- providers: [],
3844
- exports: [
3845
- SafeHtmlPipe,
3846
- UploadDocComponent,
3847
- UploadFileComponent,
3848
- DisplayObjectsComponent,
3849
- HeaderComponent,
3850
- ResultTableComponent,
3851
- SearchFormComponent,
3852
- ConfirmationComponent,
3853
- PromptComponent,
3854
- SecurePipe,
3855
- SecureImgComponent,
3856
- MenuListItemComponent,
3857
- CodeEditorComponent,
3858
- HtmlEditorComponent,
3859
- HtmlFormatPipe,
3860
- FoldersComponent,
3861
- DownloadProgressComponent,
3862
- SecureAComponent,
3863
- DummyComponent,
3864
- SelectComponent,
3865
- AutoCompleteComponent,
3866
- DatetimeComponent,
3867
- MatDatepickerModule,
3868
- NgxMatDatetimePickerModule, // Existe selon ta liste
3869
- NgxMatTimepickerComponent, // Attention : ta liste dit "NgxMatTimepickerComponent"
3870
- NgxMatNativeDateModule, // Existe selon ta liste
3871
- //NgxMatMomentModule,
3872
- FilterFormComponent
3873
- ]
4424
+ providers: [{ provide: MatPaginatorIntl, useClass: GlowwMatPaginatorIntlService }],
4425
+ exports: [...GLOWW_MODULE_EXPORTS]
3874
4426
  }]
3875
4427
  }] });
3876
4428
 
@@ -4010,5 +4562,5 @@ class GlowwValidators {
4010
4562
  * Generated bundle index. Do not edit.
4011
4563
  */
4012
4564
 
4013
- export { API_SERVER_URL, AdministratorGuard, AuthGuard, AuthenticationService, AuthenticationServiceConfig, AutoCompleteComponent, BaseCollectionComponent, ChangePasswordDlgComponent, CodeEditorComponent, ConfirmationComponent, ConfirmationModel, DatetimeComponent, DialogService, DisplayObjectsComponent, DownloadProgressComponent, DummyComponent, ErrorInterceptor, FilterFormComponent, FolderService, FolderServiceConfig, FoldersComponent, GLOWW_APPLI, GlowwModule, GlowwSecurityModule, GlowwSecurityService, GlowwService, GlowwValidators, HasUnsavedDataGuard, HeaderComponent, HtmlEditorComponent, HtmlFormatPipe, JwtInterceptor, LoginComponent, MenuListItemComponent, NavService, PromptComponent, PromptModel, ResultTableComponent, SafeHtmlPipe, SearchFormComponent, SecureAComponent, SecureImgComponent, SecurePipe, SelectComponent, StagingInterceptor, UploadDocComponent, UploadFileComponent, UserMenuComponent, VersionCheckService, VoiceRecognitionService };
4565
+ export { API_SERVER_URL, AdministratorGuard, AuthGuard, AuthenticationService, AuthenticationServiceConfig, AutoCompleteComponent, BaseCollectionComponent, CallbackDirective, ChangePasswordDlgComponent, CodeEditorComponent, ConfirmationComponent, ConfirmationModel, DatetimeComponent, DialogService, DisplayObjectsComponent, DownloadProgressComponent, DummyComponent, ErrorInterceptor, FileEditComponent, FileSinkDirective, FilterFormComponent, FolderService, FolderServiceConfig, FoldersComponent, GLOWW_APPLI, GLOWW_MODULE_EXPORTS, GLOWW_SECURITY_STANDALONE_DECLARATIONS, GLOWW_STANDALONE_DECLARATIONS, GlowwModule, GlowwSecurityModule, GlowwSecurityService, GlowwService, GlowwValidators, HasUnsavedDataGuard, HeaderComponent, HtmlEditorComponent, HtmlFormatPipe, JwtInterceptor, LoginComponent, MenuListItemComponent, NavService, PromptComponent, PromptModel, ResultTableComponent, RouteDirective, SafeHtmlPipe, SearchFormComponent, SecureAComponent, SecureImgComponent, SecurePipe, SelectComponent, SocialNetworkComponent, SocialNetworkDlgComponent, StagingInterceptor, UploadDocComponent, UploadFileComponent, UserMenuComponent, VersionCheckService, VoiceRecognitionService, provideGloww, provideGlowwSecurity };
4014
4566
  //# sourceMappingURL=gloww-gloww.mjs.map