Construire un jeu Caterpillar avec Cocos2D dernières étapes

Il s’agit du septième et dernier volet de notre série de didacticiels Cocos2D sur le clonage de Centipede pour iOS. Assurez-vous d'avoir complété les parties précédentes avant de commencer.

Dernière fois…

Dans le dernier tutoriel, nous avons expliqué comment effectuer une détection de collision simple entre tous les objets de notre jeu..

Dans le didacticiel d’aujourd’hui, nous allons clore le débat en discutant du score, des conditions de victoire, de l’audio et du jeu sur écran.


Étape 1: faire avancer le jeu

À l'heure actuelle, rien ne se passe lorsque vous détruisez la chenille. La manière d'avancer consiste à augmenter le niveau et à redémarrer avec de nouveaux germes et une nouvelle chenille. Ceci est facile à réaliser car nous avons construit le jeu pour le supporter depuis le début. Ouvrez GameLayer.m et ajoutez la méthode suivante:

 - (void) checkNextLevel if ([self.caterpillars count]] == 0) // 1 self.level ++; // 2 // 3 CGPoint startingPosition = ccp (kGameAreaStartX, kGameAreaHeight + kGameAreaStartY - kGridCellSize / 2); Caterpillar * caterpillar = [[[[Allocation Caterpillar]] initWithGameLayer: niveau automatique: niveau automatique. Position: débutPosition] autorelease]; [self.caterpillars addObject: caterpillar]; // 4 int minSproutCount = kStartingSproutsCount + self.level * 2; if ([self.sprouts count] < minSproutCount)  int numberOfSproutsToPlace = minSproutCount - [self.sprouts count]; for(int x = 0; x < numberOfSproutsToPlace; x++)  [self placeRandomSprout];    
  1. Vérifiez s'il reste des chenilles
  2. Incrémenter le niveau
  3. Créez une nouvelle chenille et ajoutez-la au jeu (en fonction du nouveau niveau)
  4. Ajouter des germes pour correspondre à minSproutCount

Maintenant que la méthode est implémentée, nous devons l'appeler chaque fois que la chenille est touchée. À l'intérieur de la splitCaterpillar: atSegment: méthode, ajoutez la ligne suivante avant l'instruction return à l'intérieur de la première instruction if:

 if ([caterpillar.segments count] == ​​1) //… // Ajoutez cette ligne [self checkNextLevel]; revenir; 

C'est la condition lorsque la chenille est juste un segment. En plus de l'ajouter ici, ajoutez-le également au bas de cette méthode. Cela devrait couvrir tous les cas.

Si vous lancez le jeu à ce stade, vous devriez pouvoir jouer à l'infini, la vitesse de la chenille augmentant à chaque niveau..


Étape 2: Notation

Dans le jeu, le joueur peut augmenter son score à plusieurs endroits. Elles sont:

  • Frapper une pousse
  • Frapper la chenille
  • Passer au niveau suivant

Nous allons sauter un peu pour ajouter des scores à chacune de ces actions, alors soyez nu avec moi.

Avant de commencer à mettre à jour le score, nous devons définir trois autres constantes qui constitueront les points de base du score. Ouvrez GameConfig.h et ajoutez les 3 lignes suivantes:

 #define kSproutHitPoints 25 #define kCaterpillarHitPoints 200 #define kNextLevelPoints 1000

Vous verrez comment ils sont utilisés à mesure que nous entrons un peu plus loin dans ce tutoriel..

Commençons par ajouter au score du joueur lorsqu'il frappe une pousse dans le jeu. Ouvrez Missile.m, importez Player.h et ajoutez le code suivant à l'intérieur de la boucle qui recherche une collision avec un chou:

 self.gameLayer.player.score + = kSproutHitPoints + (arc4random ()% self.gameLayer.level) * (arc4random ()% self.gameLayer.level); [[NSNotificationCenter defaultCenter] postNotificationName: kNotificationPlayerScore object: nil];

Cela incrémente le score du joueur en fonction des points de base et d'une certaine quantité de hasard en fonction du niveau actuel. De cette façon, au fur et à mesure que le joueur monte en niveau, il gagne plus de points en éliminant les germes..

Comme nous l'avions fait lorsque nous avons défini le score initial, nous devons poster une notification qui mettra à jour l'étiquette du score du joueur. Ceci est fait à chaque mise à jour du score. Si vous lancez le jeu à ce stade, vous devriez voir l’étiquette de score du joueur se mettre à jour chaque fois que vous frappez une pousse..

