Déplacement dans le Labyrinthe
Objectif
Apprendre à gérer les événements clavier en JavaScript pour permettre à l'utilisateur d'interagir avec le jeu.
Notions théoriques
Le JavaScript est un langage événementiel, ce qui signifie que beaucoup de code s'exécute en réponse à des événements.
Dans un jeu comme Pacman, les événements clavier sont essentiels pour contrôler les mouvements du personnage.
En JavaScript, l'écoute d'événements se fait grâce à la méthode addEventListener
, qui permet de réagir à des actions de l'utilisateur, comme appuyer sur une touche.
Pour Pacman, nous utiliserons addEventListener
pour écouter les événements keydown
,
qui sont déclenchés lorsque l'utilisateur appuie sur une touche.
La propriété
event.key
nous permet de savoir quelle touche a été pressée.
Voici en Javascript comment écouter un évènement keydown
du clavier :
// Ecouter l'évènement keydown du clavier et exécuter une fonction
useEffect(() => {
function handleKeyDown(event) {
// Il suffit de placer ici le nom de la fonction qui doit être appelée
// lorsque l'utilisateur a appuyé sur une touche du clavier.
}
// Ajouter l'écouteur de l'évènement 'Appui sur une touche'
document.addEventListener("keydown", handleKeyDown);
// Retirer l'écouteur de l'évènement 'Appui sur une touche' lorsque l'appui a été traité
return () => document.removeEventListener("keydown", handleKeyDown);
// Indiquer ici le nom de la variable dépendante qui sera modifiée suite à l'appel
// de la fonction indiquée dans handleKeyDown(event) {...}
}, [positionDeObjet]);
Il est important de gérer correctement ces événements pour que le personnage ne traverse pas les murs ;-) et se déplace seulement là où c'est possible !
Exemple pratique
Dans notre jeu de Pacman, nous pourrons écouter l'évènement keydown
du clavier et exécuter la fonction deplacerPacman
, avec ce code :
// Ecouter l'évènement keydown du clavier et exécuter la fonction deplacerPacman
useEffect(() => {
function handleKeyDown(event) {
deplacerPacman(event.key, pacmanPosition, labyrinthe, setPacmanPosition);
}
document.addEventListener("keydown", handleKeyDown);
return () => document.removeEventListener("keydown", handleKeyDown);
}, [pacmanPosition]);
Et voici un extrait de la fonction deplacerPacman
qui va pouvoir déplacer le Pacman en fonction de la touche appuyée :
document.addEventListener('keydown', function(event) {
switch(event.key) {
case 'ArrowUp':
// Déplacer Pacman vers le haut si possible
break;
case 'ArrowDown':
// Déplacer Pacman vers le bas si possible
break;
case 'ArrowLeft':
// Déplacer Pacman vers la gauche si possible
break;
case 'ArrowRight':
// Déplacer Pacman vers la droite si possible
break;
}
});
Quelques éléments de code à connaître
addEventListener(type, listener)
: Attache une fonction à appeler chaque fois que l'événement spécifié est délivré à la cible.removeEventListener(type, listener)
: Supprime un écouteur d'événement.event.key
: Retourne la valeur de la touche du clavier qui a été pressée lors d'un événement clavier.
Test de mémorisation/compréhension
TP pour réfléchir et résoudre des problèmes
Votre mission
Votre mission consiste à créer un composant Pacman
et à ajouter la gestion des événements de touches pour déplacer Pacman en fonction des touches directionnelles pressées.
Etapes
Voici un exemple de code qui permet à Pacman de se déplacer dans le labyrinthe en utilisant les touches fléchées du clavier, sans traverser les murs :
-
Créez un nouveau fichier
Pacman.js
à la racine de votre projet (à côté deApp.js
) :// Pacman.js
import React from 'react';
import { View } from 'react-native';
const tailleCase = 40; -
Ajoutez la fonction
Pacman
dans votre fichierPacman.js
:// Pacman.js
import React from 'react';
import { View } from 'react-native';
const tailleCase = 40;
function Pacman(props) {
...
} -
Complétez la fonction
Pacman
, dans votre fichierPacman.js
, afin de définir les attributs et le style d'affichage de votre Pacman :// Pacman.js
import React from 'react';
import { View } from 'react-native';
const tailleCase = 40;
function Pacman(props) {
const position = props.position;
const stylePacman = {
width: tailleCase,
height: tailleCase,
borderRadius: tailleCase / 2,
backgroundColor: 'yellow',
position: 'absolute',
left: position.x * tailleCase,
top: position.y * tailleCase,
transition: 'left 0.5s, top 0.5s', // Transition douce pour le mouvement
};
return <View style={stylePacman} />;
} -
Ajoutez l'export de la fonction
Pacman
à la fin du fichierPacman.js
:export default Pacman;
-
Ajouter l'import de notre composant
Pacman
dans le code du fichierApp.js
:// App.js
import { StyleSheet, View } from 'react-native';
import Labyrinthe from './Labyrinthe';
import genererLabyrinthe from './genererLabyrinthe';
import Pacman from './Pacman';
...
-
Créez un nouveau fichier
DeplacementPacman.js
à la racine de votre projet (à côté deApp.js
), avec une fonctiondeplacerPacman
:// DeplacementPacman.js
function deplacerPacman(direction, pacmanPosition, labyrinthe, setPacmanPosition) {
...
} -
Complétez le code de la fonction
deplacerPacman
:// DeplacementPacman.js
function deplacerPacman(direction, pacmanPosition, labyrinthe, setPacmanPosition) {
var nouvellePosition = { ...pacmanPosition };
switch (direction) {
case "ArrowUp":
nouvellePosition.y -= 1;
break;
case "ArrowDown":
nouvellePosition.y += 1;
break;
case "ArrowLeft":
nouvellePosition.x -= 1;
break;
case "ArrowRight":
nouvellePosition.x += 1;
break;
default:
return; // Si la touche n'est pas reconnue, on ne fait rien.
}
// Vérifier si la nouvelle position est un chemin.
if (
labyrinthe[nouvellePosition.y] &&
labyrinthe[nouvellePosition.y][nouvellePosition.x] === 0
) {
setPacmanPosition(nouvellePosition);
}
} -
Ajoutez l'export de la fonction
deplacerPacman
à la fin du fichierDeplacementPacman.js
:export default deplacerPacman;
-
Ajouter l'import de notre fonction
deplacerPacman
dans le code du fichierApp.js
:// App.js
import { StyleSheet, View } from 'react-native';
import Labyrinthe from './Labyrinthe';
import genererLabyrinthe from './genererLabyrinthe';
import Pacman from './Pacman';
import deplacerPacman from "./DeplacementPacman";
... -
Ajouter l'import des composants
useState
etuseEffect
, dans le code du fichierApp.js
, pour mémoriser la position de Pacman et ajouter un écouteur d'événements :// App.js
import React, { useState, useEffect } from 'react';
import { StyleSheet, View } from 'react-native';
import Labyrinthe from './Labyrinthe';
import genererLabyrinthe from './genererLabyrinthe';
import Pacman from './Pacman';
...Que signifient
useState
etuseEffect
?Imaginez que vous construisez une maison avec des pièces qui ont des boitiers pour contrôler la température de chaque pièce.
-
useState
:Pour que les choses fonctionnent, chaque pièce a besoin de se souvenir de la température souhaitée dans cette pièce.
Dans le monde de la programmation, cette mémoire s'appelle "état".
useState
est un petit boitier/mémoire que vous pouvez mettre dans n'importe quelle pièce. Ce boitier vous permet de fixer la température de la pièce. -
useEffect
:Maintenant, parfois, vous voulez que certaines choses se passent automatiquement dans une pièce, comme éteindre le chauffage quand vous ouvrez la fenêtre.
Dans le monde de la programmation, ces actions automatiques s'appellent des "effets de bord".
useEffect
est comme un petit boitier/robot dans la pièce qui s'occupe de ces actions automatiques. Vous lui dites quoi faire et quand le faire (par exemple, éteindre le chauffage quand vous ouvrez la fenêtre).
En résumé,
useState
etuseEffect
sont des outils qui rendent la construction et la gestion des pièces de votre maison beaucoup plus flexible. -
-
Modifiez le code du fichier
App.js
pour mémoriser la position du Pacman (et démarrer dans la case{ x: 1, y: 1 }
) :...
export default function App() {
const [pacmanPosition, setPacmanPosition] = useState({ x: 1, y: 1 }); // Démarre en position x=1 et y=1
... -
Modifiez le code du fichier
App.js
pour écouter l'évènementkeydown
du clavier et exécuter la fonctiondeplacerPacman
:...
// Ecouter l'évènement keydown du clavier et exécuter la fonction deplacerPacman
useEffect(() => {
function handleKeyDown(event) {
deplacerPacman(event.key, pacmanPosition, labyrinthe, setPacmanPosition);
}
document.addEventListener("keydown", handleKeyDown);
return () => document.removeEventListener("keydown", handleKeyDown);
}, [pacmanPosition]);
... -
Modifiez le code du fichier
App.js
pour ajouter notre composantPacman
:...
return (
<View style={styles.container}>
<View>
<Labyrinthe labyrinthe={labyrinthe} />
<Pacman position={pacmanPosition} />
</View>
</View>
);
...
Dans ce code, nous avons :
- Créé un composant
Pacman
qui dessine Pacman sur l'écran à la position spécifiée. - Ajouté un style de transition pour que le mouvement de Pacman soit fluide à l'écran (transition douce).
- Créé une fonction
deplacerPacman
qui dessine Pacman sur l'écran à la position spécifiée. - Importé
useState
pour mémoriser la position de Pacman. - Utilisé
useEffect
pour ajouter un écouteur d'événements qui écoute les appuis sur les touches directionnelles et appelledeplacerPacman
en conséquence.
Ce code permet ainsi à Pacman de se déplacer dans le labyrinthe en utilisant les touches fléchées du clavier, sans traverser les murs.
Une solution
Vous devez être connecté pour voir le contenu.