diff --git a/tris.ino b/tris.ino new file mode 100644 index 0000000..d70a443 --- /dev/null +++ b/tris.ino @@ -0,0 +1,297 @@ +#include +#include + +const uint8_t CS = 10; +const uint8_t SEGMENTS = 4; +const uint32_t SPICLOCK = 200000; +const uint8_t SPIBITORDER = MSBFIRST; +const uint8_t SPIDATAMODE = SPI_MODE0; + +const static uint16_t ENABLE = 0x0C00; +const static uint16_t TEST = 0x0F00; +const static uint16_t INTENSITY = 0x0A00; +const static uint16_t SCAN_LIMIT = 0x0B00; +const static uint16_t DECODE_MODE = 0x0900; + +const static uint8_t P1RA = 2; +const static uint8_t P1RB = 4; +const static uint8_t P1B = 6; +const static uint8_t P2RA = 3; +const static uint8_t P2RB = 5; +const static uint8_t P2B = 7; + +const static uint8_t SPEAKER = 8; + +const static uint8_t blocks=9; +// 0 row0 , 1, row1, height, width +const static uint8_t blockdata[4][9] = {{ 0b11 , 0b11 , 0b10 , 0b01 , 0b01, 0b11 , 0b11 , 0b10 , 0b01}, + { 0b10 , 0b01 , 0b11 , 0b11 , 0b01, 0b00 , 0b11 , 0b01 , 0b10}, + { 2 , 2 , 2 , 2 , 1 , 2 , 2 , 2 , 2 }, + { 2 , 2 , 2 , 2 , 2 , 1 , 2 , 2 , 2 }}; + + +const static uint8_t logo[32]={ 15,31,24,31,15,1,31,31, 153,153,25,25,152,129,153,24, 152,152,152,248,248,152,249,249, 96,96,96,96,96,96,248,248 }; +const static uint8_t winnerlogo[2][3][32]={ + { + {146,36,73,146,146,73,36,146 ,70,150,38,70,71,39,150,70, 102,102,102,102,102,224,230,102, 99,119,127,107,99,99,99,99}, + {36,73,146,36,36,146,73,36 ,150,38,70,150,151,71,38,150, 102,102,102,102,102,224,230,102, 99,119,127,107,99,99,99,99}, + {73,146,36,73,73,36,146,73 ,38,70,150,38,39,151,70,38, 102,102,102,102,102,224,230,102, 99,119,127,107,99,99,99,99} + }, + { + {204,204,204,204,236,252,220,204 ,204,206,207,205,204,12,204,204, 98,233,228,98,98,100,105,98, 73,36,146,73,73,146,36,73}, + {204,204,204,204,236,252,220,204 ,204,206,207,205,204,12,204,204, 105,228,226,105,105,98,100,105, 36,146,73,36,36,73,146,36}, + {204,204,204,204,236,252,220,204 ,204,206,207,205,204,12,204,204, 100,226,233,100,100,105,98,100, 146,73,36,146,146,36,73,146} + } + }; + +uint8_t playfield[2][16]; +uint8_t shadowplayfield[2][16]; +uint8_t framebuffer[32]; + +// game settings +uint8_t SOUND=1; // sound on 1 , sound off 0 +uint16_t FALLDELAY=500; // delay in ms +uint16_t DROPDELAY=50; // delay in ms +uint8_t MAXROW=10; // max row of random pixel + +Encoder P1(P1RA,P1RB); +Encoder P2(P2RA,P2RB); + +void sendcommand(uint16_t command) { + SPI.beginTransaction(SPISettings(SPICLOCK,SPIBITORDER,SPIDATAMODE)); + digitalWrite(CS, 0); + //send the same command to all segments + for (uint8_t i = 0; i < SEGMENTS; ++i) { + SPI.transfer16(command); + } + digitalWrite(CS, 1); + SPI.endTransaction(); +} + +void renderframebuffer(void) { + uint8_t buffer[64]; + uint16_t cm; + for (uint8_t j = 0 ; j < 8 ; j++){ + SPI.beginTransaction(SPISettings(SPICLOCK,SPIBITORDER,SPIDATAMODE)); + digitalWrite(CS, 0); + for (uint8_t i = 0; i < SEGMENTS; ++i) { + cm=((j+1)<<8)|framebuffer[i*8+j]; + SPI.transfer16( cm); + } + digitalWrite(CS, 1); + SPI.endTransaction(); + } +} + +void prepareframebuffer(void) { + + for(uint8_t i=0; i<8;i++){ + framebuffer[i]= (((shadowplayfield[0][0]&(1<2){ + if(pxn[player]<8-blockdata[2][pbt[player]]) pxn[player]++; + if (SOUND==1) tone(SPEAKER,880,10); + P1.write(0); + } + if(P1.read()<-2){ + if(pxn[player]>0) pxn[player]--; + if (SOUND==1) tone(SPEAKER,880,10); + P1.write(0); + } + } else { + if(P2.read()>2){ + if(pxn[player]<8-blockdata[2][pbt[player]]) pxn[player]++; + if (SOUND==1) tone(SPEAKER,987,10); + P2.write(0); + } + if(P2.read()<-2){ + if(pxn[player]>0) pxn[player]--; + if (SOUND==1) tone(SPEAKER,987,10); + P2.write(0); + } + } + if( ( (playfield[player][py[player]] & (blockdata[0][pbt[player]]< pdd[player]) { + if (SOUND==1 && pdd[player]==DROPDELAY) tone(SPEAKER,1318+py[player]*10,10); + if(py[player]>=blockdata[3][pbt[player]]-1) { + py[player]--; + } + // if it reaches the bottom or runs into a existing blocks.. fix the drop, and setup for a new block + if( (py[player] < blockdata[3][pbt[player]]-1) || + ( (playfield[player][py[player]] & (blockdata[0][pbt[player]]<