Le prochain endroit où nous allons ajouter le pointage est lorsque la chenille est touchée. Tout en bas de la mettre à jour: méthode dans Missile.m, ajoutez le code suivant avant de scinder la chenille:

 if (hitCaterpillar && hitSegment) // Ajoutez ces lignes self.gameLayer.player.score + = kCaterpillarHitPoints + (arc4random ()% self.gameLayer.level) * (arc4random ()% self.gameLayer.level); [[NSNotificationCenter defaultCenter] postNotificationName: kNotificationPlayerScore object: nil]; //… code pour scinder la chenille…

Ce code n'est pas très différent de ce que vous avez vu ci-dessus. Le dernier endroit pour ajouter un score est lorsque le joueur avance en niveau. Ce code sera placé à l'intérieur du checkNextLevel méthode que vous avez écrit ci-dessus. Ouvrez GameLayer.m, accédez au checkNextLevel méthode et ajoutez le code suivant juste après l'instruction if:

 self.player.score + = kNextLevelPoints * self.level; [[NSNotificationCenter defaultCenter] postNotificationName: kNotificationPlayerScore object: nil];

Pas de surprises ici. Si vous souhaitez ajouter une variation à la notation dans votre propre jeu, n'hésitez pas à modifier les valeurs de la partition..


Étape 3: Fin du jeu

Pour le moment, votre joueur a le génie du jeu et une vie infinie. Nous avons besoin de changer ça. Tout d’abord, créez un nouveau fichier appelé GameOverLayer.m qui étend CCLayer..

Ajoutez le code suivant à GameOverLayer.h:

 #import "cocos2d.h" #import "GameConfig.h" @interface GameOverLayer: CCLayer @property (nonatomic, assign) NSInteger score; @property (nonatomic, keep) CCLabelTTF * scoreLabel; @property (nonatomic, keep) CCLabelTTF * highScoreLabel; + (CCScene *) sceneWithScore: (NSInteger) score; @fin

Je vais expliquer ce que chacune de ces propriétés et méthodes font pendant la mise en œuvre. Maintenant, ajoutez le code suivant à GameOverLayer.m

 #import "GameOverLayer.h" #import "GameLayer.h" #import "SimpleAudioEngine.h" @implementation GameOverLayer @synthesize score = _score; @synthesize scoreLabel = _scoreLabel; @synthesize highScoreLabel = _highScoreLabel; // 1 + (CCScene *) sceneWithScore: (NSInteger) score // 'scene' est un objet autorelease. CCScene * scene = [nœud CCScene]; // 'layer' est un objet autorelease. GameOverLayer * layer = [nœud GameOverLayer]; layer.score = score; // ajoute un calque en tant qu'enfant dans la scène [scene addChild: layer]; // retourne la scène retour scène;  // 2 - (void) dealloc [version de _scoreLabel]; [_highScoreLabel release]; [super dealloc];  - (id) init if ((self = [super init])) // 3 [CCTexture2D setDefaultAlphaPixelFormat: kCCTexture2DPixelFormat_RGB565]; CCSprite * background = [CCSprite spriteWithFile: @ "game-over.png"]; background.anchorPoint = ccp (0,0); [auto addChild: background]; // 4 _scoreLabel = [[CCLabelTTF labelWithString: @ "0" dimensions: CGSizeMake (320, 30) alignement: UITextAlignmentCenter fontName: @ "Helvetica" fontSize: 30 keep]; _scoreLabel.anchorPoint = ccp (0,0); _scoreLabel.position = ccp (0,155); [auto addChild: _scoreLabel]; _highScoreLabel = [[CCLabelTTF labelWithString: [NSString stringWithFormat: @ "Élevé:% d", 0] dimensions: CGSizeMake (320, 35) Alignement: UITextAlignmentCenter fontName: @ "Helvetica" fontSize: 30] retenue]; _highScoreLabel.anchorPoint = ccp (0,0); _highScoreLabel.color = (ccColor3B) 255,0,0; _highScoreLabel.position = ccp (0,195); [auto addChild: _highScoreLabel]; // 5 [[CCTouchDispatcher sharedDispatcher] addTargetedDelegate: priorité propre: 0 swallowsTouches: YES]; [[SimpleAudioEngine sharedEngine] playEffect: @ "game-over.caf"];  retourner soi-même;  - (void) setScore: (NSInteger) score _score = score; self.scoreLabel.string = [NSString stringWithFormat: @ "Score:% d", _ score]; // 6 NSUserDefaults * defaults = [NSUserDefaults standardUserDefaults]; NSInteger highScore = [defaults integerForKey: @ "CentipedeHighScore"]; // 7 if (score> highScore) highScore = score; [defaults setInteger: score forKey: @ "CentipedeHighScore"]; [synchroniser par défaut];  self.highScoreLabel.string = [NSString stringWithFormat: @ "High:% d", highScore];  // 8 - (BOOL) ccTouchBegan: (UITouch *) toucher avecEvent: (UIEvent *) événement [[[CCDirector directeur partagé]] replaceScene: [CCTransitionFade transitionWithDuration: .5 scène: [Scène GameLayer]] avecCouleur: ccWHITE]]; retourner OUI;  @fin
  1. Ceci est notre méthode standard pour créer une nouvelle scène. La seule différence est qu'il faut un NSInteger et le définit sur le score actuel.
  2. Nettoyer
  3. Rendre le fond
  4. Configurez les étiquettes pour afficher le score et le meilleur score
  5. Activer les touches
  6. Cherchez le meilleur score
  7. Comparez le nouveau score au score le plus élevé, sauvegardez le nouveau s'il est plus élevé.
  8. Commencer une nouvelle partie si le joueur touche l'écran

