Sisukord:

Arduino muusika märkmete detektor: 3 sammu
Arduino muusika märkmete detektor: 3 sammu

Video: Arduino muusika märkmete detektor: 3 sammu

Video: Arduino muusika märkmete detektor: 3 sammu
Video: Codebug muusika Arduino 2024, November
Anonim
Image
Image

Muusikamärkide tuvastamine helisignaalist on raske, eriti Arduino puhul, kuna mälu ja töötlemisvõimsus on piiratud. Üldiselt pole noot puhas siinuslaine, mis raskendab tuvastamist. Kui võtame erinevate muusikariistade sagedusmuutmise, võib see esitatava noodi põhjal sisaldada mitmeid harmoonilisi. Igal pillil on oma kombinatsioon erinevatest harmoonilistest. Selles koodis proovisin teha programmi, mis suudaks katta võimalikult palju instrumente. Võite viidata lisatud videole, kus proovisin katsetada erinevat tüüpi instrumente, klaviatuuril genereeritud erinevat tüüpi toone ja isegi vokaali heli. Avastamise täpsus varieerub instrumentide kaupa. Mõne instrumendi (st klaveri) puhul piiratud vahemikus (200–500 Hz) on see täpne, mõne instrumendi puhul aga madala täpsusega (nt suupill).

See kood kasutab varem välja töötatud FFT -koodi EasyFFT.

Koodi demonstreerimine on näidatud ülaltoodud videos koos erinevat tüüpi instrumendiheli ja vokaaliga.

Tarvikud

- Arduino Nano/Uno või kõrgem

- Arduino mikrofonimoodul

Samm: märkmete tuvastamise algoritm

Nagu eelmises etapis mainitud, on tuvastamine keeruline, kuna heliproovides on mitu sagedust.

Programm töötab järgmises voos:

1. Andmete kogumine:

- selles jaotises võetakse heliandmetest 128 näidist, kahe proovi eraldamine (proovivõtu sagedus) sõltuvalt huvipakkuvast sagedusest. Sel juhul kasutame Hannni aknafunktsiooni ja amplituudi/RMS arvutamiseks kahe proovi vahekaugust. See kood teeb ka jämeda nullimise, lahutades analoogloe väärtusest 500. Seda väärtust saab vajadusel muuta. Tüüpilisel juhul toimivad need väärtused hästi. Lisaks tuleb lisada viivitus, et proovivõtu sagedus oleks umbes 1200 Hz. 1200 Hz diskreetimissageduse korral on võimalik tuvastada maksimaalselt 600 Hz sagedust.

jaoks (int i = 0; i <128; i ++) {a = analogRead (Mic_pin) -500; // ligikaudne nullnihke summa1 = summa1+a; // keskmise väärtuseni summa2 = summa2+a*a; // RMS väärtusele a = a*(sin (i*3,14/128)*sin (i*3,14/128)); // Hanni aken = 4*a; // ujuki skaleerimine int teisendamise viivituseksMikrosekundit (195); // toimingute sagedusvahemiku põhjal}

2. FFT:

Kui andmed on valmis, viiakse FFT läbi EasyFFT abil. Seda EasyFFT -funktsiooni on muudetud, et määrata FFT 128 proovile. Koodi muudetakse ka mälutarbimise vähendamiseks. Algne EasyFFT -funktsioon on mõeldud kuni 1028 proovile (koos ühilduva plaadiga), samas kui meil on vaja ainult 128 näidist. see kood vähendab mälukasutust umbes 20% võrreldes EasyFFT algse funktsiooniga.

Kui FFT on tehtud, tagastab kood edasiseks analüüsiks 5 kõige domineerivamat sageduspiiki. See sagedus on paigutatud amplituudi kahanevas järjekorras.

3. Iga tipu puhul tuvastab kood võimalikud sellega seotud noodid. see kood skaneerib ainult kuni 1200 Hz. Maksimaalse amplituudiga sagedus ei pea olema sama.

Kõik sagedused on kaardistatud vahemikus 0 kuni 255, siin tuvastatakse esimene oktaav, näiteks 65,4 Hz kuni 130,8 tähistab ühte oktaavi, 130,8 Hz kuni 261,6 Hz tähistab teist. Iga oktaavi puhul kaardistatakse sagedused vahemikus 0 kuni 255. siin kaardistamine alates C kuni C '.

if (f_peaks > 1040) {f_peaks = 0;} if (f_peaks > = 65,4 && f_peaks = 130,8 && f_peaks = 261,6 && f_peaks = 523,25 && f_peaks = 1046 && f_peaks <= 2093) {f_peaks = 255*((f_peaks /1046) -1);}

NoteV massiivi väärtusi kasutatakse märkme tuvastamiseks määratud sagedustele.

bait NoteV [13] = {8, 23, 40, 57, 76, 96, 116, 138, 162, 187, 213, 241, 255};

4. Pärast noodi arvutamist iga sageduse jaoks võib juhtuda, et eksisteerib mitu sagedust, mis viitavad samale noodile. Täpse väljundkoodi olemasolu arvestab ka kordusi. Kood liidab kõik sagedusväärtused amplituudijärjekorra ja korduste põhjal ning annab tippu maksimaalse amplituudiga noodi.

2. samm: rakendus

Koodi kasutamine on otsekohene, kuid sellel on ka mitmeid piiranguid, mida tuleb meeles pidada. Koodi saab kopeerida, kuna seda kasutatakse märkmete tuvastamiseks. Selle kasutamise ajal tuleb arvestada järgmiste punktidega.

1. Pin määramine:

Lisatud tihvti määramist tuleb muuta. Oma katse jaoks hoidsin selle analoogpistikusse 7, void setup () {Serial.begin (250000); Mic_pin = A7; }

2. Mikrofoni tundlikkus:

Mikrofoni tundlikkust tuleb muuta, nii et lainekuju saab genereerida hea amplituudiga. Enamasti on mikrofonimoodulil tundlikkuse seade. sobiv tundlikkus tuleb valida nii, et signaal ei oleks liiga väike ega katkestaks ka suurema amplituudi tõttu.

3. Amplituudi künnis:

See kood aktiveerub ainult siis, kui signaali amplituud on piisavalt kõrge. kasutaja peab selle seade käsitsi määrama. see väärtus sõltub mikrofoni tundlikkusest ja rakendusest.

kui (summa2-summa1> 5) {

..

ülaltoodud koodis annab summa2 RMS väärtuse, summa 1 aga keskmise väärtuse. seega annab nende kahe väärtuse erinevus helisignaali amplituudi. minu puhul töötab see korralikult amplituudi väärtusega umbes 5.

4. Vaikimisi prindib see kood tuvastatud märkme. kui aga kavatsete märkmeid kasutada mõnel muul eesmärgil, tuleks kasutada otse määratud numbrit. näiteks C = 0; C#= 1, D = 2, D#= 3 ja edasi.

5. Kui seadmel on kõrgem sagedus, võib kood anda vale väljundi. maksimaalset sagedust piirab proovivõtu sagedus. nii et saate optimaalse väljundi saavutamiseks mängida allpool viivitusväärtusi. allpool koodi viivitus 195 mikrosekundit. mida saab optimaalse väljundi saamiseks muuta. See mõjutab üldist täitmisaega.

{a = analogRead (Mic_pin) -500; // jäme nullnihe

summa1 = summa1+a; // keskmise väärtuseni summa2 = summa2+a*a; // RMS väärtusele a = a*(sin (i*3,14/128)*sin (i*3,14/128)); // Hanni aken = 4*a; // ujuki skaleerimine int teisendamise viivituseksMikrosekundit (195); // toimingute sagedusvahemiku põhjal}

6. see kood töötab ainult kuni 2000Hz sageduseni. kõrvaldades viivituse proovide võtmise vahel, on võimalik saada umbes 3-4 kHz diskreetimissagedusi.

Ettevaatusabinõud:

  • Nagu EasyFFT -i õpetuses mainitud, sööb FFT tohutult palju Arduino mälu. Seega, kui teil on programm, mis vajab teatud väärtuste salvestamist, on soovitatav kasutada suurema mäluga tahvlit.
  • See kood võib ühe instrumendi/vokalisti jaoks hästi toimida ja teise jaoks halb. Reaalajas Täpne tuvastamine pole arvutuspiirangute tõttu võimalik.

3. samm: suvine

Märkmete tuvastamine on arvutusmahukas töö, reaalajas väljundi saamine on eriti Arduino puhul väga raske. See kood võib anda umbes 6,6 proovi sekundis (lisatud 195 mikrosekundi viivitus). see kood sobib hästi klaveri ja mõne muu instrumendiga.

Loodan, et see kood ja õpetus on abiks teie muusikaga seotud projektis. kahtluste või ettepanekute korral kommenteerige või saatke sõnum.

Eelseisvas õpetuses muudan seda koodi muusikaakordi tuvastamiseks. nii et püsige lainel.

Soovitan: