Skip to content

Instantly share code, notes, and snippets.

@vittorioromeo
Created October 13, 2013 16:40
Show Gist options
  • Save vittorioromeo/6964311 to your computer and use it in GitHub Desktop.
Save vittorioromeo/6964311 to your computer and use it in GitHub Desktop.
Arkanoid in 170 lines of C++11 and SFML2
#include <vector>
#include <random>
#include <SFML/Window.hpp>
#include <SFML/Graphics.hpp>
using namespace std;
using namespace sf;
constexpr float raggioPallina{5.f};
constexpr float lunghezzaBlocco{60.f}, altezzaBlocco{20.f};
constexpr float lunghezzaGiocatore{75.f}, altezzaGiocatore{15.f};
constexpr int lunghezzaFinestra{800}, altezzaFinestra{600};
constexpr int numeroBlocchiX{11}, numeroBlocchiY{4};
struct Rettangolo
{
RectangleShape forma;
Rettangolo(float mX, float mY, float mLunghezza, float mAltezza, Color mColore) :
forma{{mLunghezza, mAltezza}}
{
forma.setPosition(mX, mY);
forma.setOrigin(mLunghezza / 2.f, mAltezza / 2.f);
forma.setFillColor(mColore);
}
void muovi(Vector2f mVelocità) { forma.move(mVelocità); }
float x() { return forma.getPosition().x; }
float y() { return forma.getPosition().y; }
};
struct Cerchio
{
CircleShape forma;
Cerchio(float mX, float mY, float mRaggio, Color mColore) :
forma{mRaggio}
{
forma.setPosition(mX, mY);
forma.setOrigin(mRaggio / 2.f, mRaggio / 2.f);
forma.setFillColor(mColore);
}
void muovi(Vector2f mVelocità) { forma.move(mVelocità); }
float x() { return forma.getPosition().x; }
float y() { return forma.getPosition().y; }
};
struct Blocco : public Rettangolo
{
using Rettangolo::Rettangolo;
bool distrutto{false};
Blocco(float mX, float mY, Color mColore) : Rettangolo{mX, mY, lunghezzaBlocco, altezzaBlocco, mColore} { }
};
struct Pallina : public Cerchio
{
using Cerchio::Cerchio;
Vector2f velocità{-8.f, -8.f};
Pallina(float mX, float mY) : Cerchio{mX, mY, raggioPallina, Color::Red} { }
void update()
{
muovi(velocità);
if(x() < 0) velocità.x = 8.f; else if(x() > lunghezzaFinestra) velocità.x = -8.f;
if(y() < 0) velocità.y = 8.f; else if(y() > altezzaFinestra) velocità.y = -8.f;
}
};
struct Giocatore : public Rettangolo
{
using Rettangolo::Rettangolo;
Vector2f velocità;
Giocatore(float mX, float mY) : Rettangolo{mX, mY, lunghezzaBlocco, altezzaBlocco, Color::Red} { }
void update() { muovi(velocità); }
};
Color generaColoreCasuale()
{
static minstd_rand generatoreNumeri;
auto rangeCasuale(uniform_int_distribution<unsigned char>{0, 255});
return {rangeCasuale(generatoreNumeri), rangeCasuale(generatoreNumeri), rangeCasuale(generatoreNumeri), 255};
}
bool intersezione(Rettangolo& mRettangolo, float mX, float mY)
{
return mX >= mRettangolo.x() - mRettangolo.forma.getSize().x / 2.f &&
mX <= mRettangolo.x() + mRettangolo.forma.getSize().x / 2.f &&
mY >= mRettangolo.y() - mRettangolo.forma.getSize().y / 2.f &&
mY <= mRettangolo.y() + mRettangolo.forma.getSize().y / 2.f;
}
bool collisioneTra(Giocatore& mGiocatore, Pallina& mPallina)
{
if(!intersezione(mGiocatore, mPallina.x(), mPallina.y())) return false;
if(mPallina.x() < mGiocatore.x()) mPallina.velocità.x = -8.f;
else mPallina.velocità.x = 8.f;
return true;
}
bool collisioneTra(Blocco& mBlocco, Pallina& mPallina)
{
if(!intersezione(mBlocco, mPallina.x(), mPallina.y())) return false;
float intersezioneDaSx{mPallina.x() - (mBlocco.x() - lunghezzaBlocco / 2.f)};
float intersezioneDaDx{(mBlocco.x() + lunghezzaBlocco / 2.f) - mPallina.x()};
float intersezioneDaSopra{mPallina.y() - (mBlocco.y() - altezzaBlocco / 2.f)};;
float intersezioneDaSotto{(mBlocco.y() + altezzaBlocco / 2.f) - mPallina.y()};;
bool daSx(abs(intersezioneDaSx) < abs(intersezioneDaDx));
bool daSopra(abs(intersezioneDaSopra) < abs(intersezioneDaSotto));
float minIntersezioneX{daSx ? intersezioneDaSx : intersezioneDaDx};
float minIntersezioneY{daSopra ? intersezioneDaSopra : intersezioneDaSotto};
if(abs(minIntersezioneX) < abs(minIntersezioneY)) mPallina.velocità.x = daSx ? -8.f : 8.f;
else mPallina.velocità.y = daSopra ? -8.f : 8.f;
return true;
}
int main()
{
Giocatore giocatore{lunghezzaFinestra / 2.f, altezzaFinestra - 50.f};
Pallina pallina{giocatore.x(), giocatore.y() - 15.f};
vector<Blocco> blocchi;
for(int iX{0}; iX < numeroBlocchiX; ++iX)
for(int iY{0}; iY < numeroBlocchiY; ++iY)
blocchi.emplace_back((iX + 1) * (lunghezzaBlocco + 3), (iY + 2) * (altezzaBlocco + 3), generaColoreCasuale());
RenderWindow finestra{{lunghezzaFinestra, altezzaFinestra}, "Arkanoid"};
finestra.setFramerateLimit(60);
while(true)
{
finestra.clear(Color::Black);
if(Keyboard::isKeyPressed(Keyboard::Key::Left)) giocatore.velocità = {-10.f, 0.f};
else if(Keyboard::isKeyPressed(Keyboard::Key::Right)) giocatore.velocità = {10.f, 0.f};
else giocatore.velocità = {0.f, 0.f};
giocatore.update();
pallina.update();
if(collisioneTra(giocatore, pallina)) pallina.velocità.y = -8.f;
for(auto& blocco : blocchi) if(collisioneTra(blocco, pallina)) { blocco.distrutto = true; break; }
blocchi.erase(remove_if(begin(blocchi), end(blocchi), [](const Blocco& mBlocco){ return mBlocco.distrutto; }), end(blocchi));
for(auto& blocco : blocchi) finestra.draw(blocco.forma);
finestra.draw(giocatore.forma);
finestra.draw(pallina.forma);
finestra.display();
}
return 0;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment