@sumaris-net/ngx-components 2.5.0-beta3 → 2.5.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/doc/changelog.md +6 -0
- package/esm2020/src/app/core/account/account.page.mjs +19 -14
- package/esm2020/src/app/core/form/entity/entity-editor.class.mjs +54 -38
- package/esm2020/src/app/core/table/entities-table-datasource.class.mjs +1 -1
- package/esm2020/src/app/shared/dates.mjs +7 -1
- package/esm2020/src/app/shared/material/autocomplete/material.autocomplete.mjs +11 -7
- package/esm2020/src/app/shared/material/datetime/material.datetime.mjs +3 -3
- package/esm2020/src/app/shared/shared-routing.module.mjs +14 -7
- package/esm2020/src/app/shared/toolbar/toolbar.mjs +7 -6
- package/fesm2015/sumaris-net.ngx-components.mjs +99 -68
- package/fesm2015/sumaris-net.ngx-components.mjs.map +1 -1
- package/fesm2020/sumaris-net.ngx-components.mjs +105 -68
- package/fesm2020/sumaris-net.ngx-components.mjs.map +1 -1
- package/package.json +3 -3
- package/src/app/core/form/entity/entity-editor.class.d.ts +9 -1
- package/src/app/shared/dates.d.ts +1 -0
- package/src/app/shared/toolbar/toolbar.d.ts +2 -2
|
@@ -60,7 +60,7 @@ import { timer, merge, fromEvent, BehaviorSubject, Subscription, Subject, isObse
|
|
|
60
60
|
import { filter, map, takeUntil, first, switchMap, tap, debounceTime, startWith, distinctUntilChanged, mergeMap, catchError, throttleTime, skip, bufferWhen, mapTo, take } from 'rxjs/operators';
|
|
61
61
|
import { trigger, transition, style, animate, state } from '@angular/animations';
|
|
62
62
|
import * as i1 from '@ionic/angular';
|
|
63
|
-
import { IonicModule, Platform, ToastController, IonicSafeString, createAnimation, IonicRouteStrategy, ModalController, AlertController, IonContent, IonItem, IonModal, IonInfiniteScroll } from '@ionic/angular';
|
|
63
|
+
import { IonicModule, Platform, ToastController, IonicSafeString, createAnimation, IonicRouteStrategy, ModalController, AlertController, IonContent, IonRouterOutlet, IonItem, IonModal, IonInfiniteScroll } from '@ionic/angular';
|
|
64
64
|
import { Capacitor } from '@capacitor/core';
|
|
65
65
|
import { Keyboard } from '@capacitor/keyboard';
|
|
66
66
|
import * as i1$2 from '@ngx-translate/core';
|
|
@@ -2492,7 +2492,7 @@ class MatAutocompleteField {
|
|
|
2492
2492
|
return;
|
|
2493
2493
|
// Hide the panel (will be show when ready)
|
|
2494
2494
|
this.matSelect.panelClass = 'cdk-visually-hidden';
|
|
2495
|
-
let
|
|
2495
|
+
let subscription;
|
|
2496
2496
|
this._subscription.add(this.matSelect.openedChange
|
|
2497
2497
|
.subscribe(async (open) => {
|
|
2498
2498
|
if (open) {
|
|
@@ -2503,13 +2503,17 @@ class MatAutocompleteField {
|
|
|
2503
2503
|
this._fixMatSelectPanelPosition(overlayPane);
|
|
2504
2504
|
// Fix overlay, for searchbar
|
|
2505
2505
|
if (this.showSearchBar) {
|
|
2506
|
-
|
|
2506
|
+
subscription = await this._fixSearchbarOverlay(panelElement, overlayPane);
|
|
2507
|
+
this._subscription.add(subscription);
|
|
2507
2508
|
}
|
|
2508
2509
|
// Show the panel
|
|
2509
2510
|
this.renderer.removeClass(panelElement, 'cdk-visually-hidden');
|
|
2510
2511
|
}
|
|
2511
|
-
|
|
2512
|
-
|
|
2512
|
+
// ON close
|
|
2513
|
+
else if (subscription) {
|
|
2514
|
+
subscription.unsubscribe();
|
|
2515
|
+
this._subscription.remove(subscription);
|
|
2516
|
+
subscription = null;
|
|
2513
2517
|
}
|
|
2514
2518
|
}));
|
|
2515
2519
|
}
|
|
@@ -2547,11 +2551,11 @@ class MatAutocompleteField {
|
|
|
2547
2551
|
this.renderer.setStyle(overlayPane, 'margin-top', `-${shiftTop}px`);
|
|
2548
2552
|
this.renderer.setStyle(overlayPane, 'margin-left', `-${shiftLeft}px`);
|
|
2549
2553
|
// Return the reverse function, to replace the container in body
|
|
2550
|
-
return () => {
|
|
2554
|
+
return new Subscription(() => {
|
|
2551
2555
|
// DEBUG
|
|
2552
2556
|
console.debug(`${this.logPrefix} moving the "cdk-overlay" container from the "ion-modal" to the "body" container`);
|
|
2553
2557
|
this.renderer.appendChild(originalParent /*this.document.body*/, overlayContainer);
|
|
2554
|
-
};
|
|
2558
|
+
});
|
|
2555
2559
|
}
|
|
2556
2560
|
}
|
|
2557
2561
|
MatAutocompleteField.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.2.12", ngImport: i0, type: MatAutocompleteField, deps: [{ token: i0.ChangeDetectorRef }, { token: i1.ModalController }, { token: i0.Renderer2 }, { token: DOCUMENT }, { token: ChangeDetectorRef }, { token: i1$3.FormGroupDirective, optional: true }], target: i0.ɵɵFactoryTarget.Component });
|
|
@@ -2744,6 +2748,12 @@ class DateUtils {
|
|
|
2744
2748
|
value[MOMENT_NO_TIME_PROPERTY] = true;
|
|
2745
2749
|
return value;
|
|
2746
2750
|
}
|
|
2751
|
+
static markTime(value) {
|
|
2752
|
+
if (!value)
|
|
2753
|
+
return undefined;
|
|
2754
|
+
delete value[MOMENT_NO_TIME_PROPERTY];
|
|
2755
|
+
return value;
|
|
2756
|
+
}
|
|
2747
2757
|
static isNoTime(value) {
|
|
2748
2758
|
return value?.[MOMENT_NO_TIME_PROPERTY] === true;
|
|
2749
2759
|
}
|
|
@@ -6518,9 +6528,9 @@ class MatDateTime {
|
|
|
6518
6528
|
.subscribe((_) => this.onFormChange()));
|
|
6519
6529
|
// Listen status changes (when done outside the component - e.g. when setErrors() is calling on the formControl)
|
|
6520
6530
|
this._subscription.add(this.formControl.statusChanges
|
|
6521
|
-
.pipe(filter((_) => !this.
|
|
6531
|
+
.pipe(filter((_) => !this._readonly && !this._writing && !this._disabling) // Skip
|
|
6522
6532
|
)
|
|
6523
|
-
.subscribe(() => this.markForCheck()));
|
|
6533
|
+
.subscribe((_) => this.markForCheck()));
|
|
6524
6534
|
this._writing = false;
|
|
6525
6535
|
}
|
|
6526
6536
|
ngAfterViewInit() {
|
|
@@ -19074,28 +19084,29 @@ class ToolbarComponent {
|
|
|
19074
19084
|
const replaceUrl = !this.routerOutlet.canGoBack();
|
|
19075
19085
|
// Relative href
|
|
19076
19086
|
if (this._backHref.startsWith('.')) {
|
|
19077
|
-
|
|
19087
|
+
return this.router.navigate([this._backHref], { relativeTo: this.route, replaceUrl });
|
|
19078
19088
|
}
|
|
19079
19089
|
else {
|
|
19080
|
-
|
|
19090
|
+
return this.router.navigateByUrl(this._backHref, { replaceUrl });
|
|
19081
19091
|
}
|
|
19082
19092
|
}
|
|
19083
19093
|
else if (this.routerOutlet.canGoBack()) {
|
|
19084
|
-
|
|
19094
|
+
return this.routerOutlet.pop();
|
|
19085
19095
|
}
|
|
19086
19096
|
else if (this._defaultBackHref) {
|
|
19087
19097
|
// Relative href
|
|
19088
19098
|
if (this._defaultBackHref.startsWith('.')) {
|
|
19089
|
-
|
|
19099
|
+
return this.router.navigate([this._defaultBackHref], { relativeTo: this.route, replaceUrl: true });
|
|
19090
19100
|
}
|
|
19091
19101
|
else {
|
|
19092
|
-
|
|
19102
|
+
return this.router.navigateByUrl(this._defaultBackHref, {
|
|
19093
19103
|
replaceUrl: true
|
|
19094
19104
|
});
|
|
19095
19105
|
}
|
|
19096
19106
|
}
|
|
19097
19107
|
else {
|
|
19098
19108
|
console.error('[toolbar] Cannot go back. Missing attribute \'defaultBackHref\' or \'backHref\'');
|
|
19109
|
+
return false;
|
|
19099
19110
|
}
|
|
19100
19111
|
}
|
|
19101
19112
|
tapClose(event) {
|
|
@@ -19715,9 +19726,9 @@ class CustomReuseStrategy extends IonicRouteStrategy {
|
|
|
19715
19726
|
* @param curr
|
|
19716
19727
|
*/
|
|
19717
19728
|
shouldReuseRoute(future, curr) {
|
|
19718
|
-
const
|
|
19729
|
+
const reuse = super.shouldReuseRoute(future, curr);
|
|
19719
19730
|
// Is sam route config
|
|
19720
|
-
if (!
|
|
19731
|
+
if (!reuse && future.routeConfig && future.routeConfig === curr.routeConfig) {
|
|
19721
19732
|
// Read the parameter name, where id is stored
|
|
19722
19733
|
const pathIdParam = future.routeConfig.data && future.routeConfig.data.pathIdParam || 'id';
|
|
19723
19734
|
// Read the current route id
|
|
@@ -19728,11 +19739,17 @@ class CustomReuseStrategy extends IonicRouteStrategy {
|
|
|
19728
19739
|
const futureId = future.params[pathIdParam] === 'new'
|
|
19729
19740
|
? (future.queryParams[pathIdParam] || future.queryParams['id'] || 'new') // e.g. path like '/new/?id=<ID>'
|
|
19730
19741
|
: future.params[pathIdParam]; // e.g. path like '/<ID>'
|
|
19731
|
-
// Reuse if same ID,
|
|
19732
|
-
|
|
19733
|
-
|
|
19742
|
+
// Reuse if same ID, using a futureId, if exists
|
|
19743
|
+
if (isNotNil(futureId)) {
|
|
19744
|
+
// Allow reuse when changing from /new to /new?id=:id
|
|
19745
|
+
if (currId === 'new' && isNil(curr.queryParams[pathIdParam]) && future.params[pathIdParam] === 'new' && isNotNil(future.queryParams[pathIdParam])) {
|
|
19746
|
+
return true;
|
|
19747
|
+
}
|
|
19748
|
+
// Allow reuse same id, expect when expected '/new'
|
|
19749
|
+
return futureId !== 'new' && futureId === currId;
|
|
19750
|
+
}
|
|
19734
19751
|
}
|
|
19735
|
-
return
|
|
19752
|
+
return reuse;
|
|
19736
19753
|
}
|
|
19737
19754
|
}
|
|
19738
19755
|
CustomReuseStrategy.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.2.12", ngImport: i0, type: CustomReuseStrategy, deps: null, target: i0.ɵɵFactoryTarget.Injectable });
|
|
@@ -26849,7 +26866,7 @@ class AccountPage extends AppForm {
|
|
|
26849
26866
|
return this.form.get('settings');
|
|
26850
26867
|
}
|
|
26851
26868
|
get valid() {
|
|
26852
|
-
return super.valid && this.propertiesTable?.valid;
|
|
26869
|
+
return super.valid && (this.propertiesTable?.valid || true);
|
|
26853
26870
|
}
|
|
26854
26871
|
ngOnInit() {
|
|
26855
26872
|
super.ngOnInit();
|
|
@@ -26933,8 +26950,10 @@ class AccountPage extends AppForm {
|
|
|
26933
26950
|
propertiesEntities.push(PropertyEntity.fromObject({ id: key, value: properties[key] }));
|
|
26934
26951
|
}
|
|
26935
26952
|
});
|
|
26936
|
-
|
|
26937
|
-
|
|
26953
|
+
if (this.propertiesTable) {
|
|
26954
|
+
await this.propertiesTable.ready();
|
|
26955
|
+
this.propertiesTable.value = propertiesEntities;
|
|
26956
|
+
}
|
|
26938
26957
|
}
|
|
26939
26958
|
async refresh(event) {
|
|
26940
26959
|
this.disable();
|
|
@@ -26989,14 +27008,16 @@ class AccountPage extends AppForm {
|
|
|
26989
27008
|
...(this.accountService.account.asObject()),
|
|
26990
27009
|
...(this.form.value)
|
|
26991
27010
|
});
|
|
26992
|
-
|
|
26993
|
-
|
|
26994
|
-
|
|
26995
|
-
|
|
26996
|
-
res
|
|
26997
|
-
|
|
26998
|
-
|
|
26999
|
-
|
|
27011
|
+
if (this.propertiesTable) {
|
|
27012
|
+
// merge properties
|
|
27013
|
+
await this.propertiesTable.save();
|
|
27014
|
+
const propertyEntities = this.propertiesTable.value || [];
|
|
27015
|
+
const properties = propertyEntities.reduce((res, item) => {
|
|
27016
|
+
res[item.id] = item.value;
|
|
27017
|
+
return res;
|
|
27018
|
+
}, {});
|
|
27019
|
+
newAccount.settings.merge({ properties }, ['properties']);
|
|
27020
|
+
}
|
|
27000
27021
|
console.debug('[account] Saving account...', newAccount);
|
|
27001
27022
|
try {
|
|
27002
27023
|
this.disable();
|
|
@@ -27058,10 +27079,10 @@ class AccountPage extends AppForm {
|
|
|
27058
27079
|
}
|
|
27059
27080
|
}
|
|
27060
27081
|
AccountPage.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.2.12", ngImport: i0, type: AccountPage, deps: [{ token: i0.Injector }, { token: i1$3.UntypedFormBuilder }, { token: AccountService }, { token: NetworkService }, { token: i1$6.Router }, { token: AccountValidatorService }, { token: ConfigService }, { token: i0.ChangeDetectorRef }, { token: APP_LOCALES }], target: i0.ɵɵFactoryTarget.Component });
|
|
27061
|
-
AccountPage.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "14.2.12", type: AccountPage, selector: "app-account-page", viewQueries: [{ propertyName: "tabGroup", first: true, predicate: ["tabGroup"], descendants: true, static: true }, { propertyName: "propertiesTable", first: true, predicate: ["propertiesTable"], descendants: true, static: true }], usesInheritance: true, ngImport: i0, template: "<app-toolbar [title]=\"'ACCOUNT.TITLE'|translate\" color=\"primary\"\n [hasValidate]=\"dirty && !saving\"\n [hasClose]=\"!dirty && !saving\"\n (onValidate)=\"save($event)\"\n [canGoBack]=\"false\"\n (onClose)=\"close($event)\">\n\n <ion-buttons slot=\"end\">\n <!-- loader -->\n <ion-spinner *ngIf=\"loading || saving; else endButtons\"></ion-spinner>\n\n <ng-template #endButtons>\n <!-- refresh button (if online) -->\n <ion-button [matTooltip]=\"'COMMON.BTN_REFRESH'|translate\"\n *ngIf=\"network.online\"\n (click)=\"refresh($event)\">\n <mat-icon slot=\"icon-only\">refresh</mat-icon>\n </ion-button>\n </ng-template>\n </ion-buttons>\n</app-toolbar>\n\n<ion-content>\n\n <!-- error -->\n <ion-item *ngIf=\"error && mobile\" lines=\"none\">\n <ion-icon color=\"danger\" slot=\"start\" name=\"alert-circle\"></ion-icon>\n <ion-label color=\"danger\" class=\"error\" [innerHTML]=\"error|translate\"></ion-label>\n </ion-item>\n\n <form [formGroup]=\"form\" novalidate class=\"form-container\">\n\n <mat-tab-group #tabGroup [(selectedIndex)]=\"selectedTabIndex\" dynamicHeight>\n\n <!-- TAB: user details -->\n <mat-tab label=\"{{'ACCOUNT.USER_DETAILS.TITLE'|translate}}\" class=\"ion-padding\">\n <ng-template mat-tab-label>\n <mat-icon>\n <ion-icon matPrefix slot=\"start\" name=\"person-circle\"></ion-icon>\n </mat-icon>\n <ion-label>{{'ACCOUNT.USER_DETAILS.TITLE'|translate}}</ion-label>\n <ion-icon slot=\"end\" name=\"alert-circle\" color=\"danger\" *ngIf=\"submitted && form.invalid\"></ion-icon>\n </ng-template>\n\n <div class=\"ion-padding\">\n\n <p [innerHTML]=\"'ACCOUNT.USER_DETAILS.DESCRIPTION'|translate\"></p>\n\n <!--h1>Identit\u00E9</h1-->\n\n <!-- Email -->\n <mat-form-field>\n <input matInput [placeholder]=\"'USER.EMAIL'|translate\"\n formControlName=\"email\" autocomplete=\"section-red email\">\n <mat-error *ngIf=\"form.controls.email.hasError('required') && form.controls.email.dirty\" translate>ERROR.FIELD_REQUIRED</mat-error>\n <mat-error *ngIf=\"form.controls.email.hasError('email') && form.controls.email.dirty\">\n <span>{{'ERROR.FIELD_NOT_VALID_EMAIL' | translate }}</span>\n </mat-error>\n </mat-form-field>\n\n <ion-grid *ngIf=\"email.notConfirmed\" class=\"ion-no-padding ion-padding-bottom\">\n <ion-row>\n <ion-col color=\"danger\">\n <ion-icon slot=\"start\" color=\"danger\" name=\"alert-circle\" color=\"danger\"></ion-icon>\n <ion-text [innerHTML]=\"'ACCOUNT.EMAIL_NOT_CONFIRMED_LABEL'|translate\"></ion-text>\n </ion-col>\n </ion-row>\n\n <ion-row style=\"height: 51px;\">\n <ion-col style=\"text-align: right;\">\n <ion-text>\n <small [innerHTML]=\"'ACCOUNT.EMAIL_NOT_RECEIVED_QUESTION'|translate\"></small>\n </ion-text>\n </ion-col>\n <ion-col size=\"auto\">\n <ion-button fill=\"solid\" color=\"secondary\" *ngIf=\"!email.sending\" (click)=\"sendConfirmationEmail($event)\">\n {{'ACCOUNT.BTN_RESEND'|translate}}\n </ion-button>\n <ion-spinner class=\"ion-no-padding\" *ngIf=\"email.sending\"></ion-spinner>\n </ion-col>\n </ion-row>\n\n <ion-row *ngIf=\"email.error && !email.sending\">\n <ion-col>\n <span *ngIf=\"email.error && !email.sending\" [innerHTML]=\"email.error|translate\"></span>\n </ion-col>\n </ion-row>\n </ion-grid>\n\n <!-- Last name -->\n <mat-form-field>\n <input matInput [appAutofocus]=\"true\" [autofocusDelay]=\"500\" [placeholder]=\"'USER.LAST_NAME'|translate\"\n formControlName=\"lastName\"\n autocomplete=\"section-blue family-name\"\n required>\n <mat-error *ngIf=\"form.controls.lastName.hasError('required') && form.controls.lastName.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n <mat-error *ngIf=\"form.controls.lastName.hasError('minlength') && form.controls.lastName.dirty\">\n <span>{{'ERROR.FIELD_MIN_LENGTH' | translate: {minLength: 2} }}</span>\n </mat-error>\n </mat-form-field>\n\n <!-- First name -->\n <mat-form-field>\n <input matInput [placeholder]=\"'USER.FIRST_NAME'|translate\" formControlName=\"firstName\" autocomplete=\"section-blue given-name\"\n required>\n <mat-error *ngIf=\"form.controls.firstName.hasError('required') && form.controls.firstName.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n <mat-error *ngIf=\"form.controls.firstName.hasError('minlength') && form.controls.firstName.dirty\">\n <span>{{'ERROR.FIELD_MIN_LENGTH' | translate: {minLength: 2} }}</span>\n </mat-error>\n </mat-form-field>\n\n\n <!-- Additional fields -->\n <ng-container *ngFor=\"let definition of additionalFields\">\n <app-form-field [definition]=\"definition\"\n [formControlName]=\"definition.key\"\n [required]=\"definition.extra && definition.extra.account && definition.extra.account.required || false\">\n </app-form-field>\n </ng-container>\n\n <h3 translate>ACCOUNT.USER_DETAILS.TECHNICAL_DIVIDER</h3>\n\n <!-- profile -->\n <mat-form-field>\n <input matInput hidden readonly=\"true\" [placeholder]=\"'ACCOUNT.USER_DETAILS.PROFILE'|translate\"\n formControlName=\"mainProfile\" required>\n <span>{{'USER.PROFILE_ENUM.' + form.controls.mainProfile.value | translate}}</span>\n <mat-error *ngIf=\"form.controls.firstName.hasError('mainProfile') && form.controls.mainProfile.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n </mat-form-field>\n\n <!-- pubkey -->\n <mat-form-field>\n <input matInput readonly=\"true\" [placeholder]=\"'ACCOUNT.USER_DETAILS.PUBKEY'|translate\" formControlName=\"pubkey\"\n required>\n <mat-error *ngIf=\"form.controls.firstName.hasError('pubkey') && form.controls.firstName.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n <mat-error *ngIf=\"form.controls.firstName.hasError('pubkey') && form.controls.firstName.dirty\">\n <span translate>ERROR.FIELD_NOT_VALID_PUBKEY</span>\n </mat-error>\n </mat-form-field>\n\n </div>\n </mat-tab>\n\n <!-- TAB: settings -->\n <mat-tab label=\"{{'ACCOUNT.SETTINGS.TITLE'|translate}}\" formGroupName=\"settings\">\n <ng-template mat-tab-label>\n <mat-icon>\n <ion-icon matPrefix slot=\"start\" name=\"settings\"></ion-icon>\n </mat-icon>\n <ion-label translate>ACCOUNT.SETTINGS.TITLE</ion-label>\n </ng-template>\n\n <div class=\"ion-padding\">\n\n <p [innerHTML]=\"'ACCOUNT.SETTINGS.DESCRIPTION'|translate\"></p>\n\n <mat-form-field>\n <mat-select [placeholder]=\"'ACCOUNT.SETTINGS.LOCALE'|translate\" formControlName=\"locale\" required>\n <mat-option *ngFor=\"let item of locales\" [value]=\"item.key\">\n {{item.value}}\n </mat-option>\n </mat-select>\n <mat-error *ngIf=\"settingsForm?.controls.locale.hasError('required') && settingsForm?.controls.locale.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n </mat-form-field>\n\n <!-- lat/long format-->\n <mat-form-field>\n <mat-select [placeholder]=\"'ACCOUNT.SETTINGS.LAT_LONG_FORMAT'|translate\" formControlName=\"latLongFormat\"\n required>\n <mat-option *ngFor=\"let item of latLongFormats\" [value]=\"item\">\n {{'COMMON.LAT_LONG.' + item + '_PLACEHOLDER'|translate}}\n </mat-option>\n </mat-select>\n <mat-error *ngIf=\"settingsForm?.controls.latLongFormat.hasError('required') && settingsForm?.controls.latLongFormat.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n </mat-form-field>\n\n </div>\n\n <!-- Options table -->\n <div class=\"options-table\">\n <app-properties-table\n #propertiesTable\n i18nColumnPrefix=\"ACCOUNT.SETTINGS.OPTIONS.\"\n [definitions]=\"optionDefinitions\"\n [canEdit]=\"true\"\n (onDirty)=\"$event ? markAsDirty() : undefined\"\n ></app-properties-table>\n </div>\n\n </mat-tab>\n </mat-tab-group>\n\n\n </form>\n</ion-content>\n\n<ion-footer hidden-xs hidden-sm hidden-mobile>\n <app-form-buttons-bar (onCancel)=\"cancel()\" (onSave)=\"save($event)\" [disabled]=\"!form.dirty || !valid || saving\">\n <!-- error -->\n <ion-item *ngIf=\"error && !mobile\" lines=\"none\">\n <ion-icon color=\"danger\" slot=\"start\" name=\"alert-circle\"></ion-icon>\n <ion-label color=\"danger\" class=\"error\" [innerHTML]=\"error|translate\"></ion-label>\n </ion-item>\n </app-form-buttons-bar>\n</ion-footer>\n", styles: ["mat-tab-group .mat-tab-body-content{padding:var(--ion-grid-padding);display:grid}form{width:100%}form mat-form-field{width:100%}div.options-table{height:calc(100vh - 380px)}\n"], dependencies: [{ kind: "directive", type: i3.NgForOf, selector: "[ngFor][ngForOf]", inputs: ["ngForOf", "ngForTrackBy", "ngForTemplate"] }, { kind: "directive", type: i3.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "component", type: i1.IonButton, selector: "ion-button", inputs: ["buttonType", "color", "disabled", "download", "expand", "fill", "form", "href", "mode", "rel", "routerAnimation", "routerDirection", "shape", "size", "strong", "target", "type"] }, { kind: "component", type: i1.IonButtons, selector: "ion-buttons", inputs: ["collapse"] }, { kind: "component", type: i1.IonCol, selector: "ion-col", inputs: ["offset", "offsetLg", "offsetMd", "offsetSm", "offsetXl", "offsetXs", "pull", "pullLg", "pullMd", "pullSm", "pullXl", "pullXs", "push", "pushLg", "pushMd", "pushSm", "pushXl", "pushXs", "size", "sizeLg", "sizeMd", "sizeSm", "sizeXl", "sizeXs"] }, { kind: "component", type: i1.IonContent, selector: "ion-content", inputs: ["color", "forceOverscroll", "fullscreen", "scrollEvents", "scrollX", "scrollY"] }, { kind: "component", type: i1.IonFooter, selector: "ion-footer", inputs: ["collapse", "mode", "translucent"] }, { kind: "component", type: i1.IonGrid, selector: "ion-grid", inputs: ["fixed"] }, { kind: "component", type: i1.IonIcon, selector: "ion-icon", inputs: ["color", "flipRtl", "icon", "ios", "lazy", "md", "mode", "name", "sanitize", "size", "src"] }, { kind: "component", type: i1.IonItem, selector: "ion-item", inputs: ["button", "color", "counter", "counterFormatter", "detail", "detailIcon", "disabled", "download", "fill", "href", "lines", "mode", "rel", "routerAnimation", "routerDirection", "shape", "target", "type"] }, { kind: "component", type: i1.IonLabel, selector: "ion-label", inputs: ["color", "mode", "position"] }, { kind: "component", type: i1.IonRow, selector: "ion-row" }, { kind: "component", type: i1.IonSpinner, selector: "ion-spinner", inputs: ["color", "duration", "name", "paused"] }, { kind: "component", type: i1.IonText, selector: "ion-text", inputs: ["color", "mode"] }, { kind: "directive", type: i1$2.TranslateDirective, selector: "[translate],[ngx-translate]", inputs: ["translate", "translateParams"] }, { kind: "directive", type: i1$3.ɵNgNoValidate, selector: "form:not([ngNoForm]):not([ngNativeValidate])" }, { 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.NgControlStatusGroup, selector: "[formGroupName],[formArrayName],[ngModelGroup],[formGroup],form:not([ngNoForm]),[ngForm]" }, { kind: "directive", type: i1$3.RequiredValidator, selector: ":not([type=checkbox])[required][formControlName],:not([type=checkbox])[required][formControl],:not([type=checkbox])[required][ngModel]", inputs: ["required"] }, { 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: "directive", type: i1$3.FormGroupName, selector: "[formGroupName]", inputs: ["formGroupName"] }, { kind: "directive", type: i6$1.MatError, selector: "mat-error", inputs: ["id"] }, { kind: "component", type: i6$1.MatFormField, selector: "mat-form-field", inputs: ["color", "appearance", "hideRequiredMarker", "hintLabel", "floatLabel"], exportAs: ["matFormField"] }, { kind: "directive", type: i6$1.MatPrefix, selector: "[matPrefix]" }, { kind: "directive", type: i7.MatInput, selector: "input[matInput], textarea[matInput], select[matNativeControl], input[matNativeControl], textarea[matNativeControl]", inputs: ["disabled", "id", "placeholder", "name", "required", "type", "errorStateMatcher", "aria-describedby", "value", "readonly"], exportAs: ["matInput"] }, { kind: "component", type: i8.MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: i8$1.MatSelect, selector: "mat-select", inputs: ["disabled", "disableRipple", "tabIndex"], exportAs: ["matSelect"] }, { kind: "component", type: i2.MatOption, selector: "mat-option", exportAs: ["matOption"] }, { kind: "component", type: i15.MatTabGroup, selector: "mat-tab-group", inputs: ["color", "disableRipple"], exportAs: ["matTabGroup"] }, { kind: "directive", type: i15.MatTabLabel, selector: "[mat-tab-label], [matTabLabel]" }, { kind: "component", type: i15.MatTab, selector: "mat-tab", inputs: ["disabled", "label", "aria-label", "aria-labelledby", "labelClass", "bodyClass"], exportAs: ["matTab"] }, { kind: "directive", type: i6$3.MatTooltip, selector: "[matTooltip]", exportAs: ["matTooltip"] }, { kind: "directive", type: AutofocusDirective, selector: "[autofocus], input[appAutofocus]", inputs: ["appAutofocus", "autofocusDelay"] }, { kind: "component", type: ToolbarComponent, selector: "app-toolbar", inputs: ["progressBarMode", "title", "color", "class", "backHref", "defaultBackHref", "hasValidate", "hasClose", "hasSearch", "canGoBack", "canShowMenu"], outputs: ["onValidate", "onClose", "onValidateAndClose", "onBackClick", "onSearch"] }, { kind: "component", type: AppFormField, selector: "app-form-field", inputs: ["definition", "required", "readonly", "disabled", "formControl", "formControlName", "placeholder", "compact", "floatLabel", "tabindex", "autofocus", "chipColor", "class"], outputs: ["keyup.enter"] }, { kind: "component", type: FormButtonsBarComponent, selector: "app-form-buttons-bar", inputs: ["disabled", "disabledCancel", "classList"], outputs: ["onCancel", "onSave", "onNext", "onBack"] }, { kind: "component", type: AppPropertiesTable, selector: "app-properties-table", inputs: ["definitions", "showToolbar"] }, { kind: "pipe", type: i1$2.TranslatePipe, name: "translate" }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
|
|
27082
|
+
AccountPage.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "14.2.12", type: AccountPage, selector: "app-account-page", viewQueries: [{ propertyName: "tabGroup", first: true, predicate: ["tabGroup"], descendants: true, static: true }, { propertyName: "propertiesTable", first: true, predicate: ["propertiesTable"], descendants: true, static: true }], usesInheritance: true, ngImport: i0, template: "<app-toolbar [title]=\"'ACCOUNT.TITLE'|translate\" color=\"primary\"\n [hasValidate]=\"dirty && !saving\"\n [hasClose]=\"!dirty && !saving\"\n (onValidate)=\"save($event)\"\n [canGoBack]=\"false\"\n (onClose)=\"close($event)\">\n\n <ion-buttons slot=\"end\">\n <!-- loader -->\n <ion-spinner *ngIf=\"loading || saving; else endButtons\"></ion-spinner>\n\n <ng-template #endButtons>\n <!-- refresh button (if online) -->\n <ion-button [matTooltip]=\"'COMMON.BTN_REFRESH'|translate\"\n *ngIf=\"network.online\"\n (click)=\"refresh($event)\">\n <mat-icon slot=\"icon-only\">refresh</mat-icon>\n </ion-button>\n </ng-template>\n </ion-buttons>\n</app-toolbar>\n\n<ion-content>\n\n <!-- error -->\n <ion-item *ngIf=\"error && mobile\" lines=\"none\">\n <ion-icon color=\"danger\" slot=\"start\" name=\"alert-circle\"></ion-icon>\n <ion-label color=\"danger\" class=\"error\" [innerHTML]=\"error|translate\"></ion-label>\n </ion-item>\n\n <form [formGroup]=\"form\" novalidate class=\"form-container\">\n\n <mat-tab-group #tabGroup [(selectedIndex)]=\"selectedTabIndex\" dynamicHeight>\n\n <!-- TAB: user details -->\n <mat-tab label=\"{{'ACCOUNT.USER_DETAILS.TITLE'|translate}}\" class=\"ion-padding\">\n <ng-template mat-tab-label>\n <mat-icon>\n <ion-icon matPrefix slot=\"start\" name=\"person-circle\"></ion-icon>\n </mat-icon>\n <ion-label>{{'ACCOUNT.USER_DETAILS.TITLE'|translate}}</ion-label>\n <ion-icon slot=\"end\" name=\"alert-circle\" color=\"danger\" *ngIf=\"submitted && form.invalid\"></ion-icon>\n </ng-template>\n\n <div class=\"ion-padding\">\n\n <p [innerHTML]=\"'ACCOUNT.USER_DETAILS.DESCRIPTION'|translate\"></p>\n\n <!--h1>Identit\u00E9</h1-->\n\n <!-- Email -->\n <mat-form-field>\n <input matInput [placeholder]=\"'USER.EMAIL'|translate\"\n formControlName=\"email\" autocomplete=\"section-red email\">\n <mat-error *ngIf=\"form.controls.email.hasError('required') && form.controls.email.dirty\" translate>ERROR.FIELD_REQUIRED</mat-error>\n <mat-error *ngIf=\"form.controls.email.hasError('email') && form.controls.email.dirty\">\n <span>{{'ERROR.FIELD_NOT_VALID_EMAIL' | translate }}</span>\n </mat-error>\n </mat-form-field>\n\n <ion-grid *ngIf=\"email.notConfirmed\" class=\"ion-no-padding ion-padding-bottom\">\n <ion-row>\n <ion-col color=\"danger\">\n <ion-icon slot=\"start\" color=\"danger\" name=\"alert-circle\" color=\"danger\"></ion-icon>\n <ion-text [innerHTML]=\"'ACCOUNT.EMAIL_NOT_CONFIRMED_LABEL'|translate\"></ion-text>\n </ion-col>\n </ion-row>\n\n <ion-row style=\"height: 51px;\">\n <ion-col style=\"text-align: right;\">\n <ion-text>\n <small [innerHTML]=\"'ACCOUNT.EMAIL_NOT_RECEIVED_QUESTION'|translate\"></small>\n </ion-text>\n </ion-col>\n <ion-col size=\"auto\">\n <ion-button fill=\"solid\" color=\"secondary\" *ngIf=\"!email.sending\" (click)=\"sendConfirmationEmail($event)\">\n {{'ACCOUNT.BTN_RESEND'|translate}}\n </ion-button>\n <ion-spinner class=\"ion-no-padding\" *ngIf=\"email.sending\"></ion-spinner>\n </ion-col>\n </ion-row>\n\n <ion-row *ngIf=\"email.error && !email.sending\">\n <ion-col>\n <span *ngIf=\"email.error && !email.sending\" [innerHTML]=\"email.error|translate\"></span>\n </ion-col>\n </ion-row>\n </ion-grid>\n\n <!-- Last name -->\n <mat-form-field>\n <input matInput [appAutofocus]=\"true\" [autofocusDelay]=\"500\" [placeholder]=\"'USER.LAST_NAME'|translate\"\n formControlName=\"lastName\"\n autocomplete=\"section-blue family-name\"\n required>\n <mat-error *ngIf=\"form.controls.lastName.hasError('required') && form.controls.lastName.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n <mat-error *ngIf=\"form.controls.lastName.hasError('minlength') && form.controls.lastName.dirty\">\n <span>{{'ERROR.FIELD_MIN_LENGTH' | translate: {minLength: 2} }}</span>\n </mat-error>\n </mat-form-field>\n\n <!-- First name -->\n <mat-form-field>\n <input matInput [placeholder]=\"'USER.FIRST_NAME'|translate\" formControlName=\"firstName\" autocomplete=\"section-blue given-name\"\n required>\n <mat-error *ngIf=\"form.controls.firstName.hasError('required') && form.controls.firstName.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n <mat-error *ngIf=\"form.controls.firstName.hasError('minlength') && form.controls.firstName.dirty\">\n <span>{{'ERROR.FIELD_MIN_LENGTH' | translate: {minLength: 2} }}</span>\n </mat-error>\n </mat-form-field>\n\n\n <!-- Additional fields -->\n <ng-container *ngFor=\"let definition of additionalFields\">\n <app-form-field [definition]=\"definition\"\n [formControlName]=\"definition.key\"\n [required]=\"definition.extra && definition.extra.account && definition.extra.account.required || false\">\n </app-form-field>\n </ng-container>\n\n <h3 translate>ACCOUNT.USER_DETAILS.TECHNICAL_DIVIDER</h3>\n\n <!-- profile -->\n <mat-form-field>\n <input matInput hidden readonly=\"true\" [placeholder]=\"'ACCOUNT.USER_DETAILS.PROFILE'|translate\"\n formControlName=\"mainProfile\" required>\n <span>{{'USER.PROFILE_ENUM.' + form.controls.mainProfile.value | translate}}</span>\n <mat-error *ngIf=\"form.controls.firstName.hasError('mainProfile') && form.controls.mainProfile.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n </mat-form-field>\n\n <!-- pubkey -->\n <mat-form-field>\n <input matInput readonly=\"true\" [placeholder]=\"'ACCOUNT.USER_DETAILS.PUBKEY'|translate\" formControlName=\"pubkey\"\n required>\n <mat-error *ngIf=\"form.controls.firstName.hasError('pubkey') && form.controls.firstName.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n <mat-error *ngIf=\"form.controls.firstName.hasError('pubkey') && form.controls.firstName.dirty\">\n <span translate>ERROR.FIELD_NOT_VALID_PUBKEY</span>\n </mat-error>\n </mat-form-field>\n\n </div>\n </mat-tab>\n\n <!-- TAB: settings -->\n <mat-tab label=\"{{'ACCOUNT.SETTINGS.TITLE'|translate}}\" formGroupName=\"settings\">\n <ng-template mat-tab-label>\n <mat-icon>\n <ion-icon matPrefix slot=\"start\" name=\"settings\"></ion-icon>\n </mat-icon>\n <ion-label translate>ACCOUNT.SETTINGS.TITLE</ion-label>\n </ng-template>\n\n <div class=\"ion-padding\">\n\n <p [innerHTML]=\"'ACCOUNT.SETTINGS.DESCRIPTION'|translate\"></p>\n\n <mat-form-field>\n <mat-select [placeholder]=\"'ACCOUNT.SETTINGS.LOCALE'|translate\" formControlName=\"locale\" required>\n <mat-option *ngFor=\"let item of locales\" [value]=\"item.key\">\n {{item.value}}\n </mat-option>\n </mat-select>\n <mat-error *ngIf=\"settingsForm?.controls.locale.hasError('required') && settingsForm?.controls.locale.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n </mat-form-field>\n\n <!-- lat/long format-->\n <mat-form-field>\n <mat-select [placeholder]=\"'ACCOUNT.SETTINGS.LAT_LONG_FORMAT'|translate\" formControlName=\"latLongFormat\"\n required>\n <mat-option *ngFor=\"let item of latLongFormats\" [value]=\"item\">\n {{'COMMON.LAT_LONG.' + item + '_PLACEHOLDER'|translate}}\n </mat-option>\n </mat-select>\n <mat-error *ngIf=\"settingsForm?.controls.latLongFormat.hasError('required') && settingsForm?.controls.latLongFormat.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n </mat-form-field>\n\n </div>\n\n <!-- Options table -->\n <div class=\"options-table\" *ngIf=\"optionDefinitions | isNotEmptyArray\">\n <app-properties-table\n #propertiesTable\n i18nColumnPrefix=\"ACCOUNT.SETTINGS.OPTIONS.\"\n [definitions]=\"optionDefinitions\"\n [canEdit]=\"true\"\n (onDirty)=\"$event ? markAsDirty() : undefined\"\n ></app-properties-table>\n </div>\n\n </mat-tab>\n </mat-tab-group>\n\n\n </form>\n</ion-content>\n\n<ion-footer hidden-xs hidden-sm hidden-mobile>\n <app-form-buttons-bar (onCancel)=\"cancel()\" (onSave)=\"save($event)\" [disabled]=\"!form.dirty || !valid || saving\">\n <!-- error -->\n <ion-item *ngIf=\"error && !mobile\" lines=\"none\">\n <ion-icon color=\"danger\" slot=\"start\" name=\"alert-circle\"></ion-icon>\n <ion-label color=\"danger\" class=\"error\" [innerHTML]=\"error|translate\"></ion-label>\n </ion-item>\n </app-form-buttons-bar>\n</ion-footer>\n", styles: ["mat-tab-group .mat-tab-body-content{padding:var(--ion-grid-padding);display:grid}form{width:100%}form mat-form-field{width:100%}div.options-table{height:calc(100vh - 380px)}\n"], dependencies: [{ kind: "directive", type: i3.NgForOf, selector: "[ngFor][ngForOf]", inputs: ["ngForOf", "ngForTrackBy", "ngForTemplate"] }, { kind: "directive", type: i3.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "component", type: i1.IonButton, selector: "ion-button", inputs: ["buttonType", "color", "disabled", "download", "expand", "fill", "form", "href", "mode", "rel", "routerAnimation", "routerDirection", "shape", "size", "strong", "target", "type"] }, { kind: "component", type: i1.IonButtons, selector: "ion-buttons", inputs: ["collapse"] }, { kind: "component", type: i1.IonCol, selector: "ion-col", inputs: ["offset", "offsetLg", "offsetMd", "offsetSm", "offsetXl", "offsetXs", "pull", "pullLg", "pullMd", "pullSm", "pullXl", "pullXs", "push", "pushLg", "pushMd", "pushSm", "pushXl", "pushXs", "size", "sizeLg", "sizeMd", "sizeSm", "sizeXl", "sizeXs"] }, { kind: "component", type: i1.IonContent, selector: "ion-content", inputs: ["color", "forceOverscroll", "fullscreen", "scrollEvents", "scrollX", "scrollY"] }, { kind: "component", type: i1.IonFooter, selector: "ion-footer", inputs: ["collapse", "mode", "translucent"] }, { kind: "component", type: i1.IonGrid, selector: "ion-grid", inputs: ["fixed"] }, { kind: "component", type: i1.IonIcon, selector: "ion-icon", inputs: ["color", "flipRtl", "icon", "ios", "lazy", "md", "mode", "name", "sanitize", "size", "src"] }, { kind: "component", type: i1.IonItem, selector: "ion-item", inputs: ["button", "color", "counter", "counterFormatter", "detail", "detailIcon", "disabled", "download", "fill", "href", "lines", "mode", "rel", "routerAnimation", "routerDirection", "shape", "target", "type"] }, { kind: "component", type: i1.IonLabel, selector: "ion-label", inputs: ["color", "mode", "position"] }, { kind: "component", type: i1.IonRow, selector: "ion-row" }, { kind: "component", type: i1.IonSpinner, selector: "ion-spinner", inputs: ["color", "duration", "name", "paused"] }, { kind: "component", type: i1.IonText, selector: "ion-text", inputs: ["color", "mode"] }, { kind: "directive", type: i1$2.TranslateDirective, selector: "[translate],[ngx-translate]", inputs: ["translate", "translateParams"] }, { kind: "directive", type: i1$3.ɵNgNoValidate, selector: "form:not([ngNoForm]):not([ngNativeValidate])" }, { 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.NgControlStatusGroup, selector: "[formGroupName],[formArrayName],[ngModelGroup],[formGroup],form:not([ngNoForm]),[ngForm]" }, { kind: "directive", type: i1$3.RequiredValidator, selector: ":not([type=checkbox])[required][formControlName],:not([type=checkbox])[required][formControl],:not([type=checkbox])[required][ngModel]", inputs: ["required"] }, { 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: "directive", type: i1$3.FormGroupName, selector: "[formGroupName]", inputs: ["formGroupName"] }, { kind: "directive", type: i6$1.MatError, selector: "mat-error", inputs: ["id"] }, { kind: "component", type: i6$1.MatFormField, selector: "mat-form-field", inputs: ["color", "appearance", "hideRequiredMarker", "hintLabel", "floatLabel"], exportAs: ["matFormField"] }, { kind: "directive", type: i6$1.MatPrefix, selector: "[matPrefix]" }, { kind: "directive", type: i7.MatInput, selector: "input[matInput], textarea[matInput], select[matNativeControl], input[matNativeControl], textarea[matNativeControl]", inputs: ["disabled", "id", "placeholder", "name", "required", "type", "errorStateMatcher", "aria-describedby", "value", "readonly"], exportAs: ["matInput"] }, { kind: "component", type: i8.MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: i8$1.MatSelect, selector: "mat-select", inputs: ["disabled", "disableRipple", "tabIndex"], exportAs: ["matSelect"] }, { kind: "component", type: i2.MatOption, selector: "mat-option", exportAs: ["matOption"] }, { kind: "component", type: i15.MatTabGroup, selector: "mat-tab-group", inputs: ["color", "disableRipple"], exportAs: ["matTabGroup"] }, { kind: "directive", type: i15.MatTabLabel, selector: "[mat-tab-label], [matTabLabel]" }, { kind: "component", type: i15.MatTab, selector: "mat-tab", inputs: ["disabled", "label", "aria-label", "aria-labelledby", "labelClass", "bodyClass"], exportAs: ["matTab"] }, { kind: "directive", type: i6$3.MatTooltip, selector: "[matTooltip]", exportAs: ["matTooltip"] }, { kind: "directive", type: AutofocusDirective, selector: "[autofocus], input[appAutofocus]", inputs: ["appAutofocus", "autofocusDelay"] }, { kind: "component", type: ToolbarComponent, selector: "app-toolbar", inputs: ["progressBarMode", "title", "color", "class", "backHref", "defaultBackHref", "hasValidate", "hasClose", "hasSearch", "canGoBack", "canShowMenu"], outputs: ["onValidate", "onClose", "onValidateAndClose", "onBackClick", "onSearch"] }, { kind: "component", type: AppFormField, selector: "app-form-field", inputs: ["definition", "required", "readonly", "disabled", "formControl", "formControlName", "placeholder", "compact", "floatLabel", "tabindex", "autofocus", "chipColor", "class"], outputs: ["keyup.enter"] }, { kind: "component", type: FormButtonsBarComponent, selector: "app-form-buttons-bar", inputs: ["disabled", "disabledCancel", "classList"], outputs: ["onCancel", "onSave", "onNext", "onBack"] }, { kind: "component", type: AppPropertiesTable, selector: "app-properties-table", inputs: ["definitions", "showToolbar"] }, { kind: "pipe", type: i1$2.TranslatePipe, name: "translate" }, { kind: "pipe", type: NotEmptyArrayPipe, name: "isNotEmptyArray" }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
|
|
27062
27083
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.2.12", ngImport: i0, type: AccountPage, decorators: [{
|
|
27063
27084
|
type: Component,
|
|
27064
|
-
args: [{ selector: 'app-account-page', changeDetection: ChangeDetectionStrategy.OnPush, template: "<app-toolbar [title]=\"'ACCOUNT.TITLE'|translate\" color=\"primary\"\n [hasValidate]=\"dirty && !saving\"\n [hasClose]=\"!dirty && !saving\"\n (onValidate)=\"save($event)\"\n [canGoBack]=\"false\"\n (onClose)=\"close($event)\">\n\n <ion-buttons slot=\"end\">\n <!-- loader -->\n <ion-spinner *ngIf=\"loading || saving; else endButtons\"></ion-spinner>\n\n <ng-template #endButtons>\n <!-- refresh button (if online) -->\n <ion-button [matTooltip]=\"'COMMON.BTN_REFRESH'|translate\"\n *ngIf=\"network.online\"\n (click)=\"refresh($event)\">\n <mat-icon slot=\"icon-only\">refresh</mat-icon>\n </ion-button>\n </ng-template>\n </ion-buttons>\n</app-toolbar>\n\n<ion-content>\n\n <!-- error -->\n <ion-item *ngIf=\"error && mobile\" lines=\"none\">\n <ion-icon color=\"danger\" slot=\"start\" name=\"alert-circle\"></ion-icon>\n <ion-label color=\"danger\" class=\"error\" [innerHTML]=\"error|translate\"></ion-label>\n </ion-item>\n\n <form [formGroup]=\"form\" novalidate class=\"form-container\">\n\n <mat-tab-group #tabGroup [(selectedIndex)]=\"selectedTabIndex\" dynamicHeight>\n\n <!-- TAB: user details -->\n <mat-tab label=\"{{'ACCOUNT.USER_DETAILS.TITLE'|translate}}\" class=\"ion-padding\">\n <ng-template mat-tab-label>\n <mat-icon>\n <ion-icon matPrefix slot=\"start\" name=\"person-circle\"></ion-icon>\n </mat-icon>\n <ion-label>{{'ACCOUNT.USER_DETAILS.TITLE'|translate}}</ion-label>\n <ion-icon slot=\"end\" name=\"alert-circle\" color=\"danger\" *ngIf=\"submitted && form.invalid\"></ion-icon>\n </ng-template>\n\n <div class=\"ion-padding\">\n\n <p [innerHTML]=\"'ACCOUNT.USER_DETAILS.DESCRIPTION'|translate\"></p>\n\n <!--h1>Identit\u00E9</h1-->\n\n <!-- Email -->\n <mat-form-field>\n <input matInput [placeholder]=\"'USER.EMAIL'|translate\"\n formControlName=\"email\" autocomplete=\"section-red email\">\n <mat-error *ngIf=\"form.controls.email.hasError('required') && form.controls.email.dirty\" translate>ERROR.FIELD_REQUIRED</mat-error>\n <mat-error *ngIf=\"form.controls.email.hasError('email') && form.controls.email.dirty\">\n <span>{{'ERROR.FIELD_NOT_VALID_EMAIL' | translate }}</span>\n </mat-error>\n </mat-form-field>\n\n <ion-grid *ngIf=\"email.notConfirmed\" class=\"ion-no-padding ion-padding-bottom\">\n <ion-row>\n <ion-col color=\"danger\">\n <ion-icon slot=\"start\" color=\"danger\" name=\"alert-circle\" color=\"danger\"></ion-icon>\n <ion-text [innerHTML]=\"'ACCOUNT.EMAIL_NOT_CONFIRMED_LABEL'|translate\"></ion-text>\n </ion-col>\n </ion-row>\n\n <ion-row style=\"height: 51px;\">\n <ion-col style=\"text-align: right;\">\n <ion-text>\n <small [innerHTML]=\"'ACCOUNT.EMAIL_NOT_RECEIVED_QUESTION'|translate\"></small>\n </ion-text>\n </ion-col>\n <ion-col size=\"auto\">\n <ion-button fill=\"solid\" color=\"secondary\" *ngIf=\"!email.sending\" (click)=\"sendConfirmationEmail($event)\">\n {{'ACCOUNT.BTN_RESEND'|translate}}\n </ion-button>\n <ion-spinner class=\"ion-no-padding\" *ngIf=\"email.sending\"></ion-spinner>\n </ion-col>\n </ion-row>\n\n <ion-row *ngIf=\"email.error && !email.sending\">\n <ion-col>\n <span *ngIf=\"email.error && !email.sending\" [innerHTML]=\"email.error|translate\"></span>\n </ion-col>\n </ion-row>\n </ion-grid>\n\n <!-- Last name -->\n <mat-form-field>\n <input matInput [appAutofocus]=\"true\" [autofocusDelay]=\"500\" [placeholder]=\"'USER.LAST_NAME'|translate\"\n formControlName=\"lastName\"\n autocomplete=\"section-blue family-name\"\n required>\n <mat-error *ngIf=\"form.controls.lastName.hasError('required') && form.controls.lastName.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n <mat-error *ngIf=\"form.controls.lastName.hasError('minlength') && form.controls.lastName.dirty\">\n <span>{{'ERROR.FIELD_MIN_LENGTH' | translate: {minLength: 2} }}</span>\n </mat-error>\n </mat-form-field>\n\n <!-- First name -->\n <mat-form-field>\n <input matInput [placeholder]=\"'USER.FIRST_NAME'|translate\" formControlName=\"firstName\" autocomplete=\"section-blue given-name\"\n required>\n <mat-error *ngIf=\"form.controls.firstName.hasError('required') && form.controls.firstName.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n <mat-error *ngIf=\"form.controls.firstName.hasError('minlength') && form.controls.firstName.dirty\">\n <span>{{'ERROR.FIELD_MIN_LENGTH' | translate: {minLength: 2} }}</span>\n </mat-error>\n </mat-form-field>\n\n\n <!-- Additional fields -->\n <ng-container *ngFor=\"let definition of additionalFields\">\n <app-form-field [definition]=\"definition\"\n [formControlName]=\"definition.key\"\n [required]=\"definition.extra && definition.extra.account && definition.extra.account.required || false\">\n </app-form-field>\n </ng-container>\n\n <h3 translate>ACCOUNT.USER_DETAILS.TECHNICAL_DIVIDER</h3>\n\n <!-- profile -->\n <mat-form-field>\n <input matInput hidden readonly=\"true\" [placeholder]=\"'ACCOUNT.USER_DETAILS.PROFILE'|translate\"\n formControlName=\"mainProfile\" required>\n <span>{{'USER.PROFILE_ENUM.' + form.controls.mainProfile.value | translate}}</span>\n <mat-error *ngIf=\"form.controls.firstName.hasError('mainProfile') && form.controls.mainProfile.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n </mat-form-field>\n\n <!-- pubkey -->\n <mat-form-field>\n <input matInput readonly=\"true\" [placeholder]=\"'ACCOUNT.USER_DETAILS.PUBKEY'|translate\" formControlName=\"pubkey\"\n required>\n <mat-error *ngIf=\"form.controls.firstName.hasError('pubkey') && form.controls.firstName.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n <mat-error *ngIf=\"form.controls.firstName.hasError('pubkey') && form.controls.firstName.dirty\">\n <span translate>ERROR.FIELD_NOT_VALID_PUBKEY</span>\n </mat-error>\n </mat-form-field>\n\n </div>\n </mat-tab>\n\n <!-- TAB: settings -->\n <mat-tab label=\"{{'ACCOUNT.SETTINGS.TITLE'|translate}}\" formGroupName=\"settings\">\n <ng-template mat-tab-label>\n <mat-icon>\n <ion-icon matPrefix slot=\"start\" name=\"settings\"></ion-icon>\n </mat-icon>\n <ion-label translate>ACCOUNT.SETTINGS.TITLE</ion-label>\n </ng-template>\n\n <div class=\"ion-padding\">\n\n <p [innerHTML]=\"'ACCOUNT.SETTINGS.DESCRIPTION'|translate\"></p>\n\n <mat-form-field>\n <mat-select [placeholder]=\"'ACCOUNT.SETTINGS.LOCALE'|translate\" formControlName=\"locale\" required>\n <mat-option *ngFor=\"let item of locales\" [value]=\"item.key\">\n {{item.value}}\n </mat-option>\n </mat-select>\n <mat-error *ngIf=\"settingsForm?.controls.locale.hasError('required') && settingsForm?.controls.locale.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n </mat-form-field>\n\n <!-- lat/long format-->\n <mat-form-field>\n <mat-select [placeholder]=\"'ACCOUNT.SETTINGS.LAT_LONG_FORMAT'|translate\" formControlName=\"latLongFormat\"\n required>\n <mat-option *ngFor=\"let item of latLongFormats\" [value]=\"item\">\n {{'COMMON.LAT_LONG.' + item + '_PLACEHOLDER'|translate}}\n </mat-option>\n </mat-select>\n <mat-error *ngIf=\"settingsForm?.controls.latLongFormat.hasError('required') && settingsForm?.controls.latLongFormat.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n </mat-form-field>\n\n </div>\n\n <!-- Options table -->\n <div class=\"options-table\">\n <app-properties-table\n #propertiesTable\n i18nColumnPrefix=\"ACCOUNT.SETTINGS.OPTIONS.\"\n [definitions]=\"optionDefinitions\"\n [canEdit]=\"true\"\n (onDirty)=\"$event ? markAsDirty() : undefined\"\n ></app-properties-table>\n </div>\n\n </mat-tab>\n </mat-tab-group>\n\n\n </form>\n</ion-content>\n\n<ion-footer hidden-xs hidden-sm hidden-mobile>\n <app-form-buttons-bar (onCancel)=\"cancel()\" (onSave)=\"save($event)\" [disabled]=\"!form.dirty || !valid || saving\">\n <!-- error -->\n <ion-item *ngIf=\"error && !mobile\" lines=\"none\">\n <ion-icon color=\"danger\" slot=\"start\" name=\"alert-circle\"></ion-icon>\n <ion-label color=\"danger\" class=\"error\" [innerHTML]=\"error|translate\"></ion-label>\n </ion-item>\n </app-form-buttons-bar>\n</ion-footer>\n", styles: ["mat-tab-group .mat-tab-body-content{padding:var(--ion-grid-padding);display:grid}form{width:100%}form mat-form-field{width:100%}div.options-table{height:calc(100vh - 380px)}\n"] }]
|
|
27085
|
+
args: [{ selector: 'app-account-page', changeDetection: ChangeDetectionStrategy.OnPush, template: "<app-toolbar [title]=\"'ACCOUNT.TITLE'|translate\" color=\"primary\"\n [hasValidate]=\"dirty && !saving\"\n [hasClose]=\"!dirty && !saving\"\n (onValidate)=\"save($event)\"\n [canGoBack]=\"false\"\n (onClose)=\"close($event)\">\n\n <ion-buttons slot=\"end\">\n <!-- loader -->\n <ion-spinner *ngIf=\"loading || saving; else endButtons\"></ion-spinner>\n\n <ng-template #endButtons>\n <!-- refresh button (if online) -->\n <ion-button [matTooltip]=\"'COMMON.BTN_REFRESH'|translate\"\n *ngIf=\"network.online\"\n (click)=\"refresh($event)\">\n <mat-icon slot=\"icon-only\">refresh</mat-icon>\n </ion-button>\n </ng-template>\n </ion-buttons>\n</app-toolbar>\n\n<ion-content>\n\n <!-- error -->\n <ion-item *ngIf=\"error && mobile\" lines=\"none\">\n <ion-icon color=\"danger\" slot=\"start\" name=\"alert-circle\"></ion-icon>\n <ion-label color=\"danger\" class=\"error\" [innerHTML]=\"error|translate\"></ion-label>\n </ion-item>\n\n <form [formGroup]=\"form\" novalidate class=\"form-container\">\n\n <mat-tab-group #tabGroup [(selectedIndex)]=\"selectedTabIndex\" dynamicHeight>\n\n <!-- TAB: user details -->\n <mat-tab label=\"{{'ACCOUNT.USER_DETAILS.TITLE'|translate}}\" class=\"ion-padding\">\n <ng-template mat-tab-label>\n <mat-icon>\n <ion-icon matPrefix slot=\"start\" name=\"person-circle\"></ion-icon>\n </mat-icon>\n <ion-label>{{'ACCOUNT.USER_DETAILS.TITLE'|translate}}</ion-label>\n <ion-icon slot=\"end\" name=\"alert-circle\" color=\"danger\" *ngIf=\"submitted && form.invalid\"></ion-icon>\n </ng-template>\n\n <div class=\"ion-padding\">\n\n <p [innerHTML]=\"'ACCOUNT.USER_DETAILS.DESCRIPTION'|translate\"></p>\n\n <!--h1>Identit\u00E9</h1-->\n\n <!-- Email -->\n <mat-form-field>\n <input matInput [placeholder]=\"'USER.EMAIL'|translate\"\n formControlName=\"email\" autocomplete=\"section-red email\">\n <mat-error *ngIf=\"form.controls.email.hasError('required') && form.controls.email.dirty\" translate>ERROR.FIELD_REQUIRED</mat-error>\n <mat-error *ngIf=\"form.controls.email.hasError('email') && form.controls.email.dirty\">\n <span>{{'ERROR.FIELD_NOT_VALID_EMAIL' | translate }}</span>\n </mat-error>\n </mat-form-field>\n\n <ion-grid *ngIf=\"email.notConfirmed\" class=\"ion-no-padding ion-padding-bottom\">\n <ion-row>\n <ion-col color=\"danger\">\n <ion-icon slot=\"start\" color=\"danger\" name=\"alert-circle\" color=\"danger\"></ion-icon>\n <ion-text [innerHTML]=\"'ACCOUNT.EMAIL_NOT_CONFIRMED_LABEL'|translate\"></ion-text>\n </ion-col>\n </ion-row>\n\n <ion-row style=\"height: 51px;\">\n <ion-col style=\"text-align: right;\">\n <ion-text>\n <small [innerHTML]=\"'ACCOUNT.EMAIL_NOT_RECEIVED_QUESTION'|translate\"></small>\n </ion-text>\n </ion-col>\n <ion-col size=\"auto\">\n <ion-button fill=\"solid\" color=\"secondary\" *ngIf=\"!email.sending\" (click)=\"sendConfirmationEmail($event)\">\n {{'ACCOUNT.BTN_RESEND'|translate}}\n </ion-button>\n <ion-spinner class=\"ion-no-padding\" *ngIf=\"email.sending\"></ion-spinner>\n </ion-col>\n </ion-row>\n\n <ion-row *ngIf=\"email.error && !email.sending\">\n <ion-col>\n <span *ngIf=\"email.error && !email.sending\" [innerHTML]=\"email.error|translate\"></span>\n </ion-col>\n </ion-row>\n </ion-grid>\n\n <!-- Last name -->\n <mat-form-field>\n <input matInput [appAutofocus]=\"true\" [autofocusDelay]=\"500\" [placeholder]=\"'USER.LAST_NAME'|translate\"\n formControlName=\"lastName\"\n autocomplete=\"section-blue family-name\"\n required>\n <mat-error *ngIf=\"form.controls.lastName.hasError('required') && form.controls.lastName.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n <mat-error *ngIf=\"form.controls.lastName.hasError('minlength') && form.controls.lastName.dirty\">\n <span>{{'ERROR.FIELD_MIN_LENGTH' | translate: {minLength: 2} }}</span>\n </mat-error>\n </mat-form-field>\n\n <!-- First name -->\n <mat-form-field>\n <input matInput [placeholder]=\"'USER.FIRST_NAME'|translate\" formControlName=\"firstName\" autocomplete=\"section-blue given-name\"\n required>\n <mat-error *ngIf=\"form.controls.firstName.hasError('required') && form.controls.firstName.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n <mat-error *ngIf=\"form.controls.firstName.hasError('minlength') && form.controls.firstName.dirty\">\n <span>{{'ERROR.FIELD_MIN_LENGTH' | translate: {minLength: 2} }}</span>\n </mat-error>\n </mat-form-field>\n\n\n <!-- Additional fields -->\n <ng-container *ngFor=\"let definition of additionalFields\">\n <app-form-field [definition]=\"definition\"\n [formControlName]=\"definition.key\"\n [required]=\"definition.extra && definition.extra.account && definition.extra.account.required || false\">\n </app-form-field>\n </ng-container>\n\n <h3 translate>ACCOUNT.USER_DETAILS.TECHNICAL_DIVIDER</h3>\n\n <!-- profile -->\n <mat-form-field>\n <input matInput hidden readonly=\"true\" [placeholder]=\"'ACCOUNT.USER_DETAILS.PROFILE'|translate\"\n formControlName=\"mainProfile\" required>\n <span>{{'USER.PROFILE_ENUM.' + form.controls.mainProfile.value | translate}}</span>\n <mat-error *ngIf=\"form.controls.firstName.hasError('mainProfile') && form.controls.mainProfile.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n </mat-form-field>\n\n <!-- pubkey -->\n <mat-form-field>\n <input matInput readonly=\"true\" [placeholder]=\"'ACCOUNT.USER_DETAILS.PUBKEY'|translate\" formControlName=\"pubkey\"\n required>\n <mat-error *ngIf=\"form.controls.firstName.hasError('pubkey') && form.controls.firstName.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n <mat-error *ngIf=\"form.controls.firstName.hasError('pubkey') && form.controls.firstName.dirty\">\n <span translate>ERROR.FIELD_NOT_VALID_PUBKEY</span>\n </mat-error>\n </mat-form-field>\n\n </div>\n </mat-tab>\n\n <!-- TAB: settings -->\n <mat-tab label=\"{{'ACCOUNT.SETTINGS.TITLE'|translate}}\" formGroupName=\"settings\">\n <ng-template mat-tab-label>\n <mat-icon>\n <ion-icon matPrefix slot=\"start\" name=\"settings\"></ion-icon>\n </mat-icon>\n <ion-label translate>ACCOUNT.SETTINGS.TITLE</ion-label>\n </ng-template>\n\n <div class=\"ion-padding\">\n\n <p [innerHTML]=\"'ACCOUNT.SETTINGS.DESCRIPTION'|translate\"></p>\n\n <mat-form-field>\n <mat-select [placeholder]=\"'ACCOUNT.SETTINGS.LOCALE'|translate\" formControlName=\"locale\" required>\n <mat-option *ngFor=\"let item of locales\" [value]=\"item.key\">\n {{item.value}}\n </mat-option>\n </mat-select>\n <mat-error *ngIf=\"settingsForm?.controls.locale.hasError('required') && settingsForm?.controls.locale.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n </mat-form-field>\n\n <!-- lat/long format-->\n <mat-form-field>\n <mat-select [placeholder]=\"'ACCOUNT.SETTINGS.LAT_LONG_FORMAT'|translate\" formControlName=\"latLongFormat\"\n required>\n <mat-option *ngFor=\"let item of latLongFormats\" [value]=\"item\">\n {{'COMMON.LAT_LONG.' + item + '_PLACEHOLDER'|translate}}\n </mat-option>\n </mat-select>\n <mat-error *ngIf=\"settingsForm?.controls.latLongFormat.hasError('required') && settingsForm?.controls.latLongFormat.dirty\"\n translate>ERROR.FIELD_REQUIRED\n </mat-error>\n </mat-form-field>\n\n </div>\n\n <!-- Options table -->\n <div class=\"options-table\" *ngIf=\"optionDefinitions | isNotEmptyArray\">\n <app-properties-table\n #propertiesTable\n i18nColumnPrefix=\"ACCOUNT.SETTINGS.OPTIONS.\"\n [definitions]=\"optionDefinitions\"\n [canEdit]=\"true\"\n (onDirty)=\"$event ? markAsDirty() : undefined\"\n ></app-properties-table>\n </div>\n\n </mat-tab>\n </mat-tab-group>\n\n\n </form>\n</ion-content>\n\n<ion-footer hidden-xs hidden-sm hidden-mobile>\n <app-form-buttons-bar (onCancel)=\"cancel()\" (onSave)=\"save($event)\" [disabled]=\"!form.dirty || !valid || saving\">\n <!-- error -->\n <ion-item *ngIf=\"error && !mobile\" lines=\"none\">\n <ion-icon color=\"danger\" slot=\"start\" name=\"alert-circle\"></ion-icon>\n <ion-label color=\"danger\" class=\"error\" [innerHTML]=\"error|translate\"></ion-label>\n </ion-item>\n </app-form-buttons-bar>\n</ion-footer>\n", styles: ["mat-tab-group .mat-tab-body-content{padding:var(--ion-grid-padding);display:grid}form{width:100%}form mat-form-field{width:100%}div.options-table{height:calc(100vh - 380px)}\n"] }]
|
|
27065
27086
|
}], ctorParameters: function () { return [{ type: i0.Injector }, { type: i1$3.UntypedFormBuilder }, { type: AccountService }, { type: NetworkService }, { type: i1$6.Router }, { type: AccountValidatorService }, { type: ConfigService }, { type: i0.ChangeDetectorRef }, { type: undefined, decorators: [{
|
|
27066
27087
|
type: Inject,
|
|
27067
27088
|
args: [APP_LOCALES]
|
|
@@ -28447,6 +28468,7 @@ class AppEntityEditor extends AppTabEditor {
|
|
|
28447
28468
|
};
|
|
28448
28469
|
this.settings = injector.get(LocalSettingsService);
|
|
28449
28470
|
this.errorTranslator = injector.get(FormErrorTranslator);
|
|
28471
|
+
this.routerOutlet = injector.get(IonRouterOutlet);
|
|
28450
28472
|
this.cd = injector.get(ChangeDetectorRef);
|
|
28451
28473
|
this.dateFormat = injector.get(DateFormatService);
|
|
28452
28474
|
this.toastController = injector.get(ToastController);
|
|
@@ -28682,40 +28704,17 @@ class AppEntityEditor extends AppTabEditor {
|
|
|
28682
28704
|
* Update the route location, and open the next tab
|
|
28683
28705
|
*/
|
|
28684
28706
|
async updateTabAndRoute(data, opts) {
|
|
28685
|
-
|
|
28707
|
+
const queryParams = { ...this.queryParams };
|
|
28686
28708
|
// Open the next tab
|
|
28687
28709
|
this.updateTabIndex(opts && opts.openTabIndex);
|
|
28688
|
-
// Save the opened tab into the queryParams
|
|
28689
|
-
this.queryParams.tab = this.selectedTabIndex;
|
|
28690
28710
|
// Update route location
|
|
28691
|
-
|
|
28692
|
-
const queryParams = { ...this.queryParams };
|
|
28693
|
-
queryParams[this._pathIdAttribute] = data.id;
|
|
28694
|
-
if (this.debug)
|
|
28695
|
-
console.debug('[entity-editor] Updating route using params: ', queryParams);
|
|
28696
|
-
await this.router.navigate(['.'], {
|
|
28697
|
-
relativeTo: this.route,
|
|
28698
|
-
queryParams
|
|
28699
|
-
});
|
|
28700
|
-
}
|
|
28701
|
-
// Move to ../new
|
|
28702
|
-
else {
|
|
28703
|
-
const queryParams = { ...this.queryParams };
|
|
28704
|
-
queryParams[this._pathIdAttribute] = 'new';
|
|
28705
|
-
if (this.debug)
|
|
28706
|
-
console.debug('[entity-editor] Updating route to \'../new\' using params: ', queryParams);
|
|
28707
|
-
await this.router.navigate(['..', 'new'], {
|
|
28708
|
-
relativeTo: this.route,
|
|
28709
|
-
queryParams
|
|
28710
|
-
});
|
|
28711
|
-
}
|
|
28712
|
-
await this.updateRoute(data, this.queryParams);
|
|
28711
|
+
await this.updateRoute(data, { ...queryParams, tab: this.selectedTabIndex });
|
|
28713
28712
|
}
|
|
28714
28713
|
/**
|
|
28715
28714
|
* Update the route location, and open the next tab
|
|
28716
28715
|
*/
|
|
28717
28716
|
updateTabIndex(tabIndex) {
|
|
28718
|
-
if (isNotNil(tabIndex) && tabIndex !== this.selectedTabIndex) {
|
|
28717
|
+
if (isNotNil(tabIndex) && tabIndex >= 0 && tabIndex !== this.selectedTabIndex) {
|
|
28719
28718
|
this.selectedTabIndex = tabIndex;
|
|
28720
28719
|
this.markForCheck();
|
|
28721
28720
|
}
|
|
@@ -29005,7 +29004,7 @@ class AppEntityEditor extends AppTabEditor {
|
|
|
29005
29004
|
let parentUrl = this.defaultBackHref;
|
|
29006
29005
|
// Remove query params
|
|
29007
29006
|
if (withQueryParams !== true && parentUrl && parentUrl.indexOf('?') !== -1) {
|
|
29008
|
-
parentUrl = parentUrl.
|
|
29007
|
+
parentUrl = parentUrl.substring(0, parentUrl.indexOf('?'));
|
|
29009
29008
|
}
|
|
29010
29009
|
return parentUrl;
|
|
29011
29010
|
}
|
|
@@ -29031,17 +29030,55 @@ class AppEntityEditor extends AppTabEditor {
|
|
|
29031
29030
|
this.markForCheck();
|
|
29032
29031
|
}
|
|
29033
29032
|
}
|
|
29033
|
+
/**
|
|
29034
|
+
* Update the route, without reloading the component
|
|
29035
|
+
* @param data
|
|
29036
|
+
* @param queryParams
|
|
29037
|
+
* @protected
|
|
29038
|
+
*/
|
|
29034
29039
|
async updateRoute(data, queryParams) {
|
|
29035
|
-
const
|
|
29036
|
-
const
|
|
29037
|
-
|
|
29038
|
-
|
|
29039
|
-
|
|
29040
|
-
|
|
29041
|
-
|
|
29040
|
+
const currId = this.route.snapshot.paramMap.get(this.pathIdAttribute);
|
|
29041
|
+
const futureId = isNotNil(data.id) ? data.id.toString() : 'new';
|
|
29042
|
+
this.queryParams = {
|
|
29043
|
+
...this.queryParams,
|
|
29044
|
+
...queryParams
|
|
29045
|
+
};
|
|
29046
|
+
if (currId === futureId) {
|
|
29047
|
+
// Update queryParam only (not the path)
|
|
29048
|
+
if (!equals(this.route.snapshot.queryParams, this.queryParams)) {
|
|
29049
|
+
if (this.debug)
|
|
29050
|
+
console.debug('[entity-editor] Updating route using queryParams: ', queryParams);
|
|
29051
|
+
return await this.router.navigate(['.'], {
|
|
29052
|
+
relativeTo: this.route,
|
|
29053
|
+
queryParams: this.queryParams
|
|
29054
|
+
});
|
|
29055
|
+
}
|
|
29042
29056
|
}
|
|
29043
29057
|
else {
|
|
29044
|
-
|
|
29058
|
+
// Current route was '/new' => change to '/new?id=:id' (to allow CustomReuseStrategy to detect that route can be reused)
|
|
29059
|
+
if (currId === 'new') {
|
|
29060
|
+
const res = await this.router.navigate(['.'], {
|
|
29061
|
+
relativeTo: this.route,
|
|
29062
|
+
replaceUrl: true,
|
|
29063
|
+
queryParams: {
|
|
29064
|
+
...this.queryParams,
|
|
29065
|
+
[this.pathIdAttribute]: futureId
|
|
29066
|
+
}
|
|
29067
|
+
});
|
|
29068
|
+
if (!res)
|
|
29069
|
+
return false;
|
|
29070
|
+
}
|
|
29071
|
+
const path = this.computePageUrl(isNotNil(data.id) ? data.id : 'new');
|
|
29072
|
+
const commands = (path && typeof path === 'string') ? path.split('/').slice(1) : path;
|
|
29073
|
+
if (isNotEmptyArray(commands)) {
|
|
29074
|
+
if (this.debug)
|
|
29075
|
+
console.debug('[entity-editor] Updating route to: ' + path);
|
|
29076
|
+
return await this.router.navigate(commands, {
|
|
29077
|
+
replaceUrl: true,
|
|
29078
|
+
queryParams: this.queryParams
|
|
29079
|
+
});
|
|
29080
|
+
}
|
|
29081
|
+
return Promise.reject('Missing page URL');
|
|
29045
29082
|
}
|
|
29046
29083
|
}
|
|
29047
29084
|
}
|