Voici une capture d'écran de ce que cet écran devrait ressembler:

La dernière étape consiste à ouvrir GameLayer.m et à ajouter les lignes suivantes à la fin du updateLives méthode:

 if (lifeCount == 0) [[[CCDirector sharedDirector]] replaceScene: [CCTransitionFade transitionWithDuration: .5 scène: [GameOverLayer sceneWithScore: self.player.score] avecColor: ccWHITE]]; 

Ceci vérifie si les vies sont définies à 0. Si c'est le cas, nous remplaçons la scène actuelle par la scène Game Over.


Étape 4: Audio du jeu

La dernière étape de notre jeu consiste à ajouter du son. Tout d’abord, téléchargez les sons ci-dessous et ajoutez-les à votre projet:

GameSounds.zip

Traditionnellement, la manipulation du son a été assez pénible dans un jeu OpenGL. Vous devrez utiliser quelque chose comme OpenAL ou une autre bibliothèque C ++ compliquée. Cocos2D a grandement simplifié les choses avec leur SimpleAudioEngine bibliothèque. Il vous donne la possibilité de jouer facilement de la musique de fond en boucle ainsi que des sons rapides..

Encore une fois, nous allons beaucoup sauter. Donc, si le placement de code n'est pas clair pour vous, merci de me demander dans les commentaires ou de vous reporter au code source de ce tutoriel.

Ouvrez AppDelegate.m, importez SimpleAudioEngine.h et ajoutez la ligne suivante au bas de la applicationDidFinishLancement méthode.

 [[SimpleAudioEngine sharedEngine] playBackgroundMusic: @ "background.caf"]; i

C'est tout! Une seule ligne suffit pour jouer notre musique de fond pendant toute la durée de la lecture. Il ne reste plus qu'à jouer des effets sonores en réponse à diverses actions.

Dans Caterpillar.m, lorsque la chenille entre en collision avec le joueur (vers la fin de la mettre à jour: méthode):

 [[SimpleAudioEngine sharedEngine] playEffect: @ "player-hit.caf"];

Dans Missile.m, quand le missile frappe la pousse:

 [[SimpleAudioEngine sharedEngine] playEffect: @ "sprout-hit.caf"];

Également dans Missile.m, lorsque le missile frappe la chenille:

 [[SimpleAudioEngine sharedEngine] playEffect: @ "caterpillar-hit.caf"];

Dans la méthode init dans GameOverLayer.m:

 [[SimpleAudioEngine sharedEngine] playEffect: @ "game-over.caf"];

Cela devrait couvrir tous les sons que j'ai utilisés dans le jeu. Assurez-vous également d’importer SimpleAudioEngine.h dans chacune des classes ci-dessus..


Conclusion

Ceci conclut la série de tutoriels en 7 parties sur la création d’un jeu Caterpillar avec Cocos2D pour iPhone. A présent, vous devriez avoir une solide connaissance de la conception et de la construction d'un jeu simple à l'aide du moteur de jeu Cocos2D. Si vous avez des questions ou des commentaires, n'hésitez pas à les laisser ici ou à me les écrire sur Twitter..

Bonne codage!