feat: added bot, light and dark mode

This commit was merged in pull request #1.
This commit is contained in:
2026-04-22 10:22:22 +02:00
parent e83ec814d9
commit 2de003e497
36 changed files with 2047 additions and 498 deletions
+95 -2
View File
@@ -1,5 +1,6 @@
import { CommonModule } from '@angular/common';
import { Component } from '@angular/core';
import { FormsModule } from '@angular/forms';
import { Router } from '@angular/router';
import { finalize } from 'rxjs';
import { getErrorMessage } from '../../core/http/error-message.util';
@@ -8,18 +9,31 @@ import { GameApiService } from '../../services/game-api.service';
@Component({
selector: 'app-welcome',
standalone: true,
imports: [CommonModule],
imports: [CommonModule, FormsModule],
templateUrl: './welcome.component.html',
styleUrl: './welcome.component.css'
})
export class WelcomeComponent {
creating = false;
errorMessage = '';
showDifficultySelector = false;
showJoinGameForm = false;
gameIdInput = '';
joiningGame = false;
constructor(
private readonly router: Router,
private readonly gameApi: GameApiService
) {}
) {
this.initTheme();
}
private initTheme(): void {
const savedTheme = localStorage.getItem('theme');
if (savedTheme === 'dark') {
document.documentElement.setAttribute('data-theme', 'dark');
}
}
startOneVsOne(): void {
if (this.creating) {
@@ -41,4 +55,83 @@ export class WelcomeComponent {
}
});
}
startVsBot(difficulty: 'easy' | 'medium' | 'hard'): void {
if (this.creating) {
return;
}
this.errorMessage = '';
this.creating = true;
this.showDifficultySelector = false;
this.gameApi
.createGameVsBot(difficulty)
.pipe(finalize(() => (this.creating = false)))
.subscribe({
next: (game) => {
void this.router.navigate(['/game', game.gameId]);
},
error: (error) => {
this.errorMessage = getErrorMessage(error, 'Unable to create a game against bot.');
}
});
}
toggleDifficultySelector(): void {
this.showDifficultySelector = !this.showDifficultySelector;
this.showJoinGameForm = false;
this.errorMessage = '';
}
toggleJoinGameForm(): void {
this.showJoinGameForm = !this.showJoinGameForm;
this.showDifficultySelector = false;
this.errorMessage = '';
this.gameIdInput = '';
}
joinGame(): void {
if (this.joiningGame || !this.gameIdInput.trim()) {
return;
}
this.errorMessage = '';
this.joiningGame = true;
this.gameApi
.getGame(this.gameIdInput.trim())
.pipe(finalize(() => (this.joiningGame = false)))
.subscribe({
next: (game) => {
void this.router.navigate(['/game', game.gameId]);
},
error: (error) => {
this.errorMessage = getErrorMessage(error, 'Unable to find or join the game.');
}
});
}
clearJoinGameForm(): void {
this.showJoinGameForm = false;
this.gameIdInput = '';
this.errorMessage = '';
}
toggleDarkMode(): void {
const htmlElement = document.documentElement;
const isDarkMode = htmlElement.getAttribute('data-theme') === 'dark';
if (isDarkMode) {
htmlElement.removeAttribute('data-theme');
localStorage.removeItem('theme');
} else {
htmlElement.setAttribute('data-theme', 'dark');
localStorage.setItem('theme', 'dark');
}
}
isDarkMode(): boolean {
return document.documentElement.getAttribute('data-theme') === 'dark';
}
}