RED-3800 add dialog components

This commit is contained in:
Dan Percic 2023-06-20 14:44:03 +03:00
parent 2fe65233bc
commit 88babfd1f6
2 changed files with 88 additions and 0 deletions

View File

@ -0,0 +1,44 @@
import { Directive, HostListener, inject } from '@angular/core';
import { MAT_DIALOG_DATA, MatDialog, MatDialogRef } from '@angular/material/dialog';
import { takeUntilDestroyed } from '@angular/core/rxjs-interop';
const DATA_TYPE_SYMBOL = Symbol.for('DATA_TYPE');
const RETURN_TYPE_SYMBOL = Symbol.for('RETURN_TYPE');
export type DATA_TYPE = typeof DATA_TYPE_SYMBOL;
export type RETURN_TYPE = typeof RETURN_TYPE_SYMBOL;
@Directive()
export abstract class IqserDialogComponent<ComponentType, DataType, ReturnType> {
readonly [DATA_TYPE_SYMBOL]!: DataType;
readonly [RETURN_TYPE_SYMBOL]!: ReturnType;
readonly dialogRef = inject(MatDialogRef<ComponentType, ReturnType>);
readonly data = inject<DataType>(MAT_DIALOG_DATA);
readonly dialog = inject(MatDialog);
constructor() {
this.dialogRef
.backdropClick()
.pipe(takeUntilDestroyed())
// eslint-disable-next-line rxjs/no-ignored-subscription
.subscribe(() => this.close());
}
@HostListener('window:keydown.Escape', ['$event'])
onEscape(): void {
if (this.dialog.openDialogs.length === 1) {
this.close();
}
}
close(dialogResult?: ReturnType) {
this.dialogRef.close(dialogResult);
}
}
/**
* This is for testing only
*/
// eslint-disable-next-line @typescript-eslint/no-unused-vars
class DialogComponentImpl extends IqserDialogComponent<DialogComponentImpl, unknown, unknown> {}

View File

@ -0,0 +1,44 @@
import { inject, Injectable } from '@angular/core';
import { MatDialog, MatDialogConfig, MatDialogRef } from '@angular/material/dialog';
import { ComponentType } from '@angular/cdk/portal';
import { firstValueFrom } from 'rxjs';
import { DATA_TYPE, IqserDialogComponent, RETURN_TYPE } from './iqser-dialog-component.directive';
import { defaultDialogConfig, largeDialogConfig } from './dialog.service';
@Injectable({
providedIn: 'root',
})
export class IqserDialog {
protected readonly _dialog = inject(MatDialog);
open<
Component extends IqserDialogComponent<Component, unknown, unknown>,
Data extends Component[DATA_TYPE],
Return extends Component[RETURN_TYPE],
>(dialog: ComponentType<Component>, config?: MatDialogConfig<Data>) {
const ref = this._dialog.open<Component, Data, Return>(dialog, config);
return {
...ref,
result() {
console.log('result');
return firstValueFrom(ref.afterClosed());
},
} as MatDialogRef<Component, Return> & { result(): Promise<Return> };
}
openLarge<
Component extends IqserDialogComponent<Component, unknown, unknown>,
Data extends Component[DATA_TYPE],
Return extends Component[RETURN_TYPE],
>(dialog: ComponentType<Component>, config?: MatDialogConfig<Data>) {
return this.open<Component, Data, Return>(dialog, { ...largeDialogConfig, ...config });
}
openDefault<
Component extends IqserDialogComponent<Component, unknown, unknown>,
Data extends Component[DATA_TYPE],
Return extends Component[RETURN_TYPE],
>(dialog: ComponentType<Component>, config?: MatDialogConfig<Data>) {
return this.open<Component, Data, Return>(dialog, { ...defaultDialogConfig, ...config });
}
}