Je travaille sur un jeu de puzzle simple basé sur des blocs.
Le jeu consiste à déplacer des blocs dans la zone de jeu, c'est donc une simulation physique triviale. Mon implémentation, cependant, est à mon avis loin d'être idéale et je me demande si vous pouvez me donner des conseils sur la façon de mieux le faire.
J'ai divisé le code en deux domaines: la logique du jeu et l'interface utilisateur, comme je l'ai fait avec beaucoup de jeux de puzzle:
- La logique du jeu est responsable des règles générales du jeu (par exemple, le système de règles formel des échecs)
- L'interface utilisateur affiche la zone de jeu et les pièces (par exemple, échiquier et pièces) et est responsable des animations (par exemple, le mouvement animé des pièces d'échecs)
La logique de jeu représente l'état du jeu sous forme de grille logique, où chaque unité correspond à la largeur / hauteur d'une cellule sur la grille. Ainsi, pour une grille de largeur 6, vous pouvez déplacer un bloc de largeur 2 quatre fois jusqu'à ce qu'il entre en collision avec la frontière.
L'interface utilisateur prend cette grille et la dessine en convertissant les tailles logiques en tailles de pixels (c'est-à-dire en la multipliant par une constante). Cependant, comme le jeu n'a pratiquement aucune logique de jeu, ma couche de logique de jeu [1] n'a pas grand-chose à faire à part la détection de collision. Voici comment ça fonctionne:
- Le joueur commence à faire glisser un morceau
- L'interface utilisateur demande la logique du jeu pour la zone de mouvement légale de cette pièce et permet au joueur de la faire glisser dans cette zone
- Le joueur lâche un morceau
- L'interface utilisateur accroche la pièce à la grille (afin qu'elle soit à une position logique valide)
- L'interface utilisateur indique à la logique du jeu la nouvelle position logique (via des méthodes de mutation, que je préfère éviter)
Je ne suis pas très content de ça:
- J'écris des tests unitaires pour ma couche logique de jeu, mais pas l'interface utilisateur, et il s'est avéré que tout le code délicat se trouve dans l'interface utilisateur: empêcher la pièce d'entrer en collision avec les autres ou la frontière et l'enclencher sur la grille.
- Je n'aime pas le fait que l'interface utilisateur raconte la logique du jeu sur le nouvel état, je préfère qu'il appelle une
movePieceLeft()
méthode ou quelque chose comme ça, comme dans mes autres jeux, mais je ne suis pas allé loin avec cette approche, car la logique du jeu ne sait rien du glissement et de la capture qui sont possibles dans l'interface utilisateur.
Je pense que la meilleure chose à faire serait de se débarrasser de ma couche logique de jeu et de mettre en place une couche physique à la place. J'ai quelques questions à ce sujet:
- Une telle couche physique est-elle courante, ou est-il plus courant que la couche logique de jeu le fasse?
- Est-ce que l'accrochage à la grille et au code de déplacement de pièces appartiendrait à l'interface utilisateur ou à la couche physique?
- Une telle couche physique fonctionnerait-elle généralement avec des tailles de pixels ou avec une sorte d'unité logique, comme ma couche logique de jeu?
- J'ai vu une fois une détection de collision basée sur des événements dans la base de code d'un jeu, c'est-à-dire que le joueur faisait simplement glisser la pièce, l'interface utilisateur le rendait docilement et notifiait le système physique, et le système physique appelait une méthode onCollision () sur la pièce une fois qu'une collision est détectée. Quoi de plus commun? Cette approche ou demander d'abord la zone de mouvement légale?
[1] couche n'est probablement pas le bon mot pour ce que je veux dire, mais le sous-système semble exagéré et la classe est erronée, car chaque couche peut être composée de plusieurs classes.