Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependencies: PinDetect_KL25Z mbed-rtos mbed
main.cpp
00001 #include "mbed.h" 00002 #include "rtos.h" 00003 00004 00005 const int BUTTONS = 7; 00006 const int BUZZERS = 3; 00007 const int LETTERS = 27; 00008 00009 // Collection is the time that it takes after pressing one key and then reading 00010 // all the keys to determine what the chord is. 00011 const int COLLECTION_MS = 200; 00012 Timer collectionTimer; 00013 00014 InterruptIn buttons [BUTTONS] = { 00015 InterruptIn(D2), 00016 InterruptIn(D4), 00017 InterruptIn(D5), 00018 InterruptIn(D8), 00019 InterruptIn(D9), 00020 InterruptIn(D10), 00021 InterruptIn(D11) 00022 }; 00023 Serial pc(USBTX, USBRX); 00024 00025 // Note: there are only THREE PWMs on the board. So this is all we can use 00026 // for this particular method of sound output. The pins chosen are important 00027 // because the same PWM will map to multiple outputs. See the reference 00028 // manual for Mbed for which pins map to distinct PWMs. 00029 PwmOut buzzers [3] = { 00030 PwmOut(D0), 00031 PwmOut(D7), 00032 PwmOut(D3) 00033 }; 00034 00035 // Periods of notes in microseconds 00036 int notePeriods [8] = { 00037 3818, // C4 00038 3412, // D4 00039 3030, // E4 00040 2895, // F4 00041 2551, // G4 00042 2273, // A4 00043 2024, // B4 00044 10000000 // inaudible pitch 00045 }; 00046 // Possible chords that can be played. 00047 // Chords consist of 3 notes, and an integer for the ASCII character 00048 // that it will output via serial. 00049 // Note that 7 is no button pressed, or a 'silent' pitch. 00050 int chords [LETTERS][BUZZERS + 1] = { 00051 {0, 7, 7, 114}, // single notes 00052 {1, 7, 7, 32}, 00053 {2, 7, 7, 106}, 00054 {3, 7, 7, 107}, 00055 {4, 7, 7, 109}, 00056 {5, 7, 7, 113}, 00057 {6, 7, 7, 122}, 00058 {0, 2, 7, 115}, // diads 00059 {0, 3, 7, 112}, 00060 {0, 4, 7, 110}, 00061 {0, 5, 7, 102}, 00062 {1, 3, 7, 105}, 00063 {1, 4, 7, 98}, 00064 {1, 5, 7, 103}, 00065 {1, 6, 7, 104}, 00066 {2, 4, 7, 100}, 00067 {2, 5, 7, 121}, 00068 {2, 6, 7, 120}, 00069 {3, 4, 7, 99}, 00070 {3, 5, 7, 117}, 00071 {4, 6, 7, 119}, 00072 {0, 2, 4, 101}, // triads 00073 {0, 2, 5, 118}, 00074 {0, 3, 5, 108}, 00075 {1, 3, 6, 97}, 00076 {1, 4, 6, 116}, 00077 {1, 3, 4, 111} 00078 }; 00079 00080 void playChord(int chordIndex) { 00081 int *chord = chords[chordIndex]; 00082 for (int i = 0; i < BUZZERS; i++) { 00083 int noteIndex = chord[i]; 00084 if (noteIndex == 7) { 00085 buzzers[i] = 0; 00086 } 00087 else { 00088 buzzers[i] = .5f; 00089 int period = notePeriods[noteIndex]; 00090 buzzers[i].period_us(period); 00091 } 00092 } 00093 } 00094 00095 void setFlag() { 00096 collectionTimer.start(); 00097 } 00098 00099 void silenceBuzzers(void) { 00100 // Initialize all duty cycles to off, so we hear nothing. 00101 for (int i = 0; i < BUZZERS; i++) { 00102 buzzers[i] = 0.0f; 00103 } 00104 } 00105 00106 void registerButtonInterrupts(void) { 00107 for (int i = 0; i < BUTTONS; i++) { 00108 buttons[i].fall(&setFlag); 00109 } 00110 } 00111 00112 int readChord(void) { 00113 /* Detect the current chord from the keys pressed. Return int index of chord. 00114 Return -1 if no chord can be found with the current keys. 00115 Note that we can only read as many keys as there are buzzers, so check 00116 on each key in an ascending order. */ 00117 int firstThreeButtons[BUZZERS] = {7, 7, 7}; 00118 int pressedCount = 0; 00119 for (int i = 0; i < BUTTONS; i++) { 00120 if (buttons[i].read() == 0) { 00121 firstThreeButtons[pressedCount] = i; 00122 pressedCount++; 00123 } 00124 if (pressedCount >= BUZZERS) { 00125 break; 00126 } 00127 } 00128 int matchIndex = -1; 00129 for (int i = 0; i < LETTERS; i++) { 00130 bool chordMatches = true; 00131 for (int j = 0; j < BUZZERS; j++) { 00132 if (firstThreeButtons[j] != chords[i][j]) { 00133 chordMatches = false; 00134 break; 00135 } 00136 } 00137 if (chordMatches == true) { 00138 matchIndex = i; 00139 break; 00140 } 00141 } 00142 // pc.printf("Matched chord %d\n", matchIndex); 00143 return matchIndex; 00144 } 00145 00146 void waitForChord(void) { 00147 /* This method should be run in the main loop so that it can print */ 00148 while (true) { 00149 if (collectionTimer.read_ms() > COLLECTION_MS) { 00150 collectionTimer.stop(); 00151 collectionTimer.reset(); 00152 int chordIndex = readChord(); 00153 if (chordIndex != -1) { 00154 playChord(chordIndex); 00155 int charAscii = chords[chordIndex][BUZZERS]; 00156 pc.printf("%c", charAscii); 00157 } 00158 } 00159 wait_ms(10); 00160 } 00161 } 00162 00163 int main() { 00164 silenceBuzzers(); 00165 registerButtonInterrupts(); 00166 waitForChord(); 00167 }
Generated on Fri Jul 15 2022 13:01:27 by
1.7.2