release v1.3 beta 1
6
Makefile
Normal file
@@ -0,0 +1,6 @@
|
|||||||
|
macos:
|
||||||
|
mkdir -p bin
|
||||||
|
g++ -std=c++11 -Wall -O2 source/*.cpp -o bin/coffee_crisis_macos -lSDL2
|
||||||
|
linux:
|
||||||
|
mkdir -p bin
|
||||||
|
g++ -std=c++11 -Wall -O2 source/*.cpp -o bin/coffee_crisis_linux -lSDL2
|
||||||
BIN
data/demo.bin
Normal file
BIN
media/.DS_Store
vendored
Normal file
BIN
media/gfx/.DS_Store
vendored
Normal file
BIN
media/gfx/balloon.png
Normal file
|
After Width: | Height: | Size: 16 KiB |
BIN
media/gfx/bullet.png
Normal file
|
After Width: | Height: | Size: 348 B |
BIN
media/gfx/font_black.png
Normal file
|
After Width: | Height: | Size: 1.3 KiB |
BIN
media/gfx/font_nokia.png
Normal file
|
After Width: | Height: | Size: 2.0 KiB |
BIN
media/gfx/font_white.png
Normal file
|
After Width: | Height: | Size: 1.3 KiB |
BIN
media/gfx/game_bg.png
Normal file
|
After Width: | Height: | Size: 10 KiB |
BIN
media/gfx/game_text.png
Normal file
|
After Width: | Height: | Size: 795 B |
BIN
media/gfx/intro.png
Normal file
|
After Width: | Height: | Size: 13 KiB |
BIN
media/gfx/items.png
Normal file
|
After Width: | Height: | Size: 1.8 KiB |
BIN
media/gfx/logo.png
Normal file
|
After Width: | Height: | Size: 3.1 KiB |
BIN
media/gfx/menu.png
Normal file
|
After Width: | Height: | Size: 146 B |
BIN
media/gfx/player_body.png
Normal file
|
After Width: | Height: | Size: 6.1 KiB |
BIN
media/gfx/player_death.png
Normal file
|
After Width: | Height: | Size: 672 B |
BIN
media/gfx/player_legs.png
Normal file
|
After Width: | Height: | Size: 785 B |
BIN
media/gfx/title.png
Normal file
|
After Width: | Height: | Size: 3.6 KiB |
BIN
media/music/.DS_Store
vendored
Normal file
10
media/music/credits.txt
Normal file
@@ -0,0 +1,10 @@
|
|||||||
|
playing.ogg
|
||||||
|
ARCADE GOBLINS
|
||||||
|
https://soundimage.org/chiptunes-3/
|
||||||
|
|
||||||
|
title.ogg
|
||||||
|
ARCADE STORIES
|
||||||
|
https://soundimage.org/chiptunes-3/
|
||||||
|
|
||||||
|
intro.ogg
|
||||||
|
JailDoctor
|
||||||
BIN
media/music/intro.ogg
Normal file
BIN
media/music/playing.ogg
Normal file
BIN
media/music/title.ogg
Normal file
BIN
media/sound/balloon.wav
Normal file
BIN
media/sound/bubble1.wav
Normal file
BIN
media/sound/bubble2.wav
Normal file
BIN
media/sound/bubble3.wav
Normal file
BIN
media/sound/bubble4.wav
Normal file
BIN
media/sound/bullet.wav
Normal file
BIN
media/sound/coffeeout.wav
Normal file
60
media/sound/credits.txt
Normal file
@@ -0,0 +1,60 @@
|
|||||||
|
bullet.wav
|
||||||
|
Gun11.wav
|
||||||
|
http://www.themotionmonkey.co.uk/free-resources/retro-arcade-sounds/
|
||||||
|
|
||||||
|
balloon.wav
|
||||||
|
Impact3.wav
|
||||||
|
http://www.themotionmonkey.co.uk/free-resources/retro-arcade-sounds/
|
||||||
|
|
||||||
|
player_collision.wav
|
||||||
|
Impact5.wav
|
||||||
|
http://www.themotionmonkey.co.uk/free-resources/retro-arcade-sounds/
|
||||||
|
|
||||||
|
title.wav
|
||||||
|
Explosion2.wav
|
||||||
|
http://www.themotionmonkey.co.uk/free-resources/retro-arcade-sounds/
|
||||||
|
|
||||||
|
menu_select.wav
|
||||||
|
kenney_digitalaudio/powerUp2.ogg
|
||||||
|
www.kenney.nl
|
||||||
|
|
||||||
|
menu_move.wav
|
||||||
|
kenney_uiaudio/switch11.ogg
|
||||||
|
www.kenney.nl
|
||||||
|
|
||||||
|
hiscore.wav
|
||||||
|
kenney_digitalaudio/powerUp1.ogg
|
||||||
|
www.kenney.nl
|
||||||
|
|
||||||
|
itemdrop.wav
|
||||||
|
kenney_digitalaudio/PowerUp10.ogg
|
||||||
|
www.kenney.nl
|
||||||
|
|
||||||
|
itempickup.wav
|
||||||
|
kenney_digitalaudio/PowerUp7.ogg
|
||||||
|
www.kenney.nl
|
||||||
|
|
||||||
|
coffeeout.wav
|
||||||
|
kenney_digitalaudio/lowDown.ogg
|
||||||
|
www.kenney.nl
|
||||||
|
|
||||||
|
stage_change.wav
|
||||||
|
kenney_digitalaudio/phaserUp2.ogg
|
||||||
|
www.kenney.nl
|
||||||
|
|
||||||
|
menu_cancel.wav
|
||||||
|
kenney_digitalaudio/lowRandom.ogg
|
||||||
|
kenney_digitalaudio/pepSound1.ogg <-
|
||||||
|
www.kenney.nl
|
||||||
|
|
||||||
|
bubble1.wav
|
||||||
|
JailDoctor
|
||||||
|
|
||||||
|
bubble2.wav
|
||||||
|
JailDoctor
|
||||||
|
|
||||||
|
bubble3.wav
|
||||||
|
JailDoctor
|
||||||
|
|
||||||
|
bubble4.wav
|
||||||
|
JailDoctor
|
||||||
BIN
media/sound/hiscore.wav
Normal file
BIN
media/sound/itemdrop.wav
Normal file
BIN
media/sound/itempickup.wav
Normal file
BIN
media/sound/menu_cancel.wav
Normal file
BIN
media/sound/menu_move.wav
Normal file
BIN
media/sound/menu_select.wav
Normal file
BIN
media/sound/player_collision.wav
Normal file
BIN
media/sound/stage_change.wav
Normal file
BIN
media/sound/title.wav
Normal file
BIN
media/sound/tnt.wav
Normal file
BIN
source/.DS_Store
vendored
Normal file
112
source/animatedsprite.cpp
Normal file
@@ -0,0 +1,112 @@
|
|||||||
|
#include "const.h"
|
||||||
|
#include "animatedsprite.h"
|
||||||
|
#include <iostream>
|
||||||
|
|
||||||
|
// Constructor
|
||||||
|
AnimatedSprite::AnimatedSprite()
|
||||||
|
{
|
||||||
|
init(nullptr, nullptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
AnimatedSprite::~AnimatedSprite()
|
||||||
|
{
|
||||||
|
init(nullptr, nullptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Iniciador
|
||||||
|
void AnimatedSprite::init(LTexture *texture, SDL_Renderer *renderer)
|
||||||
|
{
|
||||||
|
mRenderer = renderer;
|
||||||
|
mTexture = texture;
|
||||||
|
for (Uint8 i = 0; i < 20; i++)
|
||||||
|
{
|
||||||
|
mAnimation[i].numFrames = 0;
|
||||||
|
mAnimation[i].speed = 0;
|
||||||
|
mAnimation[i].loop = true;
|
||||||
|
for (Uint8 j = 0; i < 20; i++)
|
||||||
|
{
|
||||||
|
mAnimation[i].frames[j].x = 0;
|
||||||
|
mAnimation[i].frames[j].y = 0;
|
||||||
|
mAnimation[i].frames[j].w = 0;
|
||||||
|
mAnimation[i].frames[j].h = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
mCurrentFrame = 0;
|
||||||
|
mAnimationCounter = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Calcula el frame correspondiente a la animación
|
||||||
|
void AnimatedSprite::animate(int index)
|
||||||
|
{
|
||||||
|
// Calculamos el frame actual a partir del contador
|
||||||
|
mCurrentFrame = mAnimationCounter / mAnimation[index].speed;
|
||||||
|
|
||||||
|
// Si alcanzamos el final de la animación, reiniciamos el contador de la animación
|
||||||
|
// en función de la variable loop
|
||||||
|
if (mCurrentFrame >= mAnimation[index].numFrames)
|
||||||
|
{
|
||||||
|
if (mAnimation[index].loop)
|
||||||
|
{
|
||||||
|
mAnimationCounter = 0;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mCurrentFrame = mAnimation[index].numFrames;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// En caso contrario
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// Escogemos el frame correspondiente de la animación
|
||||||
|
setSpriteClip(mAnimation[index].frames[mCurrentFrame]);
|
||||||
|
|
||||||
|
// Incrementamos el contador de la animacion
|
||||||
|
++mAnimationCounter;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el frame actual de la animación
|
||||||
|
void AnimatedSprite::setCurrentFrame(Uint8 num)
|
||||||
|
{
|
||||||
|
mCurrentFrame = num;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor del contador
|
||||||
|
void AnimatedSprite::setAnimationCounter(Uint16 num)
|
||||||
|
{
|
||||||
|
mAnimationCounter = num;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el rectangulo para un frame de una animación
|
||||||
|
void AnimatedSprite::setAnimationFrames(Uint8 index_animation, Uint8 index_frame, int x, int y, int w, int h)
|
||||||
|
{
|
||||||
|
mAnimation[index_animation].frames[index_frame].x = x;
|
||||||
|
mAnimation[index_animation].frames[index_frame].y = y;
|
||||||
|
mAnimation[index_animation].frames[index_frame].w = w;
|
||||||
|
mAnimation[index_animation].frames[index_frame].h = h;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece la velocidad de una animación
|
||||||
|
void AnimatedSprite::setAnimationSpeed(Uint8 index, Uint8 speed)
|
||||||
|
{
|
||||||
|
mAnimation[index].speed = speed;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el numero de frames de una animación
|
||||||
|
void AnimatedSprite::setAnimationNumFrames(Uint8 index, Uint8 num)
|
||||||
|
{
|
||||||
|
mAnimation[index].numFrames = num;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece si la animación se reproduce en bucle
|
||||||
|
void AnimatedSprite::setAnimationLoop(Uint8 index, bool loop)
|
||||||
|
{
|
||||||
|
mAnimation[index].loop = loop;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Devuelve el rectangulo de una animación y frame concreto
|
||||||
|
SDL_Rect AnimatedSprite::getAnimationClip(Uint8 index_animation, Uint8 index_frame)
|
||||||
|
{
|
||||||
|
return mAnimation[index_animation].frames[index_frame];
|
||||||
|
}
|
||||||
64
source/animatedsprite.h
Normal file
@@ -0,0 +1,64 @@
|
|||||||
|
#pragma once
|
||||||
|
#include "ifdefs.h"
|
||||||
|
#include "movingsprite.h"
|
||||||
|
|
||||||
|
#ifndef ANIMATEDSPRITE_H
|
||||||
|
#define ANIMATEDSPRITE_H
|
||||||
|
|
||||||
|
// Clase AnimatedSprite
|
||||||
|
class AnimatedSprite : public MovingSprite
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
// Constructor
|
||||||
|
AnimatedSprite();
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
~AnimatedSprite();
|
||||||
|
|
||||||
|
// Iniciador
|
||||||
|
void init(LTexture *texture, SDL_Renderer *renderer);
|
||||||
|
|
||||||
|
// Calcula el frame correspondiente a la animación
|
||||||
|
void animate(int index);
|
||||||
|
|
||||||
|
// Establece el frame actual de la animación
|
||||||
|
void setCurrentFrame(Uint8 num);
|
||||||
|
|
||||||
|
// Establece el valor del contador
|
||||||
|
void setAnimationCounter(Uint16 num);
|
||||||
|
|
||||||
|
// Establece el rectangulo para un frame de una animación
|
||||||
|
void setAnimationFrames(Uint8 index_animation, Uint8 index_frame, int x, int y, int w, int h);
|
||||||
|
|
||||||
|
// Establece la velocidad de una animación
|
||||||
|
void setAnimationSpeed(Uint8 index, Uint8 speed);
|
||||||
|
|
||||||
|
// Establece el numero de frames de una animación
|
||||||
|
void setAnimationNumFrames(Uint8 index, Uint8 num);
|
||||||
|
|
||||||
|
// Establece si la animación se reproduce en bucle
|
||||||
|
void setAnimationLoop(Uint8 index, bool loop);
|
||||||
|
|
||||||
|
// Devuelve el rectangulo de una animación y frame concreto
|
||||||
|
SDL_Rect getAnimationClip(Uint8 index_animation, Uint8 index_frame);
|
||||||
|
|
||||||
|
private:
|
||||||
|
struct sAnimation
|
||||||
|
{
|
||||||
|
SDL_Rect frames[20]; // Hasta 20 frames
|
||||||
|
Uint8 numFrames;
|
||||||
|
Uint8 speed;
|
||||||
|
bool loop;
|
||||||
|
};
|
||||||
|
|
||||||
|
// Vector con las diferentes animaciones y los diferentes frames de cada animación
|
||||||
|
sAnimation mAnimation[20]; // Hasta 20 animaciones
|
||||||
|
|
||||||
|
// Frame actual
|
||||||
|
Uint8 mCurrentFrame;
|
||||||
|
|
||||||
|
// Contador para las animaciones
|
||||||
|
Uint16 mAnimationCounter;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
644
source/balloon.cpp
Normal file
@@ -0,0 +1,644 @@
|
|||||||
|
#include "const.h"
|
||||||
|
#include "balloon.h"
|
||||||
|
|
||||||
|
// Constructor
|
||||||
|
Balloon::Balloon()
|
||||||
|
{
|
||||||
|
mSprite = new AnimatedSprite();
|
||||||
|
init(0, 0, NO_KIND, BALLON_VELX_POSITIVE, 0, nullptr, nullptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
Balloon::~Balloon()
|
||||||
|
{
|
||||||
|
delete mSprite;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Inicializador
|
||||||
|
void Balloon::init(float x, int y, Uint8 kind, float velx, Uint16 creationtimer, LTexture *texture, SDL_Renderer *renderer)
|
||||||
|
{
|
||||||
|
const Uint8 NUM_FRAMES_BALLON = 10;
|
||||||
|
const Uint8 NUM_FRAMES_BALLON_POP = 12;
|
||||||
|
const Uint8 NUM_FRAMES_BALLON_BORN = 10;
|
||||||
|
|
||||||
|
switch (kind)
|
||||||
|
{
|
||||||
|
case BALLOON_1:
|
||||||
|
// Posición inicial
|
||||||
|
mPosX = x;
|
||||||
|
mPosY = y;
|
||||||
|
|
||||||
|
// Alto y ancho del objeto
|
||||||
|
mWidth = 8;
|
||||||
|
mHeight = mWidth;
|
||||||
|
|
||||||
|
// Inicializa los valores de velocidad y gravedad
|
||||||
|
mVelX = velx;
|
||||||
|
mVelY = 0;
|
||||||
|
mMaxVelY = 3;
|
||||||
|
mGravity = 0.09f;
|
||||||
|
mDefaultVelY = 3;
|
||||||
|
|
||||||
|
// Puntos que da el globo al ser destruido
|
||||||
|
mScore = 50;
|
||||||
|
|
||||||
|
// Amenaza que genera el globo
|
||||||
|
mMenace = 1;
|
||||||
|
|
||||||
|
// Establece los frames de cada animación
|
||||||
|
for (Uint8 i = 0; i < NUM_FRAMES_BALLON; i++)
|
||||||
|
{
|
||||||
|
mSprite->setAnimationFrames(BALLOON_MOVING_ANIMATION, i, 50, 21 + (37 * i), getWidth(), getHeight());
|
||||||
|
}
|
||||||
|
for (Uint8 i = 0; i < NUM_FRAMES_BALLON_BORN; i++)
|
||||||
|
{
|
||||||
|
mSprite->setAnimationFrames(BALLOON_BORN_ANIMATION, i, 50 + 58, 21 + (37 * i), getWidth(), getHeight());
|
||||||
|
}
|
||||||
|
for (Uint8 i = 0; i < NUM_FRAMES_BALLON_POP; i++)
|
||||||
|
{
|
||||||
|
mSprite->setAnimationFrames(BALLOON_POP_ANIMATION, i, 50 + 58 + 58, 21 + (37 * i), getWidth(), getHeight());
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case BALLOON_2:
|
||||||
|
// Posición inicial
|
||||||
|
mPosX = x;
|
||||||
|
mPosY = y;
|
||||||
|
|
||||||
|
// Alto y ancho del objeto
|
||||||
|
mWidth = 13;
|
||||||
|
mHeight = mWidth;
|
||||||
|
|
||||||
|
// Inicializa los valores de velocidad y gravedad
|
||||||
|
mVelX = velx;
|
||||||
|
mVelY = 0;
|
||||||
|
mMaxVelY = 3;
|
||||||
|
mGravity = 0.10f;
|
||||||
|
mDefaultVelY = 4;
|
||||||
|
|
||||||
|
// Puntos que da el globo al ser destruido
|
||||||
|
mScore = 100;
|
||||||
|
|
||||||
|
// Amenaza que genera el globo
|
||||||
|
mMenace = 2;
|
||||||
|
|
||||||
|
// Establece los frames de cada animación
|
||||||
|
for (Uint8 i = 0; i < NUM_FRAMES_BALLON; i++)
|
||||||
|
{
|
||||||
|
mSprite->setAnimationFrames(BALLOON_MOVING_ANIMATION, i, 37, 21 + (37 * i), getWidth(), getHeight());
|
||||||
|
}
|
||||||
|
for (Uint8 i = 0; i < NUM_FRAMES_BALLON_BORN; i++)
|
||||||
|
{
|
||||||
|
mSprite->setAnimationFrames(BALLOON_BORN_ANIMATION, i, 37 + 58, 21 + (37 * i), getWidth(), getHeight());
|
||||||
|
}
|
||||||
|
for (Uint8 i = 0; i < NUM_FRAMES_BALLON_POP; i++)
|
||||||
|
{
|
||||||
|
mSprite->setAnimationFrames(BALLOON_POP_ANIMATION, i, 37 + 58 + 58, 21 + (37 * i), getWidth(), getHeight());
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case BALLOON_3:
|
||||||
|
// Posición inicial
|
||||||
|
mPosX = x;
|
||||||
|
mPosY = y;
|
||||||
|
|
||||||
|
// Alto y ancho del objeto
|
||||||
|
mWidth = 21;
|
||||||
|
mHeight = mWidth;
|
||||||
|
|
||||||
|
// Inicializa los valores de velocidad y gravedad
|
||||||
|
mVelX = velx;
|
||||||
|
mVelY = 0;
|
||||||
|
mMaxVelY = 3;
|
||||||
|
mGravity = 0.10f;
|
||||||
|
mDefaultVelY = 4.5;
|
||||||
|
|
||||||
|
// Puntos que da el globo al ser destruido
|
||||||
|
mScore = 200;
|
||||||
|
|
||||||
|
// Amenaza que genera el globo
|
||||||
|
mMenace = 4;
|
||||||
|
|
||||||
|
// Establece los frames de cada animación
|
||||||
|
for (Uint8 i = 0; i < NUM_FRAMES_BALLON; i++)
|
||||||
|
{
|
||||||
|
mSprite->setAnimationFrames(BALLOON_MOVING_ANIMATION, i, 37, 37 * i, getWidth(), getHeight());
|
||||||
|
}
|
||||||
|
for (Uint8 i = 0; i < NUM_FRAMES_BALLON_BORN; i++)
|
||||||
|
{
|
||||||
|
mSprite->setAnimationFrames(BALLOON_BORN_ANIMATION, i, 37 + 58, 37 * i, getWidth(), getHeight());
|
||||||
|
}
|
||||||
|
for (Uint8 i = 0; i < NUM_FRAMES_BALLON_POP; i++)
|
||||||
|
{
|
||||||
|
mSprite->setAnimationFrames(BALLOON_POP_ANIMATION, i, 37 + 58 + 58, 37 * i, getWidth(), getHeight());
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case BALLOON_4:
|
||||||
|
// Posición inicial
|
||||||
|
mPosX = x;
|
||||||
|
mPosY = y;
|
||||||
|
|
||||||
|
// Alto y ancho del objeto
|
||||||
|
mWidth = 37;
|
||||||
|
mHeight = mWidth;
|
||||||
|
|
||||||
|
// Inicializa los valores de velocidad y gravedad
|
||||||
|
mVelX = velx;
|
||||||
|
mVelY = 0;
|
||||||
|
mMaxVelY = 3;
|
||||||
|
mGravity = 0.10f;
|
||||||
|
mDefaultVelY = 5;
|
||||||
|
|
||||||
|
// Puntos que da el globo al ser destruido
|
||||||
|
mScore = 400;
|
||||||
|
|
||||||
|
// Amenaza que genera el globo
|
||||||
|
mMenace = 8;
|
||||||
|
|
||||||
|
// Establece los frames de cada animación
|
||||||
|
for (Uint8 i = 0; i < NUM_FRAMES_BALLON; i++)
|
||||||
|
{
|
||||||
|
mSprite->setAnimationFrames(BALLOON_MOVING_ANIMATION, i, 0, 37 * i, getWidth(), getHeight());
|
||||||
|
}
|
||||||
|
for (Uint8 i = 0; i < NUM_FRAMES_BALLON_BORN; i++)
|
||||||
|
{
|
||||||
|
mSprite->setAnimationFrames(BALLOON_BORN_ANIMATION, i, 58, 37 * i, getWidth(), getHeight());
|
||||||
|
}
|
||||||
|
for (Uint8 i = 0; i < NUM_FRAMES_BALLON_POP; i++)
|
||||||
|
{
|
||||||
|
mSprite->setAnimationFrames(BALLOON_POP_ANIMATION, i, 58 + 58, 37 * i, getWidth(), getHeight());
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
// Posición inicial
|
||||||
|
mPosX = x;
|
||||||
|
mPosY = y;
|
||||||
|
|
||||||
|
// Alto y ancho del objeto
|
||||||
|
mWidth = 0;
|
||||||
|
mHeight = mWidth;
|
||||||
|
|
||||||
|
// Inicializa los valores de velocidad y gravedad
|
||||||
|
mVelX = velx;
|
||||||
|
mVelY = 0;
|
||||||
|
mMaxVelY = 0;
|
||||||
|
mGravity = 0;
|
||||||
|
mDefaultVelY = 0;
|
||||||
|
|
||||||
|
// Puntos que da el globo al ser destruido
|
||||||
|
mScore = 0;
|
||||||
|
|
||||||
|
// Amenaza que genera el globo
|
||||||
|
mMenace = 0;
|
||||||
|
|
||||||
|
// Establece los frames de cada animación
|
||||||
|
mSprite->setAnimationFrames(0, 0, 0, 0, getWidth(), getHeight());
|
||||||
|
mSprite->setAnimationFrames(1, 0, 0, 0, getWidth(), getHeight());
|
||||||
|
mSprite->setAnimationFrames(2, 0, 0, 0, getWidth(), getHeight());
|
||||||
|
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Textura con los gráficos del sprite
|
||||||
|
mSprite->setTexture(texture);
|
||||||
|
|
||||||
|
// Renderizador
|
||||||
|
mSprite->setRenderer(renderer);
|
||||||
|
|
||||||
|
// Alto y ancho del sprite
|
||||||
|
mSprite->setWidth(mWidth);
|
||||||
|
mSprite->setHeight(mHeight);
|
||||||
|
|
||||||
|
// Posición X,Y del sprite
|
||||||
|
mSprite->setPosX(int(mPosX));
|
||||||
|
mSprite->setPosY(mPosY);
|
||||||
|
|
||||||
|
// Tamaño del circulo de colisión
|
||||||
|
mCollider.r = mWidth / 2;
|
||||||
|
|
||||||
|
// Alinea el circulo de colisión con el objeto
|
||||||
|
shiftColliders();
|
||||||
|
|
||||||
|
// Inicializa variables
|
||||||
|
mStopped = true;
|
||||||
|
mStoppedTimer = 0;
|
||||||
|
mBlinking = false;
|
||||||
|
mVisible = true;
|
||||||
|
mInvulnerable = false;
|
||||||
|
mBeingCreated = true;
|
||||||
|
mCreationTimer = creationtimer;
|
||||||
|
mPopping = false;
|
||||||
|
|
||||||
|
// Tipo
|
||||||
|
mKind = kind;
|
||||||
|
|
||||||
|
// Inicializa las variables para la animación
|
||||||
|
mSprite->setCurrentFrame(0);
|
||||||
|
mSprite->setAnimationCounter(0);
|
||||||
|
|
||||||
|
// Establece el numero de frames de cada animacion
|
||||||
|
mSprite->setAnimationNumFrames(BALLOON_MOVING_ANIMATION, NUM_FRAMES_BALLON);
|
||||||
|
mSprite->setAnimationNumFrames(BALLOON_POP_ANIMATION, NUM_FRAMES_BALLON_POP);
|
||||||
|
mSprite->setAnimationNumFrames(BALLOON_BORN_ANIMATION, NUM_FRAMES_BALLON_BORN);
|
||||||
|
|
||||||
|
// Establece la velocidad de cada animación
|
||||||
|
mSprite->setAnimationSpeed(BALLOON_MOVING_ANIMATION, 10);
|
||||||
|
mSprite->setAnimationSpeed(BALLOON_POP_ANIMATION, 5);
|
||||||
|
mSprite->setAnimationSpeed(BALLOON_BORN_ANIMATION, 20);
|
||||||
|
|
||||||
|
// Establece si la animación se reproduce en bucle
|
||||||
|
mSprite->setAnimationLoop(BALLOON_MOVING_ANIMATION, true);
|
||||||
|
mSprite->setAnimationLoop(BALLOON_POP_ANIMATION, false);
|
||||||
|
mSprite->setAnimationLoop(BALLOON_BORN_ANIMATION, true);
|
||||||
|
|
||||||
|
// Selecciona un frame para pintar
|
||||||
|
mSprite->setSpriteClip(mSprite->getAnimationClip(0, 0));
|
||||||
|
}
|
||||||
|
|
||||||
|
// Centra el globo en la posición X
|
||||||
|
void Balloon::allignTo(int x)
|
||||||
|
{
|
||||||
|
mPosX = float(x - (mWidth / 2));
|
||||||
|
|
||||||
|
if (mPosX < PLAY_AREA_LEFT)
|
||||||
|
{
|
||||||
|
mPosX = PLAY_AREA_LEFT + 1;
|
||||||
|
}
|
||||||
|
else if ((mPosX + mWidth) > PLAY_AREA_RIGHT)
|
||||||
|
{
|
||||||
|
mPosX = float(PLAY_AREA_RIGHT - mWidth - 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Posición X,Y del sprite
|
||||||
|
mSprite->setPosX(getPosX());
|
||||||
|
mSprite->setPosY(getPosY());
|
||||||
|
|
||||||
|
// Alinea el circulo de colisión con el objeto
|
||||||
|
shiftColliders();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Pinta el globo en la pantalla
|
||||||
|
void Balloon::render()
|
||||||
|
{
|
||||||
|
if (mVisible)
|
||||||
|
{
|
||||||
|
mSprite->render();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actualiza la posición y estados del globo
|
||||||
|
void Balloon::move()
|
||||||
|
{
|
||||||
|
// Comprobamos si se puede mover
|
||||||
|
if (isStopped() == false)
|
||||||
|
{
|
||||||
|
// Lo movemos a izquierda o derecha
|
||||||
|
mPosX += mVelX;
|
||||||
|
|
||||||
|
// Si queda fuera de pantalla, corregimos su posición y cambiamos su sentido
|
||||||
|
if ((mPosX < PLAY_AREA_LEFT) || (mPosX + mWidth > PLAY_AREA_RIGHT))
|
||||||
|
{
|
||||||
|
// Corregir posición
|
||||||
|
mPosX -= mVelX;
|
||||||
|
|
||||||
|
// Invertir sentido
|
||||||
|
mVelX = -mVelX;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Mueve el globo hacia arriba o hacia abajo
|
||||||
|
mPosY += int(mVelY);
|
||||||
|
|
||||||
|
// Si se sale por arriba
|
||||||
|
if (mPosY < PLAY_AREA_TOP)
|
||||||
|
{
|
||||||
|
// Corregimos
|
||||||
|
mPosY -= int(mVelY);
|
||||||
|
|
||||||
|
// Invertimos sentido
|
||||||
|
mVelY = -mVelY;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Si el globo se sale por la parte inferior
|
||||||
|
if (mPosY + mHeight > PLAY_AREA_BOTTOM)
|
||||||
|
{
|
||||||
|
// Corregimos
|
||||||
|
mPosY -= int(mVelY);
|
||||||
|
|
||||||
|
// Invertimos colocando una velocidad por defecto
|
||||||
|
mVelY = -mDefaultVelY;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Aplica gravedad al objeto, sin pasarse de un limite establecido
|
||||||
|
if (int(mVelY) > mMaxVelY)
|
||||||
|
{
|
||||||
|
mVelY = float(mMaxVelY);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mVelY += mGravity;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actualiza la posición del sprite
|
||||||
|
mSprite->setPosX(getPosX());
|
||||||
|
mSprite->setPosY(mPosY);
|
||||||
|
}
|
||||||
|
// Si no se puede mover:
|
||||||
|
// Comprobar si se está creando
|
||||||
|
else if (isBeingCreated() == true)
|
||||||
|
{
|
||||||
|
// Actualiza el valor de las variables
|
||||||
|
setStop(true);
|
||||||
|
setInvulnerable(true);
|
||||||
|
|
||||||
|
// Todavia tiene tiempo en el contador
|
||||||
|
if (mCreationTimer > 0)
|
||||||
|
{
|
||||||
|
// Desplaza lentamente el globo hacia abajo y hacia un lado
|
||||||
|
if (mCreationTimer % 10 == 0)
|
||||||
|
{
|
||||||
|
++mPosY;
|
||||||
|
mPosX += mVelX;
|
||||||
|
|
||||||
|
// Actualiza la posición del sprite
|
||||||
|
mSprite->setPosX(getPosX());
|
||||||
|
mSprite->setPosY(mPosY);
|
||||||
|
|
||||||
|
// Actualiza la posición del circulo de colisión
|
||||||
|
shiftColliders();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Hace visible el globo de forma intermitente
|
||||||
|
if (mCreationTimer > 100)
|
||||||
|
{
|
||||||
|
setVisible(mCreationTimer / 10 % 2 == 0);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
setVisible(mCreationTimer / 5 % 2 == 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
--mCreationTimer;
|
||||||
|
}
|
||||||
|
// El contador ha llegado a cero
|
||||||
|
else
|
||||||
|
{
|
||||||
|
setBeingCreated(false);
|
||||||
|
setStop(false);
|
||||||
|
setVisible(true);
|
||||||
|
setInvulnerable(false);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// Comprobar si está detenido
|
||||||
|
else if (isStopped() == true)
|
||||||
|
{
|
||||||
|
// Si todavía está detenido, reduce el contador
|
||||||
|
if (mStoppedTimer > 0)
|
||||||
|
{
|
||||||
|
--mStoppedTimer;
|
||||||
|
} // Si el contador ha llegado a cero, ya no está detenido
|
||||||
|
else
|
||||||
|
{
|
||||||
|
setStop(false);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Pone a cero todos los valores del globo
|
||||||
|
void Balloon::erase()
|
||||||
|
{
|
||||||
|
init(0, 0, NO_KIND, 0, 0, nullptr, nullptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Explosiona el globo
|
||||||
|
void Balloon::pop()
|
||||||
|
{
|
||||||
|
setPopping(true);
|
||||||
|
mSprite->setAnimationCounter(0);
|
||||||
|
setTimeToLive(120);
|
||||||
|
setStop(true);
|
||||||
|
setStoppedTimer(2000);
|
||||||
|
setInvulnerable(true);
|
||||||
|
mMenace = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actualiza al globo a su posicion, animación y controla los contadores
|
||||||
|
void Balloon::update()
|
||||||
|
{
|
||||||
|
move();
|
||||||
|
setAnimation();
|
||||||
|
shiftColliders();
|
||||||
|
if (isPopping())
|
||||||
|
{
|
||||||
|
setInvulnerable(true);
|
||||||
|
setStop(true);
|
||||||
|
if (mTimeToLive > 0)
|
||||||
|
{
|
||||||
|
--mTimeToLive;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
erase();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece la animación correspondiente al estado
|
||||||
|
void Balloon::setAnimation()
|
||||||
|
{
|
||||||
|
// Establece el frame de animación
|
||||||
|
if (isPopping())
|
||||||
|
{
|
||||||
|
mSprite->animate(BALLOON_POP_ANIMATION);
|
||||||
|
}
|
||||||
|
else if (isBeingCreated())
|
||||||
|
{
|
||||||
|
mSprite->animate(BALLOON_BORN_ANIMATION);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mSprite->animate(BALLOON_MOVING_ANIMATION);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Comprueba si el globo tiene algun tipo asignado
|
||||||
|
bool Balloon::isActive()
|
||||||
|
{
|
||||||
|
if (mKind == NO_KIND)
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
int Balloon::getPosX()
|
||||||
|
{
|
||||||
|
return int(mPosX);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
int Balloon::getPosY()
|
||||||
|
{
|
||||||
|
return mPosY;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
float Balloon::getVelY()
|
||||||
|
{
|
||||||
|
return mVelY;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
int Balloon::getWidth()
|
||||||
|
{
|
||||||
|
return mWidth;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
int Balloon::getHeight()
|
||||||
|
{
|
||||||
|
return mHeight;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Balloon::setVelY(float velY)
|
||||||
|
{
|
||||||
|
mVelY = velY;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
int Balloon::getKind()
|
||||||
|
{
|
||||||
|
return mKind;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Balloon::setStop(bool state)
|
||||||
|
{
|
||||||
|
mStopped = state;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
bool Balloon::isStopped()
|
||||||
|
{
|
||||||
|
return mStopped;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Balloon::setBlink(bool state)
|
||||||
|
{
|
||||||
|
mBlinking = state;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
bool Balloon::isBlinking()
|
||||||
|
{
|
||||||
|
return mBlinking;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Balloon::setVisible(bool state)
|
||||||
|
{
|
||||||
|
mVisible = state;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
bool Balloon::isVisible()
|
||||||
|
{
|
||||||
|
return mVisible;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Balloon::setInvulnerable(bool state)
|
||||||
|
{
|
||||||
|
mInvulnerable = state;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
bool Balloon::isInvulnerable()
|
||||||
|
{
|
||||||
|
return mInvulnerable;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Balloon::setBeingCreated(bool state)
|
||||||
|
{
|
||||||
|
mBeingCreated = state;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
bool Balloon::isBeingCreated()
|
||||||
|
{
|
||||||
|
return mBeingCreated;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Balloon::setPopping(bool state)
|
||||||
|
{
|
||||||
|
mPopping = state;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
bool Balloon::isPopping()
|
||||||
|
{
|
||||||
|
return mPopping;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Balloon::setTimeToLive(Uint16 time)
|
||||||
|
{
|
||||||
|
mTimeToLive = time;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
Uint16 Balloon::getTimeToLive()
|
||||||
|
{
|
||||||
|
return mTimeToLive;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Balloon::setStoppedTimer(Uint16 time)
|
||||||
|
{
|
||||||
|
mStoppedTimer = time;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
Uint16 Balloon::getStoppedTimer()
|
||||||
|
{
|
||||||
|
return mStoppedTimer;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
Uint16 Balloon::getScore()
|
||||||
|
{
|
||||||
|
return mScore;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el circulo de colisión
|
||||||
|
Circle &Balloon::getCollider()
|
||||||
|
{
|
||||||
|
return mCollider;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Alinea el circulo de colisión con la posición del objeto globo
|
||||||
|
void Balloon::shiftColliders()
|
||||||
|
{
|
||||||
|
// Align collider to center of balloon
|
||||||
|
mCollider.x = Uint16(mPosX + mCollider.r);
|
||||||
|
mCollider.y = mPosY + mCollider.r;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene le valor de la variable
|
||||||
|
Uint8 Balloon::getMenace()
|
||||||
|
{
|
||||||
|
return mMenace;
|
||||||
|
}
|
||||||
185
source/balloon.h
Normal file
@@ -0,0 +1,185 @@
|
|||||||
|
#pragma once
|
||||||
|
#include "struct.h"
|
||||||
|
#include "animatedsprite.h"
|
||||||
|
|
||||||
|
#ifndef BALLOON_H
|
||||||
|
#define BALLOON_H
|
||||||
|
|
||||||
|
// Clase globo
|
||||||
|
class Balloon
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
// Constructor
|
||||||
|
Balloon();
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
~Balloon();
|
||||||
|
|
||||||
|
// Inicializador
|
||||||
|
void init(float x, int y, Uint8 kind, float velx, Uint16 creationtimer, LTexture* texture, SDL_Renderer *renderer);
|
||||||
|
|
||||||
|
// Centra el globo en la posición X
|
||||||
|
void allignTo(int x);
|
||||||
|
|
||||||
|
// Pinta el globo en la pantalla
|
||||||
|
void render();
|
||||||
|
|
||||||
|
// Actualiza la posición y estados del globo
|
||||||
|
void move();
|
||||||
|
|
||||||
|
// Pone a cero todos los valores del globo
|
||||||
|
void erase();
|
||||||
|
|
||||||
|
// Explosiona el globo
|
||||||
|
void pop();
|
||||||
|
|
||||||
|
// Actualiza al globo a su posicion, animación y controla los contadores
|
||||||
|
void update();
|
||||||
|
|
||||||
|
// Establece la animación correspondiente
|
||||||
|
void setAnimation();
|
||||||
|
|
||||||
|
// Comprueba si el globo tiene algun tipo asignado
|
||||||
|
bool isActive();
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
int getPosX();
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
int getPosY();
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
float getVelY();
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
int getWidth();
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
int getHeight();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setVelY(float velY);
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
int getKind();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setStop(bool state);
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
bool isStopped();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setBlink(bool state);
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
bool isBlinking();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setVisible(bool state);
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
bool isVisible();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setInvulnerable(bool state);
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
bool isInvulnerable();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setBeingCreated(bool state);
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
bool isBeingCreated();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setPopping(bool state);
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
bool isPopping();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setTimeToLive(Uint16 time);
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
Uint16 getTimeToLive();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setStoppedTimer(Uint16 time);
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
Uint16 getStoppedTimer();
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
Uint16 getScore();
|
||||||
|
|
||||||
|
// Obtiene el circulo de colisión
|
||||||
|
Circle &getCollider();
|
||||||
|
|
||||||
|
// Obtiene le valor de la variable
|
||||||
|
Uint8 getMenace();
|
||||||
|
|
||||||
|
private:
|
||||||
|
// Posición X,Y del objeto globo
|
||||||
|
float mPosX;
|
||||||
|
int mPosY;
|
||||||
|
|
||||||
|
// Alto y ancho del objeto globo
|
||||||
|
Uint8 mWidth;
|
||||||
|
Uint8 mHeight;
|
||||||
|
|
||||||
|
// Variables para controlar la velocidad del globo
|
||||||
|
float mVelX;
|
||||||
|
float mVelY;
|
||||||
|
float mGravity;
|
||||||
|
float mDefaultVelY;
|
||||||
|
int mMaxVelY;
|
||||||
|
|
||||||
|
// Puntos que da el globo al ser destruido
|
||||||
|
Uint16 mScore;
|
||||||
|
|
||||||
|
// Nivel de amenaza del globo
|
||||||
|
Uint8 mMenace;
|
||||||
|
|
||||||
|
// Indica si el globo está parado
|
||||||
|
bool mStopped;
|
||||||
|
|
||||||
|
// Temporizador para controlar el estado "parado"
|
||||||
|
Uint16 mStoppedTimer;
|
||||||
|
|
||||||
|
// Indica si el globo está intermitente
|
||||||
|
bool mBlinking;
|
||||||
|
|
||||||
|
// Indica si el globo es visible
|
||||||
|
bool mVisible;
|
||||||
|
|
||||||
|
// Indica si el globo es invulnerable
|
||||||
|
bool mInvulnerable;
|
||||||
|
|
||||||
|
// Indica si el globo se está creando
|
||||||
|
bool mBeingCreated;
|
||||||
|
|
||||||
|
// Indica si el globo está explotando
|
||||||
|
bool mPopping;
|
||||||
|
|
||||||
|
// Indica el tiempo de vida que le queda al globo
|
||||||
|
Uint16 mTimeToLive;
|
||||||
|
|
||||||
|
// Temporizador para controlar el estado "creandose"
|
||||||
|
Uint16 mCreationTimer;
|
||||||
|
|
||||||
|
// Tipo de globo
|
||||||
|
Uint8 mKind;
|
||||||
|
|
||||||
|
// Sprite del objeto globo
|
||||||
|
AnimatedSprite *mSprite;
|
||||||
|
|
||||||
|
// Circulo de colisión del objeto
|
||||||
|
Circle mCollider;
|
||||||
|
|
||||||
|
// Alinea el circulo de colisión con la posición del objeto globo
|
||||||
|
void shiftColliders();
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
213
source/bullet.cpp
Normal file
@@ -0,0 +1,213 @@
|
|||||||
|
#include "const.h"
|
||||||
|
#include "bullet.h"
|
||||||
|
|
||||||
|
// Constructor
|
||||||
|
Bullet::Bullet()
|
||||||
|
{
|
||||||
|
mSprite = new Sprite();
|
||||||
|
init(0, 0, NO_KIND, nullptr, nullptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
Bullet::~Bullet()
|
||||||
|
{
|
||||||
|
init(0, 0, NO_KIND, nullptr, nullptr);
|
||||||
|
delete mSprite;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Iniciador
|
||||||
|
void Bullet::init(int x, int y, int kind, LTexture *texture, SDL_Renderer *renderer)
|
||||||
|
{
|
||||||
|
// Posición inicial del objeto
|
||||||
|
mPosX = x;
|
||||||
|
mPosY = y;
|
||||||
|
|
||||||
|
// Alto y ancho del objeto
|
||||||
|
mWidth = 10;
|
||||||
|
mHeight = mWidth;
|
||||||
|
|
||||||
|
// Velocidad inicial en el eje Y
|
||||||
|
mVelY = -3;
|
||||||
|
|
||||||
|
// Tipo de bala
|
||||||
|
mKind = kind;
|
||||||
|
|
||||||
|
// Textura con los gráficos del objeto
|
||||||
|
mSprite->setTexture(texture);
|
||||||
|
|
||||||
|
// Renderizador
|
||||||
|
mSprite->setRenderer(renderer);
|
||||||
|
|
||||||
|
// Alto y ancho del sprite
|
||||||
|
mSprite->setWidth(mWidth);
|
||||||
|
mSprite->setHeight(mHeight);
|
||||||
|
|
||||||
|
// Posición inicial del sprite
|
||||||
|
mSprite->setPosX(mPosX);
|
||||||
|
mSprite->setPosY(mPosY);
|
||||||
|
|
||||||
|
// Valores especificos según el tipo
|
||||||
|
switch (kind)
|
||||||
|
{
|
||||||
|
case BULLET_UP:
|
||||||
|
// Establece la velocidad inicial
|
||||||
|
mVelX = 0;
|
||||||
|
|
||||||
|
// Rectangulo con los gráficos del objeto
|
||||||
|
mSprite->setSpriteClip(0 * mWidth, 0, mSprite->getWidth(), mSprite->getHeight());
|
||||||
|
break;
|
||||||
|
|
||||||
|
case BULLET_LEFT:
|
||||||
|
// Establece la velocidad inicial
|
||||||
|
mVelX = -2;
|
||||||
|
|
||||||
|
// Rectangulo con los gráficos del objeto
|
||||||
|
mSprite->setSpriteClip(1 * mWidth, 0, mSprite->getWidth(), mSprite->getHeight());
|
||||||
|
break;
|
||||||
|
|
||||||
|
case BULLET_RIGHT:
|
||||||
|
// Establece la velocidad inicial
|
||||||
|
mVelX = 2;
|
||||||
|
|
||||||
|
// Rectangulo con los gráficos del objeto
|
||||||
|
mSprite->setSpriteClip(2 * mWidth, 0, mSprite->getWidth(), mSprite->getHeight());
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el tamaño del circulo de colisión
|
||||||
|
mCollider.r = mWidth / 2;
|
||||||
|
|
||||||
|
// Alinea el circulo de colisión con el objeto
|
||||||
|
shiftColliders();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Pinta el objeto en pantalla
|
||||||
|
void Bullet::render()
|
||||||
|
{
|
||||||
|
mSprite->render();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actualiza la posición y estado del objeto en horizontal
|
||||||
|
Uint8 Bullet::move()
|
||||||
|
{
|
||||||
|
// Variable con el valor de retorno
|
||||||
|
Uint8 msg = MSG_OK;
|
||||||
|
|
||||||
|
// Mueve el objeto a su nueva posición
|
||||||
|
mPosX += mVelX;
|
||||||
|
|
||||||
|
// Si el objeto se sale del area de juego por los laterales
|
||||||
|
if ((mPosX < PLAY_AREA_LEFT) || (mPosX + mWidth > PLAY_AREA_RIGHT))
|
||||||
|
{
|
||||||
|
// Se deshabilita
|
||||||
|
mKind = NO_KIND;
|
||||||
|
|
||||||
|
// Mensaje de salida
|
||||||
|
msg = MSG_BULLET_OUT;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Mueve el objeto a su nueva posición en vertical
|
||||||
|
mPosY += int(mVelY);
|
||||||
|
|
||||||
|
// Si el objeto se sale del area de juego por la parte superior o inferior
|
||||||
|
if ((mPosY < PLAY_AREA_TOP) || (mPosY + mHeight > PLAY_AREA_BOTTOM))
|
||||||
|
{
|
||||||
|
// Se deshabilita
|
||||||
|
mKind = NO_KIND;
|
||||||
|
|
||||||
|
// Mensaje de salida
|
||||||
|
msg = MSG_BULLET_OUT;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actualiza la posición del sprite
|
||||||
|
mSprite->setPosX(mPosX);
|
||||||
|
mSprite->setPosY(mPosY);
|
||||||
|
|
||||||
|
// Alinea el circulo de colisión con el objeto
|
||||||
|
shiftColliders();
|
||||||
|
|
||||||
|
return msg;
|
||||||
|
}
|
||||||
|
|
||||||
|
#ifdef TEST
|
||||||
|
void Bullet::testMove()
|
||||||
|
{
|
||||||
|
// Update sprite position
|
||||||
|
mSprite->setPosX(mPosX);
|
||||||
|
mSprite->setPosY(mPosY);
|
||||||
|
|
||||||
|
// Update circle colliders
|
||||||
|
shiftColliders();
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// Deshabilita el objeto
|
||||||
|
void Bullet::erase()
|
||||||
|
{
|
||||||
|
init(0, 0, 0, nullptr, nullptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Comprueba si el objeto está activo
|
||||||
|
bool Bullet::isActive()
|
||||||
|
{
|
||||||
|
if (mKind == NO_KIND)
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
int Bullet::getPosX()
|
||||||
|
{
|
||||||
|
return mPosX;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
int Bullet::getPosY()
|
||||||
|
{
|
||||||
|
return mPosY;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Bullet::setPosX(int x)
|
||||||
|
{
|
||||||
|
mPosX = x;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Bullet::setPosY(int y)
|
||||||
|
{
|
||||||
|
mPosY = y;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
int Bullet::getVelY()
|
||||||
|
{
|
||||||
|
return mVelY;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
int Bullet::getKind()
|
||||||
|
{
|
||||||
|
return mKind;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el circulo de colisión
|
||||||
|
Circle &Bullet::getCollider()
|
||||||
|
{
|
||||||
|
return mCollider;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Alinea el circulo de colisión con el objeto
|
||||||
|
void Bullet::shiftColliders()
|
||||||
|
{
|
||||||
|
mCollider.x = mPosX + mCollider.r;
|
||||||
|
mCollider.y = mPosY + mCollider.r;
|
||||||
|
}
|
||||||
80
source/bullet.h
Normal file
@@ -0,0 +1,80 @@
|
|||||||
|
#pragma once
|
||||||
|
#include "struct.h"
|
||||||
|
#include "sprite.h"
|
||||||
|
|
||||||
|
#ifndef BULLET_H
|
||||||
|
#define BULLET_H
|
||||||
|
|
||||||
|
// Clase bala
|
||||||
|
class Bullet
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
// Constructor
|
||||||
|
Bullet();
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
~Bullet();
|
||||||
|
|
||||||
|
// Iniciador
|
||||||
|
void init(int x, int y, int kind, LTexture* texture, SDL_Renderer *renderer);
|
||||||
|
|
||||||
|
// Pinta el objeto en pantalla
|
||||||
|
void render();
|
||||||
|
|
||||||
|
// Actualiza la posición y estado del objeto
|
||||||
|
Uint8 move();
|
||||||
|
|
||||||
|
// Deshabilita el objeto
|
||||||
|
void erase();
|
||||||
|
|
||||||
|
// Comprueba si el objeto está activo
|
||||||
|
bool isActive();
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
int getPosX();
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
int getPosY();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setPosX(int x);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setPosY(int y);
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
int getVelY();
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
int getKind();
|
||||||
|
|
||||||
|
// Obtiene el circulo de colisión
|
||||||
|
Circle &getCollider();
|
||||||
|
|
||||||
|
private:
|
||||||
|
// Posición X/Y del objeto
|
||||||
|
int mPosX;
|
||||||
|
int mPosY;
|
||||||
|
|
||||||
|
// Alto y ancho el objeto
|
||||||
|
Uint8 mWidth;
|
||||||
|
Uint8 mHeight;
|
||||||
|
|
||||||
|
// Velocidad del objeto
|
||||||
|
int mVelX;
|
||||||
|
int mVelY;
|
||||||
|
|
||||||
|
// Tipo de objeto
|
||||||
|
int mKind;
|
||||||
|
|
||||||
|
// Sprite con los graficos y métodos de pintado
|
||||||
|
Sprite *mSprite;
|
||||||
|
|
||||||
|
// Balloon's collision circle
|
||||||
|
Circle mCollider;
|
||||||
|
|
||||||
|
// Alinea el circulo de colisión con el objeto
|
||||||
|
void shiftColliders();
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
282
source/const.h
Normal file
@@ -0,0 +1,282 @@
|
|||||||
|
#pragma once
|
||||||
|
#include "ifdefs.h"
|
||||||
|
#include <string>
|
||||||
|
|
||||||
|
#ifndef CONST_H
|
||||||
|
#define CONST_H
|
||||||
|
|
||||||
|
// Textos
|
||||||
|
#define WINDOW_CAPTION "Coffee Crisis"
|
||||||
|
#define TEXT_COPYRIGHT "@2020,2021 JAILDESIGNER (V1.3*)"
|
||||||
|
|
||||||
|
// Recursos
|
||||||
|
const Uint8 BINFILE_SCORE = 0;
|
||||||
|
const Uint8 BINFILE_DEMO = 1;
|
||||||
|
const Uint8 BINFILE_CONFIG = 2;
|
||||||
|
|
||||||
|
const Uint8 TOTAL_BINFILE = 3;
|
||||||
|
|
||||||
|
const Uint8 MUSIC_INTRO = 0;
|
||||||
|
const Uint8 MUSIC_PLAYING = 1;
|
||||||
|
const Uint8 MUSIC_TITLE = 2;
|
||||||
|
|
||||||
|
const Uint8 TOTAL_MUSIC = 3;
|
||||||
|
|
||||||
|
const Uint8 SOUND_BALLON = 0;
|
||||||
|
const Uint8 SOUND_BULLET = 1;
|
||||||
|
const Uint8 SOUND_MENU_SELECT = 2;
|
||||||
|
const Uint8 SOUND_MENU_CANCEL = 3;
|
||||||
|
const Uint8 SOUND_MENU_MOVE = 4;
|
||||||
|
const Uint8 SOUND_TITLE = 5;
|
||||||
|
const Uint8 SOUND_PLAYER_COLLISION = 6;
|
||||||
|
const Uint8 SOUND_HISCORE = 7;
|
||||||
|
const Uint8 SOUND_ITEM_DROP = 8;
|
||||||
|
const Uint8 SOUND_ITEM_PICKUP = 9;
|
||||||
|
const Uint8 SOUND_COFFEE_OUT = 10;
|
||||||
|
const Uint8 SOUND_STAGE_CHANGE = 11;
|
||||||
|
const Uint8 SOUND_BUBBLE1 = 12;
|
||||||
|
const Uint8 SOUND_BUBBLE2 = 13;
|
||||||
|
const Uint8 SOUND_BUBBLE3 = 14;
|
||||||
|
const Uint8 SOUND_BUBBLE4 = 15;
|
||||||
|
|
||||||
|
const Uint8 TOTAL_SOUND = 16;
|
||||||
|
|
||||||
|
const Uint8 TEXTURE_BALLOON = 0;
|
||||||
|
const Uint8 TEXTURE_BULLET = 1;
|
||||||
|
const Uint8 TEXTURE_FONT_BLACK = 2;
|
||||||
|
const Uint8 TEXTURE_FONT_NOKIA = 3;
|
||||||
|
const Uint8 TEXTURE_FONT_WHITE = 4;
|
||||||
|
const Uint8 TEXTURE_GAME_BG = 5;
|
||||||
|
const Uint8 TEXTURE_GAME_TEXT = 6;
|
||||||
|
const Uint8 TEXTURE_INTRO = 7;
|
||||||
|
const Uint8 TEXTURE_ITEMS = 8;
|
||||||
|
const Uint8 TEXTURE_LOGO = 9;
|
||||||
|
const Uint8 TEXTURE_MENU = 10;
|
||||||
|
const Uint8 TEXTURE_PLAYER_BODY = 11;
|
||||||
|
const Uint8 TEXTURE_PLAYER_LEGS = 12;
|
||||||
|
const Uint8 TEXTURE_PLAYER_DEATH = 13;
|
||||||
|
const Uint8 TEXTURE_TITLE = 14;
|
||||||
|
|
||||||
|
const Uint8 TOTAL_TEXTURE = 15;
|
||||||
|
|
||||||
|
// Tamaño de bloque
|
||||||
|
const Uint8 BLOCK = 8;
|
||||||
|
const Uint8 HALF_BLOCK = BLOCK / 2;
|
||||||
|
|
||||||
|
// Tamaño de la pantalla real
|
||||||
|
const int SCREEN_WIDTH = 256;
|
||||||
|
const int SCREEN_HEIGHT = SCREEN_WIDTH * 3 / 4; // 192
|
||||||
|
|
||||||
|
// Tamaño de la pantalla que se muestra
|
||||||
|
const int VIEW_WIDTH = SCREEN_WIDTH * 3; // 768
|
||||||
|
const int VIEW_HEIGHT = SCREEN_HEIGHT * 3; // 576
|
||||||
|
|
||||||
|
// Cantidad de enteros a escribir en los ficheros de datos
|
||||||
|
const Uint8 TOTAL_SCORE_DATA = 3;
|
||||||
|
const Uint16 TOTAL_DEMO_DATA = 2000;
|
||||||
|
|
||||||
|
// Zona de juego
|
||||||
|
const int PLAY_AREA_TOP = (0 * BLOCK);
|
||||||
|
const int PLAY_AREA_BOTTOM = SCREEN_HEIGHT - (4 * BLOCK);
|
||||||
|
const int PLAY_AREA_LEFT = (0 * BLOCK);
|
||||||
|
const int PLAY_AREA_RIGHT = SCREEN_WIDTH - (0 * BLOCK);
|
||||||
|
const int PLAY_AREA_WIDTH = PLAY_AREA_RIGHT - PLAY_AREA_LEFT;
|
||||||
|
const int PLAY_AREA_HEIGHT = PLAY_AREA_BOTTOM - PLAY_AREA_TOP;
|
||||||
|
const int PLAY_AREA_CENTER_X = PLAY_AREA_LEFT + (PLAY_AREA_WIDTH / 2);
|
||||||
|
const int PLAY_AREA_CENTER_Y = PLAY_AREA_TOP + (PLAY_AREA_HEIGHT / 2);
|
||||||
|
const int PLAY_AREA_FIRST_QUARTER_Y = PLAY_AREA_HEIGHT / 4;
|
||||||
|
const int PLAY_AREA_THIRD_QUARTER_Y = (PLAY_AREA_HEIGHT / 4) * 3;
|
||||||
|
|
||||||
|
// Anclajes de pantalla
|
||||||
|
const int SCREEN_CENTER_X = SCREEN_WIDTH / 2;
|
||||||
|
const int SCREEN_FIRST_QUARTER_X = SCREEN_WIDTH / 4;
|
||||||
|
const int SCREEN_THIRD_QUARTER_X = (SCREEN_WIDTH / 4) * 3;
|
||||||
|
const int SCREEN_CENTER_Y = SCREEN_HEIGHT / 2;
|
||||||
|
const int SCREEN_FIRST_QUARTER_Y = SCREEN_HEIGHT / 4;
|
||||||
|
const int SCREEN_THIRD_QUARTER_Y = (SCREEN_HEIGHT / 4) * 3;
|
||||||
|
|
||||||
|
// Color transparente para los sprites
|
||||||
|
const Uint8 COLOR_KEY_R = 0xff;
|
||||||
|
const Uint8 COLOR_KEY_G = 0x00;
|
||||||
|
const Uint8 COLOR_KEY_B = 0xff;
|
||||||
|
|
||||||
|
// Opciones de menu
|
||||||
|
const int MENU_NO_OPTION = -1;
|
||||||
|
const int MENU_OPTION_START = 0;
|
||||||
|
const int MENU_OPTION_QUIT = 1;
|
||||||
|
const int MENU_OPTION_TOTAL = 2;
|
||||||
|
|
||||||
|
// Selector de menu
|
||||||
|
const int MENU_SELECTOR_BLACK = (BLOCK * 0);
|
||||||
|
const int MENU_SELECTOR_WHITE = (BLOCK * 1);
|
||||||
|
|
||||||
|
// Tipos de fondos para el menu
|
||||||
|
const int MENU_BACKGROUND_TRANSPARENT = 0;
|
||||||
|
const int MENU_BACKGROUND_SOLID = 1;
|
||||||
|
|
||||||
|
// Estados del jugador
|
||||||
|
const Uint8 PLAYER_STATUS_WALKING_LEFT = 0;
|
||||||
|
const Uint8 PLAYER_STATUS_WALKING_RIGHT = 1;
|
||||||
|
const Uint8 PLAYER_STATUS_WALKING_STOP = 2;
|
||||||
|
|
||||||
|
const Uint8 PLAYER_STATUS_FIRING_UP = 0;
|
||||||
|
const Uint8 PLAYER_STATUS_FIRING_LEFT = 1;
|
||||||
|
const Uint8 PLAYER_STATUS_FIRING_RIGHT = 2;
|
||||||
|
const Uint8 PLAYER_STATUS_FIRING_NO = 3;
|
||||||
|
|
||||||
|
const Uint8 PLAYER_ANIMATION_LEGS_WALKING_LEFT = 0;
|
||||||
|
const Uint8 PLAYER_ANIMATION_LEGS_WALKING_RIGHT = 1;
|
||||||
|
const Uint8 PLAYER_ANIMATION_LEGS_WALKING_STOP = 2;
|
||||||
|
|
||||||
|
const Uint8 PLAYER_ANIMATION_BODY_WALKING_LEFT = 0;
|
||||||
|
const Uint8 PLAYER_ANIMATION_BODY_FIRING_LEFT = 1;
|
||||||
|
const Uint8 PLAYER_ANIMATION_BODY_WALKING_RIGHT = 2;
|
||||||
|
const Uint8 PLAYER_ANIMATION_BODY_FIRING_RIGHT = 3;
|
||||||
|
const Uint8 PLAYER_ANIMATION_BODY_WALKING_STOP = 4;
|
||||||
|
const Uint8 PLAYER_ANIMATION_BODY_FIRING_UP = 5;
|
||||||
|
const Uint8 PLAYER_ANIMATION_BODY_WALKING_LEFT_EXTRA_HIT = 6;
|
||||||
|
const Uint8 PLAYER_ANIMATION_BODY_FIRING_LEFT_EXTRA_HIT = 7;
|
||||||
|
const Uint8 PLAYER_ANIMATION_BODY_WALKING_RIGHT_EXTRA_HIT = 8;
|
||||||
|
const Uint8 PLAYER_ANIMATION_BODY_FIRING_RIGHT_EXTRA_HIT = 9;
|
||||||
|
const Uint8 PLAYER_ANIMATION_BODY_WALKING_STOP_EXTRA_HIT = 10;
|
||||||
|
const Uint8 PLAYER_ANIMATION_BODY_FIRING_UP_EXTRA_HIT = 11;
|
||||||
|
|
||||||
|
// Variables del jugador
|
||||||
|
const Uint16 PLAYER_INVULNERABLE_TIMER = 200;
|
||||||
|
|
||||||
|
// Estados del juego
|
||||||
|
const Uint8 GAME_STATE_TITLE = 0;
|
||||||
|
const Uint8 GAME_STATE_PLAYING = 1;
|
||||||
|
const Uint8 GAME_STATE_QUIT = 2;
|
||||||
|
const Uint8 GAME_STATE_GAME_OVER_SCREEN = 3;
|
||||||
|
const Uint8 GAME_STATE_INTRO = 4;
|
||||||
|
const Uint8 GAME_STATE_DEMO = 5;
|
||||||
|
const Uint8 GAME_STATE_INSTRUCTIONS = 6;
|
||||||
|
const Uint8 GAME_STATE_LOGO = 7;
|
||||||
|
const Uint8 GAME_STATE_INIT = 8;
|
||||||
|
|
||||||
|
// Estados de cada elemento que pertenece a un evento
|
||||||
|
const Uint8 EVENT_WAITING = 1;
|
||||||
|
const Uint8 EVENT_RUNNING = 2;
|
||||||
|
const Uint8 EVENT_COMPLETED = 3;
|
||||||
|
|
||||||
|
// Cantidad de eventos de la intro
|
||||||
|
const Uint8 INTRO_TOTAL_BITMAPS = 6;
|
||||||
|
const Uint8 INTRO_TOTAL_TEXTS = 9;
|
||||||
|
const Uint8 INTRO_TOTAL_EVENTS = INTRO_TOTAL_BITMAPS + INTRO_TOTAL_TEXTS;
|
||||||
|
|
||||||
|
// Cantidad de eventos de la pantalla de titulo
|
||||||
|
const Uint8 TITLE_TOTAL_EVENTS = 2;
|
||||||
|
|
||||||
|
// Relaciones de Id con nomnbres
|
||||||
|
const Uint8 BITMAP0 = 0;
|
||||||
|
const Uint8 BITMAP1 = 1;
|
||||||
|
const Uint8 BITMAP2 = 2;
|
||||||
|
const Uint8 BITMAP3 = 3;
|
||||||
|
const Uint8 BITMAP4 = 4;
|
||||||
|
const Uint8 BITMAP5 = 5;
|
||||||
|
const Uint8 TEXT0 = 6;
|
||||||
|
const Uint8 TEXT1 = 7;
|
||||||
|
const Uint8 TEXT2 = 8;
|
||||||
|
const Uint8 TEXT3 = 9;
|
||||||
|
const Uint8 TEXT4 = 10;
|
||||||
|
const Uint8 TEXT5 = 11;
|
||||||
|
const Uint8 TEXT6 = 12;
|
||||||
|
const Uint8 TEXT7 = 13;
|
||||||
|
const Uint8 TEXT8 = 14;
|
||||||
|
|
||||||
|
// Anclajes para el marcador de puntos
|
||||||
|
const int SCORE_WORD_X = (SCREEN_WIDTH / 4) - ((5 * BLOCK) / 2);
|
||||||
|
const int SCORE_WORD_Y = SCREEN_HEIGHT - (3 * BLOCK) + 2;
|
||||||
|
const int SCORE_NUMBER_X = (SCREEN_WIDTH / 4) - ((6 * BLOCK) / 2);
|
||||||
|
const int SCORE_NUMBER_Y = SCREEN_HEIGHT - (2 * BLOCK) + 2;
|
||||||
|
|
||||||
|
const int HISCORE_WORD_X = ((SCREEN_WIDTH / 4) * 3) - ((8 * BLOCK) / 2);
|
||||||
|
const int HISCORE_WORD_Y = SCREEN_HEIGHT - (3 * BLOCK) + 2;
|
||||||
|
const int HISCORE_NUMBER_X = ((SCREEN_WIDTH / 4) * 3) - ((6 * BLOCK) / 2);
|
||||||
|
const int HISCORE_NUMBER_Y = SCREEN_HEIGHT - (2 * BLOCK) + 2;
|
||||||
|
|
||||||
|
const int MULTIPLIER_WORD_X = (SCREEN_WIDTH / 2) - ((4 * BLOCK) / 2);
|
||||||
|
const int MULTIPLIER_WORD_Y = SCREEN_HEIGHT - (3 * BLOCK) + 2;
|
||||||
|
const int MULTIPLIER_NUMBER_X = (SCREEN_WIDTH / 2) - ((3 * BLOCK) / 2);;
|
||||||
|
const int MULTIPLIER_NUMBER_Y = SCREEN_HEIGHT - (2 * BLOCK) + 2;
|
||||||
|
|
||||||
|
// Ningun tipo
|
||||||
|
const Uint8 NO_KIND = 0;
|
||||||
|
|
||||||
|
// Tipos de globo
|
||||||
|
const Uint8 BALLOON_1 = 1;
|
||||||
|
const Uint8 BALLOON_2 = 2;
|
||||||
|
const Uint8 BALLOON_3 = 3;
|
||||||
|
const Uint8 BALLOON_4 = 4;
|
||||||
|
|
||||||
|
// Velocidad del globo
|
||||||
|
const float BALLON_VELX_POSITIVE = 0.7f;
|
||||||
|
const float BALLON_VELX_NEGATIVE = -0.7f;
|
||||||
|
|
||||||
|
// Indice para las animaciones de los globos
|
||||||
|
const Uint8 BALLOON_MOVING_ANIMATION = 0;
|
||||||
|
const Uint8 BALLOON_POP_ANIMATION = 1;
|
||||||
|
const Uint8 BALLOON_BORN_ANIMATION = 2;
|
||||||
|
|
||||||
|
// Cantidad posible de globos
|
||||||
|
const Uint8 MAX_BALLOONS = 75;
|
||||||
|
|
||||||
|
// Tipos de bala
|
||||||
|
const Uint8 BULLET_UP = 1;
|
||||||
|
const Uint8 BULLET_LEFT = 2;
|
||||||
|
const Uint8 BULLET_RIGHT = 3;
|
||||||
|
|
||||||
|
// Cantidad posible de globos
|
||||||
|
const Uint8 MAX_BULLETS = 50;
|
||||||
|
|
||||||
|
// Tipos de objetos
|
||||||
|
const Uint8 ITEM_POINTS_1_DISK = 1;
|
||||||
|
const Uint8 ITEM_POINTS_2_GAVINA = 2;
|
||||||
|
const Uint8 ITEM_POINTS_3_PACMAR = 3;
|
||||||
|
const Uint8 ITEM_CLOCK = 4;
|
||||||
|
const Uint8 ITEM_TNT = 5;
|
||||||
|
const Uint8 ITEM_COFFEE = 6;
|
||||||
|
|
||||||
|
// Cantidad de objetos simultaneos
|
||||||
|
const Uint8 MAX_ITEMS = 5;
|
||||||
|
|
||||||
|
// Valores para las variables asociadas a los objetos
|
||||||
|
const Uint8 REMAINING_EXPLOSIONS = 3;
|
||||||
|
const Uint8 REMAINING_EXPLOSIONS_TIMER = 50;
|
||||||
|
const Uint16 TIME_STOPPED_TIMER = 300;
|
||||||
|
|
||||||
|
// Estados de entrada
|
||||||
|
const Uint8 NO_INPUT = 0;
|
||||||
|
const Uint8 INPUT_UP = 1;
|
||||||
|
const Uint8 INPUT_DOWN = 2;
|
||||||
|
const Uint8 INPUT_LEFT = 3;
|
||||||
|
const Uint8 INPUT_RIGHT = 4;
|
||||||
|
const Uint8 INPUT_ACCEPT = 5;
|
||||||
|
const Uint8 INPUT_CANCEL = 6;
|
||||||
|
const Uint8 INPUT_FIRE_UP = 7;
|
||||||
|
const Uint8 INPUT_FIRE_LEFT = 8;
|
||||||
|
const Uint8 INPUT_FIRE_RIGHT = 9;
|
||||||
|
const Uint8 INPUT_PAUSE = 10;
|
||||||
|
|
||||||
|
// Zona muerta del mando analógico
|
||||||
|
const int JOYSTICK_DEAD_ZONE = 8000;
|
||||||
|
|
||||||
|
// Tipos de mensajes para el retorno de las funciones
|
||||||
|
const Uint8 MSG_OK = 0;
|
||||||
|
const Uint8 MSG_BULLET_OUT = 1;
|
||||||
|
|
||||||
|
// Tipos de texto
|
||||||
|
const Uint8 TEXT_FIXED = 0;
|
||||||
|
const Uint8 TEXT_VARIABLE = 1;
|
||||||
|
|
||||||
|
// Cantidad de elementos del vector de SmartSprites
|
||||||
|
const Uint8 MAX_SMART_SPRITES = 10;
|
||||||
|
|
||||||
|
// Contadores
|
||||||
|
const Uint16 TITLE_TIMER = 800;
|
||||||
|
const Uint8 STAGE_COUNTER = 200;
|
||||||
|
const Uint16 INSTRUCTIONS_COUNTER = 600;
|
||||||
|
const Uint16 DEATH_COUNTER = 350;
|
||||||
|
|
||||||
|
#endif
|
||||||
3950
source/gamedirector.cpp
Normal file
549
source/gamedirector.h
Normal file
@@ -0,0 +1,549 @@
|
|||||||
|
#pragma once
|
||||||
|
#include "ifdefs.h"
|
||||||
|
#include "sprite.h"
|
||||||
|
#include "movingsprite.h"
|
||||||
|
#include "smartsprite.h"
|
||||||
|
#include "player.h"
|
||||||
|
#include "balloon.h"
|
||||||
|
#include "bullet.h"
|
||||||
|
#include "item.h"
|
||||||
|
#include "text.h"
|
||||||
|
#include "text2.h"
|
||||||
|
#include "menu.h"
|
||||||
|
#include "const.h"
|
||||||
|
#include "jail_audio.h"
|
||||||
|
#include <math.h>
|
||||||
|
|
||||||
|
#ifndef GAMEDIRECTOR_H
|
||||||
|
#define GAMEDIRECTOR_H
|
||||||
|
|
||||||
|
// GameDirector
|
||||||
|
class GameDirector
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
// Constructor
|
||||||
|
GameDirector();
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
~GameDirector();
|
||||||
|
|
||||||
|
// Iniciador
|
||||||
|
void init(bool reset);
|
||||||
|
|
||||||
|
// Arranca SDL y crea la ventana
|
||||||
|
bool initSDL();
|
||||||
|
|
||||||
|
// Crea el indice de ficheros
|
||||||
|
void setFileList();
|
||||||
|
|
||||||
|
// Comprueba que todos los ficheros existen
|
||||||
|
bool checkFileList();
|
||||||
|
|
||||||
|
// Carga un archivo de imagen en una textura
|
||||||
|
bool loadTextureFromFile(LTexture *texture, std::string path, SDL_Renderer *renderer);
|
||||||
|
|
||||||
|
// Carga los recursos necesarios
|
||||||
|
bool loadMedia(Uint8 section);
|
||||||
|
|
||||||
|
// Descrga los recursos necesarios
|
||||||
|
bool unLoadMedia(Uint8 section);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setExecutablePath(std::string path);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setScore(Uint32 score);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setHiScore(Uint32 score);
|
||||||
|
|
||||||
|
// Actualiza el valor de HiScore en caso necesario
|
||||||
|
void updateHiScore();
|
||||||
|
|
||||||
|
// Transforma un valor numérico en una cadena de 6 cifras
|
||||||
|
std::string updateScoreText(Uint32 num);
|
||||||
|
|
||||||
|
// Pinta el marcador en pantalla usando un objeto texto
|
||||||
|
void renderScoreBoard();
|
||||||
|
|
||||||
|
// Actualiza el valor de la variable mStage
|
||||||
|
void updateStage();
|
||||||
|
|
||||||
|
// Actualiza el estado de muerte
|
||||||
|
void updateDeath();
|
||||||
|
|
||||||
|
// Renderiza el fade final cuando se acaba la partida
|
||||||
|
void renderDeathFade();
|
||||||
|
|
||||||
|
// Mueve todos los globos activos
|
||||||
|
void moveBalloons();
|
||||||
|
|
||||||
|
// Pinta en pantalla todos los globos activos
|
||||||
|
void renderBalloons();
|
||||||
|
|
||||||
|
// Devuelve el primer indice no activo del vector de globos
|
||||||
|
Uint8 getBallonFreeIndex();
|
||||||
|
|
||||||
|
// Crea un globo nuevo en el vector de globos
|
||||||
|
Uint8 createNewBalloon(float x, int y, Uint8 kind, float velx, Uint16 stoppedtimer, LTexture *texture);
|
||||||
|
|
||||||
|
// Establece a cero todos los valores del vector de objetos globo
|
||||||
|
void resetBalloons();
|
||||||
|
|
||||||
|
// Explosiona un globo. Lo destruye y crea otros dos si es el caso
|
||||||
|
void popBalloon(Uint8 index);
|
||||||
|
|
||||||
|
// Explosiona todos los globos
|
||||||
|
void popAllBallons();
|
||||||
|
|
||||||
|
// Detiene todos los globos
|
||||||
|
void stopAllBalloons(Uint16 time);
|
||||||
|
|
||||||
|
// Pone en marcha todos los globos
|
||||||
|
void startAllBalloons();
|
||||||
|
|
||||||
|
// Obtiene el numero de globos activos
|
||||||
|
Uint8 countBalloons();
|
||||||
|
|
||||||
|
// Comprueba la colisión entre el jugador y los globos activos
|
||||||
|
bool checkPlayerBallonCollision();
|
||||||
|
|
||||||
|
// Comprueba la colisión entre el jugador y los items
|
||||||
|
void checkPlayerItemCollision();
|
||||||
|
|
||||||
|
// Comprueba la colisión entre las balas y los globos
|
||||||
|
void checkBulletBallonCollision();
|
||||||
|
|
||||||
|
// Mueve las balas activas
|
||||||
|
void moveBullets();
|
||||||
|
|
||||||
|
// Pinta las balas activas
|
||||||
|
void renderBullets();
|
||||||
|
|
||||||
|
// Devuelve el primer indice no activo del vector de balas
|
||||||
|
Uint8 getBulletFreeIndex();
|
||||||
|
|
||||||
|
// Establece a cero todos los valores del vector de objetos bala
|
||||||
|
void resetBullets();
|
||||||
|
|
||||||
|
// Crea un objeto bala
|
||||||
|
void createBullet(int x, int y, Uint8 kind);
|
||||||
|
|
||||||
|
// Actualiza los items
|
||||||
|
void updateItems();
|
||||||
|
|
||||||
|
// Pinta los items activos
|
||||||
|
void renderItems();
|
||||||
|
|
||||||
|
// Devuelve el primer indice no activo del vector de items
|
||||||
|
Uint8 getItemFreeIndex();
|
||||||
|
|
||||||
|
// Establece a cero todos los valores del vector de objetos item
|
||||||
|
void resetItems();
|
||||||
|
|
||||||
|
// Devuelve un item en función del azar
|
||||||
|
Uint8 dropItem();
|
||||||
|
|
||||||
|
// Crea un objeto item
|
||||||
|
void createItem(int x, int y, Uint8 kind);
|
||||||
|
|
||||||
|
// Crea un objeto SmartSprite
|
||||||
|
void createItemScoreSprite(int x, int y, SmartSprite *sprite);
|
||||||
|
|
||||||
|
// Crea un SmartSprite para arrojar el item café al recibir un impacto
|
||||||
|
void throwCoffee(int x, int y);
|
||||||
|
|
||||||
|
// Crea un SmartSprite para arrojar al jugador al morir
|
||||||
|
void throwPlayer(int x, int y);
|
||||||
|
|
||||||
|
// Actualiza los SmartSprites
|
||||||
|
void updateSmartSprites();
|
||||||
|
|
||||||
|
// Pinta los SmartSprites activos
|
||||||
|
void renderSmartSprites();
|
||||||
|
|
||||||
|
// Devuelve el primer indice no activo del vector de SmartSprites
|
||||||
|
Uint8 getSmartSpriteFreeIndex();
|
||||||
|
|
||||||
|
// Establece a cero todos los valores del vector de objetos SmafrtSprite
|
||||||
|
void resetSmartSprites();
|
||||||
|
|
||||||
|
// Acciones a realizar cuando el jugador muere
|
||||||
|
void killPlayer();
|
||||||
|
|
||||||
|
// Calcula y establece el valor de amenaza en funcion de los globos activos
|
||||||
|
void calculateMenaceLevel();
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
Uint8 getMenaceLevel();
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
bool isPlayFieldDrawOnly();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setPlayFieldDrawOnly(bool state);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setTimeStopped(bool value);
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
bool isTimeStopped();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setTimeStoppedTimer(Uint16 value);
|
||||||
|
|
||||||
|
// Actualiza y comprueba el valor de la variable
|
||||||
|
void updateTimeStoppedTimer();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setExplosionTime(bool value);
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
bool isExplosionTime();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setRemainingExplosions(Uint8 value);
|
||||||
|
|
||||||
|
// Actualiza y comprueba el valor de la variable
|
||||||
|
void updateRemainingExplosionsTimer();
|
||||||
|
|
||||||
|
// Gestiona el nivel de amenaza
|
||||||
|
void checkMenaceLevel();
|
||||||
|
|
||||||
|
// Actualiza el campo de juego
|
||||||
|
void updatePlayField();
|
||||||
|
|
||||||
|
// Actualiza el fondo
|
||||||
|
void updateBackground();
|
||||||
|
|
||||||
|
// Dibuja el fondo
|
||||||
|
void renderBackground();
|
||||||
|
|
||||||
|
// Dibuja el campo de juego
|
||||||
|
void renderPlayField();
|
||||||
|
|
||||||
|
// Gestiona las entradas desde el mando de juego
|
||||||
|
bool checkGameController(Uint8 state);
|
||||||
|
|
||||||
|
// Gestiona la entrada durante el juego
|
||||||
|
void checkGameInput();
|
||||||
|
|
||||||
|
// Gestiona la entrada de teclado y mando durante el menu
|
||||||
|
void checkMenuInput(Menu *menu);
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
Uint8 getGameStatus();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setGameStatus(Uint8 status);
|
||||||
|
|
||||||
|
// Pinta una transición en pantalla
|
||||||
|
void renderFade(Uint8 index);
|
||||||
|
|
||||||
|
// Pinta diferentes mensajes en la pantalla
|
||||||
|
void renderMessages();
|
||||||
|
|
||||||
|
// Habilita el efecto del item de detener el tiempo
|
||||||
|
void enableTimeStopItem();
|
||||||
|
|
||||||
|
// Deshabilita el efecto del item de detener el tiempo
|
||||||
|
void disableTimeStopItem();
|
||||||
|
|
||||||
|
// Cambia el valor de la variable de modo de pantalla completa
|
||||||
|
void changeFullScreenMode();
|
||||||
|
|
||||||
|
// Actualiza los elementos del menu de opciones
|
||||||
|
void updateOptionsMenu();
|
||||||
|
|
||||||
|
// Agita la pantalla
|
||||||
|
void shakeScreen();
|
||||||
|
|
||||||
|
// Bucle para el logo del juego
|
||||||
|
void runLogo();
|
||||||
|
|
||||||
|
// Bucle para la intro del juego
|
||||||
|
void runIntro();
|
||||||
|
|
||||||
|
// Bucle para el titulo del juego
|
||||||
|
void runTitle();
|
||||||
|
|
||||||
|
// Bucle para el juego
|
||||||
|
void runGame();
|
||||||
|
|
||||||
|
// Bucle para el menu de pausa del juego
|
||||||
|
void runPausedGame();
|
||||||
|
|
||||||
|
// Bucle para la pantalla de instrucciones
|
||||||
|
void runInstructions();
|
||||||
|
|
||||||
|
// Bucle para la pantalla de game over
|
||||||
|
void runGameOverScreen();
|
||||||
|
|
||||||
|
// Dibuja la informacion de debug en pantalla
|
||||||
|
void renderDebugInfo();
|
||||||
|
|
||||||
|
// Activa el modo Demo
|
||||||
|
void enableDemoMode();
|
||||||
|
|
||||||
|
// Desactiva el modo Demo
|
||||||
|
void disableDemoMode();
|
||||||
|
|
||||||
|
// Intercambia el proximo estado del juego despues del titulo
|
||||||
|
void toogleTitleNextGS();
|
||||||
|
|
||||||
|
private:
|
||||||
|
// La ventana donde dibujamos
|
||||||
|
SDL_Window *mWindow;
|
||||||
|
|
||||||
|
// El renderizador de la ventana
|
||||||
|
SDL_Renderer *mRenderer;
|
||||||
|
|
||||||
|
// Texturas donde dibujar
|
||||||
|
SDL_Texture *mBackbuffer;
|
||||||
|
SDL_Texture *mTitleSurface;
|
||||||
|
SDL_Texture *mInstructionsSurface;
|
||||||
|
|
||||||
|
// Manejador para el mando 1
|
||||||
|
SDL_Joystick *mGameController;
|
||||||
|
bool mGameControllerFound;
|
||||||
|
SDL_Haptic *mControllerHaptic;
|
||||||
|
|
||||||
|
// Datos del fichero
|
||||||
|
Uint32 mScoreDataFile[TOTAL_SCORE_DATA];
|
||||||
|
DemoKeys mDemoDataFile[TOTAL_DEMO_DATA];
|
||||||
|
|
||||||
|
// Manejador de eventos
|
||||||
|
SDL_Event *mEventHandler;
|
||||||
|
|
||||||
|
// El jugador
|
||||||
|
Player *mPlayer;
|
||||||
|
|
||||||
|
// Vector con los objetos globo
|
||||||
|
Balloon *mBalloon[MAX_BALLOONS];
|
||||||
|
|
||||||
|
// Vector con los objetos bala
|
||||||
|
Bullet *mBullet[MAX_BULLETS];
|
||||||
|
|
||||||
|
// Vector con los objetos item
|
||||||
|
Item *mItem[MAX_ITEMS];
|
||||||
|
|
||||||
|
// Fondo del juego
|
||||||
|
Sprite *mGameBackgroundFront;
|
||||||
|
Sprite *mGameBackgroundSky;
|
||||||
|
MovingSprite *mGBClouds1;
|
||||||
|
MovingSprite *mGBClouds1b;
|
||||||
|
MovingSprite *mGBClouds2;
|
||||||
|
MovingSprite *mGBClouds2b;
|
||||||
|
Sprite *mGrass;
|
||||||
|
|
||||||
|
// Instrucciones
|
||||||
|
Sprite *mInstructions;
|
||||||
|
|
||||||
|
// Fondo de la pantalla de titulo
|
||||||
|
Sprite *mTitleTile;
|
||||||
|
|
||||||
|
// Ventana visible de la textura de fondo del titulo
|
||||||
|
SDL_Rect mBackgroundWindow;
|
||||||
|
|
||||||
|
// Vector con los valores del seno para 360 grados
|
||||||
|
double mSen[360];
|
||||||
|
|
||||||
|
// Texto
|
||||||
|
struct text
|
||||||
|
{
|
||||||
|
Text *white;
|
||||||
|
Text *black;
|
||||||
|
Text *nokia;
|
||||||
|
};
|
||||||
|
|
||||||
|
text mText;
|
||||||
|
|
||||||
|
// Variable con lkos menus del juego
|
||||||
|
struct menu
|
||||||
|
{
|
||||||
|
Menu *title; // Menu de la pantalla de título
|
||||||
|
Menu *pause; // Menú de la pantalla de pausa
|
||||||
|
Menu *gameOver; // Menú de la pantalla de game over
|
||||||
|
Menu *options; // Menú de la pantalla de opciones
|
||||||
|
Menu *active; // Menu activo (de momento para la pantalla del titulo)
|
||||||
|
};
|
||||||
|
|
||||||
|
menu mMenu;
|
||||||
|
|
||||||
|
// Notificación GetReady!
|
||||||
|
SmartSprite *mGetReadyBitmap;
|
||||||
|
|
||||||
|
// Dibujos de la intro
|
||||||
|
SmartSprite *mIntroBitmap[INTRO_TOTAL_BITMAPS];
|
||||||
|
|
||||||
|
// Sprites con el titulo del juego para la pantalla de titulo
|
||||||
|
SmartSprite *mCoffeeBitmap;
|
||||||
|
SmartSprite *mCrisisBitmap;
|
||||||
|
AnimatedSprite *mDustSpriteLeft;
|
||||||
|
AnimatedSprite *mDustSpriteRight;
|
||||||
|
|
||||||
|
// Sprites con los puntos de algunos objetos
|
||||||
|
SmartSprite *m1000Bitmap;
|
||||||
|
SmartSprite *m2500Bitmap;
|
||||||
|
SmartSprite *m5000Bitmap;
|
||||||
|
|
||||||
|
// Vector para almacenar y gestionar SmartSprites
|
||||||
|
SmartSprite *mSmartSprite[MAX_SMART_SPRITES];
|
||||||
|
|
||||||
|
// Textos de la intro
|
||||||
|
Text2 *mIntroText[INTRO_TOTAL_TEXTS];
|
||||||
|
|
||||||
|
// Vector para coordinar los eventos de la intro
|
||||||
|
Uint8 mIntroEvents[INTRO_TOTAL_EVENTS];
|
||||||
|
|
||||||
|
// Vector para coordinar los eventos de la pantalla de titulo
|
||||||
|
Uint8 mTitleEvents[TITLE_TOTAL_EVENTS];
|
||||||
|
|
||||||
|
// Indicador para el bucle del titulo
|
||||||
|
Uint8 mTitleStatus;
|
||||||
|
|
||||||
|
struct game
|
||||||
|
{
|
||||||
|
Uint32 score; // Puntuación actual
|
||||||
|
Uint32 hiScore; // Puntuación máxima
|
||||||
|
Uint8 status; // Indicador para el bucle principal
|
||||||
|
bool paused; // Idica si el juego está en pausa
|
||||||
|
bool hiScoreAchieved; // Indica si se ha superado la puntuación máxima
|
||||||
|
Uint8 stage; // Pantalla actual
|
||||||
|
Uint8 stageCounter; // Contador para el tiempo visible del texto de Stage
|
||||||
|
double stagePath[STAGE_COUNTER]; // Vector con los puntos Y por donde pasará la etiqueta
|
||||||
|
Uint16 deathCounter; // Contador para la animación de muerte del jugador
|
||||||
|
Uint8 deathIndex; // Indice del vector de smartsprites que contiene el sprite del jugador
|
||||||
|
};
|
||||||
|
|
||||||
|
game mGame;
|
||||||
|
|
||||||
|
// Contador de ticks para ajustar la velocidad del juego
|
||||||
|
Uint32 mTicks;
|
||||||
|
|
||||||
|
// Velocidad a la que se repite el bucle de juego
|
||||||
|
Uint8 mTicksSpeed;
|
||||||
|
|
||||||
|
// Nivel de amenaza actual
|
||||||
|
Uint8 mMenaceLevel;
|
||||||
|
|
||||||
|
// Umbral del nivel de amenaza. Si el nivel de amenaza cae por debajo del umbral,
|
||||||
|
// se generan más globos. Si el umbral aumenta, aumenta el numero de globos
|
||||||
|
Uint8 mMenaceLevelThreshold;
|
||||||
|
|
||||||
|
// Indica si el bucle de juego avanza o solo pinta
|
||||||
|
bool mPlayFieldDrawOnly;
|
||||||
|
|
||||||
|
// Indica si se va a mostrar la información de debug
|
||||||
|
bool mDebug;
|
||||||
|
|
||||||
|
// Almacena los códigos de teclado correspondientes
|
||||||
|
Input mKeyboard;
|
||||||
|
|
||||||
|
// Buffer para teclas pulsadas
|
||||||
|
Input mKeyboardBuffer;
|
||||||
|
|
||||||
|
// Indica si el tiempo está detenido
|
||||||
|
bool mTimeStopped;
|
||||||
|
|
||||||
|
// Temporizador para llevar la cuenta del tiempo detenido
|
||||||
|
Uint16 mTimeStoppedTimer;
|
||||||
|
|
||||||
|
// Cantidad de explosiones restantes
|
||||||
|
Uint8 mRemainingExplosions;
|
||||||
|
|
||||||
|
// Temporizador para la cantidad de explosiones restantes
|
||||||
|
Uint16 mRemainingExplosionsTimer;
|
||||||
|
|
||||||
|
// Indica si las explosiones estan en marcha
|
||||||
|
bool mExplosionTime;
|
||||||
|
|
||||||
|
// Contador para las instrucciones
|
||||||
|
Uint16 mInstructionsCounter;
|
||||||
|
|
||||||
|
// Temporizador para la pantalla de titulo
|
||||||
|
Uint16 mTitleTimer;
|
||||||
|
|
||||||
|
// Temporizador para el fondo de tiles de la pantalla de titulo
|
||||||
|
Uint16 mTitleBackgroundTimer;
|
||||||
|
|
||||||
|
// Variable para almacenar el tipo de efecto que hará el foindo del titulo
|
||||||
|
Uint8 mTitleBackgroundMode;
|
||||||
|
|
||||||
|
// Indicador para saber si se muestra el menu del titulo o la frase intermitente
|
||||||
|
bool mTitleMenuVisible;
|
||||||
|
|
||||||
|
// Indica si está activo el modo demo
|
||||||
|
bool mDemo;
|
||||||
|
|
||||||
|
// Indica si está activado el modo para grabar la demo
|
||||||
|
bool mDemoRecording;
|
||||||
|
|
||||||
|
// Contador para el modo demo
|
||||||
|
Uint16 mDemoCounter;
|
||||||
|
DemoKeys mDemoKeys;
|
||||||
|
|
||||||
|
// Indica a que estado pasara el juego cuando acabe el temporizador del titulo
|
||||||
|
Uint8 mTiteNextGS;
|
||||||
|
|
||||||
|
// Contador para el juego
|
||||||
|
Uint32 mGameCounter;
|
||||||
|
|
||||||
|
// Variable para evitar la repetición de teclas en los menus
|
||||||
|
bool mMenuKeyPressed;
|
||||||
|
|
||||||
|
// Variables para el tamaño y modo de la ventana y variables para almacenar el valor si cancelamos en el menu de opciones
|
||||||
|
Uint32 mFullScreenMode;
|
||||||
|
Uint32 mFullScreenModePrevious;
|
||||||
|
Uint8 mWindowSize;
|
||||||
|
Uint8 mWindowSizePrevious;
|
||||||
|
|
||||||
|
// Variables para el logo
|
||||||
|
struct logo
|
||||||
|
{
|
||||||
|
Uint16 counter;
|
||||||
|
Sprite *sprite;
|
||||||
|
};
|
||||||
|
logo mLogo;
|
||||||
|
|
||||||
|
// Path del ejecutable
|
||||||
|
std::string mExecutablePath;
|
||||||
|
|
||||||
|
// Recursos
|
||||||
|
struct resourceBinFile
|
||||||
|
{
|
||||||
|
std::string file;
|
||||||
|
bool loaded;
|
||||||
|
};
|
||||||
|
|
||||||
|
resourceBinFile mBinFile[TOTAL_BINFILE];
|
||||||
|
|
||||||
|
struct resourceSound
|
||||||
|
{
|
||||||
|
std::string file;
|
||||||
|
bool loaded;
|
||||||
|
JA_Sound sound;
|
||||||
|
};
|
||||||
|
|
||||||
|
resourceSound mSound[TOTAL_SOUND];
|
||||||
|
|
||||||
|
struct resourceMusic
|
||||||
|
{
|
||||||
|
std::string file;
|
||||||
|
bool loaded;
|
||||||
|
JA_Music music;
|
||||||
|
};
|
||||||
|
|
||||||
|
resourceMusic mMusic[TOTAL_MUSIC];
|
||||||
|
|
||||||
|
struct resourceTexture
|
||||||
|
{
|
||||||
|
std::string file;
|
||||||
|
bool loaded;
|
||||||
|
LTexture *texture;
|
||||||
|
};
|
||||||
|
|
||||||
|
resourceTexture mTexture[TOTAL_TEXTURE];
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
15
source/ifdefs.h
Normal file
@@ -0,0 +1,15 @@
|
|||||||
|
#ifdef _WIN64
|
||||||
|
#include "C:\mingw_dev_lib\include\SDL2\SDL.h"
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifdef _WIN32
|
||||||
|
#include "C:\mingw_dev_lib\include\SDL2\SDL.h"
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifdef __APPLE__
|
||||||
|
#include "/Library/Frameworks/SDL2.framework/Versions/A/Headers/SDL.h"
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifdef __linux__
|
||||||
|
#include "/usr/include/SDL2/SDL.h"
|
||||||
|
#endif
|
||||||
264
source/item.cpp
Normal file
@@ -0,0 +1,264 @@
|
|||||||
|
#include "const.h"
|
||||||
|
#include "item.h"
|
||||||
|
|
||||||
|
// Constructor
|
||||||
|
Item::Item()
|
||||||
|
{
|
||||||
|
mSprite = new AnimatedSprite();
|
||||||
|
init(NO_KIND, 0, 0, nullptr, nullptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
Item::~Item()
|
||||||
|
{
|
||||||
|
init(NO_KIND, 0, 0, nullptr, nullptr);
|
||||||
|
delete mSprite;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Iniciador
|
||||||
|
void Item::init(Uint8 value, float x, float y, LTexture *texture, SDL_Renderer *renderer)
|
||||||
|
{
|
||||||
|
mClass = value;
|
||||||
|
mEnabled = true;
|
||||||
|
mTimeToLive = 600;
|
||||||
|
mPosX = x;
|
||||||
|
mPosY = y;
|
||||||
|
mWidth = 16;
|
||||||
|
mHeight = 16;
|
||||||
|
mVelX = -1.0f + ((rand() % 5) * 0.5f);
|
||||||
|
mVelY = -4.0f;
|
||||||
|
mAccelX = 0.0f;
|
||||||
|
mAccelY = 0.2f;
|
||||||
|
mCollider.r = mWidth / 2;
|
||||||
|
shiftColliders();
|
||||||
|
|
||||||
|
mSprite->init(texture, renderer);
|
||||||
|
mSprite->setAnimationFrames(0, 0, 0, 48, mWidth, mHeight);
|
||||||
|
mSprite->setAnimationFrames(0, 1, 0, 64, mWidth, mHeight);
|
||||||
|
mSprite->setCurrentFrame(0);
|
||||||
|
mSprite->setAnimationCounter(0);
|
||||||
|
mSprite->setAnimationNumFrames(0, 2);
|
||||||
|
mSprite->setAnimationSpeed(0, 10);
|
||||||
|
mSprite->setAnimationLoop(0, true);
|
||||||
|
mSprite->setSpriteClip(mSprite->getAnimationClip(0, 0));
|
||||||
|
|
||||||
|
switch (value)
|
||||||
|
{
|
||||||
|
case NO_KIND:
|
||||||
|
mEnabled = false;
|
||||||
|
mTimeToLive = 0;
|
||||||
|
mPosX = 0;
|
||||||
|
mPosY = 0;
|
||||||
|
mWidth = 0;
|
||||||
|
mHeight = 0;
|
||||||
|
mVelX = 0;
|
||||||
|
mVelY = 0;
|
||||||
|
break;
|
||||||
|
case ITEM_POINTS_1_DISK:
|
||||||
|
mSprite->setAnimationFrames(0, 0, 16 * 0, 16 * 0, mWidth, mHeight);
|
||||||
|
mSprite->setAnimationFrames(0, 1, 16 * 0, 16 * 1, mWidth, mHeight);
|
||||||
|
break;
|
||||||
|
case ITEM_POINTS_2_GAVINA:
|
||||||
|
mSprite->setAnimationFrames(0, 0, 16 * 1, 16 * 0, mWidth, mHeight);
|
||||||
|
mSprite->setAnimationFrames(0, 1, 16 * 1, 16 * 1, mWidth, mHeight);
|
||||||
|
break;
|
||||||
|
case ITEM_POINTS_3_PACMAR:
|
||||||
|
mSprite->setAnimationFrames(0, 0, 16 * 2, 16 * 0, mWidth, mHeight);
|
||||||
|
mSprite->setAnimationFrames(0, 1, 16 * 2, 16 * 1, mWidth, mHeight);
|
||||||
|
break;
|
||||||
|
case ITEM_CLOCK:
|
||||||
|
mSprite->setAnimationFrames(0, 0, 16 * 3, 16 * 0, mWidth, mHeight);
|
||||||
|
mSprite->setAnimationFrames(0, 1, 16 * 3, 16 * 1, mWidth, mHeight);
|
||||||
|
break;
|
||||||
|
case ITEM_TNT:
|
||||||
|
mSprite->setAnimationFrames(0, 0, 16 * 4, 16 * 0, mWidth, mHeight);
|
||||||
|
mSprite->setAnimationFrames(0, 1, 16 * 4, 16 * 1, mWidth, mHeight);
|
||||||
|
break;
|
||||||
|
case ITEM_COFFEE:
|
||||||
|
mSprite->setAnimationFrames(0, 0, 16 * 5, 16 * 0, mWidth, mHeight);
|
||||||
|
mSprite->setAnimationFrames(0, 1, 16 * 5, 16 * 1, mWidth, mHeight);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Centra el globo en la posición X
|
||||||
|
void Item::allignTo(int x)
|
||||||
|
{
|
||||||
|
mPosX = float(x - (mWidth / 2));
|
||||||
|
|
||||||
|
if (mPosX < PLAY_AREA_LEFT)
|
||||||
|
{
|
||||||
|
mPosX = PLAY_AREA_LEFT + 1;
|
||||||
|
}
|
||||||
|
else if ((mPosX + mWidth) > PLAY_AREA_RIGHT)
|
||||||
|
{
|
||||||
|
mPosX = float(PLAY_AREA_RIGHT - mWidth - 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Posición X,Y del sprite
|
||||||
|
mSprite->setPosX(int(mPosX));
|
||||||
|
mSprite->setPosY(int(mPosY));
|
||||||
|
|
||||||
|
// Alinea el circulo de colisión con el objeto
|
||||||
|
shiftColliders();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Pinta el globo en la pantalla
|
||||||
|
void Item::render()
|
||||||
|
{
|
||||||
|
if (mEnabled)
|
||||||
|
{
|
||||||
|
if (mTimeToLive > 200)
|
||||||
|
{
|
||||||
|
mSprite->render();
|
||||||
|
}
|
||||||
|
else if (mTimeToLive % 20 > 10)
|
||||||
|
{
|
||||||
|
mSprite->render();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actualiza la posición y estados del globo
|
||||||
|
void Item::move()
|
||||||
|
{
|
||||||
|
// Calcula la nueva posición
|
||||||
|
mPosX += mVelX;
|
||||||
|
mPosY += mVelY;
|
||||||
|
|
||||||
|
// Aplica las aceleraciones a la velocidad
|
||||||
|
mVelX += mAccelX;
|
||||||
|
mVelY += mAccelY;
|
||||||
|
|
||||||
|
// Si queda fuera de pantalla, corregimos su posición y cambiamos su sentido
|
||||||
|
if ((mPosX < PLAY_AREA_LEFT) || (mPosX + mWidth > PLAY_AREA_RIGHT))
|
||||||
|
{
|
||||||
|
// Corregir posición
|
||||||
|
mPosX -= mVelX;
|
||||||
|
|
||||||
|
// Invertir sentido
|
||||||
|
mVelX = -mVelX;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Si se sale por arriba
|
||||||
|
if (mPosY < PLAY_AREA_TOP)
|
||||||
|
{
|
||||||
|
// Corrige
|
||||||
|
mPosY = PLAY_AREA_TOP;
|
||||||
|
|
||||||
|
// Invierte el sentido
|
||||||
|
mVelY = -mVelY;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Si el objeto se sale por la parte inferior
|
||||||
|
if (mPosY + mHeight > PLAY_AREA_BOTTOM)
|
||||||
|
{
|
||||||
|
// Corrige
|
||||||
|
mPosY -= mVelY;
|
||||||
|
|
||||||
|
// Detiene el objeto
|
||||||
|
mVelY = 0;
|
||||||
|
mVelX = 0;
|
||||||
|
mAccelX = 0;
|
||||||
|
mAccelY = 0;
|
||||||
|
mPosY = PLAY_AREA_BOTTOM - mHeight;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actualiza la posición del sprite
|
||||||
|
mSprite->setPosX(int(mPosX));
|
||||||
|
mSprite->setPosY(int(mPosY));
|
||||||
|
}
|
||||||
|
|
||||||
|
// Pone a cero todos los valores del objeto
|
||||||
|
void Item::erase()
|
||||||
|
{
|
||||||
|
init(NO_KIND, 0, 0, nullptr, nullptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actualiza el objeto a su posicion, animación y controla los contadores
|
||||||
|
void Item::update()
|
||||||
|
{
|
||||||
|
if (mEnabled)
|
||||||
|
{
|
||||||
|
move();
|
||||||
|
shiftColliders();
|
||||||
|
mSprite->animate(0);
|
||||||
|
updateTimeToLive();
|
||||||
|
checkTimeToLive();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actualiza el contador
|
||||||
|
void Item::updateTimeToLive()
|
||||||
|
{
|
||||||
|
if (mTimeToLive > 0)
|
||||||
|
{
|
||||||
|
--mTimeToLive;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Comprueba si el objeto sigue vivo
|
||||||
|
void Item::checkTimeToLive()
|
||||||
|
{
|
||||||
|
if (mTimeToLive == 0)
|
||||||
|
{
|
||||||
|
erase();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
float Item::getPosX()
|
||||||
|
{
|
||||||
|
return mPosX;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
float Item::getPosY()
|
||||||
|
{
|
||||||
|
return mPosY;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
int Item::getWidth()
|
||||||
|
{
|
||||||
|
return mWidth;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
int Item::getHeight()
|
||||||
|
{
|
||||||
|
return mHeight;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
int Item::getClass()
|
||||||
|
{
|
||||||
|
return mClass;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
bool Item::isEnabled()
|
||||||
|
{
|
||||||
|
return mEnabled;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Item::setEnabled(bool value)
|
||||||
|
{
|
||||||
|
mEnabled = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el circulo de colisión
|
||||||
|
Circle &Item::getCollider()
|
||||||
|
{
|
||||||
|
return mCollider;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Alinea el circulo de colisión con la posición del objeto
|
||||||
|
void Item::shiftColliders()
|
||||||
|
{
|
||||||
|
mCollider.x = Uint16(mPosX + mCollider.r);
|
||||||
|
mCollider.y = Uint16(mPosY + mCollider.r);
|
||||||
|
}
|
||||||
105
source/item.h
Normal file
@@ -0,0 +1,105 @@
|
|||||||
|
#pragma once
|
||||||
|
#include "ifdefs.h"
|
||||||
|
#include "animatedsprite.h"
|
||||||
|
#include "struct.h"
|
||||||
|
|
||||||
|
#ifndef ITEM_H
|
||||||
|
#define ITEM_H
|
||||||
|
|
||||||
|
// Clase AnimatedSprite
|
||||||
|
class Item
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
// Constructor
|
||||||
|
Item();
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
~Item();
|
||||||
|
|
||||||
|
// Iniciador
|
||||||
|
void init(Uint8 value, float x, float y, LTexture* texture, SDL_Renderer *renderer);
|
||||||
|
|
||||||
|
// Centra el objeto en la posición X
|
||||||
|
void allignTo(int x);
|
||||||
|
|
||||||
|
// Pinta el objeto en la pantalla
|
||||||
|
void render();
|
||||||
|
|
||||||
|
// Actualiza la posición y estados del objeto
|
||||||
|
void move();
|
||||||
|
|
||||||
|
// Pone a cero todos los valores del objeto
|
||||||
|
void erase();
|
||||||
|
|
||||||
|
// Actualiza al objeto a su posicion, animación y controla los contadores
|
||||||
|
void update();
|
||||||
|
|
||||||
|
// Actualiza el contador
|
||||||
|
void updateTimeToLive();
|
||||||
|
|
||||||
|
// Comprueba si el objeto sigue vivo
|
||||||
|
void checkTimeToLive();
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
float getPosX();
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
float getPosY();
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
int getWidth();
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
int getHeight();
|
||||||
|
|
||||||
|
// Obtiene del valor de la variable
|
||||||
|
int getClass();
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
bool isEnabled();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setEnabled(bool value);
|
||||||
|
|
||||||
|
// Obtiene el circulo de colisión
|
||||||
|
Circle &getCollider();
|
||||||
|
|
||||||
|
// Temporizador con el tiempo que el objeto está presente
|
||||||
|
Uint16 mTimeToLive;
|
||||||
|
|
||||||
|
private:
|
||||||
|
// Posición X,Y del objeto
|
||||||
|
float mPosX;
|
||||||
|
float mPosY;
|
||||||
|
|
||||||
|
// Alto y ancho del objeto
|
||||||
|
Uint8 mWidth;
|
||||||
|
Uint8 mHeight;
|
||||||
|
|
||||||
|
// Variables para controlar la velocidad del objeto
|
||||||
|
float mVelX;
|
||||||
|
float mVelY;
|
||||||
|
|
||||||
|
// Aceleración
|
||||||
|
float mAccelX;
|
||||||
|
float mAccelY;
|
||||||
|
|
||||||
|
// Sprite con los graficos del objeto
|
||||||
|
AnimatedSprite *mSprite;
|
||||||
|
|
||||||
|
// Especifica el tipo de objeto que es
|
||||||
|
Uint8 mClass;
|
||||||
|
|
||||||
|
// Especifica si está habilitado el objeto
|
||||||
|
bool mEnabled;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
// Circulo de colisión del objeto
|
||||||
|
Circle mCollider;
|
||||||
|
|
||||||
|
// Alinea el circulo de colisión con la posición del objeto
|
||||||
|
void shiftColliders();
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
213
source/jail_audio.cpp
Normal file
@@ -0,0 +1,213 @@
|
|||||||
|
#include "jail_audio.h"
|
||||||
|
#include "stb_vorbis.c"
|
||||||
|
//#include <SDL2/SDL.h>
|
||||||
|
|
||||||
|
#define JA_MAX_SIMULTANEOUS_CHANNELS 5
|
||||||
|
|
||||||
|
struct JA_Sound_t {
|
||||||
|
Uint32 length {0};
|
||||||
|
Uint8* buffer {NULL};
|
||||||
|
};
|
||||||
|
|
||||||
|
struct JA_Channel_t {
|
||||||
|
JA_Sound sound;
|
||||||
|
int pos {0};
|
||||||
|
int times {0};
|
||||||
|
JA_Channel_state state { JA_CHANNEL_FREE };
|
||||||
|
};
|
||||||
|
|
||||||
|
struct JA_Music_t {
|
||||||
|
int samples {0};
|
||||||
|
int pos {0};
|
||||||
|
int times {0};
|
||||||
|
short* output {NULL};
|
||||||
|
JA_Music_state state {JA_MUSIC_INVALID};
|
||||||
|
};
|
||||||
|
|
||||||
|
JA_Music current_music{NULL};
|
||||||
|
JA_Channel_t channels[JA_MAX_SIMULTANEOUS_CHANNELS];
|
||||||
|
|
||||||
|
int JA_freq {48000};
|
||||||
|
SDL_AudioFormat JA_format {AUDIO_S16};
|
||||||
|
Uint8 JA_channels {2};
|
||||||
|
|
||||||
|
void audioCallback(void * userdata, uint8_t * stream, int len) {
|
||||||
|
SDL_memset(stream, 0, len);
|
||||||
|
if (current_music != NULL && current_music->state == JA_MUSIC_PLAYING) {
|
||||||
|
const int size = SDL_min(len, current_music->samples*2-current_music->pos);
|
||||||
|
SDL_memcpy(stream, current_music->output+current_music->pos, size);
|
||||||
|
current_music->pos += size/2;
|
||||||
|
if (size < len) {
|
||||||
|
if (current_music->times != 0) {
|
||||||
|
SDL_memcpy(stream+size, current_music->output, len-size);
|
||||||
|
current_music->pos = (len-size)/2;
|
||||||
|
if (current_music->times > 0) current_music->times--;
|
||||||
|
} else {
|
||||||
|
current_music->pos = 0;
|
||||||
|
current_music->state = JA_MUSIC_STOPPED;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// Mixar els channels mi amol
|
||||||
|
for (int i = 0; i < JA_MAX_SIMULTANEOUS_CHANNELS; i++) {
|
||||||
|
if (channels[i].state == JA_CHANNEL_PLAYING) {
|
||||||
|
const int size = SDL_min(len, channels[i].sound->length - channels[i].pos);
|
||||||
|
SDL_MixAudioFormat(stream, channels[i].sound->buffer + channels[i].pos, AUDIO_S16, size, 64);
|
||||||
|
channels[i].pos += size;
|
||||||
|
if (size < len) {
|
||||||
|
if (channels[i].times != 0) {
|
||||||
|
SDL_MixAudioFormat(stream + size, channels[i].sound->buffer, AUDIO_S16, len-size, 64);
|
||||||
|
channels[i].pos = len-size;
|
||||||
|
if (channels[i].times > 0) channels[i].times--;
|
||||||
|
} else {
|
||||||
|
JA_StopChannel(i);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void JA_Init(const int freq, const SDL_AudioFormat format, const int channels) {
|
||||||
|
JA_freq = freq;
|
||||||
|
JA_format = format;
|
||||||
|
JA_channels = channels;
|
||||||
|
SDL_AudioSpec audioSpec{JA_freq, JA_format, JA_channels, 0, 1024, 0, 0, audioCallback, NULL};
|
||||||
|
SDL_AudioDeviceID sdlAudioDevice = SDL_OpenAudioDevice(NULL, 0, &audioSpec, NULL, 0);
|
||||||
|
SDL_PauseAudioDevice(sdlAudioDevice, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
JA_Music JA_LoadMusic(const char* filename) {
|
||||||
|
int chan, samplerate;
|
||||||
|
JA_Music music = new JA_Music_t();
|
||||||
|
music->samples = stb_vorbis_decode_filename(filename, &chan, &samplerate, &music->output);
|
||||||
|
|
||||||
|
SDL_AudioCVT cvt;
|
||||||
|
SDL_BuildAudioCVT(&cvt, AUDIO_S16, chan, samplerate, JA_format, JA_channels, JA_freq);
|
||||||
|
cvt.len = music->samples * chan * 2;
|
||||||
|
cvt.buf = (Uint8 *) SDL_malloc(cvt.len * cvt.len_mult);
|
||||||
|
SDL_memcpy(cvt.buf, music->output, cvt.len);
|
||||||
|
SDL_ConvertAudio(&cvt);
|
||||||
|
free(music->output);
|
||||||
|
music->output = (short*)cvt.buf;
|
||||||
|
|
||||||
|
music->pos = 0;
|
||||||
|
music->state = JA_MUSIC_STOPPED;
|
||||||
|
|
||||||
|
return music;
|
||||||
|
}
|
||||||
|
|
||||||
|
void JA_PlayMusic(JA_Music music, const int loop) {
|
||||||
|
if (current_music != NULL) {
|
||||||
|
current_music->pos = 0;
|
||||||
|
current_music->state = JA_MUSIC_STOPPED;
|
||||||
|
}
|
||||||
|
current_music = music;
|
||||||
|
current_music->pos = 0;
|
||||||
|
current_music->state = JA_MUSIC_PLAYING;
|
||||||
|
current_music->times = loop;
|
||||||
|
}
|
||||||
|
|
||||||
|
void JA_PauseMusic() {
|
||||||
|
if (current_music == NULL || current_music->state == JA_MUSIC_INVALID) return;
|
||||||
|
current_music->state = JA_MUSIC_PAUSED;
|
||||||
|
}
|
||||||
|
|
||||||
|
void JA_ResumeMusic() {
|
||||||
|
if (current_music == NULL || current_music->state == JA_MUSIC_INVALID) return;
|
||||||
|
current_music->state = JA_MUSIC_PLAYING;
|
||||||
|
}
|
||||||
|
|
||||||
|
void JA_StopMusic() {
|
||||||
|
if (current_music == NULL || current_music->state == JA_MUSIC_INVALID) return;
|
||||||
|
current_music->pos = 0;
|
||||||
|
current_music->state = JA_MUSIC_STOPPED;
|
||||||
|
}
|
||||||
|
|
||||||
|
JA_Music_state JA_GetMusicState() {
|
||||||
|
if (current_music == NULL) return JA_MUSIC_INVALID;
|
||||||
|
return current_music->state;
|
||||||
|
}
|
||||||
|
|
||||||
|
void JA_DeleteMusic(JA_Music music) {
|
||||||
|
if (current_music == music) current_music = NULL;
|
||||||
|
SDL_free(music->output);
|
||||||
|
delete music;
|
||||||
|
}
|
||||||
|
|
||||||
|
JA_Sound JA_LoadSound(const char* filename) {
|
||||||
|
JA_Sound sound = new JA_Sound_t();
|
||||||
|
SDL_AudioSpec wavSpec;
|
||||||
|
SDL_LoadWAV(filename, &wavSpec, &sound->buffer, &sound->length);
|
||||||
|
|
||||||
|
SDL_AudioCVT cvt;
|
||||||
|
SDL_BuildAudioCVT(&cvt, wavSpec.format, wavSpec.channels, wavSpec.freq, JA_format, JA_channels, JA_freq);
|
||||||
|
cvt.len = sound->length;
|
||||||
|
cvt.buf = (Uint8 *) SDL_malloc(cvt.len * cvt.len_mult);
|
||||||
|
SDL_memcpy(cvt.buf, sound->buffer, sound->length);
|
||||||
|
SDL_ConvertAudio(&cvt);
|
||||||
|
SDL_FreeWAV(sound->buffer);
|
||||||
|
sound->buffer = cvt.buf;
|
||||||
|
sound->length = cvt.len_cvt;
|
||||||
|
|
||||||
|
return sound;
|
||||||
|
}
|
||||||
|
|
||||||
|
int JA_PlaySound(JA_Sound sound, const int loop) {
|
||||||
|
int channel = 0;
|
||||||
|
while (channel < JA_MAX_SIMULTANEOUS_CHANNELS && channels[channel].state != JA_CHANNEL_FREE) { channel++; }
|
||||||
|
if (channel == JA_MAX_SIMULTANEOUS_CHANNELS) channel = 0;
|
||||||
|
|
||||||
|
channels[channel].sound = sound;
|
||||||
|
channels[channel].times = loop;
|
||||||
|
channels[channel].pos = 0;
|
||||||
|
channels[channel].state = JA_CHANNEL_PLAYING;
|
||||||
|
return channel;
|
||||||
|
}
|
||||||
|
|
||||||
|
void JA_DeleteSound(JA_Sound sound) {
|
||||||
|
for (int i = 0; i < JA_MAX_SIMULTANEOUS_CHANNELS; i++) {
|
||||||
|
if (channels[i].sound == sound) JA_StopChannel(i);
|
||||||
|
}
|
||||||
|
SDL_free(sound->buffer);
|
||||||
|
delete sound;
|
||||||
|
}
|
||||||
|
|
||||||
|
void JA_PauseChannel(const int channel) {
|
||||||
|
if (channel == -1) {
|
||||||
|
for (int i = 0; i < JA_MAX_SIMULTANEOUS_CHANNELS; i++) {
|
||||||
|
if (channels[i].state == JA_CHANNEL_PLAYING) channels[i].state = JA_CHANNEL_PAUSED;
|
||||||
|
}
|
||||||
|
} else if (channel >= 0 && channel < JA_MAX_SIMULTANEOUS_CHANNELS) {
|
||||||
|
if (channels[channel].state == JA_CHANNEL_PLAYING) channels[channel].state = JA_CHANNEL_PAUSED;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void JA_ResumeChannel(const int channel) {
|
||||||
|
if (channel == -1) {
|
||||||
|
for (int i = 0; i < JA_MAX_SIMULTANEOUS_CHANNELS; i++) {
|
||||||
|
if (channels[i].state == JA_CHANNEL_PAUSED) channels[i].state = JA_CHANNEL_PLAYING;
|
||||||
|
}
|
||||||
|
} else if (channel >= 0 && channel < JA_MAX_SIMULTANEOUS_CHANNELS) {
|
||||||
|
if (channels[channel].state == JA_CHANNEL_PAUSED) channels[channel].state = JA_CHANNEL_PLAYING;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void JA_StopChannel(const int channel) {
|
||||||
|
if (channel == -1) {
|
||||||
|
for (int i = 0; i < JA_MAX_SIMULTANEOUS_CHANNELS; i++) {
|
||||||
|
channels[i].state = JA_CHANNEL_FREE;
|
||||||
|
channels[i].pos = 0;
|
||||||
|
channels[i].sound = NULL;
|
||||||
|
}
|
||||||
|
} else if (channel >= 0 && channel < JA_MAX_SIMULTANEOUS_CHANNELS) {
|
||||||
|
channels[channel].state = JA_CHANNEL_FREE;
|
||||||
|
channels[channel].pos = 0;
|
||||||
|
channels[channel].sound = NULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
JA_Channel_state JA_GetChannelState(const int channel) {
|
||||||
|
if (channel < 0 || channel >= JA_MAX_SIMULTANEOUS_CHANNELS) return JA_CHANNEL_INVALID;
|
||||||
|
return channels[channel].state;
|
||||||
|
}
|
||||||
|
|
||||||
26
source/jail_audio.h
Normal file
@@ -0,0 +1,26 @@
|
|||||||
|
#pragma once
|
||||||
|
#include "ifdefs.h"
|
||||||
|
|
||||||
|
enum JA_Channel_state { JA_CHANNEL_INVALID, JA_CHANNEL_FREE, JA_CHANNEL_PLAYING, JA_CHANNEL_PAUSED };
|
||||||
|
enum JA_Music_state { JA_MUSIC_INVALID, JA_MUSIC_PLAYING, JA_MUSIC_PAUSED, JA_MUSIC_STOPPED };
|
||||||
|
|
||||||
|
typedef struct JA_Sound_t *JA_Sound;
|
||||||
|
typedef struct JA_Music_t *JA_Music;
|
||||||
|
|
||||||
|
void JA_Init(const int freq, const SDL_AudioFormat format, const int channels);
|
||||||
|
|
||||||
|
JA_Music JA_LoadMusic(const char* filename);
|
||||||
|
void JA_PlayMusic(JA_Music music, const int loop = -1);
|
||||||
|
void JA_PauseMusic();
|
||||||
|
void JA_ResumeMusic();
|
||||||
|
void JA_StopMusic();
|
||||||
|
JA_Music_state JA_GetMusicState();
|
||||||
|
void JA_DeleteMusic(JA_Music music);
|
||||||
|
|
||||||
|
JA_Sound JA_LoadSound(const char* filename);
|
||||||
|
int JA_PlaySound(JA_Sound sound, const int loop = 0);
|
||||||
|
void JA_PauseChannel(const int channel);
|
||||||
|
void JA_ResumeChannel(const int channel);
|
||||||
|
void JA_StopChannel(const int channel);
|
||||||
|
JA_Channel_state JA_GetChannelState(const int channel);
|
||||||
|
void JA_DeleteSound(JA_Sound sound);
|
||||||
165
source/ltexture.cpp
Normal file
@@ -0,0 +1,165 @@
|
|||||||
|
#include <stdio.h>
|
||||||
|
#include <string>
|
||||||
|
#include "const.h"
|
||||||
|
#include "ltexture.h"
|
||||||
|
#define STB_IMAGE_IMPLEMENTATION
|
||||||
|
#include "stb_image.h"
|
||||||
|
|
||||||
|
LTexture::LTexture()
|
||||||
|
{
|
||||||
|
// Initialize
|
||||||
|
mTexture = NULL;
|
||||||
|
mWidth = 0;
|
||||||
|
mHeight = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
LTexture::~LTexture()
|
||||||
|
{
|
||||||
|
// Deallocate
|
||||||
|
free();
|
||||||
|
}
|
||||||
|
|
||||||
|
bool LTexture::loadFromFile(std::string path, SDL_Renderer *renderer)
|
||||||
|
{
|
||||||
|
int req_format = STBI_rgb_alpha;
|
||||||
|
int width, height, orig_format;
|
||||||
|
unsigned char *data = stbi_load(path.c_str(), &width, &height, &orig_format, req_format);
|
||||||
|
if (data == NULL)
|
||||||
|
{
|
||||||
|
SDL_Log("Loading image failed: %s", stbi_failure_reason());
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
int depth, pitch;
|
||||||
|
Uint32 pixel_format;
|
||||||
|
if (req_format == STBI_rgb)
|
||||||
|
{
|
||||||
|
depth = 24;
|
||||||
|
pitch = 3 * width; // 3 bytes per pixel * pixels per row
|
||||||
|
pixel_format = SDL_PIXELFORMAT_RGB24;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{ // STBI_rgb_alpha (RGBA)
|
||||||
|
depth = 32;
|
||||||
|
pitch = 4 * width;
|
||||||
|
pixel_format = SDL_PIXELFORMAT_RGBA32;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 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());
|
||||||
|
SDL_Surface *loadedSurface = SDL_CreateRGBSurfaceWithFormatFrom((void*)data, width, height, depth, pitch, pixel_format);
|
||||||
|
if (loadedSurface == NULL)
|
||||||
|
{
|
||||||
|
printf("Unable to load image %s!\n", path.c_str());
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// Color key image
|
||||||
|
SDL_SetColorKey(loadedSurface, SDL_TRUE, SDL_MapRGB(loadedSurface->format, COLOR_KEY_R, COLOR_KEY_G, COLOR_KEY_B));
|
||||||
|
|
||||||
|
// Create texture from surface pixels
|
||||||
|
newTexture = SDL_CreateTextureFromSurface(renderer, loadedSurface);
|
||||||
|
if (newTexture == NULL)
|
||||||
|
{
|
||||||
|
printf("Unable to create texture from %s! SDL Error: %s\n", path.c_str(), SDL_GetError());
|
||||||
|
}
|
||||||
|
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;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool LTexture::createBlank(SDL_Renderer *renderer, int width, int height, SDL_TextureAccess access)
|
||||||
|
{
|
||||||
|
// Create uninitialized texture
|
||||||
|
mTexture = SDL_CreateTexture(renderer, SDL_PIXELFORMAT_RGBA8888, access, width, height);
|
||||||
|
if (mTexture == NULL)
|
||||||
|
{
|
||||||
|
printf("Unable to create blank texture! SDL Error: %s\n", SDL_GetError());
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mWidth = width;
|
||||||
|
mHeight = height;
|
||||||
|
}
|
||||||
|
|
||||||
|
return mTexture != NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
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(SDL_Renderer *renderer, 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(renderer, mTexture, clip, &renderQuad, angle, center, flip);
|
||||||
|
}
|
||||||
|
|
||||||
|
void LTexture::setAsRenderTarget(SDL_Renderer *renderer)
|
||||||
|
{
|
||||||
|
// Make self render target
|
||||||
|
SDL_SetRenderTarget(renderer, mTexture);
|
||||||
|
}
|
||||||
|
|
||||||
|
int LTexture::getWidth()
|
||||||
|
{
|
||||||
|
return mWidth;
|
||||||
|
}
|
||||||
|
|
||||||
|
int LTexture::getHeight()
|
||||||
|
{
|
||||||
|
return mHeight;
|
||||||
|
}
|
||||||
66
source/ltexture.h
Normal file
@@ -0,0 +1,66 @@
|
|||||||
|
#pragma once
|
||||||
|
#include "ifdefs.h"
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <string>
|
||||||
|
|
||||||
|
#ifndef LTEXTURE_H
|
||||||
|
#define LTEXTURE_H
|
||||||
|
|
||||||
|
// Texture wrapper class
|
||||||
|
class LTexture
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
// Initializes variables
|
||||||
|
LTexture();
|
||||||
|
|
||||||
|
// Deallocates memory
|
||||||
|
~LTexture();
|
||||||
|
|
||||||
|
// Loads image at specified path
|
||||||
|
bool loadFromFile(std::string path, SDL_Renderer *renderer);
|
||||||
|
|
||||||
|
// Creates blank texture
|
||||||
|
bool createBlank(SDL_Renderer *renderer, int width, int height, SDL_TextureAccess = SDL_TEXTUREACCESS_STREAMING);
|
||||||
|
|
||||||
|
// 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(SDL_Renderer *renderer, int x, int y, SDL_Rect *clip = NULL, double angle = 0.0, SDL_Point *center = NULL, SDL_RendererFlip flip = SDL_FLIP_NONE);
|
||||||
|
|
||||||
|
// Set self as render target
|
||||||
|
void setAsRenderTarget(SDL_Renderer *renderer);
|
||||||
|
|
||||||
|
// Gets image dimensions
|
||||||
|
int getWidth();
|
||||||
|
int getHeight();
|
||||||
|
|
||||||
|
// Pixel manipulators
|
||||||
|
bool lockTexture();
|
||||||
|
bool unlockTexture();
|
||||||
|
void *getPixels();
|
||||||
|
void copyPixels(void *pixels);
|
||||||
|
int getPitch();
|
||||||
|
Uint32 getPixel32(unsigned int x, unsigned int y);
|
||||||
|
|
||||||
|
private:
|
||||||
|
// The actual hardware texture
|
||||||
|
SDL_Texture *mTexture;
|
||||||
|
void *mPixels;
|
||||||
|
int mPitch;
|
||||||
|
|
||||||
|
// Image dimensions
|
||||||
|
int mWidth;
|
||||||
|
int mHeight;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
130
source/main.cpp
Normal file
@@ -0,0 +1,130 @@
|
|||||||
|
/*
|
||||||
|
This source code copyrighted by JailDesigner (2020)
|
||||||
|
started on Castalla 15-07-2020.
|
||||||
|
Using some sample source code from Lazy Foo' Productions
|
||||||
|
*/
|
||||||
|
|
||||||
|
/*Descripción del enfoque utilizado para crear el juego.
|
||||||
|
|
||||||
|
El programa contine una serie de clases/objetos básicos: la clase sprite
|
||||||
|
permite dibujar partes de un fichero png en pantalla. La clase AnimatedSprite
|
||||||
|
contiene funcionalidad adicional para crear animaciones. La clase text permite
|
||||||
|
dibujar letras de un png en pantalla a partir de una cadena de texto. La clase
|
||||||
|
menu permite crear una estructura con diferentes elementos, escribirlos en
|
||||||
|
pantalla y seleccionar uno de ellos.
|
||||||
|
|
||||||
|
A continuación tenemos las clases enfocadas a la lógica del juego, la clase player
|
||||||
|
contiene la información del jugador, la clase balloon la de los enemigos y la
|
||||||
|
clase bullet para las balas que dispara el jugador. La clase background es
|
||||||
|
muy simple y sirve para pintar el fondo de la pantalla. Por ultimo, la clase
|
||||||
|
gamedirector es la que realiza toda la lógica y se encarga de hacer interactuar
|
||||||
|
al resto de objetos entre si.
|
||||||
|
|
||||||
|
El objeto gamedirector tiene tres estados: titulo, juego y pausa. Segun su estado
|
||||||
|
el bucle que recorre es distinto. En el bucle juego, el objeto gamedirector
|
||||||
|
tiene un objeto jugador, un vector con los objetos globo y un vector con los
|
||||||
|
objetos bala. Se encarga de comprobar las entradas de teclado o gamepad para
|
||||||
|
cerrar la aplicacion, saltar al estado de pausa y para mover al jugador. Recorre
|
||||||
|
el vector de globos y de balas y si tienen algun tipo asignado las gestiona.
|
||||||
|
Comprueba las colisiones entre los globos y el jugador y entre las balas y los
|
||||||
|
globos. Tiene ademas un nivel de amenaza que calcula en funcion del numero de globos
|
||||||
|
en pantalla y que se va incrementando conforme aumenta la puntuación del jugador.
|
||||||
|
|
||||||
|
Los objetos globo tienen varios contadores para alternar de un estado a otro.
|
||||||
|
|
||||||
|
En los vectores que contienen objetos, se considera activos los objetos que tienen
|
||||||
|
un tipo asociado diferente a NO_KIND
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "ifdefs.h"
|
||||||
|
#include <time.h>
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <string>
|
||||||
|
#include "const.h"
|
||||||
|
#include "gamedirector.h"
|
||||||
|
|
||||||
|
int main(int argc, char *args[])
|
||||||
|
{
|
||||||
|
// Inicia el generador de numeros aleatorios
|
||||||
|
srand(time(nullptr));
|
||||||
|
|
||||||
|
// Crea el objeto gameDirector
|
||||||
|
GameDirector *gameDirector = new GameDirector();
|
||||||
|
|
||||||
|
// Establece el valor de la variable con el path del ejecutable
|
||||||
|
gameDirector->setExecutablePath(args[0]);
|
||||||
|
|
||||||
|
// Inicializa la lista de ficheros
|
||||||
|
gameDirector->setFileList();
|
||||||
|
|
||||||
|
// Comprueba que existen todos los ficheros
|
||||||
|
if (!gameDirector->checkFileList())
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Arranca SDL y crea la ventana
|
||||||
|
if (!gameDirector->initSDL())
|
||||||
|
{
|
||||||
|
printf("Failed to initialize!\n");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// Carga los recursos
|
||||||
|
if (!gameDirector->loadMedia(GAME_STATE_INIT))
|
||||||
|
{
|
||||||
|
printf("Failed to load media!\n");
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// Inicializa el objeto gameDirector
|
||||||
|
gameDirector->init(false);
|
||||||
|
printf("Starting the game...\n\n");
|
||||||
|
|
||||||
|
// Mientras no se quiera salir del juego
|
||||||
|
while (!(gameDirector->getGameStatus() == GAME_STATE_QUIT))
|
||||||
|
{
|
||||||
|
switch (gameDirector->getGameStatus())
|
||||||
|
{
|
||||||
|
case GAME_STATE_LOGO:
|
||||||
|
gameDirector->loadMedia(GAME_STATE_LOGO);
|
||||||
|
gameDirector->runLogo();
|
||||||
|
gameDirector->unLoadMedia(GAME_STATE_LOGO);
|
||||||
|
break;
|
||||||
|
case GAME_STATE_INTRO:
|
||||||
|
gameDirector->loadMedia(GAME_STATE_INTRO);
|
||||||
|
gameDirector->runIntro();
|
||||||
|
gameDirector->unLoadMedia(GAME_STATE_INTRO);
|
||||||
|
break;
|
||||||
|
case GAME_STATE_TITLE:
|
||||||
|
gameDirector->loadMedia(GAME_STATE_TITLE);
|
||||||
|
gameDirector->runTitle();
|
||||||
|
gameDirector->unLoadMedia(GAME_STATE_TITLE);
|
||||||
|
break;
|
||||||
|
case GAME_STATE_PLAYING:
|
||||||
|
gameDirector->loadMedia(GAME_STATE_PLAYING);
|
||||||
|
gameDirector->runGame();
|
||||||
|
gameDirector->unLoadMedia(GAME_STATE_PLAYING);
|
||||||
|
break;
|
||||||
|
case GAME_STATE_GAME_OVER_SCREEN:
|
||||||
|
gameDirector->loadMedia(GAME_STATE_GAME_OVER_SCREEN);
|
||||||
|
gameDirector->runGameOverScreen();
|
||||||
|
gameDirector->unLoadMedia(GAME_STATE_GAME_OVER_SCREEN);
|
||||||
|
break;
|
||||||
|
case GAME_STATE_INSTRUCTIONS:
|
||||||
|
gameDirector->loadMedia(GAME_STATE_INSTRUCTIONS);
|
||||||
|
gameDirector->runInstructions();
|
||||||
|
gameDirector->unLoadMedia(GAME_STATE_INSTRUCTIONS);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Libera todos los recursos y cierra SDL
|
||||||
|
delete gameDirector;
|
||||||
|
printf("Shutting down the game...\n");
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
455
source/menu.cpp
Normal file
@@ -0,0 +1,455 @@
|
|||||||
|
#include "ifdefs.h"
|
||||||
|
#include "const.h"
|
||||||
|
#include "text.h"
|
||||||
|
#include "menu.h"
|
||||||
|
|
||||||
|
// Constructor
|
||||||
|
Menu::Menu()
|
||||||
|
{
|
||||||
|
init("", 0, 0, 0, nullptr, nullptr, nullptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
Menu::~Menu()
|
||||||
|
{
|
||||||
|
mRenderer = nullptr;
|
||||||
|
mText = nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Inicializador
|
||||||
|
void Menu::init(std::string name, int x, int y, int backgroundType, LTexture *texture, SDL_Renderer *renderer, Text *text)
|
||||||
|
{
|
||||||
|
// Inicia variables
|
||||||
|
mName = name;
|
||||||
|
mSelector.index = 0;
|
||||||
|
mTotalItems = 0;
|
||||||
|
mItemSelected = MENU_NO_OPTION;
|
||||||
|
mVerticalPadding = 1;
|
||||||
|
mPosX = x;
|
||||||
|
mPosY = y;
|
||||||
|
mRectBG.rect.x = 0;
|
||||||
|
mRectBG.rect.y = 0;
|
||||||
|
mRectBG.rect.w = 0;
|
||||||
|
mRectBG.rect.h = 0;
|
||||||
|
mRectBG.r = 0;
|
||||||
|
mRectBG.g = 0;
|
||||||
|
mRectBG.b = 0;
|
||||||
|
mSelector.rect.x = 0;
|
||||||
|
mSelector.rect.y = 0;
|
||||||
|
mSelector.rect.w = 0;
|
||||||
|
mSelector.rect.h = 0;
|
||||||
|
mSelector.r = 0;
|
||||||
|
mSelector.g = 0;
|
||||||
|
mSelector.b = 0;
|
||||||
|
mSelector.a = 255;
|
||||||
|
mBackgroundType = backgroundType;
|
||||||
|
mText = text;
|
||||||
|
mRenderer = renderer;
|
||||||
|
mIsCentered = false;
|
||||||
|
mAreElementsCentered = false;
|
||||||
|
mCenter = x + ((SCREEN_WIDTH - x) / 2);
|
||||||
|
mWidestItem = 0;
|
||||||
|
|
||||||
|
// Selector
|
||||||
|
mSelector.origin = 0;
|
||||||
|
mSelector.target = 0;
|
||||||
|
mSelector.y = 0;
|
||||||
|
mSelector.numJumps = 4;
|
||||||
|
mSelector.despY = 0;
|
||||||
|
mSelector.moving = false;
|
||||||
|
|
||||||
|
// Sprite con los graficos del selector
|
||||||
|
//mSelectorSprite.setWidth(8);
|
||||||
|
//mSelectorSprite.setHeight(8);
|
||||||
|
//mSelectorSprite.setPosX(0);
|
||||||
|
//mSelectorSprite.setPosY(0);
|
||||||
|
//mSelectorSprite.setTexture(texture);
|
||||||
|
//mSelectorSprite.setRenderer(renderer);
|
||||||
|
//mSelectorSprite.setSpriteClip(0, 0, mSelectorSprite.getWidth(), mSelectorSprite.getHeight());
|
||||||
|
|
||||||
|
// Elementos del menu
|
||||||
|
for (int i = 0; i < 10; i++)
|
||||||
|
{
|
||||||
|
mItem[i].label = "";
|
||||||
|
mItem[i].w = 0;
|
||||||
|
mItem[i].h = 0;
|
||||||
|
mItem[i].x = 0;
|
||||||
|
mItem[i].y = 0;
|
||||||
|
mItem[i].hPaddingUp = 0;
|
||||||
|
mItem[i].hPaddingDown = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Mueve el grafico del selector al elemento seleccionado
|
||||||
|
//moveSelectorSprite(mSelector.index);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el nombre del menu
|
||||||
|
std::string Menu::getName()
|
||||||
|
{
|
||||||
|
return mName;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
Uint8 Menu::getItemSelected()
|
||||||
|
{
|
||||||
|
return mItemSelected;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Mueve el grafico del selector al elemento seleccionado
|
||||||
|
/*void Menu::moveSelectorSprite(int pos)
|
||||||
|
{
|
||||||
|
mSelector.rect.y = mItem[pos].y - 1;
|
||||||
|
}*/
|
||||||
|
|
||||||
|
// Actualiza la posicion y el estado del selector
|
||||||
|
void Menu::updateSelector()
|
||||||
|
{
|
||||||
|
if (mSelector.moving)
|
||||||
|
{
|
||||||
|
mSelector.y += mSelector.despY;
|
||||||
|
if (mSelector.despY > 0) // Va hacia abajo
|
||||||
|
{
|
||||||
|
if (mSelector.y > mSelector.target) // Ha llegado al destino
|
||||||
|
{
|
||||||
|
mSelector.origin = mSelector.y = mSelector.target;
|
||||||
|
mSelector.moving = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (mSelector.despY < 0) // Va hacia abajo
|
||||||
|
{
|
||||||
|
if (mSelector.y < mSelector.target) // Ha llegado al destino
|
||||||
|
{
|
||||||
|
mSelector.origin = mSelector.y = mSelector.target;
|
||||||
|
mSelector.moving = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
mSelector.rect.y = int(mSelector.y) - 1;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mSelector.rect.y = int(mSelector.y) - 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el origen del selector
|
||||||
|
void Menu::setSelectorOrigin(int value)
|
||||||
|
{
|
||||||
|
mSelector.origin = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el destino del selector
|
||||||
|
void Menu::setSelectorTarget(int value)
|
||||||
|
{
|
||||||
|
mSelector.target = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Coloca el selector en una posición específica
|
||||||
|
void Menu::setSelectorPos(Uint8 index)
|
||||||
|
{
|
||||||
|
if (index < mTotalItems)
|
||||||
|
{
|
||||||
|
mSelector.index = index;
|
||||||
|
mSelector.y = mSelector.origin = mSelector.target = mItem[mSelector.index].y;
|
||||||
|
mSelector.moving = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene la anchura del elemento más ancho del menu
|
||||||
|
Uint16 Menu::getWidestItem()
|
||||||
|
{
|
||||||
|
Uint16 result = 0;
|
||||||
|
|
||||||
|
// Obtenemos la anchura del item mas ancho
|
||||||
|
for (Uint8 i = 0; i < mTotalItems; i++)
|
||||||
|
{
|
||||||
|
if (mItem[i].w > result)
|
||||||
|
{
|
||||||
|
result = mItem[i].w;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Deja el menu apuntando al primer elemento
|
||||||
|
void Menu::reset()
|
||||||
|
{
|
||||||
|
mItemSelected = MENU_NO_OPTION;
|
||||||
|
mSelector.index = 0;
|
||||||
|
//moveSelectorSprite(mSelector.index);
|
||||||
|
mSelector.origin = mSelector.target = mSelector.y = mItem[0].y;
|
||||||
|
mSelector.moving = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Deja el menu sin elemento seleccionado
|
||||||
|
void Menu::deselectItem()
|
||||||
|
{
|
||||||
|
mItemSelected = MENU_NO_OPTION;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actualiza el menu para recolocarlo correctamente y establecer el tamaño
|
||||||
|
void Menu::reorganize()
|
||||||
|
{
|
||||||
|
setRectSize();
|
||||||
|
if (mIsCentered)
|
||||||
|
centerMenu(mCenter);
|
||||||
|
if (mAreElementsCentered)
|
||||||
|
centerMenuElements();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Deja el menu apuntando al siguiente elemento
|
||||||
|
bool Menu::increaseSelectorIndex()
|
||||||
|
{
|
||||||
|
bool success = false;
|
||||||
|
mSelector.y = mSelector.origin = mItem[mSelector.index].y;
|
||||||
|
|
||||||
|
if (mSelector.index < (mTotalItems - 1))
|
||||||
|
{
|
||||||
|
mSelector.index++;
|
||||||
|
success = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
mSelector.target = mItem[mSelector.index].y;
|
||||||
|
mSelector.despY = (mSelector.target - mSelector.origin) / mSelector.numJumps;
|
||||||
|
mSelector.moving = true;
|
||||||
|
return success;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Deja el menu apuntando al elemento anterior
|
||||||
|
bool Menu::decreaseSelectorIndex()
|
||||||
|
{
|
||||||
|
bool success = false;
|
||||||
|
mSelector.y = mSelector.origin = mItem[mSelector.index].y;
|
||||||
|
|
||||||
|
if (mSelector.index > 0)
|
||||||
|
{
|
||||||
|
mSelector.index--;
|
||||||
|
success = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
mSelector.target = mItem[mSelector.index].y;
|
||||||
|
mSelector.despY = (mSelector.target - mSelector.origin) / mSelector.numJumps;
|
||||||
|
mSelector.moving = true;
|
||||||
|
return success;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Comprueba la entrada (teclado, gamepad) y actua en consecuencia
|
||||||
|
bool Menu::checkInput(Uint8 input)
|
||||||
|
{
|
||||||
|
bool success = false;
|
||||||
|
switch (input)
|
||||||
|
{
|
||||||
|
case INPUT_UP:
|
||||||
|
success = decreaseSelectorIndex();
|
||||||
|
//moveSelectorSprite(mSelector.index);
|
||||||
|
break;
|
||||||
|
case INPUT_DOWN:
|
||||||
|
success = increaseSelectorIndex();
|
||||||
|
//moveSelectorSprite(mSelector.index);
|
||||||
|
break;
|
||||||
|
case INPUT_ACCEPT:
|
||||||
|
mItemSelected = mSelector.index;
|
||||||
|
break;
|
||||||
|
case INPUT_CANCEL:
|
||||||
|
mItemSelected = mDefaultActionWhenCancel;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
return success;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actualiza la logica del menu
|
||||||
|
void Menu::update()
|
||||||
|
{
|
||||||
|
updateSelector();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Pinta el menu en pantalla
|
||||||
|
void Menu::render()
|
||||||
|
{
|
||||||
|
// Rendereritza el fondo del menu
|
||||||
|
if (mBackgroundType == MENU_BACKGROUND_SOLID)
|
||||||
|
{
|
||||||
|
SDL_SetRenderDrawColor(mRenderer, mRectBG.r, mRectBG.g, mRectBG.b, mRectBG.a);
|
||||||
|
SDL_RenderFillRect(mRenderer, &mRectBG.rect);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Renderiza el rectangulo del selector
|
||||||
|
SDL_SetRenderDrawColor(mRenderer, mSelector.r, mSelector.g, mSelector.b, mSelector.a);
|
||||||
|
SDL_RenderFillRect(mRenderer, &mSelector.rect);
|
||||||
|
|
||||||
|
// Renderiza el sprite del selector
|
||||||
|
//mSelectorSprite.render();
|
||||||
|
|
||||||
|
// Renderitza el text
|
||||||
|
for (Uint8 i = 0; i < mTotalItems; i++)
|
||||||
|
{
|
||||||
|
if (i == mSelector.index)
|
||||||
|
{
|
||||||
|
mText->writeColored(mItem[i].x, mItem[i].y, mItem[i].label, mSelector.itemR, mSelector.itemG, mSelector.itemB);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mText->write(mItem[i].x, mItem[i].y, mItem[i].label, 0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el rectangulo de fondo del menu y el selector
|
||||||
|
void Menu::setRectSize()
|
||||||
|
{
|
||||||
|
Uint8 i = 0;
|
||||||
|
mRectBG.rect.w = 0;
|
||||||
|
mRectBG.rect.h = 0;
|
||||||
|
mSelector.rect.w = 0;
|
||||||
|
mSelector.rect.h = 0;
|
||||||
|
|
||||||
|
// Obtenemos la anchura del item mas ancho y la altura de la suma de alturas de los items
|
||||||
|
for (i = 0; i < mTotalItems; i++)
|
||||||
|
{
|
||||||
|
if (mItem[i].w > mRectBG.rect.w)
|
||||||
|
{
|
||||||
|
mRectBG.rect.w = mItem[i].w;
|
||||||
|
}
|
||||||
|
mRectBG.rect.h += mItem[i].h + mItem[i].hPaddingDown;
|
||||||
|
}
|
||||||
|
|
||||||
|
// La anchura de la cadena más larga, mas un caracter, mas la anchura del sprite del selector
|
||||||
|
mRectBG.rect.w += (mText->getSize() * 1); // + mSelectorSprite.getWidth();
|
||||||
|
|
||||||
|
// La altura de la suma de los items mas un caracter y menos un pixel (porque el texto en realidad es de 7 pixeles)
|
||||||
|
mRectBG.rect.h += (mText->getSize() * 1) - 1;
|
||||||
|
|
||||||
|
// La posición X es la del menú menos la anchura del sprite del selector y menos medio caracter
|
||||||
|
mRectBG.rect.x = mPosX - (mText->getSize() / 2); // - mSelectorSprite.getWidth();
|
||||||
|
|
||||||
|
// La posición Y es la del menu menos la altura de medio caracter i el padding
|
||||||
|
mRectBG.rect.y = mPosY - (mText->getSize() / 2) - mVerticalPadding;
|
||||||
|
|
||||||
|
// Establecemos los valores del rectangulo del selector a partir de los valores del rectangulo de fondo
|
||||||
|
mSelector.rect.h = (mText->getSize() * 1) + 1;
|
||||||
|
mSelector.rect.w = mRectBG.rect.w;
|
||||||
|
mSelector.rect.x = mRectBG.rect.x;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Menu::setTotalItems(int num)
|
||||||
|
{
|
||||||
|
mTotalItems = num;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el color del rectangulo de fondo
|
||||||
|
void Menu::setBackgroundColor(int r, int g, int b, int alpha)
|
||||||
|
{
|
||||||
|
mRectBG.r = r;
|
||||||
|
mRectBG.g = g;
|
||||||
|
mRectBG.b = b;
|
||||||
|
mRectBG.a = alpha;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el color del rectangulo del selector
|
||||||
|
void Menu::setSelectorColor(int r, int g, int b, int alpha)
|
||||||
|
{
|
||||||
|
mSelector.r = r;
|
||||||
|
mSelector.g = g;
|
||||||
|
mSelector.b = b;
|
||||||
|
mSelector.a = alpha;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el color del texto del selector
|
||||||
|
void Menu::setSelectorTextColor(int r, int g, int b)
|
||||||
|
{
|
||||||
|
mSelector.itemR = r;
|
||||||
|
mSelector.itemG = g;
|
||||||
|
mSelector.itemB = b;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Centra el menu respecto un punto
|
||||||
|
void Menu::centerMenu(int value)
|
||||||
|
{
|
||||||
|
mIsCentered = true;
|
||||||
|
mCenter = value;
|
||||||
|
|
||||||
|
// Actualiza el rectangulo de fondo para recalcular las dimensiones
|
||||||
|
setRectSize();
|
||||||
|
|
||||||
|
// Obten el acho del menu
|
||||||
|
mWidestItem = getWidestItem();
|
||||||
|
|
||||||
|
// Establece la nueva posición centrada en funcion del elemento más ancho
|
||||||
|
mPosX = (value) - (mWidestItem / 2);
|
||||||
|
|
||||||
|
// Reposiciona los elementos del menu
|
||||||
|
for (Uint8 i = 0; i < 10; i++)
|
||||||
|
{
|
||||||
|
mItem[i].x = mPosX;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Recalcula el rectangulo de fondo
|
||||||
|
setRectSize();
|
||||||
|
|
||||||
|
// Recoloca el selector
|
||||||
|
mSelector.origin = mSelector.target = mSelector.y = mItem[mSelector.index].y;
|
||||||
|
mSelector.moving = false;
|
||||||
|
//moveSelectorSprite(mSelector.index);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Centra los elementos del menu
|
||||||
|
void Menu::centerMenuElements()
|
||||||
|
{
|
||||||
|
mAreElementsCentered = true;
|
||||||
|
|
||||||
|
for (Uint8 i = 0; i < mTotalItems; i++)
|
||||||
|
{
|
||||||
|
//mItem[i].x = (mCenter - ((mText->lenght(mItem[i].label, 0)) / 2));
|
||||||
|
mItem[i].x = (mCenter - (mItem[i].w / 2));
|
||||||
|
}
|
||||||
|
|
||||||
|
// Mueve el grafico del selector al elemento seleccionado
|
||||||
|
//moveSelectorSprite(mSelector.index);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Añade un item al menu
|
||||||
|
void Menu::addItem(std::string text, const Uint8 hPaddingUp, const Uint8 hPaddingDown)
|
||||||
|
{
|
||||||
|
// Si es el primer item coge la posición y del propio menu
|
||||||
|
if (mTotalItems == 0)
|
||||||
|
{
|
||||||
|
mItem[mTotalItems].label = text;
|
||||||
|
mItem[mTotalItems].w = mText->lenght(mItem[mTotalItems].label, 0);
|
||||||
|
mItem[mTotalItems].h = mText->getSize() + (mVerticalPadding * 2);
|
||||||
|
mItem[mTotalItems].x = mPosX;
|
||||||
|
mItem[mTotalItems].y = mPosY;
|
||||||
|
mItem[mTotalItems].hPaddingUp = hPaddingUp;
|
||||||
|
mItem[mTotalItems].hPaddingDown = hPaddingDown;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
// En caso contrario, coge la posición y a partir del elemento anterior
|
||||||
|
if (mTotalItems < 10)
|
||||||
|
{
|
||||||
|
mItem[mTotalItems].label = text;
|
||||||
|
mItem[mTotalItems].w = mText->lenght(mItem[mTotalItems].label, 0);
|
||||||
|
mItem[mTotalItems].h = mText->getSize() + (mVerticalPadding * 2);
|
||||||
|
mItem[mTotalItems].x = mPosX;
|
||||||
|
mItem[mTotalItems].y = mItem[mTotalItems - 1].y + mItem[mTotalItems - 1].h + mItem[mTotalItems - 1].hPaddingDown;
|
||||||
|
mItem[mTotalItems].hPaddingUp = hPaddingUp;
|
||||||
|
mItem[mTotalItems].hPaddingDown = hPaddingDown;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
setTotalItems(mTotalItems + 1);
|
||||||
|
reorganize();
|
||||||
|
setSelectorPos(0);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Cambia el texto de un item
|
||||||
|
void Menu::setItemCaption(Uint8 index, std::string text)
|
||||||
|
{
|
||||||
|
mItem[index].label = text;
|
||||||
|
mItem[index].w = mText->lenght(mItem[index].label, 0);
|
||||||
|
reorganize();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el indice del itemm que se usará por defecto al cancelar el menu
|
||||||
|
void Menu::setDefaultActionWhenCancel(Uint8 item)
|
||||||
|
{
|
||||||
|
mDefaultActionWhenCancel = item;
|
||||||
|
}
|
||||||
190
source/menu.h
Normal file
@@ -0,0 +1,190 @@
|
|||||||
|
#pragma once
|
||||||
|
#include "sprite.h"
|
||||||
|
#include "text.h"
|
||||||
|
|
||||||
|
#ifndef MENU_H
|
||||||
|
#define MENU_H
|
||||||
|
|
||||||
|
// Clase menu
|
||||||
|
class Menu
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
// Constructor
|
||||||
|
Menu();
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
~Menu();
|
||||||
|
|
||||||
|
// Inicializador
|
||||||
|
void init(std::string name, int x, int y, int backgroundType, LTexture *texture, SDL_Renderer *renderer, Text *text);
|
||||||
|
|
||||||
|
// Obtiene el nombre del menu
|
||||||
|
std::string getName();
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
Uint8 getItemSelected();
|
||||||
|
|
||||||
|
// Deja el menu apuntando al primer elemento
|
||||||
|
void reset();
|
||||||
|
|
||||||
|
// Deja el menu sin elemento seleccionado
|
||||||
|
void deselectItem();
|
||||||
|
|
||||||
|
// Comprueba la entrada (teclado, gamepad) y actua en consecuencia
|
||||||
|
bool checkInput(Uint8 input);
|
||||||
|
|
||||||
|
// Actualiza la logica del menu
|
||||||
|
void update();
|
||||||
|
|
||||||
|
// Pinta el menu en pantalla
|
||||||
|
void render();
|
||||||
|
|
||||||
|
// Establece el color del rectangulo de fondo
|
||||||
|
void setBackgroundColor(int r, int g, int b, int alpha);
|
||||||
|
|
||||||
|
// Establece el color del rectangulo del selector
|
||||||
|
void setSelectorColor(int r, int g, int b, int alpha);
|
||||||
|
|
||||||
|
// Establece el color del texto del selector
|
||||||
|
void setSelectorTextColor(int r, int g, int b);
|
||||||
|
|
||||||
|
// Centra el menu respecto a un punto
|
||||||
|
void centerMenu(int value);
|
||||||
|
|
||||||
|
// Centra los elementos del menu
|
||||||
|
void centerMenuElements();
|
||||||
|
|
||||||
|
// Añade un item al menu
|
||||||
|
void addItem(std::string text, const Uint8 hPaddingUp = 0, const Uint8 hPaddingDown = 0);
|
||||||
|
|
||||||
|
// Cambia el texto de un item
|
||||||
|
void setItemCaption(Uint8 index, std::string text);
|
||||||
|
|
||||||
|
// Establece el indice del item que se usará por defecto al cancelar el menu
|
||||||
|
void setDefaultActionWhenCancel(Uint8 item);
|
||||||
|
|
||||||
|
private:
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setTotalItems(int num);
|
||||||
|
|
||||||
|
// Establece el rectangulo de fondo del menu
|
||||||
|
void setRectSize();
|
||||||
|
|
||||||
|
// Actualiza el menu para recolocarlo correctamente y establecer el tamaño
|
||||||
|
void reorganize();
|
||||||
|
|
||||||
|
// Deja el menu apuntando al siguiente elemento
|
||||||
|
bool increaseSelectorIndex();
|
||||||
|
|
||||||
|
// Deja el menu apuntando al elemento anterior
|
||||||
|
bool decreaseSelectorIndex();
|
||||||
|
|
||||||
|
// Mueve el grafico del selector al elemento seleccionado
|
||||||
|
//void moveSelectorSprite(int pos);
|
||||||
|
|
||||||
|
// Actualiza la posicion y el estado del selector
|
||||||
|
void updateSelector();
|
||||||
|
|
||||||
|
// Establece el origen del selector
|
||||||
|
void setSelectorOrigin(int value);
|
||||||
|
|
||||||
|
// Establece el destino del selector
|
||||||
|
void setSelectorTarget(int value);
|
||||||
|
|
||||||
|
// Coloca el selector en una posición específica
|
||||||
|
void setSelectorPos(Uint8 index);
|
||||||
|
|
||||||
|
// Obtiene la anchura del elemento más ancho del menu
|
||||||
|
Uint16 getWidestItem();
|
||||||
|
|
||||||
|
// Posicion X/Y del texto del primer elemento del menu
|
||||||
|
int mPosX; // En esta posición se pinta la primera letra del primer elemento
|
||||||
|
int mPosY;
|
||||||
|
|
||||||
|
// Nombre del menu
|
||||||
|
std::string mName;
|
||||||
|
|
||||||
|
// Numero de items del menu
|
||||||
|
Uint8 mTotalItems;
|
||||||
|
|
||||||
|
// Item del menu que ha sido seleccionado
|
||||||
|
Uint8 mItemSelected;
|
||||||
|
|
||||||
|
// Item del menu seleccionado cuando se cancela el menu
|
||||||
|
Uint8 mDefaultActionWhenCancel;
|
||||||
|
|
||||||
|
// Espacio de separacion entre items
|
||||||
|
Uint8 mVerticalPadding;
|
||||||
|
|
||||||
|
// Tipo de fondo para el menu
|
||||||
|
Uint8 mBackgroundType;
|
||||||
|
|
||||||
|
// Sprite con los graficos del selector
|
||||||
|
//Sprite mSelectorSprite;
|
||||||
|
|
||||||
|
struct rectangle
|
||||||
|
{
|
||||||
|
SDL_Rect rect;
|
||||||
|
Uint8 r; // Rojo
|
||||||
|
Uint8 g; // Verde
|
||||||
|
Uint8 b; // Azul
|
||||||
|
Uint8 a; // Transparencia
|
||||||
|
};
|
||||||
|
|
||||||
|
rectangle mRectBG; // Rectangulo de fondo del menu
|
||||||
|
|
||||||
|
// Estructura para cada elemento del menu
|
||||||
|
struct item
|
||||||
|
{
|
||||||
|
std::string label;
|
||||||
|
int x;
|
||||||
|
int y;
|
||||||
|
Uint8 w;
|
||||||
|
Uint8 h;
|
||||||
|
Uint8 hPaddingUp;
|
||||||
|
Uint8 hPaddingDown;
|
||||||
|
};
|
||||||
|
|
||||||
|
item mItem[10];
|
||||||
|
|
||||||
|
// Texto para poder escribir los items del menu
|
||||||
|
Text *mText;
|
||||||
|
|
||||||
|
// Puntero al renderizador de la ventana
|
||||||
|
SDL_Renderer *mRenderer;
|
||||||
|
|
||||||
|
// Variable para saber si el menu debe estar centrado respecto a un punto
|
||||||
|
bool mIsCentered;
|
||||||
|
|
||||||
|
// Centro del menu
|
||||||
|
int mCenter;
|
||||||
|
|
||||||
|
// Variable para saber si los elementos van centrados
|
||||||
|
bool mAreElementsCentered;
|
||||||
|
|
||||||
|
// Anchura del elemento más ancho
|
||||||
|
Uint16 mWidestItem;
|
||||||
|
|
||||||
|
struct selector
|
||||||
|
{
|
||||||
|
double origin; // Coordenada de origen
|
||||||
|
double target; // Coordenada de destino
|
||||||
|
double y; // Coordenada actual
|
||||||
|
Uint8 numJumps; // Numero de pasos preestablecido para llegar al destino
|
||||||
|
double despY; // (target - origin) / numJumps
|
||||||
|
bool moving; // Indica si el selector está avanzando hacia el destino
|
||||||
|
Uint8 index; // Elemento del menu que tiene el foco
|
||||||
|
SDL_Rect rect;
|
||||||
|
Uint8 r; // Rojo
|
||||||
|
Uint8 g; // Verde
|
||||||
|
Uint8 b; // Azul
|
||||||
|
Uint8 a; // Transparencia
|
||||||
|
Uint8 itemR; // Rojo
|
||||||
|
Uint8 itemG; // Verde
|
||||||
|
Uint8 itemB; // Azul
|
||||||
|
};
|
||||||
|
|
||||||
|
selector mSelector;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
132
source/movingsprite.cpp
Normal file
@@ -0,0 +1,132 @@
|
|||||||
|
#include "const.h"
|
||||||
|
#include "movingsprite.h"
|
||||||
|
#include <iostream>
|
||||||
|
|
||||||
|
// Constructor
|
||||||
|
MovingSprite::MovingSprite()
|
||||||
|
{
|
||||||
|
init(0, 0, 0, 0, 0, 0, 0, 0, nullptr, nullptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
MovingSprite::~MovingSprite()
|
||||||
|
{
|
||||||
|
init(0, 0, 0, 0, 0, 0, 0, 0, nullptr, nullptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Iniciador
|
||||||
|
void MovingSprite::init(float x, float y, int w, int h, float velx, float vely, float accelx, float accely, LTexture *texture, SDL_Renderer *renderer)
|
||||||
|
{
|
||||||
|
// Establece el alto y el ancho del sprite
|
||||||
|
setWidth(w);
|
||||||
|
setHeight(h);
|
||||||
|
|
||||||
|
// Establece la posición X,Y del sprite
|
||||||
|
setPosX(x);
|
||||||
|
setPosY(y);
|
||||||
|
|
||||||
|
// Establece la velocidad X,Y del sprite
|
||||||
|
setVelX(velx);
|
||||||
|
setVelY(vely);
|
||||||
|
|
||||||
|
// Establece la aceleración X,Y del sprite
|
||||||
|
setAccelX(accelx);
|
||||||
|
setAccelY(accely);
|
||||||
|
|
||||||
|
// Establece la textura donde están los gráficos para el sprite
|
||||||
|
setTexture(texture);
|
||||||
|
|
||||||
|
// Establece el renderizador
|
||||||
|
setRenderer(renderer);
|
||||||
|
|
||||||
|
// Establece el rectangulo de donde coger la imagen
|
||||||
|
setSpriteClip(0, 0, w, h);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Mueve el sprite
|
||||||
|
void MovingSprite::move()
|
||||||
|
{
|
||||||
|
mPosX += mVelX;
|
||||||
|
mPosY += mVelY;
|
||||||
|
|
||||||
|
mVelX += mAccelX;
|
||||||
|
mVelY += mAccelY;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Muestra el sprite por pantalla
|
||||||
|
void MovingSprite::render()
|
||||||
|
{
|
||||||
|
mTexture->render(mRenderer, (int)mPosX, (int)mPosY, &mSpriteClip);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
float MovingSprite::getPosX()
|
||||||
|
{
|
||||||
|
return mPosX;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
float MovingSprite::getPosY()
|
||||||
|
{
|
||||||
|
return mPosY;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
float MovingSprite::getVelX()
|
||||||
|
{
|
||||||
|
return mVelX;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
float MovingSprite::getVelY()
|
||||||
|
{
|
||||||
|
return mVelY;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
float MovingSprite::getAccelX()
|
||||||
|
{
|
||||||
|
return mAccelX;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
float MovingSprite::getAccelY()
|
||||||
|
{
|
||||||
|
return mAccelY;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void MovingSprite::setPosX(float x)
|
||||||
|
{
|
||||||
|
mPosX = x;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void MovingSprite::setPosY(float y)
|
||||||
|
{
|
||||||
|
mPosY = y;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void MovingSprite::setVelX(float x)
|
||||||
|
{
|
||||||
|
mVelX = x;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void MovingSprite::setVelY(float y)
|
||||||
|
{
|
||||||
|
mVelY = y;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void MovingSprite::setAccelX(float x)
|
||||||
|
{
|
||||||
|
mAccelX = x;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void MovingSprite::setAccelY(float y)
|
||||||
|
{
|
||||||
|
mAccelY = y;
|
||||||
|
}
|
||||||
77
source/movingsprite.h
Normal file
@@ -0,0 +1,77 @@
|
|||||||
|
#pragma once
|
||||||
|
#include "ifdefs.h"
|
||||||
|
#include "sprite.h"
|
||||||
|
|
||||||
|
#ifndef MOVINGSPRITE_H
|
||||||
|
#define MOVINGSPRITE_H
|
||||||
|
|
||||||
|
// Clase MovingSprite. Añade posicion y velocidad en punto flotante
|
||||||
|
class MovingSprite : public Sprite
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
// Constructor
|
||||||
|
MovingSprite();
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
~MovingSprite();
|
||||||
|
|
||||||
|
// Iniciador
|
||||||
|
void init(float x, float y, int w, int h, float velx, float vely, float accelx, float accely, LTexture *texture, SDL_Renderer *renderer);
|
||||||
|
|
||||||
|
// Mueve el sprite
|
||||||
|
void move();
|
||||||
|
|
||||||
|
// Muestra el sprite por pantalla
|
||||||
|
void render();
|
||||||
|
|
||||||
|
// Obten el valor de la variable
|
||||||
|
float getPosX();
|
||||||
|
|
||||||
|
// Obten el valor de la variable
|
||||||
|
float getPosY();
|
||||||
|
|
||||||
|
// Obten el valor de la variable
|
||||||
|
float getVelX();
|
||||||
|
|
||||||
|
// Obten el valor de la variable
|
||||||
|
float getVelY();
|
||||||
|
|
||||||
|
// Obten el valor de la variable
|
||||||
|
float getAccelX();
|
||||||
|
|
||||||
|
// Obten el valor de la variable
|
||||||
|
float getAccelY();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setPosX(float x);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setPosY(float y);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setVelX(float x);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setVelY(float y);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setAccelX(float x);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setAccelY(float y);
|
||||||
|
|
||||||
|
private:
|
||||||
|
// Posición
|
||||||
|
float mPosX;
|
||||||
|
float mPosY;
|
||||||
|
|
||||||
|
// Velocidad
|
||||||
|
float mVelX;
|
||||||
|
float mVelY;
|
||||||
|
|
||||||
|
// Aceleración
|
||||||
|
float mAccelX;
|
||||||
|
float mAccelY;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
751
source/player.cpp
Normal file
@@ -0,0 +1,751 @@
|
|||||||
|
#include "const.h"
|
||||||
|
#include "player.h"
|
||||||
|
|
||||||
|
// Constructor
|
||||||
|
Player::Player()
|
||||||
|
{
|
||||||
|
mSpriteLegs = new AnimatedSprite();
|
||||||
|
mSpriteBody = new AnimatedSprite();
|
||||||
|
init(0, 0, nullptr, nullptr, nullptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
Player::~Player()
|
||||||
|
{
|
||||||
|
init(0, 0, nullptr, nullptr, nullptr);
|
||||||
|
mSpriteLegs = nullptr;
|
||||||
|
mSpriteBody = nullptr;
|
||||||
|
delete mSpriteLegs;
|
||||||
|
delete mSpriteBody;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Iniciador
|
||||||
|
void Player::init(float x, int y, LTexture *textureLegs, LTexture *textureBody, SDL_Renderer *renderer)
|
||||||
|
{
|
||||||
|
// Inicializa variables de estado
|
||||||
|
mAlive = true;
|
||||||
|
mStatusWalking = PLAYER_STATUS_WALKING_STOP;
|
||||||
|
mStatusFiring = PLAYER_STATUS_FIRING_NO;
|
||||||
|
mInvulnerable = false;
|
||||||
|
mInvulnerableTimer = PLAYER_INVULNERABLE_TIMER;
|
||||||
|
mExtraHit = false;
|
||||||
|
|
||||||
|
// Establece la altura y el ancho del jugador
|
||||||
|
mWidth = 3 * BLOCK;
|
||||||
|
mHeight = 3 * BLOCK;
|
||||||
|
|
||||||
|
// Establece la posición inicial del jugador
|
||||||
|
mPosX = x;
|
||||||
|
mPosY = y;
|
||||||
|
|
||||||
|
// Establece el tamaño del circulo de colisión
|
||||||
|
mCollider.r = 7;
|
||||||
|
|
||||||
|
// Actualiza la posición del circulo de colisión
|
||||||
|
shiftColliders();
|
||||||
|
|
||||||
|
// Establece la velocidad inicial
|
||||||
|
mVelX = 0;
|
||||||
|
mVelY = 0;
|
||||||
|
|
||||||
|
// Establece la velocidad base
|
||||||
|
mBaseSpeed = 1.5;
|
||||||
|
|
||||||
|
// Establece el numero inicial de vidas
|
||||||
|
mStartingLives = 3;
|
||||||
|
mLives = mStartingLives;
|
||||||
|
|
||||||
|
// Establece la puntuación inicial
|
||||||
|
mScore = 0;
|
||||||
|
|
||||||
|
// Establece el multiplicador de puntos inicial
|
||||||
|
mScoreMultiplier = 1.0f;
|
||||||
|
|
||||||
|
// Inicia el contador para la cadencia de disparo
|
||||||
|
mCooldown = 10;
|
||||||
|
|
||||||
|
// Inicia el sprite
|
||||||
|
mSpriteLegs->init(textureLegs, renderer);
|
||||||
|
mSpriteBody->init(textureBody, renderer);
|
||||||
|
|
||||||
|
// Establece el alto y ancho del sprite
|
||||||
|
mSpriteLegs->setWidth(mWidth);
|
||||||
|
mSpriteLegs->setHeight(mHeight);
|
||||||
|
|
||||||
|
mSpriteBody->setWidth(mWidth);
|
||||||
|
mSpriteBody->setHeight(mHeight);
|
||||||
|
|
||||||
|
// Establece la posición del sprite
|
||||||
|
mSpriteLegs->setPosX(int(mPosX));
|
||||||
|
mSpriteLegs->setPosY(mPosY);
|
||||||
|
|
||||||
|
mSpriteBody->setPosX(int(mPosX));
|
||||||
|
mSpriteBody->setPosY(mPosY);
|
||||||
|
|
||||||
|
// Inicializa las variables para la animación
|
||||||
|
mSpriteLegs->setCurrentFrame(0);
|
||||||
|
mSpriteLegs->setAnimationCounter(0);
|
||||||
|
|
||||||
|
mSpriteBody->setCurrentFrame(0);
|
||||||
|
mSpriteBody->setAnimationCounter(0);
|
||||||
|
|
||||||
|
// Establece el numero de frames de cada animacion
|
||||||
|
mSpriteLegs->setAnimationNumFrames(PLAYER_ANIMATION_LEGS_WALKING_STOP, 4);
|
||||||
|
mSpriteLegs->setAnimationNumFrames(PLAYER_ANIMATION_LEGS_WALKING_LEFT, 4);
|
||||||
|
mSpriteLegs->setAnimationNumFrames(PLAYER_ANIMATION_LEGS_WALKING_RIGHT, 4);
|
||||||
|
|
||||||
|
mSpriteBody->setAnimationNumFrames(PLAYER_ANIMATION_BODY_WALKING_LEFT, 4);
|
||||||
|
mSpriteBody->setAnimationNumFrames(PLAYER_ANIMATION_BODY_FIRING_LEFT, 4);
|
||||||
|
mSpriteBody->setAnimationNumFrames(PLAYER_ANIMATION_BODY_WALKING_RIGHT, 4);
|
||||||
|
mSpriteBody->setAnimationNumFrames(PLAYER_ANIMATION_BODY_FIRING_RIGHT, 4);
|
||||||
|
mSpriteBody->setAnimationNumFrames(PLAYER_ANIMATION_BODY_WALKING_STOP, 4);
|
||||||
|
mSpriteBody->setAnimationNumFrames(PLAYER_ANIMATION_BODY_FIRING_UP, 4);
|
||||||
|
mSpriteBody->setAnimationNumFrames(PLAYER_ANIMATION_BODY_WALKING_LEFT_EXTRA_HIT, 4);
|
||||||
|
mSpriteBody->setAnimationNumFrames(PLAYER_ANIMATION_BODY_FIRING_LEFT_EXTRA_HIT, 4);
|
||||||
|
mSpriteBody->setAnimationNumFrames(PLAYER_ANIMATION_BODY_WALKING_RIGHT_EXTRA_HIT, 4);
|
||||||
|
mSpriteBody->setAnimationNumFrames(PLAYER_ANIMATION_BODY_FIRING_RIGHT_EXTRA_HIT, 4);
|
||||||
|
mSpriteBody->setAnimationNumFrames(PLAYER_ANIMATION_BODY_WALKING_STOP_EXTRA_HIT, 4);
|
||||||
|
mSpriteBody->setAnimationNumFrames(PLAYER_ANIMATION_BODY_FIRING_UP_EXTRA_HIT, 4);
|
||||||
|
|
||||||
|
// Establece la velocidad de cada animación
|
||||||
|
mSpriteLegs->setAnimationSpeed(PLAYER_ANIMATION_LEGS_WALKING_STOP, 10);
|
||||||
|
mSpriteLegs->setAnimationSpeed(PLAYER_ANIMATION_LEGS_WALKING_LEFT, 5);
|
||||||
|
mSpriteLegs->setAnimationSpeed(PLAYER_ANIMATION_LEGS_WALKING_RIGHT, 5);
|
||||||
|
|
||||||
|
mSpriteBody->setAnimationSpeed(PLAYER_ANIMATION_BODY_WALKING_LEFT, 5);
|
||||||
|
mSpriteBody->setAnimationSpeed(PLAYER_ANIMATION_BODY_FIRING_LEFT, 5);
|
||||||
|
mSpriteBody->setAnimationSpeed(PLAYER_ANIMATION_BODY_WALKING_RIGHT, 5);
|
||||||
|
mSpriteBody->setAnimationSpeed(PLAYER_ANIMATION_BODY_FIRING_RIGHT, 5);
|
||||||
|
mSpriteBody->setAnimationSpeed(PLAYER_ANIMATION_BODY_WALKING_STOP, 10);
|
||||||
|
mSpriteBody->setAnimationSpeed(PLAYER_ANIMATION_BODY_FIRING_UP, 5);
|
||||||
|
mSpriteBody->setAnimationSpeed(PLAYER_ANIMATION_BODY_WALKING_LEFT_EXTRA_HIT, 5);
|
||||||
|
mSpriteBody->setAnimationSpeed(PLAYER_ANIMATION_BODY_FIRING_LEFT_EXTRA_HIT, 5);
|
||||||
|
mSpriteBody->setAnimationSpeed(PLAYER_ANIMATION_BODY_WALKING_RIGHT_EXTRA_HIT, 5);
|
||||||
|
mSpriteBody->setAnimationSpeed(PLAYER_ANIMATION_BODY_FIRING_RIGHT_EXTRA_HIT, 5);
|
||||||
|
mSpriteBody->setAnimationSpeed(PLAYER_ANIMATION_BODY_WALKING_STOP_EXTRA_HIT, 10);
|
||||||
|
mSpriteBody->setAnimationSpeed(PLAYER_ANIMATION_BODY_FIRING_UP_EXTRA_HIT, 5);
|
||||||
|
|
||||||
|
// Establece si la animación se reproduce en bucle
|
||||||
|
mSpriteLegs->setAnimationLoop(PLAYER_ANIMATION_LEGS_WALKING_STOP, true);
|
||||||
|
mSpriteLegs->setAnimationLoop(PLAYER_ANIMATION_LEGS_WALKING_LEFT, true);
|
||||||
|
mSpriteLegs->setAnimationLoop(PLAYER_ANIMATION_LEGS_WALKING_RIGHT, true);
|
||||||
|
|
||||||
|
mSpriteBody->setAnimationLoop(PLAYER_ANIMATION_BODY_WALKING_LEFT, true);
|
||||||
|
mSpriteBody->setAnimationLoop(PLAYER_ANIMATION_BODY_FIRING_LEFT, true);
|
||||||
|
mSpriteBody->setAnimationLoop(PLAYER_ANIMATION_BODY_WALKING_RIGHT, true);
|
||||||
|
mSpriteBody->setAnimationLoop(PLAYER_ANIMATION_BODY_FIRING_RIGHT, true);
|
||||||
|
mSpriteBody->setAnimationLoop(PLAYER_ANIMATION_BODY_WALKING_STOP, true);
|
||||||
|
mSpriteBody->setAnimationLoop(PLAYER_ANIMATION_BODY_FIRING_UP, true);
|
||||||
|
mSpriteBody->setAnimationLoop(PLAYER_ANIMATION_BODY_WALKING_LEFT_EXTRA_HIT, true);
|
||||||
|
mSpriteBody->setAnimationLoop(PLAYER_ANIMATION_BODY_FIRING_LEFT_EXTRA_HIT, true);
|
||||||
|
mSpriteBody->setAnimationLoop(PLAYER_ANIMATION_BODY_WALKING_RIGHT_EXTRA_HIT, true);
|
||||||
|
mSpriteBody->setAnimationLoop(PLAYER_ANIMATION_BODY_FIRING_RIGHT_EXTRA_HIT, true);
|
||||||
|
mSpriteBody->setAnimationLoop(PLAYER_ANIMATION_BODY_WALKING_STOP_EXTRA_HIT, true);
|
||||||
|
mSpriteBody->setAnimationLoop(PLAYER_ANIMATION_BODY_FIRING_UP_EXTRA_HIT, true);
|
||||||
|
|
||||||
|
// Establece los frames de cada animación
|
||||||
|
mSpriteLegs->setAnimationFrames(PLAYER_ANIMATION_LEGS_WALKING_LEFT, 0, mWidth * 0, mHeight * 0, mWidth, mHeight);
|
||||||
|
mSpriteLegs->setAnimationFrames(PLAYER_ANIMATION_LEGS_WALKING_LEFT, 1, mWidth * 1, mHeight * 0, mWidth, mHeight);
|
||||||
|
mSpriteLegs->setAnimationFrames(PLAYER_ANIMATION_LEGS_WALKING_LEFT, 2, mWidth * 2, mHeight * 0, mWidth, mHeight);
|
||||||
|
mSpriteLegs->setAnimationFrames(PLAYER_ANIMATION_LEGS_WALKING_LEFT, 3, mWidth * 3, mHeight * 0, mWidth, mHeight);
|
||||||
|
|
||||||
|
mSpriteLegs->setAnimationFrames(PLAYER_ANIMATION_LEGS_WALKING_RIGHT, 0, mWidth * 0, mHeight * 1, mWidth, mHeight);
|
||||||
|
mSpriteLegs->setAnimationFrames(PLAYER_ANIMATION_LEGS_WALKING_RIGHT, 1, mWidth * 1, mHeight * 1, mWidth, mHeight);
|
||||||
|
mSpriteLegs->setAnimationFrames(PLAYER_ANIMATION_LEGS_WALKING_RIGHT, 2, mWidth * 2, mHeight * 1, mWidth, mHeight);
|
||||||
|
mSpriteLegs->setAnimationFrames(PLAYER_ANIMATION_LEGS_WALKING_RIGHT, 3, mWidth * 3, mHeight * 1, mWidth, mHeight);
|
||||||
|
|
||||||
|
mSpriteLegs->setAnimationFrames(PLAYER_ANIMATION_LEGS_WALKING_STOP, 0, mWidth * 0, mHeight * 2, mWidth, mHeight);
|
||||||
|
mSpriteLegs->setAnimationFrames(PLAYER_ANIMATION_LEGS_WALKING_STOP, 1, mWidth * 1, mHeight * 2, mWidth, mHeight);
|
||||||
|
mSpriteLegs->setAnimationFrames(PLAYER_ANIMATION_LEGS_WALKING_STOP, 2, mWidth * 2, mHeight * 2, mWidth, mHeight);
|
||||||
|
mSpriteLegs->setAnimationFrames(PLAYER_ANIMATION_LEGS_WALKING_STOP, 3, mWidth * 3, mHeight * 2, mWidth, mHeight);
|
||||||
|
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_LEFT, 0, mWidth * 0, mHeight * 0, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_LEFT, 1, mWidth * 1, mHeight * 0, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_LEFT, 2, mWidth * 2, mHeight * 0, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_LEFT, 3, mWidth * 3, mHeight * 0, mWidth, mHeight);
|
||||||
|
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_LEFT, 0, mWidth * 0, mHeight * 1, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_LEFT, 1, mWidth * 1, mHeight * 1, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_LEFT, 2, mWidth * 2, mHeight * 1, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_LEFT, 3, mWidth * 3, mHeight * 1, mWidth, mHeight);
|
||||||
|
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_RIGHT, 0, mWidth * 0, mHeight * 2, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_RIGHT, 1, mWidth * 1, mHeight * 2, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_RIGHT, 2, mWidth * 2, mHeight * 2, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_RIGHT, 3, mWidth * 3, mHeight * 2, mWidth, mHeight);
|
||||||
|
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_RIGHT, 0, mWidth * 0, mHeight * 3, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_RIGHT, 1, mWidth * 1, mHeight * 3, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_RIGHT, 2, mWidth * 2, mHeight * 3, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_RIGHT, 3, mWidth * 3, mHeight * 3, mWidth, mHeight);
|
||||||
|
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_STOP, 0, mWidth * 0, mHeight * 4, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_STOP, 1, mWidth * 1, mHeight * 4, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_STOP, 2, mWidth * 2, mHeight * 4, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_STOP, 3, mWidth * 3, mHeight * 4, mWidth, mHeight);
|
||||||
|
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_UP, 0, mWidth * 0, mHeight * 5, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_UP, 1, mWidth * 1, mHeight * 5, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_UP, 2, mWidth * 2, mHeight * 5, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_UP, 3, mWidth * 3, mHeight * 5, mWidth, mHeight);
|
||||||
|
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_LEFT_EXTRA_HIT, 0, mWidth * 0, mHeight * 6, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_LEFT_EXTRA_HIT, 1, mWidth * 1, mHeight * 6, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_LEFT_EXTRA_HIT, 2, mWidth * 2, mHeight * 6, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_LEFT_EXTRA_HIT, 3, mWidth * 3, mHeight * 6, mWidth, mHeight);
|
||||||
|
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_LEFT_EXTRA_HIT, 0, mWidth * 0, mHeight * 7, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_LEFT_EXTRA_HIT, 1, mWidth * 1, mHeight * 7, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_LEFT_EXTRA_HIT, 2, mWidth * 2, mHeight * 7, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_LEFT_EXTRA_HIT, 3, mWidth * 3, mHeight * 7, mWidth, mHeight);
|
||||||
|
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_RIGHT_EXTRA_HIT, 0, mWidth * 0, mHeight * 8, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_RIGHT_EXTRA_HIT, 1, mWidth * 1, mHeight * 8, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_RIGHT_EXTRA_HIT, 2, mWidth * 2, mHeight * 8, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_RIGHT_EXTRA_HIT, 3, mWidth * 3, mHeight * 8, mWidth, mHeight);
|
||||||
|
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_RIGHT_EXTRA_HIT, 0, mWidth * 0, mHeight * 9, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_RIGHT_EXTRA_HIT, 1, mWidth * 1, mHeight * 9, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_RIGHT_EXTRA_HIT, 2, mWidth * 2, mHeight * 9, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_RIGHT_EXTRA_HIT, 3, mWidth * 3, mHeight * 9, mWidth, mHeight);
|
||||||
|
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_STOP_EXTRA_HIT, 0, mWidth * 0, mHeight * 10, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_STOP_EXTRA_HIT, 1, mWidth * 1, mHeight * 10, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_STOP_EXTRA_HIT, 2, mWidth * 2, mHeight * 10, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_WALKING_STOP_EXTRA_HIT, 3, mWidth * 3, mHeight * 10, mWidth, mHeight);
|
||||||
|
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_UP_EXTRA_HIT, 0, mWidth * 0, mHeight * 11, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_UP_EXTRA_HIT, 1, mWidth * 1, mHeight * 11, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_UP_EXTRA_HIT, 2, mWidth * 2, mHeight * 11, mWidth, mHeight);
|
||||||
|
mSpriteBody->setAnimationFrames(PLAYER_ANIMATION_BODY_FIRING_UP_EXTRA_HIT, 3, mWidth * 3, mHeight * 11, mWidth, mHeight);
|
||||||
|
|
||||||
|
// Selecciona un frame para pintar
|
||||||
|
mSpriteLegs->setSpriteClip(mSpriteLegs->getAnimationClip(PLAYER_ANIMATION_LEGS_WALKING_STOP, 0));
|
||||||
|
mSpriteBody->setSpriteClip(mSpriteBody->getAnimationClip(PLAYER_ANIMATION_BODY_WALKING_STOP, 0));
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actua en consecuencia de la entrada recibida
|
||||||
|
void Player::setInput(Uint8 input)
|
||||||
|
{
|
||||||
|
switch (input)
|
||||||
|
{
|
||||||
|
case INPUT_LEFT:
|
||||||
|
mVelX = -mBaseSpeed;
|
||||||
|
if (mExtraHit)
|
||||||
|
{
|
||||||
|
setWalkingStatus(PLAYER_STATUS_WALKING_LEFT);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
setWalkingStatus(PLAYER_STATUS_WALKING_LEFT);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case INPUT_RIGHT:
|
||||||
|
mVelX = mBaseSpeed;
|
||||||
|
if (mExtraHit)
|
||||||
|
{
|
||||||
|
setWalkingStatus(PLAYER_STATUS_WALKING_RIGHT);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
setWalkingStatus(PLAYER_STATUS_WALKING_RIGHT);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case INPUT_FIRE_UP:
|
||||||
|
if (mExtraHit)
|
||||||
|
{
|
||||||
|
setFiringStatus(PLAYER_STATUS_FIRING_UP);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
setFiringStatus(PLAYER_STATUS_FIRING_UP);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case INPUT_FIRE_LEFT:
|
||||||
|
if (mExtraHit)
|
||||||
|
{
|
||||||
|
setFiringStatus(PLAYER_STATUS_FIRING_LEFT);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
setFiringStatus(PLAYER_STATUS_FIRING_LEFT);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case INPUT_FIRE_RIGHT:
|
||||||
|
if (mExtraHit)
|
||||||
|
{
|
||||||
|
setFiringStatus(PLAYER_STATUS_FIRING_RIGHT);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
setFiringStatus(PLAYER_STATUS_FIRING_RIGHT);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
mVelX = 0;
|
||||||
|
if (mExtraHit)
|
||||||
|
{
|
||||||
|
setWalkingStatus(PLAYER_STATUS_WALKING_STOP);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
setWalkingStatus(PLAYER_STATUS_WALKING_STOP);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Mueve el jugador a la posición y animación que le corresponde
|
||||||
|
void Player::move()
|
||||||
|
{
|
||||||
|
if (isAlive())
|
||||||
|
{
|
||||||
|
// Mueve el jugador a derecha o izquierda
|
||||||
|
mPosX += mVelX;
|
||||||
|
|
||||||
|
// Si el jugador abandona el area de juego por los laterales
|
||||||
|
if ((mPosX < PLAY_AREA_LEFT) || (mPosX + mWidth > PLAY_AREA_RIGHT))
|
||||||
|
{
|
||||||
|
// Restaura su posición
|
||||||
|
mPosX -= mVelX;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actualiza la posición del sprite
|
||||||
|
mSpriteLegs->setPosX(getPosX());
|
||||||
|
mSpriteLegs->setPosY(mPosY);
|
||||||
|
|
||||||
|
mSpriteBody->setPosX(getPosX());
|
||||||
|
mSpriteBody->setPosY(mPosY);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Pinta el jugador en pantalla
|
||||||
|
void Player::render()
|
||||||
|
{
|
||||||
|
if (isAlive())
|
||||||
|
{
|
||||||
|
if (mInvulnerable)
|
||||||
|
{
|
||||||
|
if ((mInvulnerableTimer % 10) > 4)
|
||||||
|
{
|
||||||
|
mSpriteLegs->render();
|
||||||
|
mSpriteBody->render();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mSpriteLegs->render();
|
||||||
|
mSpriteBody->render();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el estado del jugador cuando camina
|
||||||
|
void Player::setWalkingStatus(Uint8 status)
|
||||||
|
{
|
||||||
|
// Si cambiamos de estado, reiniciamos la animación
|
||||||
|
if (mStatusWalking != status)
|
||||||
|
{
|
||||||
|
mStatusWalking = status;
|
||||||
|
mSpriteLegs->setCurrentFrame(0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el estado del jugador cuando dispara
|
||||||
|
void Player::setFiringStatus(Uint8 status)
|
||||||
|
{
|
||||||
|
// Si cambiamos de estado, reiniciamos la animación
|
||||||
|
if (mStatusFiring != status)
|
||||||
|
{
|
||||||
|
mStatusFiring = status;
|
||||||
|
mSpriteBody->setCurrentFrame(0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece la animación correspondiente al estado
|
||||||
|
void Player::setAnimation()
|
||||||
|
{
|
||||||
|
switch (mStatusWalking)
|
||||||
|
{
|
||||||
|
case PLAYER_STATUS_WALKING_LEFT:
|
||||||
|
mSpriteLegs->animate(PLAYER_ANIMATION_LEGS_WALKING_LEFT);
|
||||||
|
switch (mStatusFiring)
|
||||||
|
{
|
||||||
|
case PLAYER_STATUS_FIRING_UP:
|
||||||
|
if (mExtraHit)
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_FIRING_UP_EXTRA_HIT);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_FIRING_UP);
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case PLAYER_STATUS_FIRING_LEFT:
|
||||||
|
if (mExtraHit)
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_FIRING_LEFT_EXTRA_HIT);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_FIRING_LEFT);
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case PLAYER_STATUS_FIRING_RIGHT:
|
||||||
|
if (mExtraHit)
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_FIRING_RIGHT_EXTRA_HIT);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_FIRING_RIGHT);
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case PLAYER_STATUS_FIRING_NO:
|
||||||
|
if (mExtraHit)
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_WALKING_LEFT_EXTRA_HIT);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_WALKING_LEFT);
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_WALKING_STOP);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case PLAYER_STATUS_WALKING_RIGHT:
|
||||||
|
mSpriteLegs->animate(PLAYER_ANIMATION_LEGS_WALKING_RIGHT);
|
||||||
|
switch (mStatusFiring)
|
||||||
|
{
|
||||||
|
case PLAYER_STATUS_FIRING_UP:
|
||||||
|
if (mExtraHit)
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_FIRING_UP_EXTRA_HIT);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_FIRING_UP);
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case PLAYER_STATUS_FIRING_LEFT:
|
||||||
|
if (mExtraHit)
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_FIRING_LEFT_EXTRA_HIT);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_FIRING_LEFT);
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case PLAYER_STATUS_FIRING_RIGHT:
|
||||||
|
if (mExtraHit)
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_FIRING_RIGHT_EXTRA_HIT);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_FIRING_RIGHT);
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case PLAYER_STATUS_FIRING_NO:
|
||||||
|
if (mExtraHit)
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_WALKING_RIGHT_EXTRA_HIT);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_WALKING_RIGHT);
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_WALKING_STOP);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case PLAYER_STATUS_WALKING_STOP:
|
||||||
|
mSpriteLegs->animate(PLAYER_ANIMATION_LEGS_WALKING_STOP);
|
||||||
|
switch (mStatusFiring)
|
||||||
|
{
|
||||||
|
case PLAYER_STATUS_FIRING_UP:
|
||||||
|
if (mExtraHit)
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_FIRING_UP_EXTRA_HIT);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_FIRING_UP);
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case PLAYER_STATUS_FIRING_LEFT:
|
||||||
|
if (mExtraHit)
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_FIRING_LEFT_EXTRA_HIT);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_FIRING_LEFT);
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case PLAYER_STATUS_FIRING_RIGHT:
|
||||||
|
if (mExtraHit)
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_FIRING_RIGHT_EXTRA_HIT);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_FIRING_RIGHT);
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case PLAYER_STATUS_FIRING_NO:
|
||||||
|
if (mExtraHit)
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_WALKING_STOP_EXTRA_HIT);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_WALKING_STOP);
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
mSpriteBody->animate(PLAYER_ANIMATION_BODY_WALKING_STOP);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
mSpriteLegs->animate(PLAYER_ANIMATION_LEGS_WALKING_STOP);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
int Player::getPosX()
|
||||||
|
{
|
||||||
|
return int(mPosX);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
int Player::getPosY()
|
||||||
|
{
|
||||||
|
return mPosY;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
int Player::getWidth()
|
||||||
|
{
|
||||||
|
return mWidth;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
int Player::getHeight()
|
||||||
|
{
|
||||||
|
return mHeight;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Indica si el jugador puede disparar
|
||||||
|
bool Player::canFire()
|
||||||
|
{
|
||||||
|
// Si el contador a llegado a cero, podemos disparar. En caso contrario decrementamos el contador
|
||||||
|
if (mCooldown > 0)
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Player::setFireCooldown(int time)
|
||||||
|
{
|
||||||
|
mCooldown = time;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actualiza el valor de la variable
|
||||||
|
void Player::updateCooldown()
|
||||||
|
{
|
||||||
|
if (mCooldown > 0)
|
||||||
|
{
|
||||||
|
--mCooldown;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
setFiringStatus(PLAYER_STATUS_FIRING_NO);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actualiza al jugador a su posicion, animación y controla los contadores
|
||||||
|
void Player::update()
|
||||||
|
{
|
||||||
|
move();
|
||||||
|
setAnimation();
|
||||||
|
shiftColliders();
|
||||||
|
updateCooldown();
|
||||||
|
updateInvulnerableTimer();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene la puntuación del jugador
|
||||||
|
int Player::getScore()
|
||||||
|
{
|
||||||
|
return mScore;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Asigna un valor a la puntuación del jugador
|
||||||
|
void Player::setScore(int score)
|
||||||
|
{
|
||||||
|
mScore = score;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Incrementa la puntuación del jugador
|
||||||
|
void Player::addScore(int score)
|
||||||
|
{
|
||||||
|
mScore += score;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
bool Player::isAlive()
|
||||||
|
{
|
||||||
|
return mAlive;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Player::setAlive(bool value)
|
||||||
|
{
|
||||||
|
mAlive = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
float Player::getScoreMultiplier()
|
||||||
|
{
|
||||||
|
return mScoreMultiplier;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Player::setScoreMultiplier(float value)
|
||||||
|
{
|
||||||
|
mScoreMultiplier = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Aumenta el valor de la variable hasta un máximo
|
||||||
|
void Player::incScoreMultiplier()
|
||||||
|
{
|
||||||
|
if (mScoreMultiplier < 5.0f)
|
||||||
|
{
|
||||||
|
mScoreMultiplier += 0.1f;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Decrementa el valor de la variable hasta un mínimo
|
||||||
|
void Player::decScoreMultiplier()
|
||||||
|
{
|
||||||
|
if (mScoreMultiplier > 1.0f)
|
||||||
|
{
|
||||||
|
mScoreMultiplier -= 0.1f;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
bool Player::isInvulnerable()
|
||||||
|
{
|
||||||
|
return mInvulnerable;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Player::setInvulnerable(bool value)
|
||||||
|
{
|
||||||
|
mInvulnerable = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
bool Player::getInvulnerableTimer()
|
||||||
|
{
|
||||||
|
return mInvulnerableTimer;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Player::setInvulnerableTimer(Uint16 value)
|
||||||
|
{
|
||||||
|
mInvulnerableTimer = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actualiza el valor de la variable
|
||||||
|
void Player::updateInvulnerableTimer()
|
||||||
|
{
|
||||||
|
if (mInvulnerableTimer > 0)
|
||||||
|
{
|
||||||
|
--mInvulnerableTimer;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mInvulnerable = false;
|
||||||
|
mInvulnerableTimer = PLAYER_INVULNERABLE_TIMER;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
bool Player::hasExtraHit()
|
||||||
|
{
|
||||||
|
return mExtraHit;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Concede un toque extra al jugador
|
||||||
|
void Player::giveExtraHit()
|
||||||
|
{
|
||||||
|
mExtraHit = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Quita el toque extra al jugador
|
||||||
|
void Player::removeExtraHit()
|
||||||
|
{
|
||||||
|
mExtraHit = false;
|
||||||
|
mInvulnerable = true;
|
||||||
|
mInvulnerableTimer = PLAYER_INVULNERABLE_TIMER;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el circulo de colisión
|
||||||
|
Circle &Player::getCollider()
|
||||||
|
{
|
||||||
|
return mCollider;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actualiza el circulo de colisión a la posición del jugador
|
||||||
|
void Player::shiftColliders()
|
||||||
|
{
|
||||||
|
mCollider.x = Uint16(mPosX + (mWidth / 2));
|
||||||
|
mCollider.y = mPosY + (mHeight / 2);
|
||||||
|
}
|
||||||
173
source/player.h
Normal file
@@ -0,0 +1,173 @@
|
|||||||
|
#pragma once
|
||||||
|
#include "struct.h"
|
||||||
|
#include "animatedsprite.h"
|
||||||
|
|
||||||
|
#ifndef PLAYER_H
|
||||||
|
#define PLAYER_H
|
||||||
|
|
||||||
|
// The player
|
||||||
|
class Player
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
// Constructor
|
||||||
|
Player();
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
~Player();
|
||||||
|
|
||||||
|
// Iniciador
|
||||||
|
void init(float x, int y, LTexture *textureLegs, LTexture *textureBody, SDL_Renderer *renderer);
|
||||||
|
|
||||||
|
// Actua en consecuencia de la entrada recibida
|
||||||
|
void setInput(Uint8 input);
|
||||||
|
|
||||||
|
// Mueve el jugador a la posición y animación que le corresponde
|
||||||
|
void move();
|
||||||
|
|
||||||
|
// Pinta el jugador en pantalla
|
||||||
|
void render();
|
||||||
|
|
||||||
|
// Establece el estado del jugador
|
||||||
|
void setWalkingStatus(Uint8 status);
|
||||||
|
void setFiringStatus(Uint8 status);
|
||||||
|
|
||||||
|
// Establece la animación correspondiente al estado
|
||||||
|
void setAnimation();
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
int getPosX();
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
int getPosY();
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
int getWidth();
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
int getHeight();
|
||||||
|
|
||||||
|
// Indica si el jugador puede disparar
|
||||||
|
bool canFire();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setFireCooldown(int time);
|
||||||
|
|
||||||
|
// Actualiza el valor de la variable
|
||||||
|
void updateCooldown();
|
||||||
|
|
||||||
|
// Actualiza al jugador a su posicion, animación y controla los contadores
|
||||||
|
void update();
|
||||||
|
|
||||||
|
// Obtiene la puntuación del jugador
|
||||||
|
int getScore();
|
||||||
|
|
||||||
|
// Asigna un valor a la puntuación del jugador
|
||||||
|
void setScore(int score);
|
||||||
|
|
||||||
|
// Incrementa la puntuación del jugador
|
||||||
|
void addScore(int score);
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
bool isAlive();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setAlive(bool value);
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
float getScoreMultiplier();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setScoreMultiplier(float value);
|
||||||
|
|
||||||
|
// Aumenta el valor de la variable hasta un máximo
|
||||||
|
void incScoreMultiplier();
|
||||||
|
|
||||||
|
// Decrementa el valor de la variable hasta un mínimo
|
||||||
|
void decScoreMultiplier();
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
bool isInvulnerable();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setInvulnerable(bool value);
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
bool getInvulnerableTimer();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setInvulnerableTimer(Uint16 value);
|
||||||
|
|
||||||
|
// Actualiza el valor de la variable
|
||||||
|
void updateInvulnerableTimer();
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
bool hasExtraHit();
|
||||||
|
|
||||||
|
// Concede un toque extra al jugador
|
||||||
|
void giveExtraHit();
|
||||||
|
|
||||||
|
// Quita el toque extra al jugador
|
||||||
|
void removeExtraHit();
|
||||||
|
|
||||||
|
// Obtiene el circulo de colisión
|
||||||
|
Circle &getCollider();
|
||||||
|
|
||||||
|
private:
|
||||||
|
// Posición X, Y del jugador
|
||||||
|
float mPosX;
|
||||||
|
int mPosY;
|
||||||
|
|
||||||
|
// Altura y anchura del jugador
|
||||||
|
Uint8 mWidth;
|
||||||
|
Uint8 mHeight;
|
||||||
|
|
||||||
|
// Velocidad X, Y del jugador
|
||||||
|
float mVelX;
|
||||||
|
int mVelY;
|
||||||
|
|
||||||
|
// Velocidad base del jugador
|
||||||
|
float mBaseSpeed;
|
||||||
|
|
||||||
|
// Contador durante el cual no puede disparar
|
||||||
|
int mCooldown;
|
||||||
|
|
||||||
|
// Vidas actuales del jugador
|
||||||
|
Uint8 mLives;
|
||||||
|
|
||||||
|
// Vidas iniciales del jugador
|
||||||
|
Uint8 mStartingLives;
|
||||||
|
|
||||||
|
// Puntos del jugador
|
||||||
|
Uint32 mScore;
|
||||||
|
|
||||||
|
// Multiplicador de puntos
|
||||||
|
float mScoreMultiplier;
|
||||||
|
|
||||||
|
// Estado del jugador
|
||||||
|
Uint8 mStatusWalking;
|
||||||
|
Uint8 mStatusFiring;
|
||||||
|
|
||||||
|
// Indica si el jugador está vivo
|
||||||
|
bool mAlive;
|
||||||
|
|
||||||
|
// Indica si el jugador es invulnerable
|
||||||
|
bool mInvulnerable;
|
||||||
|
|
||||||
|
// Temporizador para la invulnerabilidad
|
||||||
|
Uint16 mInvulnerableTimer;
|
||||||
|
|
||||||
|
// Indica si el jugador tiene un toque extra
|
||||||
|
bool mExtraHit;
|
||||||
|
|
||||||
|
// Sprite para dibujar al jugador en pantalla
|
||||||
|
AnimatedSprite *mSpriteLegs;
|
||||||
|
AnimatedSprite *mSpriteBody;
|
||||||
|
|
||||||
|
// Circulo de colisión del jugador
|
||||||
|
Circle mCollider;
|
||||||
|
|
||||||
|
// Actualiza el circulo de colisión a la posición del jugador
|
||||||
|
void shiftColliders();
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
228
source/smartsprite.cpp
Normal file
@@ -0,0 +1,228 @@
|
|||||||
|
#include "const.h"
|
||||||
|
#include "smartsprite.h"
|
||||||
|
|
||||||
|
// Constructor
|
||||||
|
SmartSprite::SmartSprite()
|
||||||
|
{
|
||||||
|
init(nullptr, nullptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
SmartSprite::~SmartSprite()
|
||||||
|
{
|
||||||
|
init(nullptr, nullptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Inicializador
|
||||||
|
void SmartSprite::init(LTexture *texture, SDL_Renderer *renderer)
|
||||||
|
{
|
||||||
|
setTexture(texture);
|
||||||
|
setRenderer(renderer);
|
||||||
|
|
||||||
|
setPosX(0);
|
||||||
|
setPosY(0);
|
||||||
|
setWidth(0);
|
||||||
|
setHeight(0);
|
||||||
|
|
||||||
|
setVelX(0);
|
||||||
|
setVelY(0);
|
||||||
|
setAccelX(0);
|
||||||
|
setAccelY(0);
|
||||||
|
|
||||||
|
setSpriteClip(0, 0, 0, 0);
|
||||||
|
|
||||||
|
setEnabled(false);
|
||||||
|
setEnabledTimer(0);
|
||||||
|
|
||||||
|
mIsOnDestination = false;
|
||||||
|
mDestX = 0;
|
||||||
|
mDestY = 0;
|
||||||
|
|
||||||
|
// El Id siempre es >=0, por lo tanto si no se le asigna Id se queda en negativo
|
||||||
|
mId = -1;
|
||||||
|
|
||||||
|
mIntroEvents = nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Pone a cero los elementos del objeto
|
||||||
|
void SmartSprite::erase()
|
||||||
|
{
|
||||||
|
init(nullptr, nullptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
bool SmartSprite::isEnabled()
|
||||||
|
{
|
||||||
|
return mEnabled;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void SmartSprite::setEnabled(bool state)
|
||||||
|
{
|
||||||
|
mEnabled = state;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
Uint16 SmartSprite::getEnabledTimer()
|
||||||
|
{
|
||||||
|
return mEnabledTimer;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void SmartSprite::setEnabledTimer(Uint16 time)
|
||||||
|
{
|
||||||
|
mEnabledTimer = time;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void SmartSprite::setDestX(int value)
|
||||||
|
{
|
||||||
|
mDestX = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void SmartSprite::setDestY(int value)
|
||||||
|
{
|
||||||
|
mDestY = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
int SmartSprite::getDestX()
|
||||||
|
{
|
||||||
|
return mDestX;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
int SmartSprite::getDestY()
|
||||||
|
{
|
||||||
|
return mDestY;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actualiza la posición y comprueba si ha llegado a su destino
|
||||||
|
bool SmartSprite::update()
|
||||||
|
{
|
||||||
|
if (mEnabled)
|
||||||
|
{
|
||||||
|
move();
|
||||||
|
|
||||||
|
// Comprueba si se desplaza en el eje X hacia la derecha
|
||||||
|
if ((getAccelX() > 0) || ((getAccelX() == 0) && (getVelX() > 0)))
|
||||||
|
{
|
||||||
|
// Comprueba si hemos llegado al destino
|
||||||
|
if (getPosX() > mDestX)
|
||||||
|
{
|
||||||
|
// Lo coloca en posición
|
||||||
|
setPosX(mDestX);
|
||||||
|
|
||||||
|
// Lo detiene
|
||||||
|
setVelX(0.0f);
|
||||||
|
setAccelX(0.0f);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Comprueba si se desplaza en el eje X hacia la izquierda
|
||||||
|
else if ((getAccelX() < 0) || ((getAccelX() == 0) && (getVelX() < 0)))
|
||||||
|
{
|
||||||
|
// Comprueba si hemos llegado al destino
|
||||||
|
if (getPosX() < mDestX)
|
||||||
|
{
|
||||||
|
// Lo coloca en posición
|
||||||
|
setPosX(mDestX);
|
||||||
|
|
||||||
|
// Lo detiene
|
||||||
|
setVelX(0.0f);
|
||||||
|
setAccelX(0.0f);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Comprueba si se desplaza en el eje Y hacia abajo
|
||||||
|
if ((getAccelY() > 0) || ((getAccelY() == 0) && (getVelY() > 0)))
|
||||||
|
{
|
||||||
|
// Comprueba si hemos llegado al destino
|
||||||
|
if (getPosY() > mDestY)
|
||||||
|
{
|
||||||
|
// Lo coloca en posición
|
||||||
|
setPosY(mDestY);
|
||||||
|
|
||||||
|
// Lo detiene
|
||||||
|
setVelY(0.0f);
|
||||||
|
setAccelY(0.0f);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// Comprueba si se desplaza en el eje Y hacia arriba
|
||||||
|
else if ((getAccelY() < 0) || ((getAccelY() == 0) && (getVelY() < 0)))
|
||||||
|
{
|
||||||
|
// Comprueba si hemos llegado al destino
|
||||||
|
if (getPosY() < mDestY)
|
||||||
|
{
|
||||||
|
// Lo coloca en posición
|
||||||
|
setPosY(mDestY);
|
||||||
|
|
||||||
|
// Lo detiene
|
||||||
|
setVelY(0.0f);
|
||||||
|
setAccelY(0.0f);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Comprueba si ha llegado a su destino
|
||||||
|
if ((getPosX() == mDestX) && (getPosY() == mDestY))
|
||||||
|
{
|
||||||
|
mIsOnDestination = true;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mIsOnDestination = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Si esta en el destino comprueba su contador
|
||||||
|
if (mIsOnDestination)
|
||||||
|
{
|
||||||
|
// Si el contador es mayor que cero, lo decrementa
|
||||||
|
if (mEnabledTimer > 0)
|
||||||
|
{
|
||||||
|
--mEnabledTimer;
|
||||||
|
}
|
||||||
|
// Si ha llegado a cero, deshabilita el objeto o manda el aviso en función de si tiene Id
|
||||||
|
else if (mEnabledTimer == 0)
|
||||||
|
{
|
||||||
|
if (mId < 0)
|
||||||
|
{
|
||||||
|
mEnabled = false;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mIntroEvents[mId] = EVENT_COMPLETED;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return mIsOnDestination;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
bool SmartSprite::isOnDestination()
|
||||||
|
{
|
||||||
|
return mIsOnDestination;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Pinta el objeto en pantalla
|
||||||
|
void SmartSprite::render()
|
||||||
|
{
|
||||||
|
if (mEnabled)
|
||||||
|
{
|
||||||
|
MovingSprite::render();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void SmartSprite::setId(int id)
|
||||||
|
{
|
||||||
|
mId = id;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void SmartSprite::setIntroEvents(Uint8 *value)
|
||||||
|
{
|
||||||
|
mIntroEvents = value;
|
||||||
|
}
|
||||||
84
source/smartsprite.h
Normal file
@@ -0,0 +1,84 @@
|
|||||||
|
#pragma once
|
||||||
|
#include "struct.h"
|
||||||
|
#include "animatedsprite.h"
|
||||||
|
|
||||||
|
#ifndef SMARTSPRITE_H
|
||||||
|
#define SMARTSPRITE_H
|
||||||
|
|
||||||
|
// Clase SmartSprite
|
||||||
|
class SmartSprite : public AnimatedSprite
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
// Constructor
|
||||||
|
SmartSprite();
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
~SmartSprite();
|
||||||
|
|
||||||
|
// Inicializador
|
||||||
|
void init(LTexture *texture, SDL_Renderer *renderer);
|
||||||
|
|
||||||
|
// Pone a cero los elementos del objeto
|
||||||
|
void erase();
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
bool isEnabled();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setEnabled(bool state);
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
Uint16 getEnabledTimer();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setEnabledTimer(Uint16 time);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setDestX(int value);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setDestY(int value);
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
int getDestX();
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
int getDestY();
|
||||||
|
|
||||||
|
// Actualiza la posición y comprueba si ha llegado a su destino
|
||||||
|
bool update();
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
bool isOnDestination();
|
||||||
|
|
||||||
|
// Pinta el objeto en pantalla
|
||||||
|
void render();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setId(int id);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setIntroEvents(Uint8 *value);
|
||||||
|
|
||||||
|
private:
|
||||||
|
// Indica si esta habilitado
|
||||||
|
bool mEnabled;
|
||||||
|
|
||||||
|
// Contador
|
||||||
|
Uint16 mEnabledTimer;
|
||||||
|
|
||||||
|
// Indica si está en el destino
|
||||||
|
bool mIsOnDestination;
|
||||||
|
|
||||||
|
// Posicion de destino
|
||||||
|
int mDestX;
|
||||||
|
int mDestY;
|
||||||
|
|
||||||
|
// Identificador
|
||||||
|
int mId;
|
||||||
|
|
||||||
|
// Dirección del array de eventos donde notificar el estado
|
||||||
|
Uint8 *mIntroEvents;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
149
source/sprite.cpp
Normal file
@@ -0,0 +1,149 @@
|
|||||||
|
#include "sprite.h"
|
||||||
|
|
||||||
|
// Constructor
|
||||||
|
Sprite::Sprite()
|
||||||
|
{
|
||||||
|
init(0, 0, 0, 0, nullptr, nullptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
Sprite::~Sprite()
|
||||||
|
{
|
||||||
|
mTexture = nullptr;
|
||||||
|
mRenderer = nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Inicializador
|
||||||
|
void Sprite::init(int x, int y, int w, int h, LTexture *texture, SDL_Renderer *renderer)
|
||||||
|
{
|
||||||
|
// Establece el alto y el ancho del sprite
|
||||||
|
setWidth(w);
|
||||||
|
setHeight(h);
|
||||||
|
|
||||||
|
// Establece la posición X,Y del sprite
|
||||||
|
setPosX(x);
|
||||||
|
setPosY(y);
|
||||||
|
|
||||||
|
// Establece el puntero al renderizador de la ventana
|
||||||
|
setRenderer(renderer);
|
||||||
|
|
||||||
|
// Establece la textura donde están los gráficos para el sprite
|
||||||
|
setTexture(texture);
|
||||||
|
|
||||||
|
// Establece el rectangulo de donde coger la imagen
|
||||||
|
setSpriteClip(0, 0, w, h);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Inicializador
|
||||||
|
void Sprite::init(SDL_Rect rect, LTexture *texture, SDL_Renderer *renderer)
|
||||||
|
{
|
||||||
|
// Establece el alto y el ancho del sprite
|
||||||
|
mWidth = rect.w;
|
||||||
|
mHeight = rect.h;
|
||||||
|
|
||||||
|
// Establece la posición X,Y del sprite
|
||||||
|
mPosX = rect.x;
|
||||||
|
mPosY = rect.y;
|
||||||
|
|
||||||
|
// Establece el puntero al renderizador de la ventana
|
||||||
|
setRenderer(renderer);
|
||||||
|
|
||||||
|
// Establece la textura donde están los gráficos para el sprite
|
||||||
|
setTexture(texture);
|
||||||
|
|
||||||
|
// Establece el rectangulo de donde coger la imagen
|
||||||
|
setSpriteClip(rect);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Muestra el sprite por pantalla
|
||||||
|
void Sprite::render()
|
||||||
|
{
|
||||||
|
mTexture->render(mRenderer, mPosX, mPosY, &mSpriteClip);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obten el valor de la variable
|
||||||
|
int Sprite::getPosX()
|
||||||
|
{
|
||||||
|
return mPosX;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obten el valor de la variable
|
||||||
|
int Sprite::getPosY()
|
||||||
|
{
|
||||||
|
return mPosY;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obten el valor de la variable
|
||||||
|
int Sprite::getWidth()
|
||||||
|
{
|
||||||
|
return mWidth;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obten el valor de la variable
|
||||||
|
int Sprite::getHeight()
|
||||||
|
{
|
||||||
|
return mHeight;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Sprite::setPosX(int x)
|
||||||
|
{
|
||||||
|
mPosX = x;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Sprite::setPosY(int y)
|
||||||
|
{
|
||||||
|
mPosY = y;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Sprite::setWidth(int w)
|
||||||
|
{
|
||||||
|
mWidth = w;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Sprite::setHeight(int h)
|
||||||
|
{
|
||||||
|
mHeight = h;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obten el valor de la variable
|
||||||
|
SDL_Rect Sprite::getSpriteClip()
|
||||||
|
{
|
||||||
|
return mSpriteClip;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Sprite::setSpriteClip(SDL_Rect rect)
|
||||||
|
{
|
||||||
|
mSpriteClip = rect;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Sprite::setSpriteClip(int x, int y, int w, int h)
|
||||||
|
{
|
||||||
|
mSpriteClip.x = x;
|
||||||
|
mSpriteClip.y = y;
|
||||||
|
mSpriteClip.w = w;
|
||||||
|
mSpriteClip.h = h;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obten el valor de la variable
|
||||||
|
LTexture *Sprite::getTexture()
|
||||||
|
{
|
||||||
|
return mTexture;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Sprite::setTexture(LTexture *texture)
|
||||||
|
{
|
||||||
|
mTexture = texture;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Sprite::setRenderer(SDL_Renderer *renderer)
|
||||||
|
{
|
||||||
|
mRenderer = renderer;
|
||||||
|
}
|
||||||
87
source/sprite.h
Normal file
@@ -0,0 +1,87 @@
|
|||||||
|
#pragma once
|
||||||
|
#include "ifdefs.h"
|
||||||
|
#include "ltexture.h"
|
||||||
|
|
||||||
|
#ifndef SPRITE_H
|
||||||
|
#define SPRITE_H
|
||||||
|
|
||||||
|
// Clase sprite
|
||||||
|
class Sprite
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
// Constructor
|
||||||
|
Sprite();
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
~Sprite();
|
||||||
|
|
||||||
|
// Inicializador
|
||||||
|
void init(int x, int y, int w, int h, LTexture *texture, SDL_Renderer *renderer);
|
||||||
|
void init(SDL_Rect rect, LTexture *texture, SDL_Renderer *renderer);
|
||||||
|
|
||||||
|
// Muestra el sprite por pantalla
|
||||||
|
void render();
|
||||||
|
|
||||||
|
// Obten el valor de la variable
|
||||||
|
int getPosX();
|
||||||
|
|
||||||
|
// Obten el valor de la variable
|
||||||
|
int getPosY();
|
||||||
|
|
||||||
|
// Obten el valor de la variable
|
||||||
|
int getWidth();
|
||||||
|
|
||||||
|
// Obten el valor de la variable
|
||||||
|
int getHeight();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setPosX(int x);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setPosY(int y);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setWidth(int w);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setHeight(int h);
|
||||||
|
|
||||||
|
// Obten el valor de la variable
|
||||||
|
SDL_Rect getSpriteClip();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setSpriteClip(SDL_Rect rect);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setSpriteClip(int x, int y, int w, int h);
|
||||||
|
|
||||||
|
// Obten el valor de la variable
|
||||||
|
LTexture* getTexture();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setTexture(LTexture *texture);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setRenderer(SDL_Renderer *renderer);
|
||||||
|
|
||||||
|
|
||||||
|
protected:
|
||||||
|
// Posición X,Y donde dibujar el sprite
|
||||||
|
int mPosX;
|
||||||
|
int mPosY;
|
||||||
|
|
||||||
|
// Alto y ancho del sprite
|
||||||
|
Uint16 mWidth;
|
||||||
|
Uint16 mHeight;
|
||||||
|
|
||||||
|
// Puntero al renderizador de la ventana
|
||||||
|
SDL_Renderer *mRenderer;
|
||||||
|
|
||||||
|
// Textura donde estan todos los dibujos del sprite
|
||||||
|
LTexture *mTexture;
|
||||||
|
|
||||||
|
// Rectangulo de la textura que se dibujará en pantalla
|
||||||
|
SDL_Rect mSpriteClip;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
7762
source/stb_image.h
Normal file
5565
source/stb_vorbis.c
Normal file
42
source/struct.h
Normal file
@@ -0,0 +1,42 @@
|
|||||||
|
#pragma once
|
||||||
|
#include "ifdefs.h"
|
||||||
|
|
||||||
|
#ifndef STRUCT_H
|
||||||
|
#define STRUCT_H
|
||||||
|
|
||||||
|
// Estructura para definir un circulo
|
||||||
|
struct Circle
|
||||||
|
{
|
||||||
|
Uint16 x;
|
||||||
|
Uint16 y;
|
||||||
|
Uint8 r;
|
||||||
|
};
|
||||||
|
|
||||||
|
// Estructura para definir todas las entradas que aceptará el programa
|
||||||
|
struct Input
|
||||||
|
{
|
||||||
|
Uint8 up;
|
||||||
|
Uint8 down;
|
||||||
|
Uint8 left;
|
||||||
|
Uint8 right;
|
||||||
|
Uint8 escape;
|
||||||
|
Uint8 pause;
|
||||||
|
Uint8 fire;
|
||||||
|
Uint8 fireLeft;
|
||||||
|
Uint8 fireRight;
|
||||||
|
Uint8 accept;
|
||||||
|
Uint8 cancel;
|
||||||
|
};
|
||||||
|
|
||||||
|
// Estructura para mapear el teclado usado en la demo
|
||||||
|
struct DemoKeys
|
||||||
|
{
|
||||||
|
Uint8 left;
|
||||||
|
Uint8 right;
|
||||||
|
Uint8 noInput;
|
||||||
|
Uint8 fire;
|
||||||
|
Uint8 fireLeft;
|
||||||
|
Uint8 fireRight;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
244
source/text.cpp
Normal file
@@ -0,0 +1,244 @@
|
|||||||
|
#include "const.h"
|
||||||
|
#include "text.h"
|
||||||
|
|
||||||
|
// Constructor
|
||||||
|
Text::Text()
|
||||||
|
{
|
||||||
|
mSprite = new Sprite();
|
||||||
|
init(nullptr, nullptr, 0, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
Text::~Text()
|
||||||
|
{
|
||||||
|
delete mSprite;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Inicializador
|
||||||
|
void Text::init(LTexture *texture, SDL_Renderer *renderer, Uint8 type, Uint8 size)
|
||||||
|
{
|
||||||
|
// Inicializa variables
|
||||||
|
mType = type;
|
||||||
|
mSize = size;
|
||||||
|
|
||||||
|
// Inicia los valores del sprite que dibuja las letras
|
||||||
|
mSprite->setWidth(size);
|
||||||
|
mSprite->setHeight(size);
|
||||||
|
mSprite->setPosX(0);
|
||||||
|
mSprite->setPosY(0);
|
||||||
|
mSprite->setTexture(texture);
|
||||||
|
mSprite->setRenderer(renderer);
|
||||||
|
mSprite->setSpriteClip(0, 0, mSprite->getWidth(), mSprite->getHeight());
|
||||||
|
|
||||||
|
// Cadena con los caracteres ascii que se van a inicializar
|
||||||
|
// std::string text = " 0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz-/().:#!";
|
||||||
|
std::string text = " !\"#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ{\\[]]^_`abcdefghijklmnopqrstuvwxyz";
|
||||||
|
|
||||||
|
// Inicializa a cero el vector con las coordenadas
|
||||||
|
for (Uint8 i = 0; i < 255; i++)
|
||||||
|
{
|
||||||
|
mOffset[i].x = 0;
|
||||||
|
mOffset[i].y = 0;
|
||||||
|
mOffset[i].w = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece las coordenadas para cada caracter ascii de la cadena y su ancho
|
||||||
|
for (Uint8 i = 0; i < text.length(); ++i)
|
||||||
|
{
|
||||||
|
mOffset[int(text[i])].x = ((int(text[i]) - 32) % 15) * mSprite->getWidth();
|
||||||
|
mOffset[int(text[i])].y = ((int(text[i]) - 32) / 15) * mSprite->getHeight();
|
||||||
|
if (type == TEXT_FIXED)
|
||||||
|
{
|
||||||
|
mOffset[int(text[i])].w = size;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el ancho de cada caracter
|
||||||
|
if (type == TEXT_VARIABLE)
|
||||||
|
{
|
||||||
|
mOffset[int(' ')].w = 7;
|
||||||
|
mOffset[int('-')].w = 6;
|
||||||
|
mOffset[int('/')].w = 5;
|
||||||
|
mOffset[int('(')].w = 5;
|
||||||
|
mOffset[int(')')].w = 5;
|
||||||
|
mOffset[int('.')].w = 4;
|
||||||
|
mOffset[int(':')].w = 4;
|
||||||
|
mOffset[int('#')].w = 7;
|
||||||
|
mOffset[int('!')].w = 7;
|
||||||
|
mOffset[int('\'')].w = 3;
|
||||||
|
|
||||||
|
mOffset[int('0')].w = 7;
|
||||||
|
mOffset[int('1')].w = 5;
|
||||||
|
mOffset[int('2')].w = 7;
|
||||||
|
mOffset[int('3')].w = 7;
|
||||||
|
mOffset[int('4')].w = 7;
|
||||||
|
mOffset[int('5')].w = 7;
|
||||||
|
mOffset[int('6')].w = 7;
|
||||||
|
mOffset[int('7')].w = 7;
|
||||||
|
mOffset[int('8')].w = 7;
|
||||||
|
mOffset[int('9')].w = 7;
|
||||||
|
|
||||||
|
mOffset[int('A')].w = 7;
|
||||||
|
mOffset[int('B')].w = 7;
|
||||||
|
mOffset[int('C')].w = 7;
|
||||||
|
mOffset[int('D')].w = 7;
|
||||||
|
mOffset[int('E')].w = 7;
|
||||||
|
mOffset[int('F')].w = 7;
|
||||||
|
mOffset[int('G')].w = 7;
|
||||||
|
mOffset[int('H')].w = 7;
|
||||||
|
mOffset[int('I')].w = 4;
|
||||||
|
mOffset[int('J')].w = 6;
|
||||||
|
mOffset[int('K')].w = 8;
|
||||||
|
mOffset[int('L')].w = 6;
|
||||||
|
mOffset[int('M')].w = 9;
|
||||||
|
mOffset[int('N')].w = 8;
|
||||||
|
mOffset[int('O')].w = 8;
|
||||||
|
mOffset[int('P')].w = 7;
|
||||||
|
mOffset[int('Q')].w = 8;
|
||||||
|
mOffset[int('R')].w = 7;
|
||||||
|
mOffset[int('S')].w = 6;
|
||||||
|
mOffset[int('T')].w = 8;
|
||||||
|
mOffset[int('U')].w = 7;
|
||||||
|
mOffset[int('V')].w = 8;
|
||||||
|
mOffset[int('W')].w = 9;
|
||||||
|
mOffset[int('X')].w = 8;
|
||||||
|
mOffset[int('Y')].w = 8;
|
||||||
|
mOffset[int('Z')].w = 7;
|
||||||
|
|
||||||
|
mOffset[int('a')].w = 7;
|
||||||
|
mOffset[int('b')].w = 7;
|
||||||
|
mOffset[int('c')].w = 6;
|
||||||
|
mOffset[int('d')].w = 7;
|
||||||
|
mOffset[int('e')].w = 7;
|
||||||
|
mOffset[int('f')].w = 5;
|
||||||
|
mOffset[int('g')].w = 7;
|
||||||
|
mOffset[int('h')].w = 7;
|
||||||
|
mOffset[int('i')].w = 4;
|
||||||
|
mOffset[int('j')].w = 5;
|
||||||
|
mOffset[int('k')].w = 7;
|
||||||
|
mOffset[int('l')].w = 4;
|
||||||
|
mOffset[int('m')].w = 10;
|
||||||
|
mOffset[int('n')].w = 7;
|
||||||
|
mOffset[int('o')].w = 7;
|
||||||
|
mOffset[int('p')].w = 7;
|
||||||
|
mOffset[int('q')].w = 7;
|
||||||
|
mOffset[int('r')].w = 6;
|
||||||
|
mOffset[int('s')].w = 6;
|
||||||
|
mOffset[int('t')].w = 5;
|
||||||
|
mOffset[int('u')].w = 7;
|
||||||
|
mOffset[int('v')].w = 7;
|
||||||
|
mOffset[int('w')].w = 9;
|
||||||
|
mOffset[int('x')].w = 7;
|
||||||
|
mOffset[int('y')].w = 7;
|
||||||
|
mOffset[int('z')].w = 7;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Escribe el texto en pantalla
|
||||||
|
void Text::write(int x, int y, std::string text)
|
||||||
|
{
|
||||||
|
Uint16 shift = 0;
|
||||||
|
for (Uint8 i = 0; i < text.length(); ++i)
|
||||||
|
{
|
||||||
|
mSprite->setSpriteClip(mOffset[int(text[i])].x, mOffset[int(text[i])].y, mSprite->getWidth(), mSprite->getHeight());
|
||||||
|
mSprite->setPosX(x + shift);
|
||||||
|
mSprite->setPosY(y);
|
||||||
|
mSprite->render();
|
||||||
|
shift += (mOffset[int(text[i])].w);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Escribe el texto en pantalla con kerning
|
||||||
|
void Text::write(int x, int y, std::string text, int kerning)
|
||||||
|
{
|
||||||
|
Uint16 shift = 0;
|
||||||
|
for (Uint8 i = 0; i < text.length(); ++i)
|
||||||
|
{
|
||||||
|
mSprite->setSpriteClip(mOffset[int(text[i])].x, mOffset[int(text[i])].y, mSprite->getWidth(), mSprite->getHeight());
|
||||||
|
mSprite->setPosX(x + shift);
|
||||||
|
mSprite->setPosY(y);
|
||||||
|
mSprite->render();
|
||||||
|
shift += (mOffset[int(text[i])].w + kerning);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Escribe una cantidad determinada de caracteres del texto en pantalla
|
||||||
|
void Text::write(int x, int y, std::string text, int kerning, Uint8 lenght)
|
||||||
|
{
|
||||||
|
Uint16 shift = 0;
|
||||||
|
for (Uint8 i = 0; i < lenght; ++i)
|
||||||
|
{
|
||||||
|
if (text[i] == '*')
|
||||||
|
{
|
||||||
|
shift = 0;
|
||||||
|
y += mSize;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mSprite->setSpriteClip(mOffset[int(text[i])].x, mOffset[int(text[i])].y, mSprite->getWidth(), mSprite->getHeight());
|
||||||
|
mSprite->setPosX(x + shift);
|
||||||
|
mSprite->setPosY(y);
|
||||||
|
mSprite->render();
|
||||||
|
shift += (mOffset[int(text[i])].w + kerning);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Escribe el texto con colores
|
||||||
|
void Text::writeColored(int x, int y, std::string text, Uint8 R, Uint8 G, Uint8 B)
|
||||||
|
{
|
||||||
|
mSprite->getTexture()->setColor(R, G, B);
|
||||||
|
write(x, y, text);
|
||||||
|
mSprite->getTexture()->setColor(255, 255, 255);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Escribe el texto centrado en un punto x y con kerning
|
||||||
|
void Text::writeCentered(int x, int y, std::string text, int kerning)
|
||||||
|
{
|
||||||
|
// Uint16 lenght = Text::lenght(text, kerning);
|
||||||
|
x = x - (Text::lenght(text, kerning) / 2);
|
||||||
|
Uint16 shift = 0;
|
||||||
|
for (Uint8 i = 0; i < text.length(); ++i)
|
||||||
|
{
|
||||||
|
mSprite->setSpriteClip(mOffset[int(text[i])].x, mOffset[int(text[i])].y, mSprite->getWidth(), mSprite->getHeight());
|
||||||
|
mSprite->setPosX(x + shift);
|
||||||
|
mSprite->setPosY(y);
|
||||||
|
mSprite->render();
|
||||||
|
shift += (mOffset[int(text[i])].w + kerning);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene la longitud en pixels de una cadena
|
||||||
|
Uint16 Text::lenght(std::string text, int kerning)
|
||||||
|
{
|
||||||
|
Uint16 shift = 0;
|
||||||
|
for (Uint8 i = 0; i < text.length(); ++i)
|
||||||
|
{
|
||||||
|
shift += (mOffset[int(text[i])].w + kerning);
|
||||||
|
}
|
||||||
|
return shift;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
Uint8 Text::getType()
|
||||||
|
{
|
||||||
|
return mType;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Text::setType(Uint8 type)
|
||||||
|
{
|
||||||
|
mType = type;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
Uint8 Text::getSize()
|
||||||
|
{
|
||||||
|
return mSize;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Text::setSize(Uint8 size)
|
||||||
|
{
|
||||||
|
mSize = size;
|
||||||
|
}
|
||||||
66
source/text.h
Normal file
@@ -0,0 +1,66 @@
|
|||||||
|
#pragma once
|
||||||
|
#include "sprite.h"
|
||||||
|
|
||||||
|
#ifndef TEXT_H
|
||||||
|
#define TEXT_H
|
||||||
|
|
||||||
|
// Clase texto. Pinta texto en pantalla a partir de un bitmap
|
||||||
|
class Text
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
// Constructor
|
||||||
|
Text();
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
~Text();
|
||||||
|
|
||||||
|
// Inicializador
|
||||||
|
void init(LTexture *texture, SDL_Renderer *renderer, Uint8 type, Uint8 size);
|
||||||
|
|
||||||
|
// Escribe el texto en pantalla
|
||||||
|
void write(int x, int y, std::string text);
|
||||||
|
void write(int x, int y, std::string text, int kerning);
|
||||||
|
void write(int x, int y, std::string text, int kerning, Uint8 lenght);
|
||||||
|
|
||||||
|
// Escribe el texto con colores
|
||||||
|
void writeColored(int x, int y, std::string text, Uint8 R, Uint8 G, Uint8 B);
|
||||||
|
|
||||||
|
// Escribe el texto centrado en un punto x y con kerning
|
||||||
|
void writeCentered(int x, int y, std::string text, int kerning);
|
||||||
|
|
||||||
|
// Obtiene la longitud en pixels de una cadena
|
||||||
|
Uint16 lenght(std::string text, int kerning);
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
Uint8 getType();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setType(Uint8 type);
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
Uint8 getSize();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setSize(Uint8 size);
|
||||||
|
|
||||||
|
private:
|
||||||
|
// Objeto con los graficos para el texto
|
||||||
|
Sprite *mSprite;
|
||||||
|
|
||||||
|
// Coordenadas dentro del PNG para cada código ascii y su anchura
|
||||||
|
struct Offset
|
||||||
|
{
|
||||||
|
int x;
|
||||||
|
int y;
|
||||||
|
Uint8 w;
|
||||||
|
};
|
||||||
|
|
||||||
|
// Vector con las posiciones y ancho de cada letra
|
||||||
|
Offset mOffset[255];
|
||||||
|
|
||||||
|
// Indica si el texto es de anchura fija o variable
|
||||||
|
Uint8 mType;
|
||||||
|
Uint8 mSize;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
158
source/text2.cpp
Normal file
@@ -0,0 +1,158 @@
|
|||||||
|
#include "const.h"
|
||||||
|
#include "text2.h"
|
||||||
|
|
||||||
|
// Constructor
|
||||||
|
Text2::Text2()
|
||||||
|
{
|
||||||
|
init(nullptr, nullptr, 0, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
Text2::~Text2()
|
||||||
|
{
|
||||||
|
init(nullptr, nullptr, 0, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Inicializador
|
||||||
|
void Text2::init(LTexture *texture, SDL_Renderer *renderer, Uint8 type, Uint8 size)
|
||||||
|
{
|
||||||
|
Text::init(texture, renderer, type, size);
|
||||||
|
mPosX = 0;
|
||||||
|
mPosY = 0;
|
||||||
|
mKerning = 0;
|
||||||
|
mCaption = "";
|
||||||
|
mWrittingSpeed = 0;
|
||||||
|
mWrittingTimer = 0;
|
||||||
|
mIndex = 0;
|
||||||
|
mLenght = 0;
|
||||||
|
mWrittingCompleted = false;
|
||||||
|
mEnabled = false;
|
||||||
|
mEnabledTimer = 0;
|
||||||
|
mId = -1;
|
||||||
|
mIntroEvents = nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Text2::setPosX(int value)
|
||||||
|
{
|
||||||
|
mPosX = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Text2::setPosY(int value)
|
||||||
|
{
|
||||||
|
mPosY = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Text2::setKerning(int value)
|
||||||
|
{
|
||||||
|
mKerning = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Text2::setCaption(std::string text)
|
||||||
|
{
|
||||||
|
mCaption = text;
|
||||||
|
mLenght = text.length();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Text2::setWrittingSpeed(Uint16 value)
|
||||||
|
{
|
||||||
|
mWrittingSpeed = value;
|
||||||
|
mWrittingTimer = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Text2::setEnabled(bool value)
|
||||||
|
{
|
||||||
|
mEnabled = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
bool Text2::IsEnabled()
|
||||||
|
{
|
||||||
|
return mEnabled;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Text2::setEnabledTimer(Uint16 value)
|
||||||
|
{
|
||||||
|
mEnabledTimer = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
Uint16 Text2::getEnabledTimer()
|
||||||
|
{
|
||||||
|
return mEnabledTimer;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Actualiza el objeto
|
||||||
|
void Text2::update()
|
||||||
|
{
|
||||||
|
if (mEnabled)
|
||||||
|
{
|
||||||
|
if (mWrittingCompleted == false)
|
||||||
|
{
|
||||||
|
if (mWrittingTimer > 0)
|
||||||
|
{
|
||||||
|
--mWrittingTimer;
|
||||||
|
}
|
||||||
|
if (mWrittingTimer == 0)
|
||||||
|
{
|
||||||
|
++mIndex;
|
||||||
|
mWrittingTimer = mWrittingSpeed;
|
||||||
|
}
|
||||||
|
if (mIndex == mLenght)
|
||||||
|
{
|
||||||
|
mWrittingCompleted = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (mWrittingCompleted)
|
||||||
|
{
|
||||||
|
if (mEnabledTimer > 0)
|
||||||
|
{
|
||||||
|
--mEnabledTimer;
|
||||||
|
}
|
||||||
|
else if (mEnabledTimer == 0)
|
||||||
|
{
|
||||||
|
if (mId < 0)
|
||||||
|
{
|
||||||
|
mEnabled = false;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mIntroEvents[mId] = EVENT_COMPLETED;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Dibuja el objeto en pantalla
|
||||||
|
void Text2::render()
|
||||||
|
{
|
||||||
|
if (mEnabled)
|
||||||
|
{
|
||||||
|
Text::write(mPosX, mPosY, mCaption, mKerning, mIndex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Centra la cadena de texto a un punto X
|
||||||
|
void Text2::center(int x)
|
||||||
|
{
|
||||||
|
setPosX(x - (lenght(mCaption, mKerning) / 2));
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Text2::setId(int id)
|
||||||
|
{
|
||||||
|
mId = id;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void Text2::setIntroEvents(Uint8 *value)
|
||||||
|
{
|
||||||
|
mIntroEvents = value;
|
||||||
|
}
|
||||||
102
source/text2.h
Normal file
@@ -0,0 +1,102 @@
|
|||||||
|
#pragma once
|
||||||
|
#include "sprite.h"
|
||||||
|
#include "text.h"
|
||||||
|
|
||||||
|
#ifndef TEXT2_H
|
||||||
|
#define TEXT2_H
|
||||||
|
|
||||||
|
// Clase texto. Pinta texto en pantalla a partir de un bitmap
|
||||||
|
class Text2 : public Text
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
// Constructor
|
||||||
|
Text2();
|
||||||
|
|
||||||
|
// Destructor
|
||||||
|
~Text2();
|
||||||
|
|
||||||
|
// Inicializador
|
||||||
|
void init(LTexture *texture, SDL_Renderer *renderer, Uint8 type, Uint8 size);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setPosX(int value);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setPosY(int value);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setKerning(int value);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setCaption(std::string text);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setWrittingSpeed(Uint16 value);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setEnabled(bool value);
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
bool IsEnabled();
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setEnabledTimer(Uint16 value);
|
||||||
|
|
||||||
|
// Obtiene el valor de la variable
|
||||||
|
Uint16 getEnabledTimer();
|
||||||
|
|
||||||
|
// Actualiza el objeto
|
||||||
|
void update();
|
||||||
|
|
||||||
|
// Dibuja el objeto en pantalla
|
||||||
|
void render();
|
||||||
|
|
||||||
|
// Centra la cadena de texto a un punto X
|
||||||
|
void center(int x);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setId(int id);
|
||||||
|
|
||||||
|
// Establece el valor de la variable
|
||||||
|
void setIntroEvents(Uint8 *value);
|
||||||
|
|
||||||
|
private:
|
||||||
|
// Posicion X/Y donde empezar a escribir el texto
|
||||||
|
int mPosX;
|
||||||
|
int mPosY;
|
||||||
|
|
||||||
|
// Kerning del texto
|
||||||
|
int mKerning;
|
||||||
|
|
||||||
|
// Texto para escribir
|
||||||
|
std::string mCaption;
|
||||||
|
|
||||||
|
// Velocidad de escritura
|
||||||
|
Uint16 mWrittingSpeed;
|
||||||
|
|
||||||
|
// Temporizador de escritura para cada caracter
|
||||||
|
Uint16 mWrittingTimer;
|
||||||
|
|
||||||
|
// Posición del texto que se está escribiendo
|
||||||
|
Uint16 mIndex;
|
||||||
|
|
||||||
|
// Longitud de la cadena a escribir
|
||||||
|
Uint16 mLenght;
|
||||||
|
|
||||||
|
// Indica si se ha escrito todo el texto
|
||||||
|
bool mWrittingCompleted;
|
||||||
|
|
||||||
|
// Indica si el objeto está habilitado
|
||||||
|
bool mEnabled;
|
||||||
|
|
||||||
|
// Temporizador para deshabilitar el objeto
|
||||||
|
Uint16 mEnabledTimer;
|
||||||
|
|
||||||
|
// Identificador
|
||||||
|
int mId;
|
||||||
|
|
||||||
|
// Dirección del array de eventos donde notificar el estado
|
||||||
|
Uint8 *mIntroEvents;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
36
sync.sh
Executable file
@@ -0,0 +1,36 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
readonly PROJECT=coffee_crisis
|
||||||
|
|
||||||
|
readonly USAGE="
|
||||||
|
USAGE:
|
||||||
|
$(basename "$0") [UPLOAD or DOWNLOAD]"
|
||||||
|
|
||||||
|
function help_message() {
|
||||||
|
echo "$USAGE"
|
||||||
|
}
|
||||||
|
|
||||||
|
PARAMETERS="UPLOAD DOWNLOAD upload download"
|
||||||
|
|
||||||
|
# check if there are all the parameters
|
||||||
|
if [ "$#" -ne 1 ]; then
|
||||||
|
help_message
|
||||||
|
exit 0
|
||||||
|
fi
|
||||||
|
|
||||||
|
# check if the systems parameter is valid
|
||||||
|
if ! echo "$PARAMETERS" | grep -w "$1" >/dev/null; then
|
||||||
|
help_message
|
||||||
|
exit 0
|
||||||
|
fi
|
||||||
|
|
||||||
|
# UPLOAD
|
||||||
|
if [ "$1" = upload ] || [ "$1" = UPLOAD ]; then
|
||||||
|
printf "\n%s\n" "uploading $PROJECT"
|
||||||
|
rsync -azmPu --delete -e 'ssh -p 4545' . sergio@sustancia.synology.me:/home/sergio/backup/code/$PROJECT/
|
||||||
|
rsync -azmPu -e 'ssh -p 4545' . sergio@sustancia.synology.me:/home/sergio/backup/code/$PROJECT.all/
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ "$1" = download ] || [ "$1" = DOWNLOAD ]; then
|
||||||
|
printf "%s\n" "downloading $PROJECT"
|
||||||
|
rsync -azmP --delete -e 'ssh -p 4545' sergio@sustancia.synology.me:/home/sergio/backup/code/$PROJECT/* .
|
||||||
|
fi
|
||||||