diff --git a/src/app/football-field/football-field.component.css b/src/app/football-field/football-field.component.css
index 3ae33b6..7e74b69 100644
--- a/src/app/football-field/football-field.component.css
+++ b/src/app/football-field/football-field.component.css
@@ -100,3 +100,12 @@ canvas {
font-size: 12px;
text-align: center;
}
+
+.time-indicator {
+ position: absolute;
+ top: 0;
+ width: 3px; /* Epaisseur du trait */
+ height: 100%; /* La hauteur couvre toute la timeline */
+ background-color: red; /* Couleur du trait de temps */
+ left: 0; /* Point de départ du trait */
+}
\ No newline at end of file
diff --git a/src/app/football-field/football-field.component.html b/src/app/football-field/football-field.component.html
index 8376d7a..811965a 100644
--- a/src/app/football-field/football-field.component.html
+++ b/src/app/football-field/football-field.component.html
@@ -39,9 +39,11 @@
-->
-
-
-
+
+
+
+
+
diff --git a/src/app/football-field/football-field.component.ts b/src/app/football-field/football-field.component.ts
index f10e0bb..c4d52fe 100644
--- a/src/app/football-field/football-field.component.ts
+++ b/src/app/football-field/football-field.component.ts
@@ -1,6 +1,7 @@
import { Component, ViewChild, ElementRef, HostListener } from '@angular/core';
import { CommonModule } from '@angular/common';
import { FormsModule } from '@angular/forms';
+import { C } from '@angular/cdk/keycodes';
interface TimelineStep {
startTime: number; // Le temps de début en millisecondes
@@ -226,10 +227,6 @@ export class FootballFieldComponent {
}
private animate() {
- //this.updatePositions();
- //if (this.isAnimating && this.selectedPlayer) {
- // this.updatePlayerPosition(this.selectedPlayer);
- //}
// Effacer le canvas pour redessiner
this.ctx.clearRect(0, 0, this.canvas.nativeElement.width, this.canvas.nativeElement.height);
@@ -251,11 +248,17 @@ export class FootballFieldComponent {
hasAnimation = true; // Indiquer qu'il y a encore de l'animation
}
});
+ // Mettre à jour la position du trait de visualisation du temps
+ this.updateTimeIndicator(currentTime);
}
});
this.drawField();
requestAnimationFrame(() => this.animate());
+
+ if (this.isPlaying === false) {
+ this.stopTimeline();
+ }
// Continuer l'animation seulement si au moins un joueur est encore en mouvement
//if ((this.isAnimating) || (hasAnimation && this.isPlaying)) {
// requestAnimationFrame(() => this.animate());
@@ -269,6 +272,30 @@ export class FootballFieldComponent {
this.isPlaying = false;
}
+ // Mise à jour de la position du trait de temps sur la timeline
+ updateTimeIndicator(currentTime: number) {
+ //const timeIndicator = document.getElementById('time-indicator');
+ const elmnts = document.querySelectorAll('[id=time-indicator]');
+ if (elmnts) {
+ const timeline = document.querySelector('.timeline') as HTMLElement;
+ const timelineWidth = timeline.offsetWidth; // Largeur totale de la timeline
+ // Calcul de la position du trait en pixels
+ let timePosition = (currentTime / this.getTotalTimelineDuration()) * timelineWidth;
+ // Si l'indicateur est à la fin de la timeline, on arrete l'animation
+ if(timePosition >= timelineWidth) {
+ timePosition = timelineWidth;
+ this.isPlaying = false;
+ }
+ // Mettre à jour la position du trait
+ //timeIndicator.style.left = `${timePosition}px`;
+
+ // Mettre à jour la position du trait
+ elmnts.forEach(element =>
+ (element as HTMLElement).style.left = `${timePosition}px`
+ );
+ }
+ }
+
private updatePlayerPosition(player: Circle) {
if (player.timeline.length === 0 || player.currentStepIndex >= player.timeline.length) {
return; // Pas d'animation si la timeline est vide
@@ -544,12 +571,12 @@ export class FootballFieldComponent {
this.selectedPlayer.timeline.push({
startTime: prevStartTime,
- endTime: prevStartTime + 200,
+ endTime: prevStartTime + 1000,
startX: this.startX,
startY: this.startY,
endX: this.endX,
endY: this.endY,
- duration: 200 // Durée d'animation arbitraire, peut être ajustée
+ duration: 1000 // Durée d'animation arbitraire, peut être ajustée
});
console.log("timeline:", this.selectedPlayer.timeline);
this.selectedPlayer.currentStepIndex = 0; // Réinitialiser au début de la timeline
@@ -944,6 +971,18 @@ export class FootballFieldComponent {
this.isAnimating = true; // Redémarrer l'animation
}
+ reinitPlayers() {
+ // Réinitialiser la progression et l'étape actuelle
+ this.players.forEach(player => {
+ player.progress = 0;
+ player.currentStepIndex = 0;
+ this.updatePlayerPosition(player);
+ });
+
+ const currentTime = performance.now();
+ this.updateTimeIndicator(currentTime);
+ }
+
/* GESTION DE LA TIMELINE */
getMousePosOnTimeline(event: MouseEvent): { x: number } {
@@ -965,7 +1004,9 @@ export class FootballFieldComponent {
// La durée totale de la timeline
const totalDuration = this.getTotalTimelineDuration();
// La longueur de la timeline en pixels (par exemple, 1000px)
- const timelineWidth = this.timelineWidth;
+ const timeline = document.querySelector('.timeline') as HTMLElement;
+ const timelineWidth = timeline.offsetWidth; // Largeur totale de la timeline
+ //const timelineWidth = this.timelineWidth;
// La durée totale de l'animation en millisecondes
return (time / totalDuration) * timelineWidth;
}
@@ -1011,30 +1052,60 @@ export class FootballFieldComponent {
onTimelineMouseMove(event: MouseEvent) {
if (this.isTimelineDragging && this.draggedTimelinePlayer) {
- //const { x } = this.getMousePos(event);
const { x } = this.getMousePosOnTimeline(event);
// Calculer la nouvelle position du bloc
const newStartX = x - this.dragOffsetX;
const totalDuration = this.getTotalTimelineDuration();
- //const newStartTime = Math.floor((newStartX / this.canvas.nativeElement.width) * totalDuration);
const newStartTime = Math.floor((newStartX / this.timelineWidth) * totalDuration);
console.log("[onTimelineMouseMove] - x:",x,
+ " - dragOffsetX:", this.dragOffsetX,
" - newStartX:", newStartX,
- " - newStartTime:", newStartTime);
+ " - newStartTime:", newStartTime,
+ " - dragged Index:", this.draggedTimelineIndex,
+ " - timeline len:", this.draggedTimelinePlayer.timeline.length,
+ );
// Mettre à jour l'étape avec la nouvelle position
const step = this.draggedTimelinePlayer.timeline[this.draggedTimelineIndex];
- if (step.endTime < this.getTotalTimelineDuration()) {
- step.startTime = Math.max(0, newStartTime); // Ne pas permettre les valeurs négatives
+ let prevStep:TimelineStep = null;
+ // Le bloc N ne peut pas dépasser le bloc N+1 si celui-ci existe
+ // De même, le bloc N ne peut pas dépasser le bloc N-1 si celui-ci existe
+ if ((this.draggedTimelineIndex + 1) < this.draggedTimelinePlayer.timeline.length) {
+ const nextStep = this.draggedTimelinePlayer.timeline[this.draggedTimelineIndex + 1];
+ if ((this.draggedTimelineIndex - 1) >= 0) {
+ prevStep = this.draggedTimelinePlayer.timeline[this.draggedTimelineIndex - 1];
+ }
+ if ((((newStartTime + step.duration) < nextStep.startTime) &&
+ prevStep === null) ||
+ (prevStep != null &&
+ ((prevStep.endTime <= newStartTime) && ((newStartTime + step.duration) < nextStep.startTime)))) {
+ //console.log("PLOP0.1: (",newStartTime + step.duration, "/", nextStep.startTime,")");
+ step.startTime = Math.max(0, newStartTime); // Ne pas permettre les valeurs négatives
+ step.endTime = Math.max(0, step.startTime + step.duration); // Ne pas permettre les valeurs négatives
+ }
+ } else if (((this.draggedTimelineIndex - 1) >= 0) &&
+ (this.draggedTimelinePlayer.timeline[this.draggedTimelineIndex - 1])) {
+ const prevStep = this.draggedTimelinePlayer.timeline[this.draggedTimelineIndex - 1];
+ if ((prevStep.endTime <= newStartTime) &&
+ ((newStartTime + step.duration) <= (this.getTotalTimelineDuration()))) {
+ //console.log("PLOP1.1: (",prevStep.endTime, "/", newStartTime,"),(",newStartTime + step.duration,"/",this.getTotalTimelineDuration(),")");
+ step.startTime = Math.max(0, newStartTime); // Ne pas permettre les valeurs négatives
+ step.endTime = Math.max(0, step.startTime + step.duration); // Ne pas permettre les valeurs négatives
+ }
+
+ } else {
+ if (step.endTime < this.getTotalTimelineDuration()) {
+ step.startTime = Math.max(0, newStartTime); // Ne pas permettre les valeurs négatives
+ }
+ step.endTime = Math.max(0, step.startTime + step.duration); // Ne pas permettre les valeurs négatives
}
- step.endTime = Math.max(0, newStartTime + step.duration); // Ne pas permettre les valeurs négatives
/*
- // Ajuster la position de fin si nécessaire
- if (this.draggedTimelineIndex > 0) {
- const previousStep = this.draggedTimelinePlayer.timeline[this.draggedTimelineIndex - 1];
- previousStep.endTime = step.startTime;
- }
+ console.log("PLOP2");
+ if (step.endTime < this.getTotalTimelineDuration()) {
+ step.startTime = Math.max(0, newStartTime); // Ne pas permettre les valeurs négatives
+ }
+ step.endTime = Math.max(0, step.startTime + step.duration); // Ne pas permettre les valeurs négatives
*/
}
}
@@ -1042,6 +1113,7 @@ export class FootballFieldComponent {
onTimelineMouseUp() {
console.log("onMouseUp");
if (this.isTimelineDragging) {
+ console.log("timeline:", this.draggedTimelinePlayer.timeline);
this.isTimelineDragging = false;
this.draggedTimelinePlayer = null;
this.draggedTimelineIndex = -1;
@@ -1075,7 +1147,9 @@ export class FootballFieldComponent {
}
playTimeline() {
- if (this.isPlaying) return; // Ne pas relancer si déjà en cours
+ if (this.isPlaying) {
+ return; // Ne pas relancer si déjà en cours
+ }
this.isPlaying = true;
this.animationStartTime = performance.now(); // Obtenir le timestamp de départ