Advertisement
Guest User

Untitled

a guest
Jul 22nd, 2014
322
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C 8.47 KB | None | 0 0
  1. #include <avr/pgmspace.h>
  2. #include "Tone.h"
  3.  
  4. // Output for PWM
  5. int PWMPin = 6;
  6. // External PWM enable
  7. int PWMPower = 5;
  8. // 7-segment pins
  9. int A = 13;
  10. int B = 12;
  11. int C = 11;
  12. int D = 10;
  13. int E = 9;
  14. int F = 8;
  15. int G = 7;
  16.  
  17. volatile int mode;  // 0 = Output Off, 1 = Manual PWM, 2 = PC MIDI, 3 = External MIDI
  18.  
  19. //Audio output pins
  20. //Using Analog pins simply becaues they were open
  21. int ch0out = A0;
  22. int ch1out = A1;
  23. int ch2out = A2;
  24. int ch3out = A3;
  25. int ch4out = A4;
  26. int ch5out = A5;
  27.  
  28. //MIDI notes
  29. Tone ch0;
  30. Tone ch1;
  31. Tone ch2;
  32. Tone ch3;
  33. Tone ch4;
  34. Tone ch5;
  35.  
  36. // Number of modes
  37. #define modeNum 3
  38. // Highest channel (0-15)
  39. // Will eventually use an array to keep track
  40. // of discrete channels we want to play
  41. #define channelNum 5
  42.  
  43. // midi commands
  44. #define MIDI_CMD_NOTE_OFF 0x80
  45. #define MIDI_CMD_NOTE_ON 0x90
  46.  
  47. /* Probably don't need these for my project
  48. #define MIDI_CMD_KEY_PRESSURE 0xA0
  49. #define MIDI_CMD_CONTROLLER_CHANGE 0xB0
  50. #define MIDI_CMD_PROGRAM_CHANGE 0xC0
  51. #define MIDI_CMD_CHANNEL_PRESSURE 0xD0
  52. #define MIDI_CMD_PITCH_BEND 0xE0
  53. */
  54.  
  55. // a dummy "ignore" state for commands which
  56. // we wish to ignore.
  57. #define MIDI_IGNORE 0x00
  58.  
  59. // midi "state" - which data byte we are receiving
  60. #define MIDI_STATE_BYTE1 0x00
  61. #define MIDI_STATE_BYTE2 0x01
  62.  
  63. // store note frequencies
  64. uint16_t frequency[128] PROGMEM = {8, 9, 9, 10, 10, 11, 12, 12, 13, 14, 15, 15, 16, 17, 18, 19, 21,
  65.                                     22, 23, 24, 26, 28, 29, 31, 33, 35, 37, 39, 41, 44, 46, 49, 52,
  66.                                     55, 58, 62, 65, 69, 73, 78, 82, 87, 92, 98, 104, 110, 117, 123,
  67.                                     131, 139, 147, 156, 165, 175, 185, 196, 208, 220, 233, 247, 262,
  68.                                     277, 294, 311, 330, 349, 370, 392, 415, 440, 466, 494, 523, 554,
  69.                                     587, 622, 659, 698, 740, 784, 831, 880, 932, 988, 1047, 1109,
  70.                                     1175, 1245, 1319, 1397, 1480, 1568, 1661, 1760, 1865, 1976, 2093,
  71.                                     2217, 2349, 2489, 2637, 2794, 2960, 3136, 3322, 3520, 3729, 3951,
  72.                                     4186, 4435, 4699, 4978, 5274, 5588, 5920, 5920, 6645, 7040, 7459,
  73.                                     7902, 8372, 8870, 9397, 9956, 10548, 11175, 11840, 12544};
  74.  
  75. void setup() {
  76.  
  77.   // Power on signal to external PWM circuitry
  78.   pinMode(PWMPower, OUTPUT);
  79.  
  80.   // 7-segment display pins
  81.   pinMode(A, OUTPUT);
  82.   pinMode(B, OUTPUT);
  83.   pinMode(C, OUTPUT);
  84.   pinMode(D, OUTPUT);
  85.   pinMode(E, OUTPUT);
  86.   pinMode(F, OUTPUT);
  87.   pinMode(G, OUTPUT);
  88.  
  89.   // Interrupt to watch for mode-change button press
  90.   attachInterrupt(0, changeMode, RISING);
  91.   mode = 0;
  92.  
  93.   displayMode();
  94.  
  95.   // Make sure power signal to external PWM is off
  96.   digitalWrite(PWMPower, LOW);
  97. }
  98.  
  99. void loop () {
  100.    
  101.   if (mode == 0) {
  102.   }
  103.   else if (mode == 1) {
  104.   }
  105.  
  106.   /*************************************************
  107.    ** This is where the MIDI signal is processed  **
  108.    *************************************************/
  109.  
  110.   else if (mode == 2) {
  111.     static byte note;                                       // Variable to store note number
  112.     static byte state;                                      // Variable to store state (Byte 1, Byte 2)
  113.     static byte lastByte;                                   // Variable to store previous byte value
  114.     static int cmd = MIDI_IGNORE;                           // Variable to store current command
  115.     static int channel;                                     // Variable to store current channel number
  116.  
  117.     while (Serial.available()) {
  118.      
  119.       // read the incoming byte:
  120.       byte thisByte = Serial.read();                        //Read incoming byte
  121.  
  122.       if (thisByte & 0b10000000) {                          //Is this a command byte?
  123.         if (channel <= channelNum) {                        // Is this one of our channels?
  124.           cmd = thisByte & 0xF0;                            //Save the command
  125.           channel = thisByte & 0x0F;                        //Save the channel number
  126.         } else {
  127.           cmd = MIDI_IGNORE;                                // Otherwise, ignore message
  128.         }
  129.         state = MIDI_STATE_BYTE1;                           // Prepare for Byte 1 (note)
  130.       } else if ((state == MIDI_STATE_BYTE1) && (cmd != MIDI_IGNORE)) {    // Is this data Byte 1?
  131.         if ( cmd==MIDI_CMD_NOTE_OFF ) {                     //If command is for NOTE OFF
  132.           state = MIDI_STATE_BYTE2;                         // expect to receive a velocity byte
  133.         } else if ( cmd == MIDI_CMD_NOTE_ON ) {             // If command is for NOTE ON
  134.           if (channel == 0x00) ch0.begin(ch0out);           // prepare to play note on specified channel
  135.           else if (channel == 0x01) ch1.begin(ch1out);
  136.           else if (channel == 0x02) ch2.begin(ch2out);
  137.           else if (channel == 0x03) ch3.begin(ch3out);
  138.           else if (channel == 0x04) ch4.begin(ch4out);
  139.           else if (channel == 0x05) ch5.begin(ch5out);
  140.         }
  141.         lastByte=thisByte;                                  // save the current note
  142.         state = MIDI_STATE_BYTE2;                           // prepare for Byte2 (velocity)
  143.       } else if ((state == MIDI_STATE_BYTE2) && (cmd != MIDI_IGNORE)) {    // Is this data for Byte 2 (velocity)?
  144.         if (cmd == MIDI_CMD_NOTE_OFF) {
  145.           if (channel == 0x00) ch0.stop();                  // turn off note on current channel
  146.           else if (channel == 0x01) ch1.stop();
  147.           else if (channel == 0x02) ch2.stop();
  148.           else if (channel == 0x03) ch3.stop();
  149.           else if (channel == 0x04) ch4.stop();
  150.           else if (channel == 0x05) ch5.stop();
  151.         } else if (cmd == MIDI_CMD_NOTE_ON) {
  152.           if (thisByte != 0) {                              // if we're actually playing a note
  153.             note = lastByte;                                // get note number
  154.             if (channel == 0x00) ch0.play((unsigned int)pgm_read_word(&frequency[note]));        // Play specified note on specified channel
  155.             else if (channel == 0x01) ch1.play((unsigned int)pgm_read_word(&frequency[note]));
  156.             else if (channel == 0x02) ch2.play((unsigned int)pgm_read_word(&frequency[note]));
  157.             else if (channel == 0x03) ch3.play((unsigned int)pgm_read_word(&frequency[note]));
  158.             else if (channel == 0x04) ch4.play((unsigned int)pgm_read_word(&frequency[note]));
  159.             else if (channel == 0x05) ch5.play((unsigned int)pgm_read_word(&frequency[note]));
  160.           }
  161.         }
  162.         state = MIDI_STATE_BYTE1; // message data complete
  163.       }
  164.     }
  165.   }
  166.  
  167.   /**********************************
  168.    ** End MIDI Processing Section  **
  169.    **********************************/
  170. }
  171.  
  172. void changeMode(){
  173.   static unsigned long last_interrupt_time = 0;
  174.   unsigned long interrupt_time = millis();
  175.   // If interrupts come faster than 200ms, assume it's a bounce and ignore
  176.   if (interrupt_time - last_interrupt_time > 200)
  177.   {
  178.     Serial.end();
  179.     mode++;
  180.     if (mode > modeNum) {
  181.       mode = 0;
  182.     }
  183.   }
  184.   last_interrupt_time = interrupt_time;
  185.  
  186.   if (mode == 0) {
  187.     stopAllChannels();
  188.   } else if (mode == 1) {
  189.     stopAllChannels();
  190.     digitalWrite(PWMPower, HIGH);
  191.   } else if (mode == 2) {
  192.     digitalWrite(PWMPower, LOW);
  193.     Serial.begin(57600);
  194.   } else if (mode == 3) {
  195.     stopAllChannels();
  196.     digitalWrite(PWMPower, LOW);
  197.   }
  198.   displayMode();
  199. }
  200.  
  201. //For stopping all MIDI channels
  202. void stopAllChannels() {
  203.   ch0.stop();
  204.   ch1.stop();
  205.   ch2.stop();
  206.   ch3.stop();
  207.   ch4.stop();
  208.   ch5.stop();
  209. }
  210.  
  211. void displayMode(){
  212.   if (mode == 0) {
  213.     digitalWrite(A, HIGH);
  214.     digitalWrite(B, HIGH);
  215.     digitalWrite(C, HIGH);
  216.     digitalWrite(D, HIGH);
  217.     digitalWrite(E, HIGH);
  218.     digitalWrite(F, HIGH);
  219.     digitalWrite(G, LOW);
  220.   }
  221.   if (mode == 1) {
  222.     digitalWrite(A, LOW);
  223.     digitalWrite(B, HIGH);
  224.     digitalWrite(C, HIGH);
  225.     digitalWrite(D, LOW);
  226.     digitalWrite(E, LOW);
  227.     digitalWrite(F, LOW);
  228.     digitalWrite(G, LOW);
  229.   }
  230.   else if (mode == 2) {
  231.     digitalWrite(A, HIGH);
  232.     digitalWrite(B, HIGH);
  233.     digitalWrite(C, LOW);
  234.     digitalWrite(D, HIGH);
  235.     digitalWrite(E, HIGH);
  236.     digitalWrite(F, LOW);
  237.     digitalWrite(G, HIGH);
  238.   }
  239.   else if (mode == 3) {
  240.     digitalWrite(A, HIGH);
  241.     digitalWrite(B, HIGH);
  242.     digitalWrite(C, HIGH);
  243.     digitalWrite(D, HIGH);
  244.     digitalWrite(E, LOW);
  245.     digitalWrite(F, LOW);
  246.     digitalWrite(G, HIGH);
  247.   }
  248. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement