interface Midi teensy 3.6

Jojomonk

Member
Hello,

I'm trying to build a small midi interface with a teensy 3.6 card, and the following electric druid circuit: https://electricdruid.net/wp-content/uploads/2016/04/MIDISchematic-3.jpg

I upload the example code teensy3x3, (my goal, in the long run, is to make an interface with at least 2 inputs and 2 outputs, but I'm already testing with 1 in 1 out).

Everything works, but I would like to have this operation: IN1 -> USB, USB -> OUT1 or for now, I have IN1 -> USB + IN1 -> OUT1, USB -> OUT1.

I tried to change the numbers of the virtual cables but it doesn't work...

Here is the code:

C:
/* Create a "class compliant " USB to 3 MIDI IN and 3 MIDI OUT interface.

   MIDI receive (6N138 optocoupler) input circuit and series resistor
   outputs need to be connected to Serial1, Serial2 and Serial3.

   You must select MIDIx4 from the "Tools > USB Type" menu

   This example code is in the public domain.
*/

#include <MIDI.h>

// Create the Serial MIDI ports
MIDI_CREATE_INSTANCE(HardwareSerial, Serial1, MIDI1);
MIDI_CREATE_INSTANCE(HardwareSerial, Serial2, MIDI2);
MIDI_CREATE_INSTANCE(HardwareSerial, Serial3, MIDI3);
MIDI_CREATE_INSTANCE(HardwareSerial, Serial4, MIDI4);
MIDI_CREATE_INSTANCE(HardwareSerial, Serial5, MIDI5);
MIDI_CREATE_INSTANCE(HardwareSerial, Serial6, MIDI6);


// A variable to know how long the LED has been turned on
elapsedMillis ledOnMillis;


void setup() {
  Serial.begin(115200);
  pinMode(13, OUTPUT); // LED pin
  digitalWrite(13, LOW);
  MIDI1.begin(MIDI_CHANNEL_OMNI);
  MIDI2.begin(MIDI_CHANNEL_OMNI);
  MIDI3.begin(MIDI_CHANNEL_OMNI);
  MIDI4.begin(MIDI_CHANNEL_OMNI);
  MIDI5.begin(MIDI_CHANNEL_OMNI);
  MIDI6.begin(MIDI_CHANNEL_OMNI);
}


void loop() {
  bool activity = false;

  if (MIDI1.read()) {
    // get a MIDI IN1 (Serial) message
    byte type = MIDI1.getType();
    byte channel = MIDI1.getChannel();
    byte data1 = MIDI1.getData1();
    byte data2 = MIDI1.getData2();

    // forward the message to USB MIDI virtual cable #0
    if (type != midi::SystemExclusive) {
      // Normal messages, simply give the data to the usbMIDI.send()
      usbMIDI.send(type, data1, data2, channel, 3);
    } else {
      // SysEx messages are special.  The message length is given in data1 & data2
      unsigned int SysExLength = data1 + data2 * 256;
      usbMIDI.sendSysEx(SysExLength, MIDI1.getSysExArray(), true, 0);
    }
    activity = true;
  }

  if (MIDI2.read()) {
    // get a MIDI IN2 (Serial) message
    byte type = MIDI2.getType();
    byte channel = MIDI2.getChannel();
    byte data1 = MIDI2.getData1();
    byte data2 = MIDI2.getData2();

    // forward the message to USB MIDI virtual cable #1
    if (type != midi::SystemExclusive) {
      // Normal messages, simply give the data to the usbMIDI.send()
      usbMIDI.send(type, data1, data2, channel, 4);
    } else {
      // SysEx messages are special.  The message length is given in data1 & data2
      unsigned int SysExLength = data1 + data2 * 256;
      usbMIDI.sendSysEx(SysExLength, MIDI1.getSysExArray(), true, 1);
    }
    activity = true;
  }

  if (MIDI3.read()) {
    // get a MIDI IN1 (Serial) message
    byte type = MIDI3.getType();
    byte channel = MIDI3.getChannel();
    byte data1 = MIDI3.getData1();
    byte data2 = MIDI3.getData2();

    // forward the message to USB MIDI virtual cable #0
    if (type != midi::SystemExclusive) {
      // Normal messages, simply give the data to the usbMIDI.send()
      usbMIDI.send(type, data1, data2, channel, 5);
    } else {
      // SysEx messages are special.  The message length is given in data1 & data2
      unsigned int SysExLength = data1 + data2 * 256;
      usbMIDI.sendSysEx(SysExLength, MIDI1.getSysExArray(), true, 2);
    }
    activity = true;
  }

  if (usbMIDI.read()) {
    // get the USB MIDI message, defined by these 5 numbers (except SysEX)
    byte type = usbMIDI.getType();
    byte channel = usbMIDI.getChannel();
    byte data1 = usbMIDI.getData1();
    byte data2 = usbMIDI.getData2();
    byte cable = usbMIDI.getCable();

    // forward this message to 1 of the 3 Serial MIDI OUT ports
    if (type != usbMIDI.SystemExclusive) {
      // Normal messages, first we must convert usbMIDI's type (an ordinary
      // byte) to the MIDI library's special MidiType.
      midi::MidiType mtype = (midi::MidiType)type;

      // Then simply give the data to the MIDI library send()
      switch (cable) {
        case 0:
          MIDI1.send(mtype, data1, data2, channel);
          break;
        case 1:
          MIDI2.send(mtype, data1, data2, channel);
          break;
        case 2:
          MIDI3.send(mtype, data1, data2, channel);
          break;
        case 3:
          MIDI4.send(mtype, data1, data2, channel);
          break;
        case 4:
          MIDI5.send(mtype, data1, data2, channel);
          break;
        case 5:
          MIDI6.send(mtype, data1, data2, channel);
          break;
      }

    } else {
      // SysEx messages are special.  The message length is given in data1 & data2
      unsigned int SysExLength = data1 + data2 * 256;
      switch (cable) {
        case 0:
          MIDI1.sendSysEx(SysExLength, usbMIDI.getSysExArray(), true);
          break;
        case 1:
          MIDI2.sendSysEx(SysExLength, usbMIDI.getSysExArray(), true);
          break;
        case 2:
          MIDI3.sendSysEx(SysExLength, usbMIDI.getSysExArray(), true);
          break;
      }
    }
    activity = true;
  }

  // blink the LED when any activity has happened
  if (activity) {
    digitalWriteFast(13, HIGH); // LED on
    ledOnMillis = 0;
  }
  if (ledOnMillis > 15) {
    digitalWriteFast(13, LOW);  // LED off
  }

}
 

Attachments

  • Capture d’écran 2024-05-04 à 22.11.25.png
    Capture d’écran 2024-05-04 à 22.11.25.png
    1.1 MB · Views: 6
On your computer where you use the USB connection you can have 1, 4 or 16 MIDI devices (if you have selected MIDI, MIDIx4 or MIDIx16 in the Arduino IDE). When you are saying "USB", which one exactly is meant? Or would you like to use only one?

In this (unaltered) sketch each USB MIDI device/port is routed to the hardware outputs, i.e. USB MIDI 1 to hardware MIDI 1 and so on. Cable is the number of the USB MIDI device which makes it possible to have the information from which USB device/port the data is coming in.

Each hardware MIDI port is routed to one USB MIDI port, i.e. MIDI IN 1 to USB MIDI 1 and so on.

I would expect "IN1 -> USB, USB -> OUT1" to be working already in the unaltered sketch when you select the first USB MIDI device on your computer.

To add "IN1 -> OUT1" you could add a line in the code:

C++:
  if (MIDI1.read()) {
    // get a MIDI IN1 (Serial) message
...

    // forward the message to USB MIDI virtual cable #0
    if (type != midi::SystemExclusive) {
      // Normal messages, simply give the data to the usbMIDI.send()
      usbMIDI.send(type, data1, data2, channel, 0); // <<< changed back to cable 0 to send data from MIDI IN 1 to first USB MIDI port

     // send data from MIDI IN 1 to MIDI OUT 1
    MIDI1.send(type, data1, data2, channel); // added line <<<<
....

Some helpful information can also be found here:
 
I tried with MIDIx4, it doesn't work.
I wanted to try with MIDIx16, impossible to declare it in MIDIx16, after uploading the code the teensy is still in MIDIx4
 
To explain a little more, for example:

On my computer, with ableton live, I choose teensy MIDIx4-port 1 output, the midi data is well sent to the MIDI-1 output and my hardware synth plays, on another track I choose teensy MIDIx4-port 2 input, if I play with a midi controller, I hear the sound of the virtual synth, but my hardware synth also reacts.
 
Please be more specific what exactly you are trying to achieve and what should be routed to what. What is connected to what and how?

plus: Ableton Live can also send the notes from your midi controller to any available midi output if you configure the tracks that way.
 
Ok, here is the configuration:

The electric druid is the diagram I posted above.

What I want is for the shruthi to react only data sent by ableton live, and for ableton live to react only to data sent by the EWI, but for now, when I play EWI, the shruthi reacts all the time, regardless of the configuration used in ableton live...
Capture d’écran 2024-05-05 à 19.04.37.png
 
In the sketch it is not visible that there is any data sent via the Teensy from hardware MIDI IN to hardware MIDI OUT. To rule out anything from Ableton you could close the software or even run the Teensy from an USB Hub/ Powerbank without PC ... to see if this still occurs. If yes the problem should be found in the electrical part. If I understand the schematic that should be no connection from MIDI IN to MIDI OUT. Only from MIDI IN to MIDI through which is desired. Are you building the circuit? Can you check the connections there? To rule the Teensy out you could disconnect the TX and RX lines to further check if the problem is caused in the remaining part.
 
That's it, someone told me the solution on the arduino forum, we must add:
C:
MIDI1.turnThruOff();
 
Last edited:
Back
Top