C++ Game Programming
Basic C++ Lessons
This set of lessons will give you a simple introduction to programming in the C++ language.
Allegro Lessons
This set of lessons will demonstrate how to use the Allegro graphics library to create video games.
Game Source Code
Here you will find source code to several games so that you can see the code in action.
Recommended Books
Here is a list of books which should help you with C++

Allegro Animation II
Ok lets look into how to make a character move across the screen while swaying his arms and moving his legs. First you'll need to download the images for this tutorial located here. As always the images are not of the highest quality, but they serve their purpose :). Now on to the example code. The program is divided into 3 files, main.cpp, character.h, and character.cpp:

//main.cpp

#include <allegro.h>
#include "Character.h"

using namespace std;

BITMAP* buffer;
Character myChar;

void Setup(){

     buffer= create_bitmap(640, 480);
     myChar.SetImagesLeft( "left1.bmp", "left2.bmp", "left3.bmp");
     myChar.SetImagesRight( "right1.bmp", "right2.bmp", "right3.bmp");
     myChar.SetImagesUp( "up1.bmp", "up2.bmp", "up3.bmp");
     myChar.SetImagesDown( "down1.bmp", "down2.bmp", "down3.bmp");
     
     myChar.Show( screen);

}

void movePlayer(){

    if( key[KEY_LEFT]){
        myChar.MoveOnX( LEFT, buffer, screen);
    } else if( key[KEY_RIGHT]){
        myChar.MoveOnX( RIGHT, buffer, screen);
    } else if( key[KEY_UP]){
        myChar.MoveOnY( UP, buffer, screen);
    } else if( key[KEY_DOWN]){
        myChar.MoveOnY( DOWN, buffer, screen);
    }

}

int main(int argc, char *argv[])
{
    allegro_init(); 
    install_mouse(); 
    install_keyboard(); 
    set_color_depth(16); 
    
    set_gfx_mode( GFX_AUTODETECT, 640, 480, 0, 0); 
    
    Setup();
    
    while( !key[KEY_ESC]){
        movePlayer();
    }
    
    return 0;
}
END_OF_MAIN();


//Character.h

#ifndef CHARACTER_H
#define CHARACTER_H

#define LEFT 1
#define RIGHT 2
#define UP 3
#define DOWN 4

#include <allegro.h>

class Character{

public:
       Character();
       ~Character();
       
       // The following 4 methods will be used to set the images for the different
       //stages of movement
       void SetImagesLeft( char image1[], char image2[], char image3[]);
       void SetImagesRight( char image1[], char image2[], char image3[]);
       void SetImagesUp( char image1[], char image2[], char image3[]);
       void SetImagesDown( char image1[], char image2[], char image3[]);
       
       //To keep the program from crashing, this function will be used before 
       //calling any movement methods
       bool CheckImages();
       
       int GetX();
       void SetX( int newValue);
       void MoveOnX( int newValue, BITMAP* tempBitmap, BITMAP* mainBitmap);
       
       int GetY();
       void SetY( int newValue);
       void MoveOnY( int newValue, BITMAP* tempBitmap, BITMAP* mainBitmap);
       
       void EraseOldSprite( BITMAP* tempBitmap);
       void DrawNewSprite( BITMAP* tempBitmap, BITMAP* spriteToDraw);  
       
       void Show(BITMAP* mainBitmap);     
       
private:
        bool leftDone;
        bool rightDone;
        bool upDone;
        bool downDone;
        
        int direction;
        
        
        
        int x;
        int y;
        
        //This will contain all the images, [0][0-2] will be left movements, [1][0-2] right
        //[2][0-2] upwards, and [3][0-2] downwards
        BITMAP *images[4][3]; 


};

#endif

//Character.cpp
#include "Character.h"

Character::Character(){

        leftDone= false;
        rightDone= false;
        upDone= false;
        downDone= false;
        
        direction = DOWN;
        
        int x= 0;
        int y= 0;

}

Character::~Character(){

    delete [] images;

}

void Character::SetImagesLeft( char image1[], char image2[], char image3[]){
       
   images[0][0]= load_bitmap(image1, NULL);
   images[0][1]= load_bitmap(image2, NULL);
   images[0][2]= load_bitmap(image3, NULL);
   
   leftDone= true;
       
}

void Character::SetImagesRight(char image1[], char image2[], char image3[]){

   images[1][0]= load_bitmap(image1, NULL);
   images[1][1]= load_bitmap(image2, NULL);
   images[1][2]= load_bitmap(image3, NULL);
   
   rightDone= true;

}

