Greed: Difference between revisions

From Rosetta Code
Content added Content deleted
(Created page with "{{draft task|Games}} This task is about making a clone of the game "GREED" by Matthew Day. This game is played on a grid of 79 column by 22 rows of random numbers from 1 to 9...")
 
No edit summary
Line 11: Line 11:


[https://www.youtube.com/watch?v=XQHq6tdxylk&list=PLdvB7n7RN2UDkjHAWCmbQ8okmgSrjWcvE Video on YouTube]
[https://www.youtube.com/watch?v=XQHq6tdxylk&list=PLdvB7n7RN2UDkjHAWCmbQ8okmgSrjWcvE Video on YouTube]


{{header|C++}}
Windows console version.
[[File:GreedCpp.png|200px|thumb|right]]
<lang cpp>
#include <windows.h>
#include <iostream>
#include <ctime>

const int WID = 79, HEI = 22;
const float NCOUNT = ( float )( WID * HEI );

class coord : public COORD {
public:
coord( short x = 0, short y = 0 ) { set( x, y ); }
void set( short x, short y ) { X = x; Y = y; }
};
class winConsole {
public:
static winConsole* getInstamnce() { if( 0 == inst ) { inst = new winConsole(); } return inst; }
void showCursor( bool s ) { CONSOLE_CURSOR_INFO ci = { 1, s }; SetConsoleCursorInfo( conOut, &ci ); }
void setColor( WORD clr ) { SetConsoleTextAttribute( conOut, clr ); }
void setCursor( coord p ) { SetConsoleCursorPosition( conOut, p ); }
void flush() { FlushConsoleInputBuffer( conIn ); }
void kill() { delete inst; }
private:
winConsole() { conOut = GetStdHandle( STD_OUTPUT_HANDLE );
conIn = GetStdHandle( STD_INPUT_HANDLE ); showCursor( false ); }
static winConsole* inst;
HANDLE conOut, conIn;
};
class greed {
public:
greed() { console = winConsole::getInstamnce(); }
~greed() { console->kill(); }
void play() {
char g; do {
console->showCursor( false ); createBoard();
do { displayBoard(); getInput(); } while( existsMoves() );
displayBoard(); console->setCursor( coord( 0, 24 ) ); console->setColor( 0x07 );
console->setCursor( coord( 19, 8 ) ); std::cout << "+----------------------------------------+";
console->setCursor( coord( 19, 9 ) ); std::cout << "| GAME OVER |";
console->setCursor( coord( 19, 10 ) ); std::cout << "| PLAY AGAIN(Y/N)? |";
console->setCursor( coord( 19, 11 ) ); std::cout << "+----------------------------------------+";
console->setCursor( coord( 48, 10 ) ); console->showCursor( true ); console->flush(); std::cin >> g;
} while( g == 'Y' || g == 'y' );
}
private:
void createBoard() {
for( int y = 0; y < HEI; y++ ) {
for( int x = 0; x < WID; x++ ) {
brd[x + WID * y] = rand() % 9 + 1;
}
}
cursor.set( rand() % WID, rand() % HEI );
brd[cursor.X + WID * cursor.Y] = 0; score = 0;
printScore();
}
void displayBoard() {
console->setCursor( coord() ); int i;
for( int y = 0; y < HEI; y++ ) {
for( int x = 0; x < WID; x++ ) {
i = brd[x + WID * y]; console->setColor( 6 + i );
if( !i ) std::cout << " "; else std::cout << i;
}
std::cout << "\n";
}
console->setColor( 15 ); console->setCursor( cursor ); std::cout << "@";
}
void getInput() {
while( 1 ) {
if( ( GetAsyncKeyState( 'Q' ) & 0x8000 ) && cursor.X > 0 && cursor.Y > 0 ) { execute( -1, -1 ); break; }
if( ( GetAsyncKeyState( 'W' ) & 0x8000 ) && cursor.Y > 0 ) { execute( 0, -1 ); break; }
if( ( GetAsyncKeyState( 'E' ) & 0x8000 ) && cursor.X < WID - 1 && cursor.Y > 0 ) { execute( 1, -1 ); break; }
if( ( GetAsyncKeyState( 'A' ) & 0x8000 ) && cursor.X > 0 ) { execute( -1, 0 ); break; }
if( ( GetAsyncKeyState( 'D' ) & 0x8000 ) && cursor.X < WID - 1 ) { execute( 1, 0 ); break; }
if( ( GetAsyncKeyState( 'Y' ) & 0x8000 ) && cursor.X > 0 && cursor.Y < HEI - 1 ) { execute( -1, 1 ); break; }
if( ( GetAsyncKeyState( 'X' ) & 0x8000 ) && cursor.Y < HEI - 1 ) { execute( 0, 1 ); break; }
if( ( GetAsyncKeyState( 'C' ) & 0x8000 ) && cursor.X < WID - 1 && cursor.Y < HEI - 1 ) { execute( 1, 1 ); break; }
}
console->flush(); printScore();
}
void printScore() {
console->setCursor( coord( 0, 24 ) ); console->setColor( 0x2a );
std::cout << " SCORE: " << score * 100.f / NCOUNT << "% ";
}
void execute( int x, int y ) {
int i = brd[cursor.X + x + WID * ( cursor.Y + y )];
if( countSteps( i, x, y ) ) {
score += i;
while( i ) {
--i; cursor.X += x; cursor.Y += y;
brd[cursor.X + WID * cursor.Y] = 0;
}
}
}
bool countSteps( int i, int x, int y ) {
coord t( cursor.X, cursor.Y );
while( i ) {
--i; t.X += x; t.Y += y;
if( t.X < 0 || t.Y < 0 || t.X >= WID || t.Y >= HEI || !brd[t.X + WID * t.Y] ) return false;
}
return true;
}
bool existsMoves() {
int i;
for( int y = -1; y < 2; y++ ) {
for( int x = -1; x < 2; x++ ) {
if( !x && !y ) continue;
i = brd[cursor.X + x + WID * ( cursor.Y + y )];
if( i > 0 && countSteps( i, x, y ) ) return true;
}
}
return false;
}
winConsole* console;
int brd[WID * HEI];
float score; coord cursor;
};
winConsole* winConsole::inst = 0;
int main( int argc, char* argv[] ) {
srand( ( unsigned )time( 0 ) );
SetConsoleTitle( "Greed" );
greed g; g.play(); return 0;
}
</lang>

Revision as of 09:39, 13 April 2016

Greed is a draft programming task. It is not yet considered ready to be promoted as a complete task, for reasons that should be found in its talk page.

This task is about making a clone of the game "GREED" by Matthew Day.

This game is played on a grid of 79 column by 22 rows of random numbers from 1 to 9. The player location is signified by the '@' symbol.

The object of Greed is to erase as much of the screen as possible by moving around (all 8 directions are allowed) in this grid. When you move in a direction, you erase N number of grid squares in that direction, N being the first number in that direction. Your score reflects the total number of squares eaten.

You may not make a move that places you off the grid or over a previously eaten square.

The game is over if there is no more valid moves.

Video on YouTube


C++ Windows console version.

File:GreedCpp.png

<lang cpp>

  1. include <windows.h>
  2. include <iostream>
  3. include <ctime>

const int WID = 79, HEI = 22; const float NCOUNT = ( float )( WID * HEI );

class coord : public COORD { public:

   coord( short x = 0, short y = 0 ) { set( x, y ); }
   void set( short x, short y ) { X = x; Y = y; }

}; class winConsole { public:

   static winConsole* getInstamnce() { if( 0 == inst ) { inst = new winConsole(); } return inst; }
   void showCursor( bool s ) { CONSOLE_CURSOR_INFO ci = { 1, s }; SetConsoleCursorInfo( conOut, &ci ); }
   void setColor( WORD clr ) { SetConsoleTextAttribute( conOut, clr ); }
   void setCursor( coord p ) { SetConsoleCursorPosition( conOut, p ); }
   void flush() { FlushConsoleInputBuffer( conIn ); }
   void kill() { delete inst; }

private:

   winConsole() { conOut = GetStdHandle( STD_OUTPUT_HANDLE ); 
                  conIn  = GetStdHandle( STD_INPUT_HANDLE ); showCursor( false ); }
   static winConsole* inst;
   HANDLE conOut, conIn;

}; class greed { public:

   greed() { console = winConsole::getInstamnce(); }
   ~greed() { console->kill(); }
   void play() {
       char g; do {
           console->showCursor( false ); createBoard();
           do { displayBoard(); getInput(); } while( existsMoves() );
           displayBoard(); console->setCursor( coord( 0, 24 ) ); console->setColor( 0x07 );
           console->setCursor( coord( 19,  8 ) ); std::cout << "+----------------------------------------+";
           console->setCursor( coord( 19,  9 ) ); std::cout << "|               GAME OVER                |";
           console->setCursor( coord( 19, 10 ) ); std::cout << "|            PLAY AGAIN(Y/N)?            |";
           console->setCursor( coord( 19, 11 ) ); std::cout << "+----------------------------------------+";
           console->setCursor( coord( 48, 10 ) ); console->showCursor( true ); console->flush(); std::cin >> g;
       } while( g == 'Y' || g == 'y' );
   }

private:

   void createBoard() {
       for( int y = 0; y < HEI; y++ ) {
           for( int x = 0; x < WID; x++ ) {
               brd[x + WID * y] = rand() % 9 + 1;
           }
       }
       cursor.set( rand() % WID, rand() % HEI );
       brd[cursor.X + WID * cursor.Y] = 0; score = 0;
       printScore();
   }
   void displayBoard() {
       console->setCursor( coord() ); int i;

for( int y = 0; y < HEI; y++ ) {

           for( int x = 0; x < WID; x++ ) {
               i = brd[x + WID * y]; console->setColor( 6 + i );
               if( !i ) std::cout << " "; else std::cout << i;
           }
           std::cout << "\n";
       }
       console->setColor( 15 ); console->setCursor( cursor ); std::cout << "@";
   }
   void getInput() { 
       while( 1 ) {
           if( ( GetAsyncKeyState( 'Q' ) & 0x8000 ) && cursor.X > 0 && cursor.Y > 0 ) { execute( -1, -1 ); break; }
           if( ( GetAsyncKeyState( 'W' ) & 0x8000 ) &&  cursor.Y > 0 ) { execute( 0, -1 ); break; }
           if( ( GetAsyncKeyState( 'E' ) & 0x8000 ) && cursor.X < WID - 1 && cursor.Y > 0 ) { execute( 1, -1 ); break; }
           if( ( GetAsyncKeyState( 'A' ) & 0x8000 ) && cursor.X > 0 ) { execute( -1, 0 ); break; }
           if( ( GetAsyncKeyState( 'D' ) & 0x8000 ) && cursor.X < WID - 1 ) { execute( 1, 0 ); break; }
           if( ( GetAsyncKeyState( 'Y' ) & 0x8000 ) && cursor.X > 0 && cursor.Y < HEI - 1 ) { execute( -1, 1 ); break; }
           if( ( GetAsyncKeyState( 'X' ) & 0x8000 ) && cursor.Y < HEI - 1 ) { execute( 0, 1 ); break; }
           if( ( GetAsyncKeyState( 'C' ) & 0x8000 ) && cursor.X < WID - 1 && cursor.Y < HEI - 1 ) { execute( 1, 1 ); break; }
       }
       console->flush(); printScore();
   }
   void printScore() {
       console->setCursor( coord( 0, 24 ) ); console->setColor( 0x2a );
       std::cout << "      SCORE: " << score * 100.f / NCOUNT << "%      ";
   }
   void execute( int x, int y ) {
       int i = brd[cursor.X + x + WID * ( cursor.Y + y )];
       if( countSteps( i, x, y ) ) {
           score += i;
           while( i ) {
               --i; cursor.X += x; cursor.Y += y;
               brd[cursor.X + WID * cursor.Y] = 0;
           }
       }
   }
   bool countSteps( int i, int x, int y ) {
       coord t( cursor.X, cursor.Y );
       while( i ) {
           --i; t.X += x; t.Y += y;
           if( t.X < 0 || t.Y < 0 || t.X >= WID || t.Y >= HEI || !brd[t.X + WID * t.Y] ) return false;
       }
       return true;
   }
   bool existsMoves() {
       int i;
       for( int y = -1; y < 2; y++ ) {
           for( int x = -1; x < 2; x++ ) {
               if( !x && !y ) continue;
               i = brd[cursor.X + x + WID * ( cursor.Y + y )];
               if( i > 0 && countSteps( i, x, y ) ) return true;
           }
       }
       return false;
   }
   winConsole* console;
   int brd[WID * HEI];
   float score; coord cursor;

}; winConsole* winConsole::inst = 0; int main( int argc, char* argv[] ) {

   srand( ( unsigned )time( 0 ) );
   SetConsoleTitle( "Greed" );
   greed g; g.play(); return 0;

} </lang>