Kazalo:

Komplet bobnov MIDI na Pythonu in Arduinu: 5 korakov (s slikami)
Komplet bobnov MIDI na Pythonu in Arduinu: 5 korakov (s slikami)

Video: Komplet bobnov MIDI na Pythonu in Arduinu: 5 korakov (s slikami)

Video: Komplet bobnov MIDI na Pythonu in Arduinu: 5 korakov (s slikami)
Video: Драм-секвенсор Arduino: 8 дорожек, 16 шагов на такт, 8 тактов на паттерн 2024, Julij
Anonim
Image
Image
Komplet bobnov MIDI na Pythonu in Arduinu
Komplet bobnov MIDI na Pythonu in Arduinu
Komplet bobnov MIDI na Pythonu in Arduinu
Komplet bobnov MIDI na Pythonu in Arduinu

Od malega sem si vedno želel kupiti komplet bobnov. Takrat vsa glasbena oprema ni imela vseh digitalnih aplikacij, kot jih imamo danes veliko, zato so bile cene skupaj s pričakovanji previsoke. Pred kratkim sem se odločil za nakup najcenejšega kompleta bobnov pri eBayu z edino prednostjo: možnost, da ga podrem in na napravo priključim svojo strojno in programsko opremo.

Nakup nikakor ni razočaral: prenosni komplet zvijajočih se bobnov z 9 različnimi zvočnimi ploščami, dve stopalki za stikalo za boben in hi-hat ter vtičnico za mikro USB. Kar je resnično demotiviralo, so izhodni zvoki (Dejanska uporaba tega kompleta je priključitev zunanjega zvočnika in uživanje). Zato sem se odločil, da ga pretvorim v svoj programirljiv prek USB -ja, komplet bobnov MIDI na osnovi Arduina in uporabniški vmesnik na osnovi Pythona, za priročno uporabo in enostavne spremembe, kot so izbira glasnosti, zapiskov in kanalov.

Značilnosti naprave:

  • Nizka cena
  • Ustvarjanje kompleta bobnov iz vseh digitalnih vhodov - celo vrste gumbov
  • Podpora za komunikacijo in napajanje samo prek vmesnika USB - integracija pretvornika USB v UART in naprave Arduino
  • Minimalni deli za pravilno delovanje
  • Enostaven za uporabo Python uporabniški vmesnik
  • Popolna podpora za MIDI z nastavljivimi zatiči za hitrost, noto in Arduino
  • Shrani in naloži konfiguracije bobna po meri, shranjene v pomnilniku naprave

Nadaljujmo s projektom …

1. korak: Teorija delovanja

Teorija delovanja
Teorija delovanja
Teorija delovanja
Teorija delovanja
Teorija delovanja
Teorija delovanja

Blok diagram

Najprej se osredotočimo na strukturo projekta in jo razdelimo v ločene bloke:

Komplet zvitega bobna

Glavna enota projekta. Sestavljen je iz 9 ločenih bobnastih ploščic, kjer je vsaka ploščica vrsta gumbov, ki med udarcem spremenijo svoje logično stanje. Zaradi svoje strukture obstaja možnost izdelave tega kompleta bobnov iz katerega koli gumba. Vsaka bobnasta plošča je povezana z vlečnim uporom na glavni elektronski plošči, tako da je ob večkratnem udarcu bobnaste ploščice določeno stikalo vezano na ozemljitveno vezje in na liniji bobnastih plošč je logično nizko. Ko ni pritiska, je stikalo bobna odprto in zaradi vlečnega upora do napajalnega voda je na liniji bobnastih plošč prisotna logična HIGH. Ker je namen projekta ustvariti popolno digitalno MIDI napravo, je mogoče zanemariti vse analogne dele na glavnem tiskanem vezju. Pomembno je omeniti, da ima komplet bobnov dva pedala za kick boben in hi-hat, ki sta prav tako vezana na vlečne upore in imata isto logiko delovanja kot vse ploščice bobna (o tem bomo razpravljali nekoliko kasneje).

Arduino Pro-Micro

Možgani kompleta bobnov. Njegov namen je odkriti, ali iz bobnaste plošče prihaja signal, in zagotoviti ustrezen MIDI izhod z vsemi potrebnimi parametri: Opomba, hitrost in trajanje signala. Zaradi digitalne narave bobnastih ploščic jih je mogoče preprosto povezati z digitalnimi vhodi arduino (skupaj 10 pinov). Za shranjevanje vseh želenih nastavitev in informacij MIDI bomo uporabili njen pomnilnik-EEPROM, zato se ob vsakem vklopu naprave naložijo informacije MIDI iz EEPROM-a, zaradi česar jih je mogoče ponovno programirati in ponovno konfigurirati. Arduino Pro-Micro je na voljo tudi v zelo majhnem paketu in ga je mogoče zlahka namestiti v notranjo ohišje kompleta bobnov.

