Skip to content

Commit 67e1347

Browse files
committed
fix(interval-timer): handle interval initialization and apply minimum based on delay options
1 parent c0415b5 commit 67e1347

File tree

1 file changed

+42
-25
lines changed

1 file changed

+42
-25
lines changed

src/app/IntervalTimer/interval-timer.component.ts

Lines changed: 42 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ import {
66
Output,
77
EventEmitter,
88
} from '@angular/core';
9-
import { Settings, SettingsService } from '../data/settings.service';
9+
import { SettingsService } from '../data/settings.service';
1010
import { Subscription } from 'rxjs';
1111

1212
@Component({
@@ -21,7 +21,7 @@ export class IntervalTimerComponent implements OnInit, OnDestroy {
2121

2222
// Optional parameter to define the interval times that are needed in the parent Component. This overwrites the default of 10, 30, 60, 120 and 300 seconds if provided
2323
@Input()
24-
delayOptionsArray: number[] = [10, 30, 60, 120, 300];
24+
delayOptions: number[] = [10, 30, 60, 120, 300];
2525

2626
// Optional parameter to provide another label for the Timer Component than "Refresh Rate"
2727
@Input()
@@ -30,50 +30,67 @@ export class IntervalTimerComponent implements OnInit, OnDestroy {
3030
public callInterval: ReturnType<typeof setInterval> | null = null;
3131
public currentCallDelay: number;
3232
public circleVisible: boolean = true;
33-
public delayOptions: Generator;
3433
private settingsSubscription: Subscription;
34+
private defaultInterval: number = 30;
3535

3636
constructor(private settingsService: SettingsService) {}
3737

3838
ngOnInit(): void {
39-
function* cycle<T>(array: T[]) {
40-
while (true) yield* array;
41-
}
42-
this.delayOptions = cycle(this.delayOptionsArray);
4339
this.settingsSubscription = this.settingsService.settings$.subscribe(
44-
(settings: Settings) => {
45-
this.currentCallDelay = settings.refresh_timer_interval;
46-
this.changeDelay(false);
40+
({ refresh_timer_interval }) => {
41+
this.currentCallDelay = this.settingsDelayOrDefault(
42+
refresh_timer_interval,
43+
);
44+
this.startTimer();
4745
},
4846
);
4947
}
5048

51-
onTimerClick() {
49+
onTimerClick(): void {
5250
this.changeDelay();
5351
this.intervalElapsed.emit();
52+
5453
this.settingsService
5554
.update({ refresh_timer_interval: this.currentCallDelay })
5655
.subscribe();
5756
}
5857

59-
changeDelay(incrementInterval: boolean = true) {
60-
//Set next value of the interval array as call delay
61-
if (incrementInterval) {
62-
this.currentCallDelay = this.delayOptions.next().value;
63-
}
64-
if (this.callInterval !== null) {
58+
changeDelay(): void {
59+
this.currentCallDelay = this.nextHigherOrFirst(this.currentCallDelay);
60+
this.startTimer();
61+
}
62+
63+
private startTimer(): void {
64+
if (this.callInterval) {
6565
clearInterval(this.callInterval);
66-
this.callInterval = null;
6766
}
68-
this.callInterval = setInterval(() => {
69-
this.intervalElapsed.emit();
70-
}, this.currentCallDelay * 1000);
7167

72-
//Reload the Circle to refresh the Animation
68+
this.callInterval = setInterval(
69+
() => this.intervalElapsed.emit(),
70+
this.currentCallDelay * 1000,
71+
);
72+
73+
// Restart animation
7374
this.circleVisible = false;
74-
setTimeout(() => {
75-
this.circleVisible = true;
76-
}, 0);
75+
setTimeout(() => (this.circleVisible = true));
76+
}
77+
78+
private settingsDelayOrDefault(value?: number): number {
79+
if (value && value > 0) {
80+
return Math.max(value, this.minInterval);
81+
}
82+
83+
return this.defaultInterval;
84+
}
85+
86+
private nextHigherOrFirst(current: number): number {
87+
const sorted = [...this.delayOptions].sort((a, b) => a - b);
88+
89+
return sorted.find((v) => v > current) ?? sorted[0];
90+
}
91+
92+
private get minInterval(): number {
93+
return Math.min(...this.delayOptions);
7794
}
7895

7996
ngOnDestroy(): void {

0 commit comments

Comments
 (0)