0% found this document useful (0 votes)
62 views

Code Game

This document defines classes and functions for a 2D game engine in C++ using SDL. It includes classes for textures, timers, and a character that can move and collide with walls. Functions are defined for initializing the engine, loading textures, rendering textures, and handling input events for character movement. Constants are defined for the screen size and character dimensions and velocity.

Uploaded by

Nguyễn Hải
Copyright
© © All Rights Reserved
Available Formats
Download as TXT, PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
62 views

Code Game

This document defines classes and functions for a 2D game engine in C++ using SDL. It includes classes for textures, timers, and a character that can move and collide with walls. Functions are defined for initializing the engine, loading textures, rendering textures, and handling input events for character movement. Constants are defined for the screen size and character dimensions and velocity.

Uploaded by

Nguyễn Hải
Copyright
© © All Rights Reserved
Available Formats
Download as TXT, PDF, TXT or read online on Scribd
You are on page 1/ 11

#include<iostream>

#include<SDL.h>
#include<SDL_image.h>
#include<string>

const int SCREEN_WIDTH = 1500;


const int SCREEN_HEIGHT = 760;

bool init();
bool loadMedia();
void close();

//Box collision detector


bool checkCollision( SDL_Rect a, SDL_Rect b );

SDL_Texture* loadTexture(std::string path);


SDL_Window* gWindow = NULL;
SDL_Renderer* gRenderer = NULL;
SDL_Texture* background = NULL;

//Texture wrapper class


class LTexture
{
public:
//Initializes variables
LTexture();

//Deallocates memory
~LTexture();

//Loads image at specified path


bool loadFromFile( std::string path );

#if defined(SDL_TTF_MAJOR_VERSION)
//Creates image from font string
bool loadFromRenderedText( std::string textureText, SDL_Color textColor
);
#endif

//Deallocates texture
void free();

//Set color modulation


void setColor( Uint8 red, Uint8 green, Uint8 blue );

//Set blending
void setBlendMode( SDL_BlendMode blending );

//Set alpha modulation


void setAlpha( Uint8 alpha );

//Renders texture at given point


void render( int x, int y, SDL_Rect* clip = NULL, double angle = 0.0,
SDL_Point* center = NULL, SDL_RendererFlip flip = SDL_FLIP_NONE );

//Gets image dimensions


int getWidth();
int getHeight();
private:
//The actual hardware texture
SDL_Texture* mTexture;

//Image dimensions
int mWidth;
int mHeight;
};

//The application time based timer


class LTimer
{
public:
//Initializes variables
LTimer();

//The various clock actions


void start();
void stop();
void pause();
void unpause();

//Gets the timer's time


Uint32 getTicks();

//Checks the status of the timer


bool isStarted();
bool isPaused();

private:
//The clock time when the timer started
Uint32 mStartTicks;

//The ticks stored when the timer was paused


Uint32 mPausedTicks;

//The timer status


bool mPaused;
bool mStarted;
};

//The character that will move around on the screen


class Character
{
public:
//The dimensions of the character
static const int CHARACTER_WIDTH = 192;
static const int CHARACTER_HEIGHT = 192;

//Maximum axis velocity of the character


static const int CHARACTER_VEL = 1;

//Initializes the variables


Character();

//Takes key presses and adjusts the character's velocity


void handleEvent( SDL_Event& e );

//Moves the character and checks collision


void move( SDL_Rect& wall);

//Shows the character on the screen


void render();

private:
//The X and Y offsets of the character
int mPosX, mPosY;

//The velocity of the character


int mVelX, mVelY;

//Character's collision box


SDL_Rect mCollider;
};

//Attack animation
const int ATTACK_ANIMATION_FRAMES = 14;
SDL_Rect gSpriteClips[ ATTACK_ANIMATION_FRAMES ];
LTexture gSpriteSheetTexture;

//Scene textures
LTexture gCharacterTexture;

LTexture::LTexture()
{
//Initialize
mTexture = NULL;
mWidth = 0;
mHeight = 0;
}

LTexture::~LTexture()
{
//Deallocate
free();
}

bool LTexture::loadFromFile( std::string path )


