Jusqu'à présent, cette série a couvert les bases de la mise en place d'un jeu de Match 3 et de la mise en œuvre des éléments de jeu initiaux tels que l'échange de blocs. Dans ce tutoriel, nous allons construire sur tout cela, et commencer à détecter quand le joueur a fait une correspondance.
Voici une démonstration du jeu sur lequel nous travaillons tout au long de cette série:
Pour le moment, nous n'allons mettre en œuvre qu'une version de base du système de correspondance, en nous concentrant sur la recherche des correspondances existantes et sur la destruction des blocs correspondants. Dans les articles suivants, nous continuerons à développer et à faire avancer le système.
Pointe: Vous devriez lire comment une fonction récursive fonctionne, si vous ne le savez pas déjà. essentiellement, c'est une fonction qui s'appelle elle-même. Les fonctions récursives peuvent fonctionner de la même manière que les boucles, mais comme elles peuvent aussi prendre et renvoyer des variables, elles ont beaucoup plus d'utilisations que les boucles..
Comme avec le tutoriel précédent, je veux d’abord discuter du fonctionnement du système, puis tenter de le construire..
Bloc
objet. Bloc
, il transmettra la couleur et la position du bloc examiné à une fonction récursive, qui examinera le voisin horizontal ou vertical et déterminera si elles ont la même couleur. Appariés
avec le IsMatched
variable d'instance que nous avons faite dans l'un des tutoriels précédents; sinon, ça ne fait rien. Tout d’abord, nous avons besoin d’un événement pouvant parcourir chaque événement. Bloc
. La façon dont j'ai construit le système, il itère en fait à travers les blocs deux fois: une fois pour vérifier les correspondances verticales et une fois pour vérifier les correspondances horizontales. En fonction de la vérification effectuée, il utilisera une fonction différente pour rechercher le match..
La toute première chose à faire est de faire un Variable globale pour garder une trace du nombre de blocs correspondants trouvés dans une itération donnée:
Nom de la variable globale: "NumMatchesFound" Type = Valeur numérique = 0
Maintenant, faisons la un événement cela va parcourir les blocs:
Evénement: Fonction> Nom de la fonction: "FindMatches" Sous-événement: Système> Pour chaque objet: Action du bloc: Système> Valeur définie NumMatchesFound = 1 Action: Fonction> Nom de la fonction d'appel: "CheckMatchesX" Paramètre 0: Block.X Paramètre 1 : Block.Y Paramètre 2: Sous-événement Block.Color: Système> Comparaison de variable NumMatchesFound> = 3 Action: Bloc> Définir une valeur booléenne IsMatched = True Sous-événement: Système> Pour chaque objet: Action de bloc: Système> Définir une valeur NumMatchesFound = 1 Action: Fonction> Fonction d'appel Nom: "CheckMatchesY" Paramètre 0: Block.X Paramètre 1: Block.Y Paramètre 2: Block.Color Sous-événement: Système> Comparer la variable NumMatchesFound> = 3 Action: Bloquer> Définir Booléen IsMatched =. Vrai sous-événement: Block> Est-ce que la variable d'instance booléenne est définie sur System> Wait Second = 0.1 Block> Destroy
Votre code devrait ressembler à ceci:
Dans ce cas, nous parcourons chaque bloc et les envoyons dans CheckMatchesX
ou CheckMatchesY
, les fonctions qui vérifieront si le bloc voisin est un match.
Pour envoyer le bloc dans la fonction, nous transmettons à la fonction trois paramètres différents:
Une fois que chaque bloc est envoyé dans l’une des fonctions et que la fonction se termine, elle vérifie NumMatchesFound
pour voir si elle a trouvé trois blocs correspondants ou plus, puis les étiquettes comme suit: Appariés
si c'était le cas.
Enfin, chaque bloc marqué comme étant Appariés
est détruit après 0,1 seconde. Ce attendre
déclaration est là pour permettre au jeu de changer les images des Blocs pour l’image qui indique qu’elles sont appariées, et pour donner au joueur un moment pour remarquer ce changement.
(Bien que vous puissiez retirer le attendre
déclaration sans impacter négativement le gameplay, elle facilite la compréhension de la correspondance par le joueur et ralentit le jeu assez pour que le joueur puisse facilement suivre ce qui se passe.)
Ensuite, nous devons faire la CheckMatchesX
et CheckMatchesY
les fonctions. Ces fonctions fonctionneront de la même manière que les itérateurs ci-dessus, en ce qu’il y aura une version pour vérifier les correspondances horizontales., CheckMatchesX
, et un pour les matches verticaux, CheckMatchesY
.
Tout d'abord, construisons la fonction de vérification horizontale:
Evénement: Fonction> Fonction activée Nom: "CheckMatchesX" Sous-événement: Condition: Bloc> Comparer XX = Function.Param (0) + (Block.Width + 2) Condition: Bloc> Comparer YY = Function.Param (1) Condition : Bloc> Variable d 'instance de comparaison Couleur = Function.Param (2) Action: Système> Ajouter à la variable = NumBlocks Valeur = 1 Action: Fonction> Nom de la fonction d' appel: "CheckMatchesX" Paramètre 0: Function.Param (0) + (Block. Largeur + 2) Paramètre 1: Function.Param (1) Paramètre 2: Function.Param (2) Sous-événement: Système> Comparer la variable NumMatchesFound> = 3 Action: Bloc> Définir la valeur booléenne IsMatched = True.
Votre code devrait ressembler à ceci:
Alors, quelle est cette fonction fait?
NumMatchesFound
par un, et passe le bloc nouvellement trouvé dans la fonction comme il le faisait pour l'original.Maintenant, créons une autre version de cette fonction qui fera la même chose pour les correspondances verticales. Cela va être notre CheckMatchesY
une fonction. Vous pouvez soit copier la fonction d'origine et apporter toutes les modifications appropriées, ou simplement la recréer à partir de zéro; dans les deux cas, voici à quoi devrait ressembler votre fonction une fois celle-ci terminée:
Evénement: Fonction> Fonction activée Nom: "CheckMatchesY" Sous-événement: Condition: Bloc> Comparer XX = Fonction.Param (0) Condition: Bloc> Comparer YY = Fonction.Param (1) + (Block.Width + 2) Condition : Bloc> Variable d'instance de comparaison Couleur = Function.Param (2) Action: Système> Ajouter à la variable = NumBlocks Valeur = 1 Action: Fonction> Nom de la fonction d'appel: "CheckMatchesY" Paramètre 0: Fonction.Param (0) Paramètre 1: Fonction .Param (1) + (Block.Width + 2) Paramètre 2: Function.Param (2) Sous-événement: Système> Comparer la variable NumMatchesFound> = 3 Action: Bloc> Définir la valeur booléenne IsMatched = True
Votre code devrait ressembler à ceci:
Enfin, nous devons appeler le FindMatches
une fonction. Aller au SwapBlocks
fonction et ajoutez un nouveau sous-événement à la fin de la fonction:
Evénement: Fonction> Sous-événement: Action: Fonction> Fonction d'appel Nom: "FindMatches"
Vous remarquerez que ce sous-événement ne comporte aucune condition. Si vous n'avez jamais créé un sous-événement comme celui-ci auparavant, créez simplement un sous-événement avec n'importe quelle condition, puisqu'il vous oblige à donner une condition lors de la création d'un sous-événement, puis supprimez la condition, mais laissez la sous-événement. De cette façon, vous vous assurez que le sous-événement est toujours exécuté.
Votre SwapBlocks
L'événement devrait maintenant ressembler à ceci:
Si vous lancez le jeu à ce stade, vous verrez que les blocs sont détruits lors des matchs. Vous remarquerez également que toutes les correspondances présentes au début du jeu ne disparaissent pas tant que vous n'avez pas effectué d'échange. C’est parce que nous n’appelons jamais le FindMatches
fonction après la création de la grille de blocs.
La raison pour laquelle nous n'avons pas ajouté ce code est parce que dans la version finale, il y aura une autre fonction qui empêche les allumettes d'être générées automatiquement, il n'y a donc aucune raison de s'inquiéter de ce problème. (Mais n'hésitez pas à appeler le FindMatches
fonctionner plus tôt, si vous aimez.)
À ce stade, nous avons un système de correspondance assez puissant, mais le problème est que notre code est redondant. Actuellement, nous avons deux fonctions différentes qui vérifient si un voisin correspond, et la seule différence entre elles est que l'une vérifie verticalement et l'autre horizontalement..
Puisque la version gratuite de Construct 2 limite le nombre d’événements que nous pouvons avoir, c’est définitivement un gaspillage. Pour résoudre ce problème, nous allons créer une nouvelle version de la fonction pouvant effectuer les deux vérifications..
Si vous regardez la fonction, vous verrez que la seule différence entre les deux versions est que l’on ajoute Block.Width + 2
à la position x du bloc, et l'autre l'ajoute à la position y du bock. Donc, l’obstacle que nous devons surmonter pour en faire une fonction unique, est de lui donner un moyen d’ajouter Block.Width + 2
seulement X
, ou seulement Y
, sans pour autant en utilisant un Si
instruction ou plusieurs fonctions, car celles-ci nécessitent plus d'événements à exécuter.
Ma solution à ce problème n’est pas très complexe, mais elle sera plus facile à comprendre si nous pouvons la voir se concrétiser. Nous la mettrons en œuvre, et j’expliquerai comment cela fonctionne une fois que nous pouvons tout voir en action..
CheckMatchesY
un événement.CheckMatchesX
événement à, tout simplement, CheckMatches
.CheckMatchesX
sous le FindMatches
un événement: CheckMatches
au lieu de CheckMatchesX
.Paramètre 3
. 1
.Paramètre 4.
0
.CheckMatchesY
sous le FindMatches
un événement: CheckMatches
au lieu de CheckMatchesY
.Paramètre 3
. 0
.Paramètre 4
. 1
.Comme je l'expliquerai bientôt, ces paramètres ajoutés indiqueront CheckMatches
si elle fait une vérification horizontale ou une vérification verticale. Quand on envoie 1
pour Paramètre 3
, et 0
pour Paramètre 4
, c'est une vérification horizontale, et quand nous envoyons 0
pour Paramètre 3
, et 1
pour Paramètre 4
, c'est une vérification verticale.
Maintenant, retournez à la CheckMatches
fonction, et modifiez les conditions et les actions pour qu'elles ressemblent à ceci:
Evénement: Fonction> Fonction activée Nom: "CheckMatches" Sous-événement: Condition: Bloquer> Comparer XX = Function.Param (0) + ((Block.Width + 2) * Function.Param (3)) Condition: Bloquer> Comparer YY = Function.Param (1) + ((Block.Width + 2) * Function.Param (4)) Condition: Block> Comparaison de la variable d'instance Color = Function.Param (2) Action: Block> Set Boolean IsMatched = True Action : Fonction> Appeler la fonction Nom: "CheckMatches" Paramètre 0: Function.Param (0) + ((Block.Width + 2) * Function.Param (3)) Paramètre 1: Function.Param (1) + ((Block. Largeur + 2) * Function.Param (4)) Paramètre 2: Function.Param (2) Paramètre 3: Function.Param (3) Paramètre 4: Function.Param (4) Sous-événement: Système> Comparer la variable NumMatchesFound> = 3 Action: Bloquer> Définir la valeur booléenne IsMatched = True
C'est ce que votre FindMatches
et CheckMatches
Le code devrait maintenant ressembler à ceci:
Alors, quelle est cette nouvelle version de la fonction en train de faire?
Eh bien, chaque fois que vous appelez CheckMatches
vous envoyez maintenant deux autres paramètres, et plutôt que d'ajouter Block.Width + 2
soit à la position x ou à la position y, il ajoute (Block.Width + 2) * Function.Param (3)
à la position x, et (Block.Width + 2) * Function.Param (4)
à la position y.
Étant donné que l'un de ces deux paramètres sera toujours 1
, et l'autre sera toujours 0
, cela signifie que la position x ou la position y sera modifiée - jamais les deux!
Par exemple, si on passe à 1
pour Paramètre 3
, et 0
pour Paramètre 4
, alors il ajoute (Block.Width + 2) * 1
, qui est simplement Block.Width + 2
, à la position x, et (Block.Width + 2) * 0
, lequel est 0
, à la position y.
Voici un exemple rapide pour montrer ce que je veux dire et comment il calcule la position du bloc où il recherchera la correspondance. Disons que dans cet exemple, le bloc d'origine est à (200, 200)
, et les blocs ont une largeur de 40
. Donc, si nous voulons obtenir la position du bloc vertical voisin, les formules fonctionneraient comme suit:
X = 200 + ((Block.Width + 2) * 0) = 200 + (40 + 2) * 0 = 200 + 0 = 200
Y = 200 + ((Block.Width + 2) * 1) = 200 + (40 + 2) * 1 = 200 + 42 = 242
Si nous voulions connaître la position du bloc horizontal voisin, les formules fonctionneraient comme suit:
X = 200 + ((Block.Width + 2) * 1) = 200 + (40 + 2) * 1 = 200 + 42 = 242
Y = 200 + ((Block.Width + 2) * 0) = 200 + (40 + 2) * 0 = 200 + 0 = 200
Si vous lancez le jeu maintenant, vous devriez voir que le système de match fonctionne toujours comme auparavant, mais de notre point de vue, c'est en fait un meilleur système..
À ce stade, notre fonction de détection des correspondances est encore incomplète, mais nous avons déjà beaucoup travaillé dans ce tutoriel et je pense qu'il est important de laisser tout cela entrer avant d'ajouter quoi que ce soit. Dans cet esprit, je vais terminer cet article ici. Découvrez la démo dans sa forme actuelle.
Dans le prochain article, nous ajouterons un système de points, nous améliorerons le système de correspondance et nous ajouterons "la gravité" afin que les blocs tombent lorsque les blocs situés en dessous d'eux seront éliminés..
Si vous souhaitez avoir une longueur d'avance sur le prochain article, prenez le temps de réfléchir à la manière dont vous le détecteriez lorsqu'il y a un espace vide sous un bloc. Essayez de regarder le Bloquer> se chevauche au décalage
fonction d'inspiration!