Skip to content

Commit

Permalink
fix: reset controls when registration change fails
Browse files Browse the repository at this point in the history
Refs: #39
  • Loading branch information
MaSch0212 committed Jun 9, 2024
1 parent a45a0fe commit c9c8cc8
Show file tree
Hide file tree
Showing 5 changed files with 50 additions and 17 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ export const registerForEventAction = createHttpAction<{
}>()(PLAYER_EVENTS_ACTION_SCOPE, 'Register For Event');

export const registerForEventReducers: Reducers<PlayerEventsFeatureState> = [
on(registerForEventAction, (state, { props }) =>
on(registerForEventAction.success, (state, { props }) =>
playerEventEntityAdapter.mapOne(
{
id: props.eventId,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -44,17 +44,6 @@
</ng-template>
</p-messages>
}
@if (hasRegistrationFailed()) {
<p-messages severity="error">
<ng-template pTemplate>
<span class="i-[mdi--close-circle-outline] mr-2"></span>
<span
>{{ translations.playerEvents_error_registration() }}
{{ translations.shared_tryAgainLater() }}</span
>
</ng-template>
</p-messages>
}

@if (canRegister() || !event.isStarted) {
<h2 class="m-0 pt-4">{{ translations.playerEvents_registrations() }}</h2>
Expand All @@ -73,6 +62,7 @@ <h2 class="m-0 pt-4">{{ translations.playerEvents_registrations() }}</h2>
"
[ngModel]="timeslot.isRegistered"
(ngModelChange)="setTimeslotRegistration(timeslot, $event)"
[resetNgModel]="resetNgModel"
/>
</div>
@if (timeslot.isRegistered && timeslot.isFallbackAllowed) {
Expand All @@ -95,6 +85,7 @@ <h2 class="m-0 pt-4">{{ translations.playerEvents_registrations() }}</h2>
[disabled]="!canRegister() || isChanginRegistration()"
[ngModel]="timeslot.chosenFallbackTimeslotId"
(ngModelChange)="setFallbackTimeslot(timeslot, $event)"
[resetNgModel]="resetNgModel"
[options]="timeslotsWithoutFallback()"
[optionValue]="'id'"
[placeholder]="translations.playerEvents_noFallbackTimeslot()"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ import { MessagesModule } from 'primeng/messages';
import { OverlayPanelModule } from 'primeng/overlaypanel';
import { ProgressSpinnerModule } from 'primeng/progressspinner';
import { TooltipModule } from 'primeng/tooltip';
import { map, timer } from 'rxjs';
import { map, Subject, timer } from 'rxjs';

import { hasActionFailed, isActionBusy } from '../../../+state/action-state';
import {
Expand All @@ -23,12 +23,13 @@ import {
selectPlayerEventsActionState,
} from '../../../+state/player-events';
import { ApiEventTimeslotRegistration } from '../../../api/models';
import { ResetNgModelDirective } from '../../../directives/reset-ng-model.directive';
import { PlayerEventTimeslot } from '../../../models/parsed-models';
import { AuthService } from '../../../services/auth.service';
import { TranslateService } from '../../../services/translate.service';
import { ifTruthy } from '../../../utils/common.utils';
import { compareTimes, getTimeDifference } from '../../../utils/date.utils';
import { selectSignal } from '../../../utils/ngrx.utils';
import { errorToastEffect, selectSignal } from '../../../utils/ngrx.utils';
import { hasTouchScreen } from '../../../utils/user-agent.utils';

// 1 1/2 hours
Expand All @@ -49,6 +50,7 @@ const gameDuration = 90 * 60 * 1000;
TooltipModule,
MessagesModule,
InputSwitchModule,
ResetNgModelDirective,
],
templateUrl: './player-event-details.component.html',
styleUrl: './player-event-details.component.scss',
Expand All @@ -63,6 +65,7 @@ export class PlayerEventDetailsComponent {
protected readonly locale = this._translateService.language;
protected readonly hasTouchScreen = hasTouchScreen;
protected readonly user = inject(AuthService).user;
protected readonly resetNgModel = new Subject<void>();

private readonly eventId = toSignal(this._activatedRoute.params.pipe(map(data => data['id'])));
private readonly actionState = selectSignal(selectPlayerEventsActionState('loadOne'));
Expand All @@ -76,9 +79,6 @@ export class PlayerEventDetailsComponent {
protected readonly isChanginRegistration = computed(() =>
isActionBusy(this.registerActionState())
);
protected readonly hasRegistrationFailed = computed(() =>
hasActionFailed(this.registerActionState())
);
protected readonly event = selectSignal(computed(() => selectPlayerEvent(this.eventId())));
protected readonly timeslots = computed(() =>
[...(this.event()?.timeslots ?? [])].sort((a, b) => compareTimes(a.time, b.time))
Expand Down Expand Up @@ -120,6 +120,20 @@ export class PlayerEventDetailsComponent {
},
{ allowSignalWrites: true }
);

effect(
() => {
if (hasActionFailed(this.registerActionState())) {
this.resetNgModel.next();
}
},
{ allowSignalWrites: true }
);

errorToastEffect(
computed(() => this.translations.playerEvents_error_registration()),
this.registerActionState
);
}

protected setTimeslotRegistration(timeslot: PlayerEventTimeslot, isRegistered: boolean) {
Expand Down
27 changes: 27 additions & 0 deletions src/client/src/app/directives/reset-ng-model.directive.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
import { Directive, effect, inject, input, OnDestroy } from '@angular/core';
import { NG_VALUE_ACCESSOR } from '@angular/forms';
import { Observable, Subscription } from 'rxjs';

@Directive({
selector: '[resetNgModel]',
standalone: true,
})
export class ResetNgModelDirective implements OnDestroy {
private readonly _valueAccessor = inject(NG_VALUE_ACCESSOR);
private _subscription?: Subscription;

public readonly resetNgModel = input.required<Observable<unknown>>();
public readonly ngModel = input<unknown>();

constructor() {
effect(() => {
this._subscription = this.resetNgModel().subscribe(() => {
this._valueAccessor.forEach(x => x.writeValue(this.ngModel()));
});
});
}

public ngOnDestroy(): void {
this._subscription?.unsubscribe();
}
}
1 change: 1 addition & 0 deletions src/client/src/app/utils/ngrx.utils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@ export function errorToastEffect(
severity: 'error',
summary: message(),
detail: translations.shared_tryAgainLater(),
life: 7500,
});
}
});
Expand Down

0 comments on commit c9c8cc8

Please sign in to comment.