{
//Get rid of preexisting texture
free();

//The final texture


SDL_Texture* newTexture = NULL;

//Load image at specified path


SDL_Surface* loadedSurface = IMG_Load( path.c_str() );
if( loadedSurface == NULL )
{
std::cout << "Unable to load image!" << IMG_GetError() << std::endl;
}
else
{
//Color key image
SDL_SetColorKey( loadedSurface, SDL_TRUE, SDL_MapRGB( loadedSurface-
>format, 0, 0xFF, 0xFF ) );

//Create texture from surface pixels


newTexture = SDL_CreateTextureFromSurface( gRenderer, loadedSurface );
if( newTexture == NULL )
{
std::cout << "Unable to create texture from " << path << ' ' <<
SDL_GetError() << std::endl;
}
else
{
//Get image dimensions
mWidth = loadedSurface->w;
mHeight = loadedSurface->h;
}

//Get rid of old loaded surface


SDL_FreeSurface( loadedSurface );
}

//Return success
mTexture = newTexture;
return mTexture != NULL;
}

#if defined(SDL_TTF_MAJOR_VERSION)
bool LTexture::loadFromRenderedText( std::string textureText, SDL_Color textColor )
{
//Get rid of preexisting texture
free();

//Render text surface


SDL_Surface* textSurface = TTF_RenderText_Solid( gFont, textureText.c_str(),
textColor );
if( textSurface != NULL )
{
//Create texture from surface pixels
mTexture = SDL_CreateTextureFromSurface( gRenderer, textSurface );
if( mTexture == NULL )
{
printf( "Unable to create texture from rendered text! SDL Error:
%s\n", SDL_GetError() );
}
else
{
//Get image dimensions
mWidth = textSurface->w;
mHeight = textSurface->h;
}

//Get rid of old surface


SDL_FreeSurface( textSurface );
}
else
{
printf( "Unable to render text surface! SDL_ttf Error: %s\n",
TTF_GetError() );
}

//Return success
return mTexture != NULL;
}
#endif

void LTexture::free()
{
//Free texture if it exists
if( mTexture != NULL )
{
SDL_DestroyTexture( mTexture );
mTexture = NULL;
mWidth = 0;
mHeight = 0;
}
}

void LTexture::setColor( Uint8 red, Uint8 green, Uint8 blue )


{
//Modulate texture rgb
SDL_SetTextureColorMod( mTexture, red, green, blue );
}

void LTexture::setBlendMode( SDL_BlendMode blending )


{
//Set blending function
SDL_SetTextureBlendMode( mTexture, blending );
}

void LTexture::setAlpha( Uint8 alpha )


{
//Modulate texture alpha
SDL_SetTextureAlphaMod( mTexture, alpha );
}

void LTexture::render( int x, int y, SDL_Rect* clip, double angle, SDL_Point*


center, SDL_RendererFlip flip )
{
//Set rendering space and render to screen
SDL_Rect renderQuad = { x, y, mWidth, mHeight };

//Set clip rendering dimensions


if( clip != NULL )
{
renderQuad.w = clip->w;
renderQuad.h = clip->h;
}

//Render to screen
SDL_RenderCopyEx( gRenderer, mTexture, clip, &renderQuad, angle, center, flip
);
}

int LTexture::getWidth()
{
return mWidth;
}

int LTexture::getHeight()
{
return mHeight;
}

Character::Character()
{
//Initialize the offsets
mPosX = 0;
mPosY = 0;

//Set collision box dimension


mCollider.w = CHARACTER_WIDTH;
mCollider.h = CHARACTER_HEIGHT;

//Initialize the velocity


mVelX = 0;
mVelY = 0;
}

void Character::handleEvent( SDL_Event& e )


{
//If a key was pressed
if( e.type == SDL_KEYDOWN && e.key.repeat == 0 )
{
//Adjust the velocity
switch( e.key.keysym.sym )
{
case SDLK_UP: mVelY -= CHARACTER_VEL; break;
case SDLK_DOWN: mVelY += CHARACTER_VEL; break;
case SDLK_LEFT: mVelX -= CHARACTER_VEL; break;
case SDLK_RIGHT: mVelX += CHARACTER_VEL; break;
}
}
//If a key was released
else if( e.type == SDL_KEYUP && e.key.repeat == 0 )
{
//Adjust the velocity
switch( e.key.keysym.sym )
{
case SDLK_UP: mVelY += CHARACTER_VEL; break;
case SDLK_DOWN: mVelY -= CHARACTER_VEL; break;
case SDLK_LEFT: mVelX += CHARACTER_VEL; break;
case SDLK_RIGHT: mVelX -= CHARACTER_VEL; break;
}
}
}

void Character::move( SDL_Rect& wall )


{
//Move the dot left or right
mPosX += mVelX;
mCollider.x = mPosX;

//If the dot collided or went too far to the left or right
if( ( mPosX < -70 ) || ( mPosX + CHARACTER_WIDTH > SCREEN_WIDTH + 70 ) ||
checkCollision( mCollider, wall ) )
{
//Move back
mPosX -= mVelX;
mCollider.x = mPosX;
}

//Move the dot up or down


mPosY += mVelY;
mCollider.y = mPosY;

//If the dot collided or went too far up or down


if( ( mPosY < -30 ) || ( mPosY + CHARACTER_HEIGHT > SCREEN_HEIGHT ) ||
checkCollision( mCollider, wall ) )
{
//Move back
mPosY -= mVelY;
mCollider.y = mPosY;
}
}

void Character::render()
{
//Show the dot
gCharacterTexture.render( mPosX, mPosY );
}

bool init() {
bool success = true;
if(SDL_Init(SDL_INIT_VIDEO)<0) {
std::cout << "SDL could not initialize!" << SDL_GetError() << std::endl;
success = false;
}
else {
gWindow = SDL_CreateWindow("Game Đối Kháng", SDL_WINDOWPOS_UNDEFINED,
SDL_WINDOWPOS_UNDEFINED, SCREEN_WIDTH, SCREEN_HEIGHT, SDL_WINDOW_SHOWN);
if(gWindow==NULL) {
std::cout << "Window could not be initialized!" << SDL_GetError() <<
std::endl;
success = false;
}
else {
gRenderer = SDL_CreateRenderer(gWindow, -1, SDL_RENDERER_ACCELERATED);
if(gRenderer==NULL) {
std::cout << "Renderer could not be initialized!" << SDL_GetError()
<< std::endl;
success = false;
}
else {
SDL_SetRenderDrawColor(gRenderer, 0xFF, 0xFF, 0xFF, 0xFF);
int imgFlags = IMG_INIT_PNG;
if(!(IMG_Init(imgFlags) & imgFlags)) {
std::cout << "SDL_image could not initialize!" <<
IMG_GetError() << std::endl;
success = false;
}
}
}
}
return success;
}

bool loadMedia() {
bool success = true;
background = loadTexture("game_material/background2.png");
if(background==NULL) {
std::cout << "Failed to load texture!" << std::endl;
success = false;
}

if( !gCharacterTexture.loadFromFile( "game_material/character.bmp" ) )


{
printf( "Failed to load dot texture!\n" );
success = false;
}

//Load sprite sheet texture


if( !gSpriteSheetTexture.loadFromFile( "game_material/sprite sheet
3x.png" ) )
{
std::cout << "Failed to load sprite sheet texture!\n";
success = false;
}
else {
gSpriteClips[0].x = 192*5;
gSpriteClips[0].y = 0;
gSpriteClips[0].w = 192;
gSpriteClips[0].h = 192;

gSpriteClips[1].x = 192*6;
gSpriteClips[1].y = 0;
gSpriteClips[1].w = 192;
gSpriteClips[1].h = 192;

gSpriteClips[2].x = 192*7;
gSpriteClips[2].y = 0;
gSpriteClips[2].w = 192;
gSpriteClips[2].h = 192;

gSpriteClips[3].x = 0;
gSpriteClips[3].y = 192;
gSpriteClips[3].w = 192;
gSpriteClips[3].h = 192;

gSpriteClips[4].x = 192*1;
gSpriteClips[4].y = 192;
gSpriteClips[4].w = 192;
gSpriteClips[4].h = 192;

gSpriteClips[5].x = 192*2;
gSpriteClips[5].y = 192;
gSpriteClips[5].w = 192;
gSpriteClips[5].h = 192;

gSpriteClips[6].x = 192*3;
gSpriteClips[6].y = 192;
gSpriteClips[6].w = 192;
gSpriteClips[6].h = 192;

gSpriteClips[7].x = 192*4;
gSpriteClips[7].y = 192;
gSpriteClips[7].w = 192;
gSpriteClips[7].h = 192;
gSpriteClips[8].x = 192*5;
gSpriteClips[8].y = 192;
gSpriteClips[8].w = 192;
gSpriteClips[8].h = 192;

gSpriteClips[9].x = 192*6;
gSpriteClips[9].y = 192;
gSpriteClips[9].w = 192;
gSpriteClips[9].h = 192;

gSpriteClips[10].x = 192*7;
gSpriteClips[10].y = 192;
gSpriteClips[10].w = 192;
gSpriteClips[10].h = 192;

gSpriteClips[11].x = 0;
gSpriteClips[11].y = 192*2;
gSpriteClips[11].w = 192;
gSpriteClips[11].h = 192;

gSpriteClips[12].x = 192*1;
gSpriteClips[12].y = 192*2;
gSpriteClips[12].w = 192;
gSpriteClips[12].h = 192;

gSpriteClips[13].x = 192*2;
gSpriteClips[13].y = 192*2;
gSpriteClips[13].w = 192;
gSpriteClips[13].h = 192;
}
return success;
}

void close() {
gSpriteSheetTexture.free();
gCharacterTexture.free();
SDL_DestroyTexture(background);
background = NULL;
SDL_DestroyRenderer(gRenderer);
SDL_DestroyWindow(gWindow);
gWindow = NULL;
gRenderer = NULL;
IMG_Quit();
SDL_Quit();
}

SDL_Texture* loadTexture(std::string path) {


SDL_Texture* newTexture;
SDL_Surface* loadedSurface = IMG_Load(path.c_str());
if(loadedSurface==NULL) {
std::cout << "Unable to load image!" << IMG_GetError() << std::endl;
}
else {
newTexture = SDL_CreateTextureFromSurface(gRenderer, loadedSurface);
if(newTexture==NULL) {
std::cout << "Unable to create texture!" << SDL_GetError() <<
std::endl;
}
}
SDL_FreeSurface(loadedSurface);
return newTexture;
}

bool checkCollision( SDL_Rect a, SDL_Rect b )


{
//The sides of the rectangles
int leftA, leftB;
int rightA, rightB;
int topA, topB;
int bottomA, bottomB;

//Calculate the sides of rect A


leftA = a.x;
rightA = a.x + a.w;
topA = a.y;
bottomA = a.y + a.h;

//Calculate the sides of rect B


leftB = b.x;
rightB = b.x + b.w;
topB = b.y;
bottomB = b.y + b.h;

//If any of the sides from A are outside of B


if( bottomA <= topB )
{
return false;
}

if( topA >= bottomB )


{
return false;
}

if( rightA <= leftB )


{
return false;
}

if( leftA >= rightB )


{
return false;
}

//If none of the sides from A are outside B


return true;
}

int main(int arg, char* args[]) {


if(!init()) {
std::cout << "Failed to initialize!" << std::endl;
}
else {
if(!loadMedia()) {
std::cout << "Failed to load image!" << std::endl;
}
else {
bool quit = false;
SDL_Event e;
//The character that will be moving around on the screen
Character character;

//Set the wall


SDL_Rect wall;
wall.x = 0;
wall.y = 595;
wall.w = 1500;
wall.h = 360;

int frame = 0;
while(!quit) {
while(SDL_PollEvent(&e)!=0) {
if(e.type==SDL_QUIT) {
quit = true;
}
//Handle input for the character
character.handleEvent( e );
}
character.move( wall );

SDL_SetRenderDrawColor(gRenderer, 0xFF, 0xFF, 0xFF, 0xFF);


SDL_RenderClear(gRenderer);

SDL_RenderCopy(gRenderer, background, NULL, NULL);

SDL_Rect* currentClip = &gSpriteClips[frame/100];


gSpriteSheetTexture.render( 20, 400, currentClip );

character.render();
SDL_RenderPresent(gRenderer);

frame++;
//Cycle animation
if( frame / 100 >= ATTACK_ANIMATION_FRAMES )
{
frame = 0;
}
}
}
}
close();
return 0;
}

You might also like