oscsB[i]->frequency((1.0f / detune) * noteFreqs[voiceToNote[i]]);
#include <Bounce.h>
#include <Audio.h>
#include <Wire.h>
#include <SPI.h>
#include <SD.h>
#include <SerialFlash.h>
Bounce button0 = Bounce(25, 15);
Bounce button1 = Bounce(26, 15);
Bounce button2 = Bounce(27, 15);
Bounce button3 = Bounce(28, 15);
Bounce button4 = Bounce(29, 15);
Bounce button5 = Bounce(30, 15);
Bounce button6 = Bounce(31, 15);
Bounce button7 = Bounce(32, 15);
// Include USBHost Library
#include <USBHost_t36.h>
USBHost myusb;
MIDIDevice midi1(myusb);
// GUItool: begin automatically generated code
AudioSynthWaveformModulated osc1a; //xy=390.6000061035156,161.00000190734863
AudioSynthWaveformModulated osc1b; //xy=390.6000061035156,197.00000190734863
AudioSynthWaveformModulated osc3a; //xy=390.6000061035156,344
AudioSynthWaveformModulated osc7a; //xy=389.6000061035156,751
AudioSynthWaveformModulated osc3b; //xy=391.6000061035156,381
AudioSynthWaveformModulated osc11a; //xy=388.6000061035156,1164
AudioSynthWaveformModulated osc11b; //xy=388.6000099182129,1199.000018119812
AudioSynthWaveformModulated osc7b; //xy=390.6000061035156,788
AudioSynthWaveformModulated osc4a; //xy=393.6000061035156,421
AudioSynthWaveformModulated osc8a; //xy=392.6000061035156,828
AudioSynthWaveformModulated osc12a; //xy=391.6000061035156,1241
AudioSynthWaveformModulated osc2a; //xy=395.6000061035156,265
AudioSynthWaveformModulated osc6a; //xy=394.6000061035156,672
AudioSynthWaveformModulated osc4b; //xy=395.6000061035156,459
AudioSynthWaveformModulated osc10a; //xy=393.6000099182129,1083.0000162124634
AudioSynthWaveformModulated osc8b; //xy=394.6000061035156,866
AudioSynthWaveformModulated osc12b; //xy=393.6000099182129,1277.0000190734863
AudioSynthWaveformModulated osc2b; //xy=397.6000061035156,300
AudioSynthWaveformModulated osc6b; //xy=396.6000061035156,707
AudioSynthWaveformModulated osc10b; //xy=395.6000061035156,1120
AudioSynthWaveformModulated osc5b; //xy=397.6000061035156,621
AudioSynthWaveformModulated osc9b; //xy=396.6000061035156,1034
AudioSynthWaveformModulated osc5a; //xy=398.6000061035156,587
AudioSynthWaveformModulated osc9a; //xy=397.6000061035156,1000
AudioSynthWaveformModulated osc15a; //xy=398.6000061035156,1568
AudioSynthWaveformModulated osc15b; //xy=399.6000061035156,1605
AudioSynthWaveformModulated osc17a; //xy=399,1777.0000019073486
AudioSynthWaveformModulated osc17b; //xy=399,1813.0000019073486
AudioSynthWaveformModulated osc19a; //xy=399,1960
AudioSynthWaveformModulated osc23a; //xy=398,2367
AudioSynthWaveformModulated osc19b; //xy=400,1997
AudioSynthWaveformModulated osc27a; //xy=397,2780
AudioSynthWaveformModulated osc16a; //xy=401.6000061035156,1645
AudioSynthWaveformModulated osc27b; //xy=397.00000381469727,2815.000018119812
AudioSynthWaveformModulated osc23b; //xy=399,2404
AudioSynthWaveformModulated osc14a; //xy=403.6000061035156,1489
AudioSynthWaveformModulated osc20a; //xy=402,2037
AudioSynthWaveformModulated osc16b; //xy=403.6000061035156,1683
AudioSynthWaveformModulated osc24a; //xy=401,2444
AudioSynthWaveformModulated osc28a; //xy=400,2857
AudioSynthWaveformModulated osc18a; //xy=404,1881
AudioSynthWaveformModulated osc14b; //xy=405.6000061035156,1524
AudioSynthWaveformModulated osc22b; //xy=403.00000762939453,2311.0000343322754
AudioSynthWaveformModulated osc20b; //xy=404,2075
AudioSynthWaveformModulated osc13b; //xy=406.6000061035156,1438
AudioSynthWaveformModulated osc26a; //xy=402.00000381469727,2699.0000162124634
AudioSynthWaveformModulated osc24b; //xy=403,2482
AudioSynthWaveformModulated osc22a; //xy=404.00000381469727,2278.0000343322754
AudioSynthWaveformModulated osc13a; //xy=407.6000061035156,1404
AudioSynthWaveformModulated osc28b; //xy=402.00000381469727,2893.0000190734863
AudioSynthWaveformModulated osc18b; //xy=406.00000381469727,1916.0000286102295
AudioSynthWaveformModulated osc26b; //xy=404,2736
AudioSynthWaveformModulated osc21b; //xy=406,2237
AudioSynthWaveformModulated osc25b; //xy=405,2650
AudioSynthWaveformModulated osc21a; //xy=407,2203
AudioSynthWaveformModulated osc25a; //xy=406,2616
AudioSynthWaveformModulated osc31a; //xy=407,3184
AudioSynthWaveformModulated osc31b; //xy=408,3221
AudioSynthWaveformModulated osc32a; //xy=410,3261
AudioSynthWaveformModulated osc30a; //xy=412,3105
AudioSynthWaveformModulated osc32b; //xy=412,3299
AudioSynthWaveformModulated osc30b; //xy=414,3140
AudioSynthWaveformModulated osc29b; //xy=415,3054
AudioSynthWaveformModulated osc29a; //xy=416,3020
AudioMixer4 voice1Mixer; //xy=611.6000061035156,202
AudioMixer4 voice2Mixer; //xy=611.6000061035156,281
AudioMixer4 voice5Mixer; //xy=610.599983215332,607.0000095367432
AudioMixer4 voice6Mixer; //xy=610.599983215332,685.0000114440918
AudioMixer4 voice9Mixer; //xy=609.6000061035156,1022
AudioMixer4 voice10Mixer; //xy=609.6000061035156,1101
AudioMixer4 voice3Mixer; //xy=613.6000061035156,356
AudioMixer4 voice7Mixer; //xy=612.6000061035156,763
AudioMixer4 voice11Mixer; //xy=611.6000061035156,1176
AudioMixer4 voice4Mixer; //xy=614.6000061035156,431
AudioMixer4 voice8Mixer; //xy=613.6000061035156,838
AudioMixer4 voice12Mixer; //xy=612.6000061035156,1251
AudioMixer4 voice13Mixer; //xy=619.6000061035156,1426
AudioMixer4 voice14Mixer; //xy=619.6000061035156,1505
AudioMixer4 voice17Mixer; //xy=620,1818
AudioMixer4 voice18Mixer; //xy=620,1897
AudioMixer4 voice21Mixer; //xy=618.9999771118164,2223.000009536743
AudioMixer4 voice15Mixer; //xy=621.6000061035156,1580
AudioMixer4 voice22Mixer; //xy=619.0000076293945,2299.0000343322754
AudioMixer4 voice25Mixer; //xy=618,2638
AudioMixer4 voice26Mixer; //xy=618,2717
AudioMixer4 voice16Mixer; //xy=622.6000061035156,1655
AudioMixer4 voice23Mixer; //xy=620.0000076293945,2377.0000343322754
AudioMixer4 voice19Mixer; //xy=622,1972
AudioMixer4 voice27Mixer; //xy=620,2792
AudioMixer4 voice20Mixer; //xy=623.0000076293945,2044.0000305175781
AudioMixer4 voice24Mixer; //xy=622.0000076293945,2455.0000343322754
AudioMixer4 voice28Mixer; //xy=621,2867
AudioMixer4 voice29Mixer; //xy=628,3042
AudioMixer4 voice30Mixer; //xy=628,3121
AudioMixer4 voice31Mixer; //xy=630,3196
AudioMixer4 voice32Mixer; //xy=631,3271
AudioEffectEnvelope envelope2; //xy=803.6000061035156,280
AudioEffectEnvelope envelope3; //xy=803.6000061035156,350
AudioEffectEnvelope envelope6; //xy=802.6000061035156,687
AudioEffectEnvelope envelope1; //xy=804.6000061035156,207
AudioEffectEnvelope envelope7; //xy=802.6000061035156,757
AudioEffectEnvelope envelope10; //xy=801.6000061035156,1100
AudioEffectEnvelope envelope5; //xy=803.6000061035156,614
AudioEffectEnvelope envelope11; //xy=801.6000061035156,1170
AudioEffectEnvelope envelope4; //xy=804.6000061035156,425
AudioEffectEnvelope envelope9; //xy=802.6000061035156,1027
AudioEffectEnvelope envelope8; //xy=803.6000061035156,832
AudioEffectEnvelope envelope12; //xy=802.6000061035156,1245
AudioEffectEnvelope envelope14; //xy=811.6000061035156,1504
AudioEffectEnvelope envelope15; //xy=811.6000061035156,1574
AudioEffectEnvelope envelope13; //xy=812.6000061035156,1431
AudioEffectEnvelope envelope16; //xy=812.6000061035156,1649
AudioEffectEnvelope envelope18; //xy=812,1896
AudioEffectEnvelope envelope19; //xy=812,1966
AudioEffectEnvelope envelope22; //xy=811,2303
AudioEffectEnvelope envelope17; //xy=813,1823
AudioEffectEnvelope envelope23; //xy=811,2373
AudioEffectEnvelope envelope26; //xy=810,2716
AudioEffectEnvelope envelope21; //xy=812,2230
AudioEffectEnvelope envelope27; //xy=810,2786
AudioEffectEnvelope envelope20; //xy=813,2041
AudioEffectEnvelope envelope25; //xy=811,2643
AudioEffectEnvelope envelope24; //xy=812,2448
AudioEffectEnvelope envelope28; //xy=811,2861
AudioEffectEnvelope envelope30; //xy=820,3120
AudioEffectEnvelope envelope31; //xy=820,3190
AudioEffectEnvelope envelope29; //xy=821,3047
AudioEffectEnvelope envelope32; //xy=821,3265
AudioMixer4 voiceMixer1; //xy=992.5999908447266,306.00000381469727
AudioMixer4 voiceMixer2; //xy=991.6000061035156,715
AudioMixer4 voiceMixer3; //xy=990.6000061035156,1128
AudioMixer4 voiceMixer4; //xy=1000.5999908447266,1530.0000228881836
AudioMixer4 voiceMixer5; //xy=1000.9999847412109,1922.0000038146973
AudioMixer4 voiceMixer6; //xy=1000,2331
AudioMixer4 voiceMixer7; //xy=999,2744
AudioMixer4 voiceMixer8; //xy=1008.9999847412109,3146.0000228881836
AudioMixer4 subMixer2; //xy=1242.3999938964844,1753.9999771118164
AudioMixer4 subMixer1; //xy=1244.0000915527344,1658.9999752044678
AudioMixer4 lastMixer; //xy=1406.599998474121,1708.1999778747559
AudioFilterStateVariable filter1; //xy=1565,1710.9999771118164
AudioOutputI2S i2s1; //xy=1733,1698.999976158142
AudioConnection patchCord1(osc1a, 0, voice1Mixer, 0);
AudioConnection patchCord2(osc1b, 0, voice1Mixer, 1);
AudioConnection patchCord3(osc3a, 0, voice3Mixer, 0);
AudioConnection patchCord4(osc7a, 0, voice7Mixer, 0);
AudioConnection patchCord5(osc3b, 0, voice3Mixer, 1);
AudioConnection patchCord6(osc11a, 0, voice11Mixer, 0);
AudioConnection patchCord7(osc11b, 0, voice11Mixer, 1);
AudioConnection patchCord8(osc7b, 0, voice7Mixer, 1);
AudioConnection patchCord9(osc4a, 0, voice4Mixer, 0);
AudioConnection patchCord10(osc8a, 0, voice8Mixer, 0);
AudioConnection patchCord11(osc12a, 0, voice12Mixer, 0);
AudioConnection patchCord12(osc2a, 0, voice2Mixer, 0);
AudioConnection patchCord13(osc6a, 0, voice6Mixer, 0);
AudioConnection patchCord14(osc4b, 0, voice4Mixer, 1);
AudioConnection patchCord15(osc10a, 0, voice10Mixer, 0);
AudioConnection patchCord16(osc8b, 0, voice8Mixer, 1);
AudioConnection patchCord17(osc12b, 0, voice12Mixer, 1);
AudioConnection patchCord18(osc2b, 0, voice2Mixer, 1);
AudioConnection patchCord19(osc6b, 0, voice6Mixer, 1);
AudioConnection patchCord20(osc10b, 0, voice10Mixer, 1);
AudioConnection patchCord21(osc5b, 0, voice5Mixer, 1);
AudioConnection patchCord22(osc9b, 0, voice9Mixer, 1);
AudioConnection patchCord23(osc5a, 0, voice5Mixer, 0);
AudioConnection patchCord24(osc9a, 0, voice9Mixer, 0);
AudioConnection patchCord25(osc15a, 0, voice15Mixer, 0);
AudioConnection patchCord26(osc15b, 0, voice15Mixer, 1);
AudioConnection patchCord27(osc17a, 0, voice17Mixer, 0);
AudioConnection patchCord28(osc17b, 0, voice17Mixer, 1);
AudioConnection patchCord29(osc19a, 0, voice19Mixer, 0);
AudioConnection patchCord30(osc23a, 0, voice23Mixer, 0);
AudioConnection patchCord31(osc19b, 0, voice19Mixer, 1);
AudioConnection patchCord32(osc27a, 0, voice27Mixer, 0);
AudioConnection patchCord33(osc16a, 0, voice16Mixer, 0);
AudioConnection patchCord34(osc27b, 0, voice27Mixer, 1);
AudioConnection patchCord35(osc23b, 0, voice23Mixer, 1);
AudioConnection patchCord36(osc14a, 0, voice14Mixer, 0);
AudioConnection patchCord37(osc20a, 0, voice20Mixer, 0);
AudioConnection patchCord38(osc16b, 0, voice16Mixer, 1);
AudioConnection patchCord39(osc24a, 0, voice24Mixer, 0);
AudioConnection patchCord40(osc28a, 0, voice28Mixer, 0);
AudioConnection patchCord41(osc18a, 0, voice18Mixer, 0);
AudioConnection patchCord42(osc14b, 0, voice14Mixer, 1);
AudioConnection patchCord43(osc22b, 0, voice22Mixer, 1);
AudioConnection patchCord44(osc20b, 0, voice20Mixer, 1);
AudioConnection patchCord45(osc13b, 0, voice13Mixer, 1);
AudioConnection patchCord46(osc26a, 0, voice26Mixer, 0);
AudioConnection patchCord47(osc24b, 0, voice24Mixer, 1);
AudioConnection patchCord48(osc22a, 0, voice22Mixer, 0);
AudioConnection patchCord49(osc13a, 0, voice13Mixer, 0);
AudioConnection patchCord50(osc28b, 0, voice28Mixer, 1);
AudioConnection patchCord51(osc18b, 0, voice18Mixer, 1);
AudioConnection patchCord52(osc26b, 0, voice26Mixer, 1);
AudioConnection patchCord53(osc21b, 0, voice21Mixer, 1);
AudioConnection patchCord54(osc25b, 0, voice25Mixer, 1);
AudioConnection patchCord55(osc21a, 0, voice21Mixer, 0);
AudioConnection patchCord56(osc25a, 0, voice25Mixer, 0);
AudioConnection patchCord57(osc31a, 0, voice31Mixer, 0);
AudioConnection patchCord58(osc31b, 0, voice31Mixer, 1);
AudioConnection patchCord59(osc32a, 0, voice32Mixer, 0);
AudioConnection patchCord60(osc30a, 0, voice30Mixer, 0);
AudioConnection patchCord61(osc32b, 0, voice32Mixer, 1);
AudioConnection patchCord62(osc30b, 0, voice30Mixer, 1);
AudioConnection patchCord63(osc29b, 0, voice29Mixer, 1);
AudioConnection patchCord64(osc29a, 0, voice29Mixer, 0);
AudioConnection patchCord65(voice1Mixer, envelope1);
AudioConnection patchCord66(voice2Mixer, envelope2);
AudioConnection patchCord67(voice5Mixer, envelope5);
AudioConnection patchCord68(voice6Mixer, envelope6);
AudioConnection patchCord69(voice9Mixer, envelope9);
AudioConnection patchCord70(voice10Mixer, envelope10);
AudioConnection patchCord71(voice3Mixer, envelope3);
AudioConnection patchCord72(voice7Mixer, envelope7);
AudioConnection patchCord73(voice11Mixer, envelope11);
AudioConnection patchCord74(voice4Mixer, envelope4);
AudioConnection patchCord75(voice8Mixer, envelope8);
AudioConnection patchCord76(voice12Mixer, envelope12);
AudioConnection patchCord77(voice13Mixer, envelope13);
AudioConnection patchCord78(voice14Mixer, envelope14);
AudioConnection patchCord79(voice17Mixer, envelope17);
AudioConnection patchCord80(voice18Mixer, envelope18);
AudioConnection patchCord81(voice21Mixer, envelope21);
AudioConnection patchCord82(voice15Mixer, envelope15);
AudioConnection patchCord83(voice22Mixer, envelope22);
AudioConnection patchCord84(voice25Mixer, envelope25);
AudioConnection patchCord85(voice26Mixer, envelope26);
AudioConnection patchCord86(voice16Mixer, envelope16);
AudioConnection patchCord87(voice23Mixer, envelope23);
AudioConnection patchCord88(voice19Mixer, envelope19);
AudioConnection patchCord89(voice27Mixer, envelope27);
AudioConnection patchCord90(voice20Mixer, envelope20);
AudioConnection patchCord91(voice24Mixer, envelope24);
AudioConnection patchCord92(voice28Mixer, envelope28);
AudioConnection patchCord93(voice29Mixer, envelope29);
AudioConnection patchCord94(voice30Mixer, envelope30);
AudioConnection patchCord95(voice31Mixer, envelope31);
AudioConnection patchCord96(voice32Mixer, envelope32);
AudioConnection patchCord97(envelope2, 0, voiceMixer1, 1);
AudioConnection patchCord98(envelope3, 0, voiceMixer1, 2);
AudioConnection patchCord99(envelope6, 0, voiceMixer2, 1);
AudioConnection patchCord100(envelope1, 0, voiceMixer1, 0);
AudioConnection patchCord101(envelope7, 0, voiceMixer2, 2);
AudioConnection patchCord102(envelope10, 0, voiceMixer3, 1);
AudioConnection patchCord103(envelope5, 0, voiceMixer2, 0);
AudioConnection patchCord104(envelope11, 0, voiceMixer3, 2);
AudioConnection patchCord105(envelope4, 0, voiceMixer1, 3);
AudioConnection patchCord106(envelope9, 0, voiceMixer3, 0);
AudioConnection patchCord107(envelope8, 0, voiceMixer2, 3);
AudioConnection patchCord108(envelope12, 0, voiceMixer3, 3);
AudioConnection patchCord109(envelope14, 0, voiceMixer4, 1);
AudioConnection patchCord110(envelope15, 0, voiceMixer4, 2);
AudioConnection patchCord111(envelope13, 0, voiceMixer4, 0);
AudioConnection patchCord112(envelope16, 0, voiceMixer4, 3);
AudioConnection patchCord113(envelope18, 0, voiceMixer5, 1);
AudioConnection patchCord114(envelope19, 0, voiceMixer5, 2);
AudioConnection patchCord115(envelope22, 0, voiceMixer6, 1);
AudioConnection patchCord116(envelope17, 0, voiceMixer5, 0);
AudioConnection patchCord117(envelope23, 0, voiceMixer6, 2);
AudioConnection patchCord118(envelope26, 0, voiceMixer7, 1);
AudioConnection patchCord119(envelope21, 0, voiceMixer6, 0);
AudioConnection patchCord120(envelope27, 0, voiceMixer7, 2);
AudioConnection patchCord121(envelope20, 0, voiceMixer5, 3);
AudioConnection patchCord122(envelope25, 0, voiceMixer7, 0);
AudioConnection patchCord123(envelope24, 0, voiceMixer6, 3);
AudioConnection patchCord124(envelope28, 0, voiceMixer7, 3);
AudioConnection patchCord125(envelope30, 0, voiceMixer8, 1);
AudioConnection patchCord126(envelope31, 0, voiceMixer8, 2);
AudioConnection patchCord127(envelope29, 0, voiceMixer8, 0);
AudioConnection patchCord128(envelope32, 0, voiceMixer8, 3);
AudioConnection patchCord129(voiceMixer1, 0, subMixer1, 0);
AudioConnection patchCord130(voiceMixer2, 0, subMixer1, 1);
AudioConnection patchCord131(voiceMixer3, 0, subMixer1, 2);
AudioConnection patchCord132(voiceMixer4, 0, subMixer1, 3);
AudioConnection patchCord133(voiceMixer5, 0, subMixer2, 0);
AudioConnection patchCord134(voiceMixer6, 0, subMixer2, 1);
AudioConnection patchCord135(voiceMixer7, 0, subMixer2, 2);
AudioConnection patchCord136(voiceMixer8, 0, subMixer2, 3);
AudioConnection patchCord137(subMixer2, 0, lastMixer, 1);
AudioConnection patchCord138(subMixer1, 0, lastMixer, 0);
AudioConnection patchCord139(lastMixer, 0, filter1, 0);
AudioConnection patchCord140(filter1, 0, i2s1, 0);
AudioConnection patchCord141(filter1, 0, i2s1, 1);
AudioControlSGTL5000 sgtl5000_1; //xy=1713.599998474121,1614.0000190734863
// GUItool: end automatically generated code
#define NUM_VOICES 32
int wave1 = WAVEFORM_SINE;
int wave2 = WAVEFORM_TRIANGLE;
int filterTemp = 10000 * analogRead(A3) / 1023;;
byte globalVelocity = 127;
int attackTemp = 11880 * analogRead(A0) / 1023;
int releaseTemp = analogRead(A1) / 1023;
int attackKnob = 11880 * analogRead(A0) / 1023;
int releaseKnob = 11880 * analogRead(A1) / 1023;
float centsTemp = 100 * analogRead(A17) / 1023;
float cents = 100 * analogRead(A17) / 1023;
float detune = 1.0;
const float noteFreqs[128] = {8.176, 8.662, 9.177, 9.723, 10.301, 10.913, 11.562, 12.25, 12.978, 13.75, 14.568, 15.434, 16.352, 17.324, 18.354, 19.445, 20.602, 21.827, 23.125, 24.5, 25.957, 27.5, 29.135, 30.868, 32.703, 34.648, 36.708, 38.891, 41.203, 43.654, 46.249, 48.999, 51.913, 55, 58.27, 61.735, 65.406, 69.296, 73.416, 77.782, 82.407, 87.307, 92.499, 97.999, 103.826, 110, 116.541, 123.471, 130.813, 138.591, 146.832, 155.563, 164.814, 174.614, 184.997, 195.998, 207.652, 220, 233.082, 246.942, 261.626, 277.183, 293.665, 311.127, 329.628, 349.228, 369.994, 391.995, 415.305, 440, 466.164, 493.883, 523.251, 554.365, 587.33, 622.254, 659.255, 698.456, 739.989, 783.991, 830.609, 880, 932.328, 987.767, 1046.502, 1108.731, 1174.659, 1244.508, 1318.51, 1396.913, 1479.978, 1567.982, 1661.219, 1760, 1864.655, 1975.533, 2093.005, 2217.461, 2349.318, 2489.016, 2637.02, 2793.826, 2959.955, 3135.963, 3322.438, 3520, 3729.31, 3951.066, 4186.009, 4434.922, 4698.636, 4978.032, 5274.041, 5587.652, 5919.911, 6271.927, 6644.875, 7040, 7458.62, 7902.133, 8372.018, 8869.844, 9397.273, 9956.063, 10548.08, 11175.3, 11839.82, 12543.85};
AudioSynthWaveformModulated *oscsA[NUM_VOICES] = { &osc1a, &osc2a, &osc3a, &osc4a, &osc5a, &osc6a, &osc7a, &osc8a, &osc9a, &osc10a, &osc11a, &osc12a, &osc13a, &osc14a, &osc15a, &osc16a, &osc17a, &osc18a, &osc19a, &osc20a, &osc21a, &osc22a, &osc23a, &osc24a, &osc25a, &osc26a, &osc27a, &osc28a, &osc29a, &osc30a, &osc31a, &osc32a };
AudioSynthWaveformModulated *oscsB[NUM_VOICES] = { &osc1b, &osc2b, &osc3b, &osc4b, &osc5b, &osc6b, &osc7b, &osc8b, &osc9b, &osc10b, &osc11b, &osc12b, &osc13b, &osc14b, &osc15b, &osc16b, &osc17b, &osc18b, &osc19b, &osc20b, &osc21b, &osc22b, &osc23b, &osc24b, &osc25b, &osc26b, &osc27b, &osc28b, &osc29b, &osc30b, &osc31b, &osc32b};
AudioEffectEnvelope *envelopes[NUM_VOICES] = { &envelope1, &envelope2, &envelope3, &envelope4, &envelope5, &envelope6, &envelope7, &envelope8, &envelope9, &envelope10, &envelope11, &envelope12, &envelope13, &envelope14, &envelope15, &envelope16, &envelope17, &envelope18, &envelope19, &envelope20, &envelope21, &envelope22, &envelope23, &envelope24, &envelope25, &envelope26, &envelope27, &envelope28, &envelope29, &envelope30, &envelope31, &envelope32 };
Bounce *mybutton[] = { &button0, &button1, &button2, &button3, &button4, &button5, &button6, &button7};
const float buttonFreqs[8] = {48, 50, 52, 53, 55, 57, 59, 60};
unsigned long voiceOnTimes[NUM_VOICES] = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
bool idleVoices[NUM_VOICES] = {true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true };
byte voiceToNote[NUM_VOICES] = {255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255 }; // Dummy value outside range of valid notes is used to init each.
elapsedMillis readPots = 0;
void NoteOn(byte channel, byte note, byte velocity) {
bool found = false;
int voiceToUse = 0;
// Acquire an idle voice if possible.
for (int i = 0; i < NUM_VOICES; i++) {
if (idleVoices[i]) {
voiceToUse = i;
found = 1;
break;
}
}
// Steal voice if needed.
if (!found) {
unsigned long oldest = millis();
for (int i = 0; i < NUM_VOICES; i++) {
if (voiceOnTimes[i] < oldest) {
oldest = voiceOnTimes[i];
voiceToUse = i;
}
}
}
// Now use the acquired voice.
idleVoices[voiceToUse] = false;
voiceToNote[voiceToUse] = note;
AudioNoInterrupts();
oscsA[voiceToUse]->frequency(noteFreqs[note]);
oscsA[voiceToUse]->amplitude(.5f);
oscsB[voiceToUse]->frequency(detune * noteFreqs[note]);
oscsB[voiceToUse]->amplitude(.5f);
envelopes[voiceToUse]->noteOn();
AudioInterrupts();
voiceOnTimes[voiceToUse] = millis();
}
void NoteOff(byte channel, byte note, byte velocity) {
for (int i = 0; i < NUM_VOICES; i++) {
if (voiceToNote[i] == note) {
envelopes[i]->noteOff();
voiceToNote[i] = -1;
}
}
}
void IdleCheck(void) {
for (uint8_t i = 0; i < NUM_VOICES; i++) {
if (!envelopes[i]->isActive()) {
oscsA[i]->amplitude(0);
oscsB[i]->amplitude(0);
idleVoices[i] = 1;
} else {
idleVoices[i] = false;
}
}
}
void setup() {
AudioMemory(160);
Serial.begin(115200);
myusb.begin();
pinMode(25, INPUT_PULLUP);
pinMode(26, INPUT_PULLUP);
pinMode(27, INPUT_PULLUP);
pinMode(28, INPUT_PULLUP);
pinMode(29, INPUT_PULLUP);
pinMode(30, INPUT_PULLUP);
pinMode(31, INPUT_PULLUP);
pinMode(32, INPUT_PULLUP);
for (int i = 0; i < 4; i++) {
// Set all mixers.
voice1Mixer.gain(i, .5f);
voice2Mixer.gain(i, .5f);
voice3Mixer.gain(i, .5f);
voice4Mixer.gain(i, .5f);
voice5Mixer.gain(i, .5f);
voice6Mixer.gain(i, .5f);
voice7Mixer.gain(i, .5f);
voice8Mixer.gain(i, .5f);
voice9Mixer.gain(i, .5f);
voice10Mixer.gain(i, .5f);
voice11Mixer.gain(i, .5f);
voice12Mixer.gain(i, .5f);
voice13Mixer.gain(i, .5f);
voice14Mixer.gain(i, .5f);
voice15Mixer.gain(i, .5f);
voice16Mixer.gain(i, .5f);
voice17Mixer.gain(i, .5f);
voice18Mixer.gain(i, .5f);
voice19Mixer.gain(i, .5f);
voice20Mixer.gain(i, .5f);
voice21Mixer.gain(i, .5f);
voice22Mixer.gain(i, .5f);
voice23Mixer.gain(i, .5f);
voice24Mixer.gain(i, .5f);
voice25Mixer.gain(i, .5f);
voice26Mixer.gain(i, .5f);
voice27Mixer.gain(i, .5f);
voice28Mixer.gain(i, .5f);
voice29Mixer.gain(i, .5f);
voice30Mixer.gain(i, .5f);
voice31Mixer.gain(i, .5f);
voice32Mixer.gain(i, .5f);
voiceMixer1.gain(i, .5f);
voiceMixer2.gain(i, .5f);
voiceMixer3.gain(i, .5f);
voiceMixer4.gain(i, .5f);
voiceMixer5.gain(i, .5f);
voiceMixer6.gain(i, .5f);
voiceMixer7.gain(i, .5f);
voiceMixer8.gain(i, .5f);
subMixer1.gain(i, .5f);
subMixer2.gain(i, .5f);
lastMixer.gain(i, .6f);
// Set oscs to default waves.
oscsA[i]->begin(wave1);
oscsB[i]->begin(wave2);
// Set envelopes to something reasonable.
envelopes[i]->attack(attackKnob);
envelopes[i]->decay(10);
envelopes[i]->sustain(.5f);
envelopes[i]->release(releaseKnob);
//Set default filter value
int filterKnob = 10000 * analogRead(A3) / 1023;
filter1.frequency(filterKnob);
}
// Enable codec
sgtl5000_1.enable();
sgtl5000_1.volume(.5f);
// Set USB MIDI device callbacks.
midi1.setHandleNoteOff(NoteOff);
midi1.setHandleNoteOn(NoteOn);
}
void loop() {
// Only read pots every 50 milliseconds to reduce glitchiness due to noise...
// This could be done with averaging or something instead.
if (readPots >= 50) {
// Reset elapsed time.
readPots = 0;
float cents = 100 * analogRead(A17) / 1023;
float detune = pow(2, (cents / 1200));
if (centsTemp != cents) {
for (int i = 0; i < NUM_VOICES; i++) {
if (voiceToNote[i] != 255) {
oscsB[i]->frequency((1.0f / detune) * noteFreqs[voiceToNote[i]]);
Serial.println(voiceToNote[i]);
Serial.println(detune);
}
}
centsTemp = cents;
}
// Read waveform selection pots.
int wave1Temp = map(analogRead(A14), 0, 1023, WAVEFORM_SINE, WAVEFORM_TRIANGLE);
int wave2Temp = map(analogRead(A16), 0, 1023, WAVEFORM_SINE, WAVEFORM_TRIANGLE);
// Update A oscs only if waveform has changed.
// Oscillator phase will be reset by calling begin(), that's why we only want to do it when knob has changed.
if (wave1Temp != wave1) {
wave1 = wave1Temp;
Serial.printf("Knob 1: %d\n", wave1);
for (int i = 0; i < NUM_VOICES; i++) {
oscsA[i]->begin(wave1);
}
}
// Same thing for B oscs.
if (wave2Temp != wave2) {
wave2 = wave2Temp;
Serial.printf("Knob 2: %d\n", wave2);
for (int i = 0; i < NUM_VOICES; i++) {
oscsB[i]->begin(wave2);
}
}
//Lowpass Filter
int filterKnob = 10000 * analogRead(A3) / 1023;
if (filterTemp != filterKnob) {
filterTemp = filterKnob;
filter1.frequency(filterKnob);
//Resonace will be controlled by its own knob
filter1.resonance(3.8);
}
//Attack and Release
int attackKnob = 11880 * analogRead(A0) / 1023;
int releaseKnob = 11880 * analogRead(A1) / 1023;
if (attackTemp != attackKnob) {
attackTemp = attackKnob;
for (int i = 0; i < NUM_VOICES; i++) {
envelopes[i]->attack(attackKnob);
}
}
if (releaseTemp != releaseKnob) {
releaseTemp = releaseKnob;
for (int i = 0; i < NUM_VOICES; i++) {
envelopes[i]->release(releaseKnob);
}
}
}
for (int i = 0; i < 8; i++) {
mybutton[i]->update();
if (mybutton[i]->fallingEdge()) {
NoteOn(1, buttonFreqs[i], globalVelocity);
}
if (mybutton[i]->risingEdge()) {
NoteOff(1, buttonFreqs[i], globalVelocity);
}
}
IdleCheck();
midi1.read();
}
// Includes
#include <Bounce.h>
#include <Audio.h>
#include <Wire.h>
#include <SPI.h>
#include <SD.h>
#include <SerialFlash.h>
// My synth has 8 onboard buttons. Bounce my Buttons :)
Bounce button0 = Bounce(25, 15);
Bounce button1 = Bounce(26, 15);
Bounce button2 = Bounce(27, 15);
Bounce button3 = Bounce(28, 15);
Bounce button4 = Bounce(29, 15);
Bounce button5 = Bounce(30, 15);
Bounce button6 = Bounce(31, 15);
Bounce button7 = Bounce(32, 15);
// Include USBHost Library
#include <USBHost_t36.h>
// Setup USBHost objects
USBHost myusb;
MIDIDevice midi1(myusb);
// GUItool: begin automatically generated code
AudioSynthWaveformModulated osc1a; //xy=390.6000061035156,161.00000190734863
AudioSynthWaveformModulated osc1b; //xy=390.6000061035156,197.00000190734863
AudioSynthWaveformModulated osc3a; //xy=390.6000061035156,344
AudioSynthWaveformModulated osc7a; //xy=389.6000061035156,751
AudioSynthWaveformModulated osc3b; //xy=391.6000061035156,381
AudioSynthWaveformModulated osc11a; //xy=388.6000061035156,1164
AudioSynthWaveformModulated osc11b; //xy=388.6000099182129,1199.000018119812
AudioSynthWaveformModulated osc7b; //xy=390.6000061035156,788
AudioSynthWaveformModulated osc4a; //xy=393.6000061035156,421
AudioSynthWaveformModulated osc8a; //xy=392.6000061035156,828
AudioSynthWaveformModulated osc12a; //xy=391.6000061035156,1241
AudioSynthWaveformModulated osc2a; //xy=395.6000061035156,265
AudioSynthWaveformModulated osc6a; //xy=394.6000061035156,672
AudioSynthWaveformModulated osc4b; //xy=395.6000061035156,459
AudioSynthWaveformModulated osc10a; //xy=393.6000099182129,1083.0000162124634
AudioSynthWaveformModulated osc8b; //xy=394.6000061035156,866
AudioSynthWaveformModulated osc12b; //xy=393.6000099182129,1277.0000190734863
AudioSynthWaveformModulated osc2b; //xy=397.6000061035156,300
AudioSynthWaveformModulated osc6b; //xy=396.6000061035156,707
AudioSynthWaveformModulated osc10b; //xy=395.6000061035156,1120
AudioSynthWaveformModulated osc5b; //xy=397.6000061035156,621
AudioSynthWaveformModulated osc9b; //xy=396.6000061035156,1034
AudioSynthWaveformModulated osc5a; //xy=398.6000061035156,587
AudioSynthWaveformModulated osc9a; //xy=397.6000061035156,1000
AudioSynthWaveformModulated osc15a; //xy=398.6000061035156,1568
AudioSynthWaveformModulated osc15b; //xy=399.6000061035156,1605
AudioSynthWaveformModulated osc17a; //xy=399,1777.0000019073486
AudioSynthWaveformModulated osc17b; //xy=399,1813.0000019073486
AudioSynthWaveformModulated osc19a; //xy=399,1960
AudioSynthWaveformModulated osc23a; //xy=398,2367
AudioSynthWaveformModulated osc19b; //xy=400,1997
AudioSynthWaveformModulated osc27a; //xy=397,2780
AudioSynthWaveformModulated osc16a; //xy=401.6000061035156,1645
AudioSynthWaveformModulated osc27b; //xy=397.00000381469727,2815.000018119812
AudioSynthWaveformModulated osc23b; //xy=399,2404
AudioSynthWaveformModulated osc14a; //xy=403.6000061035156,1489
AudioSynthWaveformModulated osc20a; //xy=402,2037
AudioSynthWaveformModulated osc16b; //xy=403.6000061035156,1683
AudioSynthWaveformModulated osc24a; //xy=401,2444
AudioSynthWaveformModulated osc28a; //xy=400,2857
AudioSynthWaveformModulated osc18a; //xy=404,1881
AudioSynthWaveformModulated osc14b; //xy=405.6000061035156,1524
AudioSynthWaveformModulated osc22b; //xy=403.00000762939453,2311.0000343322754
AudioSynthWaveformModulated osc20b; //xy=404,2075
AudioSynthWaveformModulated osc13b; //xy=406.6000061035156,1438
AudioSynthWaveformModulated osc26a; //xy=402.00000381469727,2699.0000162124634
AudioSynthWaveformModulated osc24b; //xy=403,2482
AudioSynthWaveformModulated osc22a; //xy=404.00000381469727,2278.0000343322754
AudioSynthWaveformModulated osc13a; //xy=407.6000061035156,1404
AudioSynthWaveformModulated osc28b; //xy=402.00000381469727,2893.0000190734863
AudioSynthWaveformModulated osc18b; //xy=406.00000381469727,1916.0000286102295
AudioSynthWaveformModulated osc26b; //xy=404,2736
AudioSynthWaveformModulated osc21b; //xy=406,2237
AudioSynthWaveformModulated osc25b; //xy=405,2650
AudioSynthWaveformModulated osc21a; //xy=407,2203
AudioSynthWaveformModulated osc25a; //xy=406,2616
AudioSynthWaveformModulated osc31a; //xy=407,3184
AudioSynthWaveformModulated osc31b; //xy=408,3221
AudioSynthWaveformModulated osc32a; //xy=410,3261
AudioSynthWaveformModulated osc30a; //xy=412,3105
AudioSynthWaveformModulated osc32b; //xy=412,3299
AudioSynthWaveformModulated osc30b; //xy=414,3140
AudioSynthWaveformModulated osc29b; //xy=415,3054
AudioSynthWaveformModulated osc29a; //xy=416,3020
AudioMixer4 voice1Mixer; //xy=611.6000061035156,202
AudioMixer4 voice2Mixer; //xy=611.6000061035156,281
AudioMixer4 voice5Mixer; //xy=610.599983215332,607.0000095367432
AudioMixer4 voice6Mixer; //xy=610.599983215332,685.0000114440918
AudioMixer4 voice9Mixer; //xy=609.6000061035156,1022
AudioMixer4 voice10Mixer; //xy=609.6000061035156,1101
AudioMixer4 voice3Mixer; //xy=613.6000061035156,356
AudioMixer4 voice7Mixer; //xy=612.6000061035156,763
AudioMixer4 voice11Mixer; //xy=611.6000061035156,1176
AudioMixer4 voice4Mixer; //xy=614.6000061035156,431
AudioMixer4 voice8Mixer; //xy=613.6000061035156,838
AudioMixer4 voice12Mixer; //xy=612.6000061035156,1251
AudioMixer4 voice13Mixer; //xy=619.6000061035156,1426
AudioMixer4 voice14Mixer; //xy=619.6000061035156,1505
AudioMixer4 voice17Mixer; //xy=620,1818
AudioMixer4 voice18Mixer; //xy=620,1897
AudioMixer4 voice21Mixer; //xy=618.9999771118164,2223.000009536743
AudioMixer4 voice15Mixer; //xy=621.6000061035156,1580
AudioMixer4 voice22Mixer; //xy=619.0000076293945,2299.0000343322754
AudioMixer4 voice25Mixer; //xy=618,2638
AudioMixer4 voice26Mixer; //xy=618,2717
AudioMixer4 voice16Mixer; //xy=622.6000061035156,1655
AudioMixer4 voice23Mixer; //xy=620.0000076293945,2377.0000343322754
AudioMixer4 voice19Mixer; //xy=622,1972
AudioMixer4 voice27Mixer; //xy=620,2792
AudioMixer4 voice20Mixer; //xy=623.0000076293945,2044.0000305175781
AudioMixer4 voice24Mixer; //xy=622.0000076293945,2455.0000343322754
AudioMixer4 voice28Mixer; //xy=621,2867
AudioMixer4 voice29Mixer; //xy=628,3042
AudioMixer4 voice30Mixer; //xy=628,3121
AudioMixer4 voice31Mixer; //xy=630,3196
AudioMixer4 voice32Mixer; //xy=631,3271
AudioEffectEnvelope envelope2; //xy=803.6000061035156,280
AudioEffectEnvelope envelope3; //xy=803.6000061035156,350
AudioEffectEnvelope envelope6; //xy=802.6000061035156,687
AudioEffectEnvelope envelope1; //xy=804.6000061035156,207
AudioEffectEnvelope envelope7; //xy=802.6000061035156,757
AudioEffectEnvelope envelope10; //xy=801.6000061035156,1100
AudioEffectEnvelope envelope5; //xy=803.6000061035156,614
AudioEffectEnvelope envelope11; //xy=801.6000061035156,1170
AudioEffectEnvelope envelope4; //xy=804.6000061035156,425
AudioEffectEnvelope envelope9; //xy=802.6000061035156,1027
AudioEffectEnvelope envelope8; //xy=803.6000061035156,832
AudioEffectEnvelope envelope12; //xy=802.6000061035156,1245
AudioEffectEnvelope envelope14; //xy=811.6000061035156,1504
AudioEffectEnvelope envelope15; //xy=811.6000061035156,1574
AudioEffectEnvelope envelope13; //xy=812.6000061035156,1431
AudioEffectEnvelope envelope16; //xy=812.6000061035156,1649
AudioEffectEnvelope envelope18; //xy=812,1896
AudioEffectEnvelope envelope19; //xy=812,1966
AudioEffectEnvelope envelope22; //xy=811,2303
AudioEffectEnvelope envelope17; //xy=813,1823
AudioEffectEnvelope envelope23; //xy=811,2373
AudioEffectEnvelope envelope26; //xy=810,2716
AudioEffectEnvelope envelope21; //xy=812,2230
AudioEffectEnvelope envelope27; //xy=810,2786
AudioEffectEnvelope envelope20; //xy=813,2041
AudioEffectEnvelope envelope25; //xy=811,2643
AudioEffectEnvelope envelope24; //xy=812,2448
AudioEffectEnvelope envelope28; //xy=811,2861
AudioEffectEnvelope envelope30; //xy=820,3120
AudioEffectEnvelope envelope31; //xy=820,3190
AudioEffectEnvelope envelope29; //xy=821,3047
AudioEffectEnvelope envelope32; //xy=821,3265
AudioMixer4 voiceMixer1; //xy=992.5999908447266,306.00000381469727
AudioMixer4 voiceMixer2; //xy=991.6000061035156,715
AudioMixer4 voiceMixer3; //xy=990.6000061035156,1128
AudioMixer4 voiceMixer4; //xy=1000.5999908447266,1530.0000228881836
AudioMixer4 voiceMixer5; //xy=1000.9999847412109,1922.0000038146973
AudioMixer4 voiceMixer6; //xy=1000,2331
AudioMixer4 voiceMixer7; //xy=999,2744
AudioMixer4 voiceMixer8; //xy=1008.9999847412109,3146.0000228881836
AudioMixer4 subMixer2; //xy=1242.3999938964844,1753.9999771118164
AudioMixer4 subMixer1; //xy=1244.0000915527344,1658.9999752044678
AudioMixer4 lastMixer; //xy=1406.599998474121,1708.1999778747559
AudioFilterStateVariable filter1; //xy=1565,1710.9999771118164
AudioOutputI2S i2s1; //xy=1733,1698.999976158142
AudioConnection patchCord1(osc1a, 0, voice1Mixer, 0);
AudioConnection patchCord2(osc1b, 0, voice1Mixer, 1);
AudioConnection patchCord3(osc3a, 0, voice3Mixer, 0);
AudioConnection patchCord4(osc7a, 0, voice7Mixer, 0);
AudioConnection patchCord5(osc3b, 0, voice3Mixer, 1);
AudioConnection patchCord6(osc11a, 0, voice11Mixer, 0);
AudioConnection patchCord7(osc11b, 0, voice11Mixer, 1);
AudioConnection patchCord8(osc7b, 0, voice7Mixer, 1);
AudioConnection patchCord9(osc4a, 0, voice4Mixer, 0);
AudioConnection patchCord10(osc8a, 0, voice8Mixer, 0);
AudioConnection patchCord11(osc12a, 0, voice12Mixer, 0);
AudioConnection patchCord12(osc2a, 0, voice2Mixer, 0);
AudioConnection patchCord13(osc6a, 0, voice6Mixer, 0);
AudioConnection patchCord14(osc4b, 0, voice4Mixer, 1);
AudioConnection patchCord15(osc10a, 0, voice10Mixer, 0);
AudioConnection patchCord16(osc8b, 0, voice8Mixer, 1);
AudioConnection patchCord17(osc12b, 0, voice12Mixer, 1);
AudioConnection patchCord18(osc2b, 0, voice2Mixer, 1);
AudioConnection patchCord19(osc6b, 0, voice6Mixer, 1);
AudioConnection patchCord20(osc10b, 0, voice10Mixer, 1);
AudioConnection patchCord21(osc5b, 0, voice5Mixer, 1);
AudioConnection patchCord22(osc9b, 0, voice9Mixer, 1);
AudioConnection patchCord23(osc5a, 0, voice5Mixer, 0);
AudioConnection patchCord24(osc9a, 0, voice9Mixer, 0);
AudioConnection patchCord25(osc15a, 0, voice15Mixer, 0);
AudioConnection patchCord26(osc15b, 0, voice15Mixer, 1);
AudioConnection patchCord27(osc17a, 0, voice17Mixer, 0);
AudioConnection patchCord28(osc17b, 0, voice17Mixer, 1);
AudioConnection patchCord29(osc19a, 0, voice19Mixer, 0);
AudioConnection patchCord30(osc23a, 0, voice23Mixer, 0);
AudioConnection patchCord31(osc19b, 0, voice19Mixer, 1);
AudioConnection patchCord32(osc27a, 0, voice27Mixer, 0);
AudioConnection patchCord33(osc16a, 0, voice16Mixer, 0);
AudioConnection patchCord34(osc27b, 0, voice27Mixer, 1);
AudioConnection patchCord35(osc23b, 0, voice23Mixer, 1);
AudioConnection patchCord36(osc14a, 0, voice14Mixer, 0);
AudioConnection patchCord37(osc20a, 0, voice20Mixer, 0);
AudioConnection patchCord38(osc16b, 0, voice16Mixer, 1);
AudioConnection patchCord39(osc24a, 0, voice24Mixer, 0);
AudioConnection patchCord40(osc28a, 0, voice28Mixer, 0);
AudioConnection patchCord41(osc18a, 0, voice18Mixer, 0);
AudioConnection patchCord42(osc14b, 0, voice14Mixer, 1);
AudioConnection patchCord43(osc22b, 0, voice22Mixer, 1);
AudioConnection patchCord44(osc20b, 0, voice20Mixer, 1);
AudioConnection patchCord45(osc13b, 0, voice13Mixer, 1);
AudioConnection patchCord46(osc26a, 0, voice26Mixer, 0);
AudioConnection patchCord47(osc24b, 0, voice24Mixer, 1);
AudioConnection patchCord48(osc22a, 0, voice22Mixer, 0);
AudioConnection patchCord49(osc13a, 0, voice13Mixer, 0);
AudioConnection patchCord50(osc28b, 0, voice28Mixer, 1);
AudioConnection patchCord51(osc18b, 0, voice18Mixer, 1);
AudioConnection patchCord52(osc26b, 0, voice26Mixer, 1);
AudioConnection patchCord53(osc21b, 0, voice21Mixer, 1);
AudioConnection patchCord54(osc25b, 0, voice25Mixer, 1);
AudioConnection patchCord55(osc21a, 0, voice21Mixer, 0);
AudioConnection patchCord56(osc25a, 0, voice25Mixer, 0);
AudioConnection patchCord57(osc31a, 0, voice31Mixer, 0);
AudioConnection patchCord58(osc31b, 0, voice31Mixer, 1);
AudioConnection patchCord59(osc32a, 0, voice32Mixer, 0);
AudioConnection patchCord60(osc30a, 0, voice30Mixer, 0);
AudioConnection patchCord61(osc32b, 0, voice32Mixer, 1);
AudioConnection patchCord62(osc30b, 0, voice30Mixer, 1);
AudioConnection patchCord63(osc29b, 0, voice29Mixer, 1);
AudioConnection patchCord64(osc29a, 0, voice29Mixer, 0);
AudioConnection patchCord65(voice1Mixer, envelope1);
AudioConnection patchCord66(voice2Mixer, envelope2);
AudioConnection patchCord67(voice5Mixer, envelope5);
AudioConnection patchCord68(voice6Mixer, envelope6);
AudioConnection patchCord69(voice9Mixer, envelope9);
AudioConnection patchCord70(voice10Mixer, envelope10);
AudioConnection patchCord71(voice3Mixer, envelope3);
AudioConnection patchCord72(voice7Mixer, envelope7);
AudioConnection patchCord73(voice11Mixer, envelope11);
AudioConnection patchCord74(voice4Mixer, envelope4);
AudioConnection patchCord75(voice8Mixer, envelope8);
AudioConnection patchCord76(voice12Mixer, envelope12);
AudioConnection patchCord77(voice13Mixer, envelope13);
AudioConnection patchCord78(voice14Mixer, envelope14);
AudioConnection patchCord79(voice17Mixer, envelope17);
AudioConnection patchCord80(voice18Mixer, envelope18);
AudioConnection patchCord81(voice21Mixer, envelope21);
AudioConnection patchCord82(voice15Mixer, envelope15);
AudioConnection patchCord83(voice22Mixer, envelope22);
AudioConnection patchCord84(voice25Mixer, envelope25);
AudioConnection patchCord85(voice26Mixer, envelope26);
AudioConnection patchCord86(voice16Mixer, envelope16);
AudioConnection patchCord87(voice23Mixer, envelope23);
AudioConnection patchCord88(voice19Mixer, envelope19);
AudioConnection patchCord89(voice27Mixer, envelope27);
AudioConnection patchCord90(voice20Mixer, envelope20);
AudioConnection patchCord91(voice24Mixer, envelope24);
AudioConnection patchCord92(voice28Mixer, envelope28);
AudioConnection patchCord93(voice29Mixer, envelope29);
AudioConnection patchCord94(voice30Mixer, envelope30);
AudioConnection patchCord95(voice31Mixer, envelope31);
AudioConnection patchCord96(voice32Mixer, envelope32);
AudioConnection patchCord97(envelope2, 0, voiceMixer1, 1);
AudioConnection patchCord98(envelope3, 0, voiceMixer1, 2);
AudioConnection patchCord99(envelope6, 0, voiceMixer2, 1);
AudioConnection patchCord100(envelope1, 0, voiceMixer1, 0);
AudioConnection patchCord101(envelope7, 0, voiceMixer2, 2);
AudioConnection patchCord102(envelope10, 0, voiceMixer3, 1);
AudioConnection patchCord103(envelope5, 0, voiceMixer2, 0);
AudioConnection patchCord104(envelope11, 0, voiceMixer3, 2);
AudioConnection patchCord105(envelope4, 0, voiceMixer1, 3);
AudioConnection patchCord106(envelope9, 0, voiceMixer3, 0);
AudioConnection patchCord107(envelope8, 0, voiceMixer2, 3);
AudioConnection patchCord108(envelope12, 0, voiceMixer3, 3);
AudioConnection patchCord109(envelope14, 0, voiceMixer4, 1);
AudioConnection patchCord110(envelope15, 0, voiceMixer4, 2);
AudioConnection patchCord111(envelope13, 0, voiceMixer4, 0);
AudioConnection patchCord112(envelope16, 0, voiceMixer4, 3);
AudioConnection patchCord113(envelope18, 0, voiceMixer5, 1);
AudioConnection patchCord114(envelope19, 0, voiceMixer5, 2);
AudioConnection patchCord115(envelope22, 0, voiceMixer6, 1);
AudioConnection patchCord116(envelope17, 0, voiceMixer5, 0);
AudioConnection patchCord117(envelope23, 0, voiceMixer6, 2);
AudioConnection patchCord118(envelope26, 0, voiceMixer7, 1);
AudioConnection patchCord119(envelope21, 0, voiceMixer6, 0);
AudioConnection patchCord120(envelope27, 0, voiceMixer7, 2);
AudioConnection patchCord121(envelope20, 0, voiceMixer5, 3);
AudioConnection patchCord122(envelope25, 0, voiceMixer7, 0);
AudioConnection patchCord123(envelope24, 0, voiceMixer6, 3);
AudioConnection patchCord124(envelope28, 0, voiceMixer7, 3);
AudioConnection patchCord125(envelope30, 0, voiceMixer8, 1);
AudioConnection patchCord126(envelope31, 0, voiceMixer8, 2);
AudioConnection patchCord127(envelope29, 0, voiceMixer8, 0);
AudioConnection patchCord128(envelope32, 0, voiceMixer8, 3);
AudioConnection patchCord129(voiceMixer1, 0, subMixer1, 0);
AudioConnection patchCord130(voiceMixer2, 0, subMixer1, 1);
AudioConnection patchCord131(voiceMixer3, 0, subMixer1, 2);
AudioConnection patchCord132(voiceMixer4, 0, subMixer1, 3);
AudioConnection patchCord133(voiceMixer5, 0, subMixer2, 0);
AudioConnection patchCord134(voiceMixer6, 0, subMixer2, 1);
AudioConnection patchCord135(voiceMixer7, 0, subMixer2, 2);
AudioConnection patchCord136(voiceMixer8, 0, subMixer2, 3);
AudioConnection patchCord137(subMixer2, 0, lastMixer, 1);
AudioConnection patchCord138(subMixer1, 0, lastMixer, 0);
AudioConnection patchCord139(lastMixer, 0, filter1, 0);
AudioConnection patchCord140(filter1, 0, i2s1, 0);
AudioConnection patchCord141(filter1, 0, i2s1, 1);
AudioControlSGTL5000 sgtl5000_1; //xy=1713.599998474121,1614.0000190734863
// GUItool: end automatically generated code
// GLOBAL VARIABLES
#define NUM_VOICES 32
int wave1 = WAVEFORM_SINE;
int wave2 = WAVEFORM_TRIANGLE;
int filterTemp = 10000 * analogRead(A3) / 1023;;
byte globalVelocity = 127;
int attackTemp = 11880 * analogRead(A0) / 1023;
int releaseTemp = analogRead(A1) / 1023;
int attackKnob = 11880 * analogRead(A0) / 1023;
int releaseKnob = 11880 * analogRead(A1) / 1023;
float centsTemp = 100 * analogRead(A17) / 1023;
float cents = 100 * analogRead(A17) / 1023;
float detune = 1.0;
// Array to convert MIDI notes to thier corresponding frequency. Super useful
const float noteFreqs[128] = {8.176, 8.662, 9.177, 9.723, 10.301, 10.913, 11.562, 12.25, 12.978, 13.75, 14.568, 15.434, 16.352, 17.324, 18.354, 19.445, 20.602, 21.827, 23.125, 24.5, 25.957, 27.5, 29.135, 30.868, 32.703, 34.648, 36.708, 38.891, 41.203, 43.654, 46.249, 48.999, 51.913, 55, 58.27, 61.735, 65.406, 69.296, 73.416, 77.782, 82.407, 87.307, 92.499, 97.999, 103.826, 110, 116.541, 123.471, 130.813, 138.591, 146.832, 155.563, 164.814, 174.614, 184.997, 195.998, 207.652, 220, 233.082, 246.942, 261.626, 277.183, 293.665, 311.127, 329.628, 349.228, 369.994, 391.995, 415.305, 440, 466.164, 493.883, 523.251, 554.365, 587.33, 622.254, 659.255, 698.456, 739.989, 783.991, 830.609, 880, 932.328, 987.767, 1046.502, 1108.731, 1174.659, 1244.508, 1318.51, 1396.913, 1479.978, 1567.982, 1661.219, 1760, 1864.655, 1975.533, 2093.005, 2217.461, 2349.318, 2489.016, 2637.02, 2793.826, 2959.955, 3135.963, 3322.438, 3520, 3729.31, 3951.066, 4186.009, 4434.922, 4698.636, 4978.032, 5274.041, 5587.652, 5919.911, 6271.927, 6644.875, 7040, 7458.62, 7902.133, 8372.018, 8869.844, 9397.273, 9956.063, 10548.08, 11175.3, 11839.82, 12543.85};
// Pointer Arrays for Oscillators, envelopes, and buttons
AudioSynthWaveformModulated *oscsA[NUM_VOICES] = { &osc1a, &osc2a, &osc3a, &osc4a, &osc5a, &osc6a, &osc7a, &osc8a, &osc9a, &osc10a, &osc11a, &osc12a, &osc13a, &osc14a, &osc15a, &osc16a, &osc17a, &osc18a, &osc19a, &osc20a, &osc21a, &osc22a, &osc23a, &osc24a, &osc25a, &osc26a, &osc27a, &osc28a, &osc29a, &osc30a, &osc31a, &osc32a };
AudioSynthWaveformModulated *oscsB[NUM_VOICES] = { &osc1b, &osc2b, &osc3b, &osc4b, &osc5b, &osc6b, &osc7b, &osc8b, &osc9b, &osc10b, &osc11b, &osc12b, &osc13b, &osc14b, &osc15b, &osc16b, &osc17b, &osc18b, &osc19b, &osc20b, &osc21b, &osc22b, &osc23b, &osc24b, &osc25b, &osc26b, &osc27b, &osc28b, &osc29b, &osc30b, &osc31b, &osc32b};
AudioEffectEnvelope *envelopes[NUM_VOICES] = { &envelope1, &envelope2, &envelope3, &envelope4, &envelope5, &envelope6, &envelope7, &envelope8, &envelope9, &envelope10, &envelope11, &envelope12, &envelope13, &envelope14, &envelope15, &envelope16, &envelope17, &envelope18, &envelope19, &envelope20, &envelope21, &envelope22, &envelope23, &envelope24, &envelope25, &envelope26, &envelope27, &envelope28, &envelope29, &envelope30, &envelope31, &envelope32 };
Bounce *mybutton[] = { &button0, &button1, &button2, &button3, &button4, &button5, &button6, &button7};
// My synth has 8 onboard buttons. This sets the MIDI notes for each button
const float buttonFreqs[8] = {48, 50, 52, 53, 55, 57, 59, 60};
// Array to store how long a voice is playing, in milliseconds
unsigned long voiceOnTimes[NUM_VOICES] = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
// A bool array. Boolean arrays hold either a true or false value at each array position. 0's and 1's also work
bool idleVoices[NUM_VOICES] = {true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true, true };
// Array to hold played note frequency values. 255 is jammed in there as a place holder
byte voiceToNote[NUM_VOICES] = {255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255 }; // Dummy value outside range of valid notes is used to init each.
// Millisecond timer variable set to zero to start
elapsedMillis readPots = 0;
// Function named NoteOn, receives 3 variables that can be use in the function. MIDI channel, MIDI note, and note velocity
void NoteOn(byte channel, byte note, byte velocity) {
// Set a boolean variable named 'found' to false, or zero. Boolean values can only be true or false, 0 or 1.
bool found = false;
// Set an integer variable named voiceToUse to 0
int voiceToUse = 0;
// Acquire an idle voice if possible.
for (int i = 0; i < NUM_VOICES; i++) {
// if the next idleVoices entry is TRUE...
if (idleVoices[i]) {
// ...set voice to use variable to the number corresponding to that idleVoices entry
voiceToUse = i;
// Set found to 1 or true
found = 1;
// Kill this loop
break;
}
}
// Steal voice if needed.
// If found is FALSE...
if (!found) {
// ...create a variable named oldest and set its value to milliseconds clock
unsigned long oldest = millis();
for (int i = 0; i < NUM_VOICES; i++) {
// if the current voiceOnTimes is less than oldest
if (voiceOnTimes[i] < oldest) {
// Set that voiceOnTime value to the current oldest value
oldest = voiceOnTimes[i];
// Increment voiceToUse value
voiceToUse = i;
}
}
}
// Now use the acquired voice.
//Set that voice entry to false
idleVoices[voiceToUse] = false;
// Set voiceToUse entry to MIDI note value that was just pressed
voiceToNote[voiceToUse] = note;
AudioNoInterrupts();
oscsA[voiceToUse]->frequency(noteFreqs[note]);
oscsA[voiceToUse]->amplitude(.5f);
oscsB[voiceToUse]->frequency(detune * noteFreqs[note]);
oscsB[voiceToUse]->amplitude(.5f);
envelopes[voiceToUse]->noteOn();
AudioInterrupts();
voiceOnTimes[voiceToUse] = millis();
}
// Function named NoteOff, receives 3 variables that can be use in the function. MIDI channel, MIDI note, and note velocity
void NoteOff(byte channel, byte note, byte velocity) {
for (int i = 0; i < NUM_VOICES; i++) {
// Do this 32(NUM_VOICES value) times
if (voiceToNote[i] == note) {
envelopes[i]->noteOff();
voiceToNote[i] = -1;
}
}
}
void IdleCheck(void) {
for (uint8_t i = 0; i < NUM_VOICES; i++) {
// Checks all 32 envelopes, if an envelope IS NOT ACTIVE ( thats the "!" ) set that envelopes corresponding oscillators amplitude to zero
if (!envelopes[i]->isActive()) {
oscsA[i]->amplitude(0);
oscsB[i]->amplitude(0);
// Set the voices corresponding entry in the idleVoices array to 1, or true
idleVoices[i] = 1;
} else {
// Otherwise set the voices corresponding entry in the idleVoices array to 0, or false
idleVoices[i] = false;
}
}
}
void setup() {
// Audio programs need memory to be allocated. 160 is probably a lot more than I need
AudioMemory(160);
// Start serial and start usb object.
Serial.begin(115200);
myusb.begin();
// Set the pin mode of my 8 buttons
pinMode(25, INPUT_PULLUP);
pinMode(26, INPUT_PULLUP);
pinMode(27, INPUT_PULLUP);
pinMode(28, INPUT_PULLUP);
pinMode(29, INPUT_PULLUP);
pinMode(30, INPUT_PULLUP);
pinMode(31, INPUT_PULLUP);
pinMode(32, INPUT_PULLUP);
// Each mixer has 4 inputs. This cycles through all my mixers setting the gain 4 times so I only have to type them out once :)
for (int i = 0; i < 4; i++) {
// Set all mixers.
voice1Mixer.gain(i, .5f);
voice2Mixer.gain(i, .5f);
voice3Mixer.gain(i, .5f);
voice4Mixer.gain(i, .5f);
voice5Mixer.gain(i, .5f);
voice6Mixer.gain(i, .5f);
voice7Mixer.gain(i, .5f);
voice8Mixer.gain(i, .5f);
voice9Mixer.gain(i, .5f);
voice10Mixer.gain(i, .5f);
voice11Mixer.gain(i, .5f);
voice12Mixer.gain(i, .5f);
voice13Mixer.gain(i, .5f);
voice14Mixer.gain(i, .5f);
voice15Mixer.gain(i, .5f);
voice16Mixer.gain(i, .5f);
voice17Mixer.gain(i, .5f);
voice18Mixer.gain(i, .5f);
voice19Mixer.gain(i, .5f);
voice20Mixer.gain(i, .5f);
voice21Mixer.gain(i, .5f);
voice22Mixer.gain(i, .5f);
voice23Mixer.gain(i, .5f);
voice24Mixer.gain(i, .5f);
voice25Mixer.gain(i, .5f);
voice26Mixer.gain(i, .5f);
voice27Mixer.gain(i, .5f);
voice28Mixer.gain(i, .5f);
voice29Mixer.gain(i, .5f);
voice30Mixer.gain(i, .5f);
voice31Mixer.gain(i, .5f);
voice32Mixer.gain(i, .5f);
voiceMixer1.gain(i, .5f);
voiceMixer2.gain(i, .5f);
voiceMixer3.gain(i, .5f);
voiceMixer4.gain(i, .5f);
voiceMixer5.gain(i, .5f);
voiceMixer6.gain(i, .5f);
voiceMixer7.gain(i, .5f);
voiceMixer8.gain(i, .5f);
subMixer1.gain(i, .5f);
subMixer2.gain(i, .5f);
lastMixer.gain(i, .6f);
// Set oscs to default waves
oscsA[i]->begin(wave1);
oscsB[i]->begin(wave2);
// Set envelopes to something reasonable
envelopes[i]->attack(attackKnob);
envelopes[i]->decay(10);
envelopes[i]->sustain(.5f);
envelopes[i]->release(releaseKnob);
// Set default filter value
int filterKnob = 10000 * analogRead(A3) / 1023;
filter1.frequency(filterKnob);
}
// Enable codec
sgtl5000_1.enable();
sgtl5000_1.volume(.5f);
// Set USB MIDI device callbacks. Each time a note is pressed call NoteOn function, each time its released call NoteOff function.
midi1.setHandleNoteOff(NoteOff);
midi1.setHandleNoteOn(NoteOn);
}
void loop() {
// Only read pots every 50 milliseconds to reduce glitchiness due to noise...
// This could be done with averaging or something instead
if (readPots >= 50) {
// Reset elapsed time
readPots = 0;
// Set variables to knob values
float cents = 100 * analogRead(A17) / 1023;
float detune = pow(2, (cents / 1200));
// Only execute this code if knob has been moved
if (centsTemp != cents) {
// Reset variable to knob value
centsTemp = cents;
for (int i = 0; i < NUM_VOICES; i++) {
if (voiceToNote[i] != 255) {
oscsB[i]->frequency((1.0f / detune) * noteFreqs[voiceToNote[i]]);
// Uncomment to see value in serial monitor
// Serial.println(voiceToNote[i]);
// Serial.println(detune);
}
}
}
// Read waveform selection pots
int wave1Temp = map(analogRead(A14), 0, 1023, WAVEFORM_SINE, WAVEFORM_TRIANGLE);
int wave2Temp = map(analogRead(A16), 0, 1023, WAVEFORM_SINE, WAVEFORM_TRIANGLE);
// Update A oscs only if waveform has changed.
// Oscillator phase will be reset by calling begin(), that's why we only want to do it when knob has changed
if (wave1Temp != wave1) {
//Reset variable to knob value
wave1 = wave1Temp;
// Uncomment to see value in serial monitor
// Serial.printf("Knob 1: %d\n", wave1);
// Cycle through all oscA pointer array values and restart them with the new wave value. FYI when working with pointers -> means put a . after the array value
// So this essentially executes osc1a.begin(value of wave1); then osc2a.begin(value of wave1) and so on
for (int i = 0; i < NUM_VOICES; i++) {
oscsA[i]->begin(wave1);
}
}
// Same thing for B oscs
if (wave2Temp != wave2) {
wave2 = wave2Temp;
// Uncomment to see value in serial monitor
// Serial.printf("Knob 2: %d\n", wave2);
for (int i = 0; i < NUM_VOICES; i++) {
oscsB[i]->begin(wave2);
}
}
//Lowpass Filter
// Set variables to knob values
int filterKnob = 10000 * analogRead(A3) / 1023;
// Only execute this code if knob has been moved
if (filterTemp != filterKnob) {
//Reset variable to knob value
filterTemp = filterKnob;
filter1.frequency(filterKnob);
//Resonance will be controlled by its own knob eventually. Set a resonable value for now
filter1.resonance(3.8);
}
//Attack and Release
// Set variables to knob values
int attackKnob = 11880 * analogRead(A0) / 1023;
int releaseKnob = 11880 * analogRead(A1) / 1023;
// Only execute this code if knob has been moved
if (attackTemp != attackKnob) {
attackTemp = attackKnob;
// Cycle through all envelopes pointer array values and sets new attack value. FYI when working with pointers -> means put a . after the array value
// So this essentially executes envelope1.attack(value of attackKnob); then envelope1.attack(value of attackKnob) and so on
for (int i = 0; i < NUM_VOICES; i++) {
envelopes[i]->attack(attackKnob);
}
}
// Same as Attack code
if (releaseTemp != releaseKnob) {
releaseTemp = releaseKnob;
for (int i = 0; i < NUM_VOICES; i++) {
envelopes[i]->release(releaseKnob);
}
}
}
// Do this 8 times for my 8 buttons
for (int i = 0; i < 8; i++) {
// button1.update(); button2.update(); button3.update()...
mybutton[i]->update();
// button1.fallingEdge(); button2.fallingEdge(); button3.fallingEdge()...
if (mybutton[i]->fallingEdge()) {
// When button is pressed send channel 1, corresponding buttonFreqs array value, and globalVelocity value to NoteOn() function
NoteOn(1, buttonFreqs[i], globalVelocity);
}
// button1.risingEdge(); button2.risingEdge(); button3.risingEdge()...
if (mybutton[i]->risingEdge()) {
// When button is released send channel 1, corresponding buttonFreqs array value, and globalVelocity value to NoteOff() function
NoteOff(1, buttonFreqs[i], globalVelocity);
}
}
// Run idleCheck function to see if any voices are not running and then turn them off
IdleCheck();
// Check incoming MIDI
midi1.read();
}
// Function named NoteOff, receives 3 variables that can be use in the function. MIDI channel, MIDI note, and note velocity
void NoteOff(byte channel, byte note, byte velocity) {
for (int i = 0; i < NUM_VOICES; i++) {
// Do this 32(NUM_VOICES value) times
if (voiceToNote[i] == note) {
envelopes[i]->noteOff();
voiceToNote[i] = -1;
break; // Exit loop on first match
}
}
}