Created
May 19, 2012 03:37
-
-
Save Tapped/2728897 to your computer and use it in GitHub Desktop.
Snake on novation launchpad
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#include <iostream> | |
#include <conio.h> | |
#include <cstdio> | |
#include <windows.h> | |
#include <mmsystem.h> | |
#include <cmath> | |
#include <ctime> | |
//Snake directions | |
enum {UP, DOWN, LEFT, RIGHT}; | |
//Easy way to convert between binary and int | |
union Message{ unsigned long word; char data[4];}; | |
Message message; | |
//Switch buffer of launchpad | |
void SwitchBuffer(); | |
//Set the led specified by cell green | |
void SetLedOn(int cell); | |
//Set the led specified by cell, with a color | |
void SetLedOn(int color, int cell); | |
//Set the led specified by cell off | |
void SetLedOff(int cell); | |
//Find empty space in the grid | |
int FindEmptySpace(int cell); | |
//Move a cell, and prevent it from going out of grid | |
int Move(int cell, int dirCode); | |
//Move the snake | |
void MoveSnake(); | |
int points = 0; | |
int snakeLength = 2; | |
int snakeDir; | |
int snakeCells[64]; | |
int foodCell; | |
int snakeOldCell[64]; | |
bool gameover = false; | |
int flag; | |
HMIDIOUT device; | |
using namespace std; | |
int main() | |
{ | |
srand((unsigned)time(0)); | |
flag = midiOutOpen(&device, 1, 0, 0, CALLBACK_NULL); | |
if (flag != MMSYSERR_NOERROR) { | |
cout << "Error opening MIDI Output.\n"; | |
return 1; | |
} | |
cout << "Snake, how long can you become? Use WASD to move, and press q to quit.\nPlease press enter to start.\n"; | |
cin.get(); | |
snakeCells[0] = 4; | |
snakeDir = DOWN; | |
foodCell = FindEmptySpace(rand() % 64); | |
bool shiftDir = false; | |
int pos = -1; | |
SwitchBuffer(); | |
while(1) | |
{ | |
if(_kbhit()) | |
{ | |
char key = _getch(); | |
if(key == 'q') | |
break; | |
else if(key == 's') | |
snakeDir = DOWN; | |
else if(key == 'w') | |
snakeDir = UP; | |
else if(key == 'a') | |
snakeDir = LEFT; | |
else if(key == 'd') | |
snakeDir = RIGHT; | |
} | |
if(!gameover) | |
{ | |
MoveSnake(); | |
SetLedOn(63, foodCell); | |
SwitchBuffer(); | |
Sleep(150); | |
} | |
else | |
{ | |
if(!shiftDir) | |
++pos; | |
else | |
--pos; | |
SetLedOn(62, pos); | |
if(!shiftDir && pos % 8 == 7) | |
{ | |
pos += 9; | |
shiftDir = true; | |
} | |
else if(shiftDir && pos % 8 == 0) | |
{ | |
pos += 7; | |
shiftDir = false; | |
} | |
SwitchBuffer(); | |
Sleep(20); | |
} | |
} | |
message.data[0] = (char)0xB0; | |
message.data[1] = (char)0x00; | |
message.data[2] = (char)0x00; | |
flag = midiOutShortMsg(device, message.word); | |
if(flag != MMSYSERR_NOERROR) | |
{ | |
cout << "Warning: MIDI Output is not open.\n"; | |
} | |
midiOutReset(device); | |
midiOutClose(device); | |
return 0; | |
} | |
void SwitchBuffer() | |
{ | |
static bool switchBuffer; | |
message.data[0] = (char)0xB0; | |
message.data[1] = (char)0x00; | |
if(!switchBuffer) | |
{ | |
message.data[2] = 0x31; | |
switchBuffer = true; | |
} | |
else | |
{ | |
message.data[2] = 0x34; | |
switchBuffer = false; | |
} | |
flag = midiOutShortMsg(device, message.word); | |
if(flag != MMSYSERR_NOERROR) | |
{ | |
cout << "Warning: MIDI Output is not open.\n"; | |
} | |
} | |
void SetLedOn(int cell) | |
{ | |
message.data[0] = (char)0x90; | |
message.data[1] = (int)(cell % 8) + (((int)cell / 8) * 16); | |
message.data[2] = (char)48; | |
flag = midiOutShortMsg(device, message.word); | |
if(flag != MMSYSERR_NOERROR) | |
{ | |
cout << "Warning: MIDI Output is not open.\n"; | |
} | |
} | |
void SetLedOn(int color, int cell) | |
{ | |
message.data[0] = (char)0x90; | |
message.data[1] = (int)(cell % 8) + (((int)cell / 8) * 16); | |
message.data[2] = (char)color & (char)0x73; | |
flag = midiOutShortMsg(device, message.word); | |
if(flag != MMSYSERR_NOERROR) | |
{ | |
cout << "Warning: MIDI Output is not open.\n"; | |
} | |
} | |
void SetLedOff(int cell) | |
{ | |
message.data[0] = (char)0x90; | |
message.data[1] = (int)(cell % 8) + (((int)cell / 8) * 16); | |
message.data[2] = 0; | |
flag = midiOutShortMsg(device, message.word); | |
if(flag != MMSYSERR_NOERROR) | |
{ | |
cout << "Warning: MIDI Output is not open.\n"; | |
} | |
} | |
int FindEmptySpace(int cell) | |
{ | |
for(int i = 0;i < snakeLength;++i) | |
{ | |
if(snakeCells[i] == cell) | |
{ | |
return FindEmptySpace(rand() % 64); | |
} | |
} | |
return cell; | |
} | |
void MoveSnake() | |
{ | |
int oldCell = snakeCells[0]; | |
snakeCells[0] = Move(snakeCells[0], snakeDir); | |
snakeOldCell[0] = oldCell; | |
SetLedOn(15, snakeCells[0]); | |
//Hide old cells | |
if(oldCell != snakeCells[0]) | |
{ | |
SetLedOff(oldCell); | |
} | |
for(int i = 1;i < snakeLength;++i) | |
{ | |
oldCell = snakeCells[i]; | |
snakeCells[i] = snakeOldCell[i - 1]; | |
snakeOldCell[i] = oldCell; | |
//Check for collision with head | |
if(snakeCells[0] == snakeCells[i]) | |
{ | |
message.data[0] = (char)0xB0; | |
message.data[1] = (char)0x00; | |
message.data[2] = (char)0x00; | |
flag = midiOutShortMsg(device, message.word); | |
if(flag != MMSYSERR_NOERROR) | |
{ | |
cout << "Warning: MIDI Output is not open.\n"; | |
} | |
gameover = true; | |
return; | |
} | |
SetLedOn(snakeCells[i]); | |
if(oldCell != snakeCells[i]) | |
{ | |
SetLedOff(oldCell); | |
} | |
} | |
//Check for collision with food | |
if(snakeCells[0] == foodCell) | |
{ | |
snakeCells[snakeLength] = snakeOldCell[snakeLength - 1]; | |
snakeOldCell[snakeLength] = snakeOldCell[snakeLength - 1]; | |
foodCell = FindEmptySpace(rand() % 64); | |
++snakeLength; | |
points += 10; | |
system("cls"); | |
cout << "You have " << points << " points." << "\n"; | |
} | |
} | |
int Move(int cell, int dirCode) | |
{ | |
int column = cell % 8; | |
int row = cell / 8; | |
if(dirCode == DOWN) | |
{ | |
if(row + 1 > 7) | |
return cell; | |
else | |
return cell + 8; | |
} | |
else if(dirCode == UP) | |
{ | |
if(row - 1 < 0) | |
return cell; | |
else | |
return cell - 8; | |
} | |
else if(dirCode == LEFT) | |
{ | |
if(column - 1 < 0) | |
return cell; | |
else | |
return cell - 1; | |
} | |
else if(dirCode == RIGHT) | |
{ | |
if(column + 1 > 7) | |
return cell; | |
else | |
return cell + 1; | |
} | |
return cell; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment