Unopad - MIDI-контроллер Arduino с Ableton
Компоненты и расходные материалы
![]() |
| × | 1 | |||
![]() |
| × | 9 | |||
![]() |
| × | 1 |
Необходимые инструменты и машины
![]() |
|
Приложения и онлайн-сервисы
| ||||
| ||||
|
Об этом проекте
Резюме
Большинство руководств и проектов для контроллеров Midi основаны только на объяснении работы Arduino, но не столько на ее использовании в самой DAW. Я хочу создать руководство со всем необходимым в одном месте. Этим проектом я хотел помочь новичкам лучше понять процесс создания и использования контроллера, и надеюсь, что он будет кому-то полезен.
Давно хотел сделать миди-контроллер, наконец-то это сделал и сейчас поделюсь этим проектом с вами. Я использовал Arduino Uno, у которого нет возможности отправлять MIDI-сообщения через USB, поэтому для этого пришлось использовать специальные программы (будет объяснено позже в тексте).
В следующих разделах описывается электрическая схема, код Arduino, а также способы подключения к компьютеру и DAW, в данном случае Ableton.
Схема
Это очень простая схема. Я использовал 9 кнопок, но не в матрице, потому что мне нужна была возможность нажимать несколько кнопок (это проще, и у меня есть неиспользуемые цифровые контакты - я использую 9, в матрице будет 6).
Button 3 ==> D2 Button 2 ==> D3 Button 1 ==> D4 Button 6 ==> D5 Button 5 ==> D6 Button 4 ==> D7Button 9 ==> D8 Button 8 ==> Кнопка D9 7 ==> D10
Сопоставления MIDI
Я определил 9 нот MIDI, от 36 до 45, а также NOTE_ON и NOTE_OFF.
Это руководство по MIDI поможет вам понять, как можно использовать язык MIDI для управления любым устройством, использующим протокол MIDI.
#define NOTE_ONE 36 #define NOTE_TWO 37 // Определите здесь все ноты. #define NOTE_ON_CMD 0x90 #define NOTE_OFF_CMD 0x80 # define MAX_MIDI_VELOCITY 127
MIDI через USB
Поскольку Arduino Uno не может отправлять MIDI-ноты в DAW, мы должны использовать две дополнительные программы - LoopMidi и Hairless MIDI <-> Serial Bridge.
С помощью LoopMidi мы создаем виртуальный MIDI-порт, который мы можем использовать в Hairless Midi для подключения к порту Arduino.
Объяснение кода
Я создал класс Button и использую его так:
int NUMBER_BUTTONS =9; Button Button1 (4, NOTE_ONE); Button Button2 (3, NOTE_TWO); Button Button3 (2, NOTE_THREE); Button Button4 (7, NOTE_FOUR); Button Button5 (6, NOTE_FIVE); Button Button6 (5, NOTE_SIX); Button Button7 (10, NOTE_SEVEN); Button Button8 (9, NOTE_EIGHT); Button Button9 (8, NOTE_NINE); Button * Buttons [] {&Button1, &Button2, &Button3, &Button4, &Button5, &Button6 , &Button7, &Button8, &Button9};
Дополнительную информацию о реализации кнопки см. в Buttons.cpp.
Поскольку мы не используем резисторы, а только подключаем кнопку к цифровому выводу и земле, мы используем INPUT_PULLUP вместо INPUT.
//Buttons.cpppinMode(_pin, INPUT_PULLUP);
Единственная сложность в том, что вы не ищете HIGH
сигнал, как вы могли предположить - ваша кнопка будет выдавать LOW
(0)
при нажатии.
// кнопка нажата if (state ==0) {midiNoteOn (Buttons [i] -> Note, 127); } // Кнопка не нажата, если (state ==1) {}
Это также означает, что исходное состояние кнопки равно 1, а не 0.
//Buttons.cpp _state =1;
Каждое сообщение NOTE ON требует соответствующего сообщения NOTE OFF. При нажатии кнопки отправляется сообщение NOTE_ON. Когда кнопка отпускается, она отправляет сообщение NOTE_OFF, поэтому в дополнение к начальному состоянию я добавил в код последнее запомненное состояние.
//Buttons.cpp _lastState =1;
Мы отправляем MIDI-сообщения только в том случае, если текущее состояние отличается от последнего состояния.
//Buttons.cppif(state!=_lastState) {// ....}
Используйте эти две функции для отправки MIDI-сообщений. Параметры функций: примечание и midiVelocity (Я использовал максимальную скорость).
void midiNoteOn (байт примечание, байт midiVelocity) {Serial.write (NOTE_ON_CMD); Serial.write (примечание); Serial.write (midiVelocity);} void midiNoteOff (байт примечание, байт midiVelocity) {Serial.write (NOTE_OFF_CMD); Serial.write (примечание); Serial.write (midiVelocity);}
Я поместил логику программы в функцию updateButtons
функция.
void updateButtons () {для (int i =0; i getButtonState (); // Кнопка нажата if (state ==0) {midiNoteOn (Buttons [i] -> Note, 127); } // Кнопка не нажата if (state ==1) midiNoteOff (Buttons [i] -> Note, 0); }}
Функция вызывается внутри метода цикла.
void loop () {if (NUMBER_BUTTONS! =0) updateButtons ();}
Используйте свой контроллер с DAW (Ableton Live)
Как новичок в использовании DAW, я не знал, как там что-то подключить. Когда я подключил свой Korg Nanokey, Эблтон сам узнал его, и я сразу смог использовать контроллер. Этого (конечно же) не было в случае с контроллером Arduino, поскольку это не HID-устройство, и ПК по-прежнему распознает его как Arduino.
Я покажу вам, как подключить и использовать ваш MIDI-контроллер Arduino в Ableton Live 10.
- Связаться с Ableton
Откройте loopMIDI и создайте новый виртуальный порт MIDI, как на следующих изображениях.


Откройте безволосый-мидисериал и назначьте последовательный порт, MIDI Out и MIDI In, как на следующих изображениях. Для последовательного порта мы выбираем порт Arduino Uno, а для входа и выхода MIDI мы используем виртуальный порт MIDI, который мы создали на предыдущем шаге.
Установите ту же скорость передачи в скетче Arduino. Перейдите в Файл> Настройки . , и там вы должны установить скорость передачи .
Если все сделано правильно, вы можете отладить MIDI-сообщение, отправленное контроллером. Нажмите кнопку на контроллере и проверьте входящие MIDI-сообщения в Hairless MIDI.


Не закрывайте безволосые миди!
Откройте Ableton Live и перейдите на вкладку «Параметры», затем «Настройки». Вкладка Link MIDI должна выглядеть как на этом примере.

Чтобы убедиться, что все подключено правильно и Ableton читает MIDI-сообщения, мы посмотрим на верхний правый угол Ableton. Верхнее окно должно мигать при нажатии кнопки на контроллере, как показано в следующем примере.

Контроллер готов к работе!
- Использовать контроллер как стойку для барабанов или Клавиатура
Выберите MIDI-трек. В Монитор в разделе выберите В вместо Авто и в MIDI в выберите выход вашего динамика. Теперь вы должны услышать свою клавиатуру. То же самое следует сделать и с барабанной стойкой.

Мой готовый проект
В этом проекте я использовал старую коробку для динамиков и пластик, который нашел дома. Я вырезал обе пластиковые пластины по размеру корпуса и просверлил отверстия для кнопок и одного светодиода, который добавлю позже.
У меня также есть еще один старый динамик в том же футляре, который я буду использовать для другого MIDI-контроллера, на этот раз с ручками и джойстиками.











Сделать
- Долгое нажатие кнопки для перехода в режим CC.
Код
- MidiDrumPad.ino
- Buttons.cpp
- Buttons.h
MidiDrumPad.ino Arduino
#include "Buttons.h" // ------ Примечания ------------- # define NOTE_ONE 36 #define NOTE_TWO 37 #define NOTE_THREE 38 # define NOTE_FOUR 39 # define NOTE_FIVE 40 # определить NOTE_SIX 41 # определить NOTE_SEVEN 42 # определить NOTE_EIGHT 43 # определить NOTE_NINE 44 # определить NOTE_ON_CMD 0x90 # определить NOTE_OFF_CMD 0x80 # определить MAX_MIDI_VELOCITY 127 // ------------------ ------ int NUMBER_BUTTONS =9; Button Button1 (4, NOTE_ONE); Button Button2 (3, NOTE_TWO); Button Button3 (2, NOTE_THREE); Button Button4 (7, NOTE_FOUR); Button Button5 (6, NOTE_FIVE); Button Button6 (5, NOTE_SIX); Button Button7 (10, NOTE_SEVEN); Button Button8 (9, NOTE_EIGHT); Button Button9 (8, NOTE_NINE); Button * Buttons [] {&Button1, &Button2, &Button3, &Button4, &Button5, &Button6 , &Button7, &Button8, &Button9}; int red_light_pin =11; int green_light_pin =12; int blue_light_pin =13; void setup () {Serial.begin (9600);} void loop () {if (NUMBER_BUTTONS! =0) updateButtons ( );} void updateButtons () {для (int i =0; igetButtonState (); // Кнопка нажата if (state ==0) {midiNoteOn (Buttons [i] -> Note, 127); } // Кнопка не нажата if (state ==1) {midiNoteOff (Buttons [i] -> Note, 0); }}} void RGB_color (int red_light_value, int green_light_value, int blue_light_value) {analogWrite (red_light_pin, red_light_value); analogWrite (green_light_pin, green_light_value); analogWrite (blue_light_pin, blue_light_value);} // Отправить MIDI-ноту ONvoid midiNoteOn (байт-нота, байт midiVelocity) {Serial.write (NOTE_ON_CMD); Serial.write (примечание); Serial.write (midiVelocity);} // Отправить MIDI-ноту OFFvoid midiNoteOff (byte note, byte midiVelocity) {Serial.write (NOTE_OFF_CMD); Serial.write (примечание); Serial.write (midiVelocity);}
Buttons.cpp Arduino
#include "Buttons.h" Button ::Button (int pin, короткое примечание) {_pin =pin; pinMode (_pin, INPUT_PULLUP); _state =1; _lastState =1; Note =note;} int Button ::getButtonState () {int returnValue =-1; int состояние =digitalRead (_pin); если (состояние ==_lastState) возврат 5; если (состояние! =_lastState) {если (состояние ==0) {returnValue =0; } еще {returnValue =1; }} _lastState =состояние; return returnValue;}
Buttons.h Arduino
#ifndef Buttons_h #define Buttons_h # include// Кнопка (номер контакта, номер ноты) class Button {public:Button (int pin, short note); int getButtonState (); int Note; частный:int _pin; короткая _note; int _state; int _lastState;}; # endif
Вы можете скачать код с моего Github
https://github.com/sadreactonly/MidiDrumpadСхема

Производственный процесс
- Затемнение света с ШИМ с помощью кнопки
- Игра с гироскопом Arduino с MPU-6050
- Датчик DHT11 со светодиодами и пьезо-динамиком
- Железный человек
- Простой датчик препятствий с Arduino
- Найди меня
- Управление увлажнителем Arduino
- Светодиодный куб 4x4x4 с Arduino Uno и 1sheeld
- Джойстик Arduino
- Шагомер (Arduino 101)