From fb8c349904b91ad37c70f12a93158b565fbaafd7 Mon Sep 17 00:00:00 2001 From: Artem Dzhereleiko Date: Wed, 2 Apr 2025 16:25:26 +0300 Subject: [PATCH] UI: Refactoring --- .../components/toggle-header.component.html | 6 ++-- .../components/toggle-header.component.ts | 30 +++++++------------ 2 files changed, 14 insertions(+), 22 deletions(-) diff --git a/ui-ngx/src/app/shared/components/toggle-header.component.html b/ui-ngx/src/app/shared/components/toggle-header.component.html index 253749d7b9..fdfabd08b5 100644 --- a/ui-ngx/src/app/shared/components/toggle-header.component.html +++ b/ui-ngx/src/app/shared/components/toggle-header.component.html @@ -41,12 +41,12 @@ [name]="name" [(ngModel)]="value" (ngModelChange)="valueChange.emit(value)"> - + {{ option.name }} warning diff --git a/ui-ngx/src/app/shared/components/toggle-header.component.ts b/ui-ngx/src/app/shared/components/toggle-header.component.ts index 3058ad285d..9add580a73 100644 --- a/ui-ngx/src/app/shared/components/toggle-header.component.ts +++ b/ui-ngx/src/app/shared/components/toggle-header.component.ts @@ -39,19 +39,18 @@ import { import { PageComponent } from '@shared/components/page.component'; import { Store } from '@ngrx/store'; import { AppState } from '@core/core.state'; -import { BehaviorSubject, Subject, Subscription } from 'rxjs'; +import { BehaviorSubject, Observable, ReplaySubject, Subject, Subscription } from 'rxjs'; import { BreakpointObserver, BreakpointState } from '@angular/cdk/layout'; import { MediaBreakpoints } from '@shared/models/constants'; import { coerceBoolean } from '@shared/decorators/coercion'; import { startWith, takeUntil } from 'rxjs/operators'; import { Platform } from '@angular/cdk/platform'; import { MatButtonToggle, MatButtonToggleGroup } from '@angular/material/button-toggle'; -import { isDefined } from '@core/utils'; export interface ToggleHeaderOption { name: string; value: any; - error?: string; + error$?: Observable; } export type ToggleHeaderAppearance = 'fill' | 'fill-invert' | 'stroked'; @@ -65,13 +64,13 @@ export type ScrollDirection = 'after' | 'before'; } ) // eslint-disable-next-line @angular-eslint/directive-class-suffix -export class ToggleOption implements OnChanges { +export class ToggleOption implements OnChanges, OnDestroy { @Input() value: any; @Input() error: string; - @Output() errorChange = new EventEmitter(); + currentError = new ReplaySubject(1); get viewValue(): string { return (this._element?.nativeElement.textContent || '').trim(); @@ -83,11 +82,15 @@ export class ToggleOption implements OnChanges { ngOnChanges(changes: SimpleChanges) { if (changes?.error) { - if (!changes.error.firstChange && changes.error.currentValue !== changes.error.previousValue) { - this.errorChange.emit(this.error); + if (changes.error.currentValue !== changes.error.previousValue) { + this.currentError.next(this.error); } } } + + ngOnDestroy() { + this.currentError.complete(); + } } @Directive() @@ -106,7 +109,6 @@ export abstract class _ToggleBase extends PageComponent implements AfterContentI ngAfterContentInit(): void { this.toggleOptions.changes.pipe(startWith(null), takeUntil(this._destroyed)).subscribe(() => { - this.subscribeToToggleOptions(); this.syncToggleHeaderOptions(); }); } @@ -116,16 +118,6 @@ export abstract class _ToggleBase extends PageComponent implements AfterContentI this._destroyed.complete(); } - private subscribeToToggleOptions() { - this.toggleOptions.forEach(option => { - if (isDefined(option.error)) { - option.errorChange.pipe(takeUntil(this._destroyed)).subscribe(() => { - this.syncToggleHeaderOptions(); - }); - } - }); - } - private syncToggleHeaderOptions() { if (this.toggleOptions?.length) { this.options.length = 0; @@ -134,7 +126,7 @@ export abstract class _ToggleBase extends PageComponent implements AfterContentI { name: option.viewValue, value: option.value, - error: option.error + error$: option.currentError.asObservable() } ); });