Programmera spel i C++ för nybörjare/Sprites och spelpjäser 2

Från Wikibooks


Sprites och spelpjäser 2[redigera]

Enkel AI[redigera]

Baserat på VC++ 2010 express, Win 7 och SFML 1.6, du bör ha gjort installationerna för ett fungerande SFML-fönster i ditt projekt innan du börjar.

Om du såg i del 1 hur man gör för att få in en spelare i spelet, är det inte svårt att få in ännu en spelare. Försök att hitta en bild på en pojke och en bild på en ko/tjur, båda 32x32 pixels.

Använd funktionerna för att läsa in grafik från föregående del. När du startar programmet bör du få upp samma vy som förut, men med en person som du kan gå med när du trycker ner tangenterna och en ko som står alldeles stilla. Anta att vi vill kunna ta oss med pojken över spelplanen utan att kon/tjuren kommer ikapp? Då måste vi skapa en enkel AI (artificiell intelligens) så att kon förstår att den skall jaga pojken.

Spelarnas X och Y koordinater[redigera]

För att veta vart kon skall gå måste vi jämföra kons position med personens position. Det finns två funktioner för det. Sprite.GetPosition().x; och Sprite.GetPosition().y; Sprite är namnet på spelpjäsen och den koordinat man får passar in på punkten för det övre vänstra hörnet. Så, om vi kallar personen för Sprite och kofiguren för ko1 kan vi ange variablerna:

float  SpriteX=0.0, ko1X = 0.0; //X positioner för pojke och ko
float  SpriteY=0.0, ko1Y = 0.0; //Y positioner för pojke och ko

Och sedan, i själva spel loopen fyller vi i koden:

SpriteX= Sprite.GetPosition().x; // Pojkens xposition, kan användas som AI
ko1X= ko1.GetPosition().x; // kons xposition, kan användas som AI
SpriteY= Sprite.GetPosition().y; // Pojkens yposition, kan användas som AI
ko1Y= ko1.GetPosition().y; // kons yposition, kan användas som AI

   if (ko1X <= SpriteX) //pojken har sprungit förbi kon
  ko1.Move( 50 * ElapsedTime, 0); 

  if (ko1X > SpriteX) //pojken har inte sprungit förbi kon
  ko1.Move( -50 * ElapsedTime, 0); 

  if (ko1Y > SpriteY ) //kon är nedanför pojken
  ko1.Move(0, -50 * ElapsedTime);

  if (ko1Y <= SpriteY ) //kon är ovanför pojken
  ko1.Move(0, 50 * ElapsedTime); 

När personen rör sig över spelplanen följer kon efter i motsatt riktning men med halva hastigheten (den går att ställa in). Om du stannar med personen, kommer kon att hinna ikapp. Vad händer då?

Här är hela den omarbetade koden från moment 1.

#include <iostream>
#include <SFML\System.hpp>
#include <SFML\Graphics.hpp>
#include <SFML\Window.hpp>


 int main() 
{  //Början av programkörningen

float  SpriteX=0.0, ko1X = 0.0; //X positioner för pojke och ko
float  SpriteY=0.0, ko1Y = 0.0; //Y positioner för pojke och ko

sf::RenderWindow App(sf::VideoMode(800, 600, 32), "SFML grafiktest"); 
// Skapa fönstret vi skall visa färgerna i
  
float ElapsedTime = App.GetFrameTime(); 
//Skapar en konstant för att hålla hastigheten likvärdig på olika datorer

sf::Image Image; //skapa en tom bildhållare som heter Image
if (!Image.LoadFromFile("boy.png")) return EXIT_FAILURE; 
//fyll den tomma bildhållaren med bilden boy.png
//bilden är  en 32x32 .png jag hittade ute på Internet med en googlesökning
sf::Sprite Sprite(Image); //Skapar den grafiska spelpjäsen Sprite med grafiken från Image
Sprite.SetPosition(200.f, 100.f); //Placera ut bilden

	   
/*Skapa en ko-----------------------------------------------------------------*/ 
sf::Image kobild; //skapa en tom bildhållare som heter Image
if (!kobild.LoadFromFile("cow.png")) return EXIT_FAILURE; 
//fyll den tomma bildhållaren med bilden boy.png
sf::Sprite ko1(kobild); 
//Skapar den grafiska spelpjäsen Sprite med grafiken från Image
ko1.SetPosition(400.f, 100.f); //Placera ut bilden på kon 
//bilden är  en 32x32 .png jag hittade ute på   
//  Internet med en googlesökning
kobild.CreateMaskFromColor(sf::Color(192,248,0)); 
//Min kobild hade en färgruta av den här färgen som jag gör transperent här
	 
/* slut på skapa ko */

while (App.IsOpened())  // Start spel-loopen
{  //while 1
  sf::Event Event; 

  while (App.GetEvent(Event)) // Ta hand om händelser 
      { //while 2
        if (Event.Type == sf::Event::Closed) //kryssat på [x] symbolen? stäng programmet
        App.Close(); 

        if (Event.Type == sf::Event::KeyPressed) // En tangent har tryckts ner
            { //if 1
             if (Event.Key.Code == sf::Key::Escape) // ESC tangenten = stäng programmet
             App.Close(); 
             } //slut if 1
        } //slut, while 2

  ElapsedTime = App.GetFrameTime(); //för att få en konstant hastighet på olika datorer

  if (App.GetInput().IsKeyDown(sf::Key::Left)) 
  Sprite.Move(-100 * ElapsedTime, 0); //pojke 
  //Om man trycker ner vänster piltangent går figuren 100 "steg" 
  // längre åt vänster än vad den var tidigare.
                
  if (App.GetInput().IsKeyDown(sf::Key::Right)) 
  Sprite.Move( 100 * ElapsedTime, 0); 
					   
  if (App.GetInput().IsKeyDown(sf::Key::Up)) 
  Sprite.Move(0, -100 * ElapsedTime); 
					  
  if (App.GetInput().IsKeyDown(sf::Key::Down)) 
  Sprite.Move(0, 100 * ElapsedTime); 
					    

  SpriteX= Sprite.GetPosition().x; // Pojkens xposition, kan användas som AI
  ko1X= ko1.GetPosition().x; // kons xposition, kan användas som AI 

  SpriteY= Sprite.GetPosition().y; // Pojkens yposition, kan användas som AI
  ko1Y= ko1.GetPosition().y; // kons yposition, kan användas som AI

  if (ko1X <= SpriteX) //pojken har sprungit förbi kon
  ko1.Move( 50 * ElapsedTime, 0); 

  if (ko1X > SpriteX) //pojken har inte sprungit förbi kon
  ko1.Move( -50 * ElapsedTime, 0); 

  if (ko1Y > SpriteY ) //kon är nedanför pojken
  ko1.Move(0, -50 * ElapsedTime);

  if (ko1Y <= SpriteY ) //kon är ovanför pojken
  ko1.Move(0, 50 * ElapsedTime); 

  App.Clear(sf::Color(0, 255, 0)); //rensa allt i fönstret och ersätt med grönfärg
  App.Draw(Sprite); //Rita upp figuren på den yta spelaren ser
  App.Draw(ko1); //Rita upp kon på den yta spelaren ser
  App.Display(); //visa upp ändringarna för användaren

 } //slut, while 1

return 0;
} //slut på programkörningen