FTDI USB v serijski pretvornik

Za programiranje in definiranje funkcij naše naprave s pomočjo računalniške aplikacije je potrebno pretvoriti vmesnik USB v serijski, ker Arduino Pro-Micro nima USB-ja. Ker komunikacija med napravami temelji na UART, se v tem projektu uporablja naprava FTDI zaradi njene enostavnosti uporabe, ne glede na njene dodatne lastnosti.

PC aplikacija - Python

Ko gre za razvoj uporabniških vmesnikov in hitrih projektov, je Python odlična rešitev. Namen uporabniškega vmesnika je, da je veliko bolj priročno redefinirati lastnosti MIDI za naš komplet bobnov, shraniti podatke, programsko napravo in vzpostaviti komunikacijo med sistemi brez potrebe po sestavljanju kode znova in znova. Ker za komunikacijo z kompletom bobnov uporabljamo serijski vmesnik, je po vsem internetu na voljo veliko brezplačnih modulov, ki podpirajo vse vrste serijske komunikacije. Poleg tega, kot bo obravnavano kasneje, vmesnik UART sestavljajo skupaj trije zatiči: RXD, TXD in DTR. DTR se uporablja za ponastavitev modula Arduino, zato, če nas zanima zagon aplikacije MIDI ali priključitev uporabniškega vmesnika na programsko napravo, ni potrebe po ponovnem priključitvi kabla USB ali karkoli drugega.

2. korak: Deli in instrumenti

Deli

  • Komplet zvitega bobna
  • 2 x Sustain pedala (običajno vključena v paket DK).
  • FTDI - USB v serijski pretvornik
  • Arduino Pro Micro
  • Kabel Micro-USB

Instrumenti

  • Spajkalnik/postaja
  • Spajkalna pločevina
  • Enožilni kabel s tankim premerom
  • Pinceta
  • Rezalnik
  • Klešče
  • Nož
  • Izvijač
  • 3D tiskalnik (neobvezno - za prilagojene stopalne platforme)

Programska oprema

  • Arduino IDE
  • Python 3 ali višji
  • JetBrains Pycharm
  • MIDI vmesnik brez dlake
  • loopMIDI

3. korak: Spajkanje in montaža

Spajkanje in montaža
Spajkanje in montaža
Spajkanje in montaža
Spajkanje in montaža
Spajkanje in montaža
Spajkanje in montaža

Ker je treba kombinirati tri module, je postopek spajkanja in sestavljanja kratek in preprost:

  • Priključite Arduino Pro-Micro z napravo FTDI in se prepričajte, da so povezave v skladu z V/I, določenimi na vsaki napravi:

    • VBUS-VBUS
    • GND-GND
    • DTR-DTR
    • RXD-TXD
    • TXD-RXD
  • Odstranite vse vijake iz plastičnega ohišja bobna, preverite, ali se lahko osredotočite na kabel od plošče do plošče in njegove vlečne upore
  • Spajkanje tankih žic za modul Arduino-FTDI, ki smo jih izdelali prej:

    • Digitalni vhodi: D [2:11]
    • VBUS
    • D+
    • D-
    • GND
  • Modul vstavite v ohišje baterije, tako da bodo žice lebdele na isti strani kot vlečni upori blazinic
  • Spajite vse digitalne vhode na sponke bobnaste ploščice, kot je prikazano na zadnji sliki.
  • Spojite vodilo micro-USB (VBUS, D+, D-, GND) na napravo FTDI in se prepričajte, da pri teh žicah ni napak.
  • Modul Arduino-FTDI z vročim lepilom pritrdite na ohišje baterije
  • Napravo sestavite z ustreznimi nastavki za vijake

Naredili smo, naprava je sestavljena. Nadaljujmo s kodo …

4. korak: Programiranje A: Arduino

Programiranje A: Arduino
Programiranje A: Arduino

Opisujmo našo skico korak za korakom:

Najprej je treba za pravilno delovanje vključiti dve potrebni knjižnici. EEPROM je že vnaprej nameščen v Arduino IDE, vendar je treba modul debouncer za kick boben namestiti ločeno

#include #include

Ta stikala se uporabljajo predvsem pri odpravljanju napak. Če želite preizkusiti povezavo priključkov Arduino z blazinicami bobna in določiti vse digitalne vhode, je treba ta stikala določiti

/ * Stikala za razvijalce: Odkomentirajte želeni način za odpravljanje napak ali inicializacijo * ///#definirajte LOAD_DEFAULT_VALUES // Naložite konstantne vrednosti namesto EEPROM -a //#definirajte PRINT_PADS_PIN_NUMBERS // Natisnite številko pin, ki je povezana z blazinico, ki je bila zadeta prek serijskih vrat

Konstantna polja predstavljajo vse privzete vrednosti, vključno s štetjem plošč bobna. Za prvi zagon naprave morate poznati natančno povezavo stopalk Hi-Hat in Kick

/ * Naštevanje vrste bobna */

naštej DRUM_POSITION {KICK = 0, SNARE, HIHAT, RIDE, CYMBAL1, CYMBAL2, TOM_HIGH, TOM_MID, TOM_LO, HIHAT_PEDAL};

/ * Privzete vrednosti */

const uint8_t DRUM_NOTES [10] = {36, 40, 42, 51, 49, 55, 47, 45, 43, 48}; const uint8_t DRUM_VELOCITIES [10] = {110, 100, 100, 110, 110, 110, 110, 110, 110, 110}; const uint8_t DRUM_PINS [10] = {8, 6, 4, 3, 11, 9, 5, 10, 2, 7};

/ * Trajanje odprave udarca bobna */

const uint8_t KICK_DB_DURATION = 30;

EEPROM se uporablja za shranjevanje/nalaganje vseh podatkov, ki prihajajo iz računalniške aplikacije. Zgornji razpon naslovov prikazuje natančno lokacijo informacij MIDI za vsako ploščo bobna

/* Preslikava naslovov EEPROM

Opombe: | 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09 |

Zatiči: | 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, 0x10, 0x11, 0x12, 0x13 | Hitrosti | 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x20, 0x21, 0x22, 0x23 | */ const uint8_t NOTES_ADDR = 0x00; const uint8_t VELOCITIES_ADDR = 0x14; const uint8_t PINS_ADDR = 0x0A;

Globalne spremenljivke se uporabljajo za določanje stanja vsakega pad -a in ustrezno izvedbo komunikacije MIDI

/ * Globalne spremenljivke */

uint8_t drumNotes [10], drumVelocities [10], drumPins [10]; // MIDI spremenljivke

uint8_t uartBuffer [64]; // UART vmesnik za zbiranje in shranjevanje udarca MIDI Data Debouncer (DRUM_PINS [KICK], KICK_DB_DURATION); // Objekt razbremenilca za hlapni bool udarnega bobna previousState [9] = {0, 0, 0, 0, 0, 0, 0, 0, 0}; // prejšnja logična stanja bobnarske plošče nestanovitni bool currentState [9] = {0, 0, 0, 0, 0, 0, 0, 0, 0}; // Trenutna logična stanja blazinice

Funkcije EEPROM

/* Shrani nastavitve v EEPROM*/

void storeEEPROM () {

memcpy (drumNotes, uartBuffer, 10); memcpy (drumPins, uartBuffer + 10, 10); memcpy (drumVelocities, uartBuffer + 20, 10); for (uint8_t i = 0; i <10; i ++) EEPROM.write (NOTES_ADDR+i, drumNotes ); for (uint8_t i = 0; i <10; i ++) EEPROM.write (PINS_ADDR+i, drumPins ); for (uint8_t i = 0; i <10; i ++) EEPROM.write (VELOCITIES_ADDR+i, drumVelocities ); }

/* Naloži nastavitve iz EEPROM -a*/

void loadEEPROM () {for (uint8_t i = 0; i <10; i ++) drumNotes = EEPROM.read (NOTES_ADDR+i); za (uint8_t i = 0; i <10; i ++) DrumPins = EEPROM.preberite (PINS_ADDR+i); for (uint8_t i = 0; i <10; i ++) drumVelocities = EEPROM.read (VELOCITIES_ADDR+i); }

Inicializacija spremenljivk in način programiranja se v primeru pedal in zagona Arduino aktivirata hkrati

void enterProgrammingMode () {

bool confirmBreak = false; uint8_t lineCnt = 0; uint8_t charCnt = 0; char readChar = 0; while (! confirmBreak) {if (Serial.available ()) {uartBuffer [charCnt] = Serial.read (); if (charCnt> = 29) confirmBreak = true; else charCnt ++; }} Serial.println ("V redu"); storeEEPROM (); }

