piano.ino (3691B)
1 #include <XPT2046_Touchscreen.h> 2 #include <TFT_eSPI.h> 3 4 #include "tones.h" 5 6 #define SIZE(arr) (sizeof(arr) / sizeof(arr[0])) 7 8 #define XPT2046_IRQ 36 9 #define XPT2046_MOSI 32 10 #define XPT2046_MISO 39 11 #define XPT2046_CLK 25 12 #define XPT2046_CS 33 13 14 #define BG (~(249 << 11) + ~(194 << 5) + ~43) 15 16 17 uint32_t timer = 0; 18 uint8_t note = 0; 19 uint8_t song[] = { 20 1, 3, 2, 1, 21 1, 3, 2, 1, 22 1, 2, 3, 4, 23 1, 2, 3, 4, 24 1, 1, 0, 2, 25 4, 5, 4, 5, 26 1, 3, 2, 1, 27 1, 3, 2, 1, 28 1, 2, 3, 4, 29 1, 2, 3, 4, 30 31 }; 32 33 TFT_eSPI tft = TFT_eSPI(); 34 SPIClass mySpi = SPIClass(VSPI); 35 XPT2046_Touchscreen ts(XPT2046_CS, XPT2046_IRQ); 36 37 void setup() { 38 mySpi.begin(XPT2046_CLK, XPT2046_MISO, XPT2046_MOSI, XPT2046_CS); 39 40 ts.begin(mySpi); 41 ts.setRotation(1); 42 43 tft.init(); 44 tft.setRotation(1); 45 46 tft.fillScreen(BG); 47 tft.setTextColor(TFT_WHITE, TFT_BLACK); 48 49 int width = (tft.width() / 7); 50 for (int i = 0; i < 7; i++) 51 //tft.fillRect(width * i + 3, 150, width - 6, 90, ~TFT_WHITE); 52 tft.fillSmoothRoundRect(width * i + 3, 150, width - 6, 90, 10, ~TFT_WHITE); 53 54 for (int i = 0; i < 7; i++) { 55 switch (i) { 56 case 0: case 1: case 3: case 4: case 5: 57 //tft.fillRect(width * i + width * 0.75, 150, width / 2, 60, ~TFT_BLACK); 58 tft.fillSmoothRoundRect(width * i + width * 0.75, 150, width / 2, 60, 10, ~TFT_BLACK); 59 break; 60 } 61 } 62 } 63 64 void drawBg() { 65 tft.fillRect(0, 0, tft.width(), 150, BG); 66 } 67 68 void playTone(TS_Point *p) { 69 noTone(26); 70 if (p->y < 2000) 71 return; 72 73 int width = 3800 / 7; 74 if (p->y > 2000 && p->y < 3350) { 75 for (int i = 0; i < 7; i++) { 76 if (p->x > width * i + width * 0.75 && p->x < width * i + width * 0.75 + width / 2) { 77 switch (i) { 78 case 0: 79 tone(26, NOTE_CS4, 100); 80 return; 81 case 1: 82 tone(26, NOTE_DS4, 100); 83 return; 84 case 3: 85 tone(26, NOTE_FS4, 100); 86 return; 87 case 4: 88 tone(26, NOTE_GS4, 100); 89 return; 90 case 5: 91 tone(26, NOTE_AS4, 100); 92 return; 93 } 94 } 95 } 96 } 97 98 if (p->x < width) 99 tone(26, NOTE_C4, 100); 100 else if (p->x < width * 2) 101 tone(26, NOTE_D4, 100); 102 else if (p->x < width * 3) 103 tone(26, NOTE_E4, 100); 104 else if (p->x < width * 4) 105 tone(26, NOTE_F4, 100); 106 else if (p->x < width * 5) 107 tone(26, NOTE_G4, 100); 108 else if (p->x < width * 6) 109 tone(26, NOTE_A4, 100); 110 else if (p->x < width * 7) 111 tone(26, NOTE_B4, 100); 112 } 113 114 int getNote(TS_Point *p) { 115 noTone(26); 116 if (p->y < 2000) 117 return -1; 118 119 int width = 3800 / 7; 120 121 if (p->x < width) 122 return 0; 123 else if (p->x < width * 2) 124 return 1; 125 else if (p->x < width * 3) 126 return 2; 127 else if (p->x < width * 4) 128 return 3; 129 else if (p->x < width * 5) 130 return 4; 131 else if (p->x < width * 6) 132 return 5; 133 else if (p->x < width * 7) 134 return 6; 135 } 136 137 void loop() { 138 static int i; 139 140 if (ts.tirqTouched() && ts.touched()) { 141 TS_Point p = ts.getPoint(); 142 playTone(&p); 143 if (getNote(&p) == song[note]) { 144 if (timer > 100) { 145 note++; 146 timer = 0; 147 } 148 } 149 } 150 151 if (timer % 10) { 152 drawBg(); 153 } 154 155 if (note < SIZE(song)) { 156 int width = (tft.width() / 7); 157 158 if (++i % 4) 159 timer++; 160 tft.fillRect(song[note] * width, timer, width, 30, ~TFT_BLACK); 161 162 if (timer > 150 - 30) { 163 timer = 0; 164 tft.println("YOU LOOSE"); 165 while (1) continue; 166 } 167 } else { 168 tft.println("YOU WIN"); 169 while (1) continue; 170 } 171 }