modif match

This commit is contained in:
ExostFlash 2025-06-02 15:04:33 +02:00
parent f61416c4d0
commit 83c6b6e504
9 changed files with 284 additions and 1 deletions

View file

@ -7,6 +7,7 @@ import { LoginComponent } from './components/essentials/login/login.component';
import { LogoutComponent } from './components/essentials/logout/logout.component';
import { HomeComponent } from './components/home/home.component';
import { MatchesComponent } from './components/matches/matches.component';
import { MatchesIdComponent } from './components/matches-id/matches-id.component';
const routes: Routes = [
{ path: 'login', component: LoginComponent },
@ -14,6 +15,7 @@ const routes: Routes = [
{ path: '', component: HomeComponent },
{ path: 'home', component: HomeComponent },
{ path: 'matches', component: MatchesComponent },
{ path: 'matches/:id', component: MatchesIdComponent },
];
@NgModule({

View file

@ -10,6 +10,7 @@ import { HomeComponent } from './components/home/home.component';
import { LoginComponent } from './components/essentials/login/login.component';
import { LogoutComponent } from './components/essentials/logout/logout.component';
import { MatchesComponent } from './components/matches/matches.component';
import { MatchesIdComponent } from './components/matches-id/matches-id.component';
@NgModule({
declarations: [
@ -20,6 +21,7 @@ import { MatchesComponent } from './components/matches/matches.component';
LoginComponent,
LogoutComponent,
MatchesComponent,
MatchesIdComponent,
],
imports: [BrowserModule, AppRoutingModule, FormsModule],
providers: [],

View file

@ -0,0 +1,3 @@
.card {
border-left-width: 0.5rem !important;
}

View file

@ -0,0 +1,94 @@
<div class="container my-4" *ngIf="match && player1 && player2">
<h2 class="mb-4 text-center">Détail du Match</h2>
<div
class="card shadow border-start-5 border-{{
getMatchStateColor(match.state)
}}"
>
<div class="card-body">
<div class="d-flex justify-content-between align-items-center mb-2">
<h5 class="mb-0">
{{ match.city }}, {{ match.country }}
<br />
<small class="text-muted"
>{{ match.date | date : "fullDate" }} -
{{ match.date | date : "shortTime" }}</small
>
</h5>
<span class="badge bg-light text-dark">{{ match.weapon }}</span>
</div>
<div class="d-flex justify-content-between align-items-center mt-3">
<div class="text-start">
<strong>{{ player1?.firstName }} {{ player1?.name }}</strong
><br />
<small class="text-muted">{{ player1?.club }}</small>
</div>
<div class="text-center">
<ng-container
*ngIf="
authService.isAuthenticated() && match.state != 2;
else displayScores
"
>
<span
class="badge bg-primary fs-4"
style="cursor: pointer"
(click)="incrementScore(1)"
>
{{ match.score1 }}
</span>
<span class="text-muted mx-2">vs</span>
<span
class="badge bg-primary fs-4"
style="cursor: pointer"
(click)="incrementScore(2)"
>
{{ match.score2 }}
</span>
</ng-container>
<ng-template #displayScores>
<span class="badge bg-primary fs-4">{{ match.score1 }}</span>
<span class="text-muted mx-2">vs</span>
<span class="badge bg-primary fs-4">{{ match.score2 }}</span>
</ng-template>
</div>
<div class="text-end">
<strong>{{ player2?.firstName }} {{ player2?.name }}</strong
><br />
<small class="text-muted">{{ player2?.club }}</small>
</div>
</div>
<div class="mt-4">
<span class="badge bg-{{ getMatchStateColor(match.state) }} p-2 fs-6">
{{ getMatchStateLabel(match.state) }}
</span>
</div>
<div class="mt-3">
<h5>Arbitre</h5>
<div *ngIf="referee">
<p class="mb-0">
<strong>{{ referee.firstName }} {{ referee.name }}</strong>
</p>
<p class="text-muted">
Niveau : {{ getRefereeLevelLabel(referee.level) }}
</p>
</div>
<div *ngIf="!referee">
<p class="text-danger">Arbitre non trouvé.</p>
</div>
</div>
</div>
</div>
</div>
<!-- Si erreur ou match introuvable -->
<div class="container my-5 text-center text-danger" *ngIf="!match">
<p>Match non trouvé.</p>
</div>

View file

@ -0,0 +1,23 @@
import { ComponentFixture, TestBed } from '@angular/core/testing';
import { MatchesIdComponent } from './matches-id.component';
describe('MatchesIdComponent', () => {
let component: MatchesIdComponent;
let fixture: ComponentFixture<MatchesIdComponent>;
beforeEach(async () => {
await TestBed.configureTestingModule({
declarations: [MatchesIdComponent]
})
.compileComponents();
fixture = TestBed.createComponent(MatchesIdComponent);
component = fixture.componentInstance;
fixture.detectChanges();
});
it('should create', () => {
expect(component).toBeTruthy();
});
});

View file

@ -0,0 +1,141 @@
import { Component, OnInit } from '@angular/core';
import { ActivatedRoute } from '@angular/router';
import { AuthService } from '@services/auth.service';
import { MatchesService } from '@services/matches.service';
import { MatchState, Matches } from '@interfaces/matches';
import { PlayerService } from '@services/player.service';
import { Player } from '@interfaces/player';
import { RefereeService } from '@services/referee.service';
import { Referee, RefereeLevel } from '@interfaces/referee';
@Component({
selector: 'app-matches-id',
standalone: false,
templateUrl: './matches-id.component.html',
styleUrl: './matches-id.component.css',
})
export class MatchesIdComponent implements OnInit {
match: Matches | undefined;
player1: Player | undefined;
player2: Player | undefined;
referee: Referee | undefined;
constructor(
private route: ActivatedRoute,
private matchService: MatchesService,
private playerService: PlayerService,
private refereeService: RefereeService,
public authService: AuthService
) {}
ngOnInit(): void {
const id = Number(this.route.snapshot.paramMap.get('id'));
this.matchService.getMatchById(id).subscribe((match) => {
if (match) {
this.match = match;
this.playerService
.getPlayerById(match.player1ID)
.subscribe((p1) => (this.player1 = p1!));
this.playerService
.getPlayerById(match.player2ID)
.subscribe((p2) => (this.player2 = p2!));
this.refereeService
.getRefereeById(match.refereeID)
.subscribe((ref) => (this.referee = ref!));
}
});
}
saveScores(): void {
if (this.match) {
this.matchService.updateMatch(this.match.id, {
score1: this.match.score1,
score2: this.match.score2,
});
}
}
getMatchStateLabel(state: MatchState): string {
switch (state) {
case MatchState.NOT_STARTED:
return 'À venir';
case MatchState.ONGOING:
return 'En cours';
case MatchState.OVER:
return 'Terminé';
default:
return 'Inconnu';
}
}
getMatchStateColor(state: MatchState): string {
switch (state) {
case MatchState.NOT_STARTED:
return 'secondary';
case MatchState.ONGOING:
return 'warning';
case MatchState.OVER:
return 'success';
default:
return 'light';
}
}
getRefereeLevelLabel(level: RefereeLevel): string {
switch (level) {
case RefereeLevel.NATIONAL:
return 'National';
case RefereeLevel.REGIONAL:
return 'Régional';
case RefereeLevel.DEPARTMENTAL:
return 'Départemental';
default:
return 'Inconnu';
}
}
updateScores(): void {
if (this.match) {
this.matchService.updateMatch(this.match.id, {
score1: this.match.score1,
score2: this.match.score2,
});
}
}
incrementScore(player: 1 | 2): void {
if (!this.match) return;
// Incrémente le score du joueur
if (player === 1) {
this.match.score1 += 1;
} else {
this.match.score2 += 1;
}
// Change l'état en fonction des scores
if (
this.match.score1 === 1 &&
this.match.score2 === 0 &&
this.match.state === MatchState.NOT_STARTED
) {
this.match.state = MatchState.ONGOING; // passage à l'état 1 (en cours)
} else if (
this.match.score2 === 1 &&
this.match.score1 === 0 &&
this.match.state === MatchState.NOT_STARTED
) {
this.match.state = MatchState.ONGOING;
}
// Si l'un des scores arrive à 15, on considère le match terminé
if (this.match.score1 >= 15 || this.match.score2 >= 15) {
this.match.state = MatchState.OVER; // passage à l'état 2 (terminé)
}
this.updateScores();
}
}

View file

@ -6,6 +6,8 @@
<div
class="card shadow-sm border-start-5"
[ngClass]="getMatchBorderColor(match.state)"
style="cursor: pointer"
(click)="goToMatchDetail(match.id)"
>
<div class="card-body">
<div class="d-flex justify-content-between align-items-center mb-2">

View file

@ -1,4 +1,5 @@
import { Component } from '@angular/core';
import { Router } from '@angular/router';
import { MatchesService } from '@services/matches.service';
import { Matches, MatchState } from '@interfaces/matches';
@ -19,7 +20,8 @@ export class MatchesComponent {
constructor(
private matchesService: MatchesService,
private playerService: PlayerService
private playerService: PlayerService,
private router: Router
) {}
ngOnInit(): void {
@ -63,4 +65,8 @@ export class MatchesComponent {
return 'Inconnu';
}
}
goToMatchDetail(matchId: number): void {
this.router.navigate(['/matches', matchId]);
}
}

View file

@ -68,4 +68,14 @@ export class MatchesService {
);
// ici tu pourrais plus tard faire : this.socket = new WebSocket('ws://...') etc.
}
updateMatch(id: number, updatedData: Partial<Matches>): void {
const match = this.matches.find((m) => m.id === id);
if (match) {
Object.assign(match, updatedData);
console.log(`[MatchesService] Match ${id} mis à jour :`, match);
} else {
console.warn(`[MatchesService] Match ${id} introuvable`);
}
}
}