void Character::SetImagesUp(char image1[], char image2[], char image3[]){

   images[2][0]= load_bitmap(image1, NULL);
   images[2][1]= load_bitmap(image2, NULL);
   images[2][2]= load_bitmap(image3, NULL);
   
   upDone= true;

}
       
void Character::SetImagesDown(char image1[], char image2[], char image3[]){

   images[3][0]= load_bitmap(image1, NULL);
   images[3][1]= load_bitmap(image2, NULL);
   images[3][2]= load_bitmap(image3, NULL);
   
   downDone= true;

}

bool Character::CheckImages(){

   if( rightDone && leftDone && upDone && downDone)
       return true;
       
   return false;         
                        
}
       
int Character::GetX(){

    return x;

}
       
int Character::GetY(){

    return y;

}

void Character::SetX( int newValue){
    x = newValue;
}

void Character::SetY( int newValue){
    y = newValue;
}

void Character::MoveOnX( int newDirection, BITMAP* tempBitmap, BITMAP* mainBitmap){

   direction = newDirection;

    if( CheckImages()){
        if( direction == LEFT){
            
            for( int i=0; i<=3; i++){
                EraseOldSprite( tempBitmap);
                x -= 5;
                
                if (i == 1 || i == 3)
                    DrawNewSprite( tempBitmap, images[0][0]);
                    
                if (i == 0)
                    DrawNewSprite( tempBitmap, images[0][1]);
    
                if (i == 2)
                    DrawNewSprite( tempBitmap, images[0][2]);
                
                
                draw_sprite( mainBitmap, tempBitmap, 0, 0);
                
                rest(50);
    
            }
        } else {
        
            for( int i=0; i<=3; i++){
                EraseOldSprite( tempBitmap);
                x += 5;
                
                if (i == 1 || i == 3)
                    DrawNewSprite( tempBitmap, images[1][0]);
                    
                if (i == 0)
                    DrawNewSprite( tempBitmap, images[1][1]);
    
                if (i == 2)
                    DrawNewSprite( tempBitmap, images[1][2]);
                
                draw_sprite( mainBitmap, tempBitmap, 0, 0);
                
                rest(50);
    
            }
               
        }
        
    }

}

void Character::MoveOnY( int newDirection, BITMAP* tempBitmap, BITMAP* mainBitmap){

   direction = newDirection;

    if( CheckImages()){
    
        if( direction == UP){
            
            for( int i=0; i<=3; i++){
                EraseOldSprite( tempBitmap);
                y -= 5;
                
                if (i == 1 || i == 3)
                    DrawNewSprite( tempBitmap, images[2][0]);
                    
                if (i == 0)
                    DrawNewSprite( tempBitmap, images[2][1]);
    
                if (i == 2)
                    DrawNewSprite( tempBitmap, images[2][2]);
                
                draw_sprite( mainBitmap, tempBitmap, 0, 0);
                
                rest(50);
    
            }
        } else {
        
            for( int i=0; i<=3; i++){
                EraseOldSprite( tempBitmap);
                y += 5;
                
                if (i == 1 || i == 3)
                    DrawNewSprite( tempBitmap, images[3][0]);
                    
                if (i == 0)
                    DrawNewSprite( tempBitmap, images[3][1]);
    
                if (i == 2)
                    DrawNewSprite( tempBitmap, images[3][2]);
                
                draw_sprite( mainBitmap, tempBitmap, 0, 0);
                
                rest(50);
    
            }
               
        }
    }
}


void Character::EraseOldSprite( BITMAP* tempBitmap){

    rectfill( tempBitmap, GetX(), GetY(), GetX() + 20, GetY() + 20, makecol ( 0, 0, 0));

}

void Character::DrawNewSprite( BITMAP* tempBitmap, BITMAP* spriteToDraw){

    draw_sprite( tempBitmap, spriteToDraw, GetX(), GetY());

}

void Character::Show(BITMAP* mainBitmap){

    if( CheckImages())
        draw_sprite( screen, images[3][0], 0, 0);

}


In this program most of the work is done by the Character class. Here the object is drawing itself and replacing the background as it goes. When the user presses an arrow key, either MoveOnX() or MoveOnY() will be called. Each of these methods will move the character 20 pixels in the desired direction, but only 5 pixels at a time. This gives the program time to change out the drawings so that each part of the animation (defined with SetImagesLeft, Right, Up, and Down) can be seen. Each time the for loop in these functions runs, it will have the old sprite drawn over by the background (in this case a black rectangle is all that is needed) and then the next step in the animation will be drawn 5 pixels past the old one. If you decide to use a more complex background, simply modify the DrawNewSprite() method so that I redraws 2 tiles from the background (the one the character is currently on, and the one he is moving to). By now you should be able to understand the rest, if not, feel free to drop by the forums and ask any questions you may have!

Google