void initValues () {

#ifdef LOAD_DEFAULT_VALUES memcpy (opombe bobna, DRUM_NOTES, 10); memcpy (drumVelocities, DRUM_VELOCITIES, 10); memcpy (drumPins, DRUM_PINS, 10); #else loadEEPROM (); #endif}

Sredstva za komunikacijo MIDI z zamikom 1 ms zadrževanja beležk

/ * Predvajaj opombo MIDI funkcijo */

void midiOut (naštej DRUM_POSITION drumIn) {

if (drumIn == HIHAT) {// Če je bil pritisnjen HI-HAT, je treba preveriti, ali je pritisnjen pedal, če (! digitalRead (drumPins [HIHAT_PEDAL])) {noteOn (0x90, drumNotes [HIHAT_PEDAL], drumVelocities [HIHAT_PEDAL]); zamuda (1); noteOn (0x90, drumNotes [HIHAT_PEDAL], 0); } else {noteOn (0x90, drumNotes [HIHAT], drumVelocities [HIHAT]); zamuda (1); noteOn (0x90, drumNotes [HIHAT], 0); }} else {// Običajni MIDI prenos note noteOn (0x90, drumNotes [drumIn], drumVelocities [drumIn]); zamuda (1); noteOn (0x90, drumNotes [drumIn], 0); }}

void noteOn (int cmd, int pitch, int hitrost) {Serial.write (cmd); Serial.write (višina); Serial.write (hitrost); }

setup () in loop () funkcije z neskončno zanko delovanja naprave:

void setup () {

Serial.begin (115200);

for (uint8_t i = 0; i <10; i ++) {pinMode (i+2, INPUT); } #ifdef PRINT_PADS_PIN_NUMBERS while (true) {// Neskončna zanka za odpravljanje napak za (uint8_t i = 0; i <10; i ++) {if (! digitalRead (i+2)) {Serial.print ("Pin št.: D"); Serial.print (i + '0'); // Pretvori številko v znak ASCII}}} #else initValues (); / * Način programiranja: Če med zagonom pritisnete dva pedala - se aktivira način */ if (! DigitalRead (drumPins [KICK]) &&! DigitalRead (drumPins [HIHAT_PEDAL])) enterProgrammingMode (); #endif}

void loop () {for (uint8_t i = 1; i <9; i = i + 1) {currentState = digitalRead (drumPins ); if (! currentState && previousState ) midiOut (i); // Primerjamo stanja in zaznamo padajoči rob previousState = currentState ; } kick.update (); // Kick boben uporablja algoritem debounce po meri if (kick.edge ()) if (kick.falling ()) midiOut (KICK); }

5. korak: Programiranje B: Python in uporabniški vmesnik

Programiranje B: Python in uporabniški vmesnik
Programiranje B: Python in uporabniški vmesnik
Programiranje B: Python in uporabniški vmesnik
Programiranje B: Python in uporabniški vmesnik
Programiranje B: Python in uporabniški vmesnik
Programiranje B: Python in uporabniški vmesnik

Uporabniški vmesnik Python je na prvi pogled nekoliko zapleten, zato bomo poskušali razložiti njegove osnove, kako uporabljati, kakšno funkcijo ima vsak gumb in kako pravilno programirati napravo Arduino.

Uporabniški vmesnik - aplikacija

UI je grafični prikaz našega programerja kompleta bobnov, zaradi česar je zelo enostaven za uporabo in priročen za programiranje naprave Arduino kadar koli. Uporabniški vmesnik je sestavljen iz več grafičnih modulov, ki so vezani na njihovo predlagano delovanje. poglejmo jih enega za drugim:

  1. Slika bobna: uporabniški vmesnik Python uporablja koordinate slike X-Y za določitev vrste bobna. Če je bila izbrana veljavna regija bobna, se prikaže sekundarno sporočilo IO z opombnimi polji, hitrostjo in priključkom Arduino za namensko ploščo bobna. Ko uporabnik preveri in odobri te parametre, se te vrednosti lahko posredujejo neposredno v napravo Arduino.
  2. Slika zunanjega krmilnika: Če želite uporabljati komplet bobnov MIDI z okoljem za ustvarjanje glasbe VST/Glasba, morate zagnati tolmač Serial-To-MIDI. Uporabil sem Hairless, ki je na voljo brezplačno in ga je mogoče zagnati neposredno iz uporabniškega vmesnika, samo s pritiskom na njegovo sliko.
  3. Seznam vrat COM: Če želite komunicirati z Arduinom, morate določiti njegova priključena vrata COM. Seznam se osveži s pritiskom na gumb Osveži.
  4. Naloži/shrani konfiguracijo: V kodi so definirane privzete vrednosti MIDI, ki jih lahko uporabnik spremeni z interakcijo z uporabniškim vmesnikom. Konfiguracija je definirana v datoteki config.txt v določeni obliki, ki jo lahko uporabnik shrani ali naloži.
  5. Gumb za programsko napravo: Če želite shraniti vse spremenjene vrednosti MIDI v Arduino EEPROM, morate po tem pritisniti na dva nožna pedala (Kick boben in Hi-hat pedal), počakajte, da se prenos podatkov zaključi. Če je prišlo do težav s komunikacijo, se prikaže ustrezno pojavno okno. Če prenos uspe, bo uporabniški vmesnik pokazal uspešno sporočilo.
  6. Gumb za izhod: Samo zapustite aplikacijo z dovoljenjem uporabnika.

Poudarki Pythonove kode

V kodi se dogaja veliko stvari, zato bomo razširili pisne funkcije in ne celotne kode.

Najprej, če želite uporabljati uporabniški vmesnik, morate prenesti več modulov, da bo koda delovala:

uvoz osimport threading import tkinter kot tk iz tkinter uvozno sporočilo iz tkinter uvoz * iz PIL uvoz ImageTk, uvoz slike numpy kot np uvoz serijski uvoz glob

Nekateri moduli so vključeni v privzeti paket Python. Z orodjem PIP je treba namestiti več modulov:

pip install Blazina

pip install numpy pip install ScreenInfo

Močno je priporočljivo, da aplikacijo zaženete prek PyCharma. V prihodnjih izdajah nameravam izvoziti izvedljivo datoteko za projekt.

Kratka razlaga kode

Kodo bo veliko lažje razumeti, če pogledamo njene vrstice z vidika funkcij in razredov:

1. Glavna funkcija - tukaj se začne koda

če _name_ == '_main_': drumkit_gui ()

2. Konstante, koordinate in privzete informacije MIDI kompleta bobnov

razred bobni: DRUM_TYPES = ["Kick", "Hihat", "Snare", "Crash 1", "Crash 2", "Tom High", "Tom Mid", "Tom Low", "Ride", "Hihat Pedal "," Krmilnik "]

COORDINATES_X = [323, 117, 205, 173, 565, 271, 386, 488, 487, 135, 79]

COORDINATES_Y = [268, 115, 192, 40, 29, 107, 104, 190, 71, 408, 208] DIMS_WIDTH = [60, 145, 130, 120, 120, 70, 70, 130, 120, 70, 145] DIMS_LENGTH = [60, 60, 80, 35, 35, 40, 40, 70, 35, 100, 50]

DRUM_ENUM = ["Kick", "Snare", "Hihat", "Ride", "Crash 1", "Crash 2", "Tom High", "Tom Mid", "Tom Low", "Hihat Pedal"]

NAPOTKI BUBNJANJA = [36, 40, 42, 51, 49, 55, 47, 45, 43, 48] BUBANJSKE VELIKOSTI = [110, 100, 100, 110, 110, 110, 110, 110, 110, 110] BUBNJIČKI = [8, 6, 4, 3, 11, 9, 5, 10, 2, 7]

3. Funkcije uporabniškega vmesnika - ravnanje z uporabniškim vmesnikom in grafičnimi objekti

def set_active (uporabniški vmesnik)

def sekundarni_ui (tip_bobna)

razred SelectionUi (tk. Frame)

razred Aplikacija (tk. Frame)

def drumkit_gui ()

def event_ui_clicked (dogodek)

def getorigin (self, event)

4. Serijska komunikacija

def get_serial_ports ()

def communication_with_arduino (vrata)

5. Delo z datotekami: shranite/naložite nastavitve iz datoteke txt

def save_config ()

def load_config ()

6. Zagon zunanje aplikacije hairless.exe iz kode z uporabo zmogljivosti Python Threading

razred ExternalExecutableThread (threading. Thread)

def run_hairless_executable ()

Za zagon kode je seznam datotek, ki jih je treba priložiti mapi projekta:

  • config.txt: Datoteka z nastavitvami
  • hairless.exe: MIDI pretvornik brez dlake
  • drumkit.png: Slika, ki opredeljuje vse ploščice bobna, ki jih je mogoče klikniti v našem uporabniškem vmesniku (prenesti je treba iz nabora slik tega koraka)
  • drumgui.py: Koda projekta

To je vse, kar moramo poudariti, da bo delovalo. Zelo pomembno je, da projektu dodate datoteke: sliko bobna, izvedljivo datoteko hairless.exe in datoteko z nastavitvami config.txt.

In.. Tukaj smo končali!:)

Upam, da vam bo ta pouk koristen.

Hvala za branje!:)

Priporočena: