Turinys:

Kaip sukurti ir išbandyti geresnį DAC naudojant ESP32: 5 žingsniai
Kaip sukurti ir išbandyti geresnį DAC naudojant ESP32: 5 žingsniai

Video: Kaip sukurti ir išbandyti geresnį DAC naudojant ESP32: 5 žingsniai

Video: Kaip sukurti ir išbandyti geresnį DAC naudojant ESP32: 5 žingsniai
Video: Kaip Sukurti Pelningą YouTube Kanalą su AI - 2024 2024, Lapkritis
Anonim
Kaip sukurti ir išbandyti geresnį DAC naudojant ESP32
Kaip sukurti ir išbandyti geresnį DAC naudojant ESP32
Kaip sukurti ir išbandyti geresnį DAC naudojant ESP32
Kaip sukurti ir išbandyti geresnį DAC naudojant ESP32

ESP32 turi 2 8 bitų skaitmeninius analoginius keitiklius (DAC). Šie DAC leidžia mums sukurti savavališką įtampą tam tikrame diapazone (0–3,3 V) su 8 bitų skiriamąja geba. Šioje instrukcijoje aš jums parodysiu, kaip sukurti DAC ir apibūdinti jo veikimą, taip pat palyginti jį su ESP32 DAC. Į našumo indeksus, kuriuos apžvelgsiu, yra

  • Triukšmo lygis
  • Pralaidumas
  • Integralus netiesiškumas
  • Diferencialinis netiesiškumas

Šiems indeksams išbandyti naudosiu ADS1115.

Svarbu pažymėti, kad visų šių rodiklių įvertinimas bus toks pat tikslus, kaip ir jūsų atskaitos prietaisas (šiuo atveju ADS115). Pavyzdžiui, ADS115 neturi 16 bitų tikslumo, kai kalbama apie įtampos poslinkį ir padidėjimą. Šios klaidos gali siekti 0,1%. Daugelio sistemų atveju šios klaidos gali būti ignoruojamos, kai absoliutus tikslumas kelia nerimą.

Prekės

  • ADS1115
  • ESP32 lenta
  • Bandomoji Lenta
  • jungiamieji laidai
  • 5 kOhm rezistorius
  • 1 mikro Farad keraminis kondensatorius

1 žingsnis: Duonos lentos išdėstymas

Duonos lentos išdėstymas
Duonos lentos išdėstymas

Sujunkite šiuos kaiščius

Tarp ESP32 ir ADS1115

3v3 VDD

GND GND

GPIO22 SCL

GPIO21 SDA

ADS1115

ADDR GND (ADS115)

DAC kūrimas

Yra daug būdų, kaip sukurti DAC. Paprasčiausias yra žemo dažnio filtras PWM signalui su rezistoriumi ir kondensatoriumi. Aš galėjau čia pridėti op-amp kaip buferį, bet norėjau, kad viskas būtų paprasta. Šią konstrukciją paprasta ir pigu įgyvendinti su bet kokiu PWM palaikančiu mikrovaldikliu. Čia nesiruošiu nagrinėti dizaino teorijos (google PWM DAC).

Tiesiog prijunkite GPIO255 KOhm rezistorių 1 „microFarad“kondensatorių

Dabar prijunkite trumpąjį laidą nuo taško, kuriame rezistorius susitinka su kondensatoriumi, prie A0 ADS115.

2 žingsnis: įvertinkite signalą iki triukšmo lygio

Įvertinkite signalą iki triukšmo lygio
Įvertinkite signalą iki triukšmo lygio

Norėdami įvertinti triukšmo lygį, tiesiog paleiskite žemiau esantį scenarijų. Norėdami tai įvertinti, mes tiesiog paliekame DAC fiksuotą vertę ir matuojame, kaip laikui bėgant svyruoja įtampa.

Dėl DAC konstrukcijos triukšmas bus didžiausias, kai PWM signalas bus 50% darbinio ciklo. Todėl čia mes jį įvertinsime. Mes taip pat įvertinsime ESP32 tuo pačiu signalo lygiu. Mes taip pat filtruosime ESP32 DAC tuo pačiu žemo dažnio filtru, kad matavimai būtų palyginami.

Man rezultatas buvo aiškus. PWM dizainas turėjo> 6 dB geresnį SNR (tai yra 2 kartus geriau). Aiškus naujo DAC laimėjimas. Viena nedidelė painiava yra ta, kad ADC yra įmontuoti filtrai, kurie neabejotinai pagerina SNR. Taigi absoliučias vertes gali būti sunku interpretuoti. Jei būčiau naudojęs antros eilės filtrą, taip nebūtų.

Bet kokiu atveju kodas yra žemiau

#įtraukti

#įtraukti „Adafruit_ADS1115“skelbimus; // adafruit biblioteka, skirta adc int16_t adc0; // void setup (void) {Serial.begin (115200); // Pradėti serijinius skelbimus.setGain (GAIN_TWO); // 2x stiprinimas +/- 2.048V 1 bitas = 0.0625mV ads.begin (); // start adc float M = 0; // pradinis vidutinis plūdė Mp = 0; // ankstesnis vidutinis plūdė S = 0; // pradinis dispersijos plūdė Sp = 0; // ankstesnė dispersija const int pakartojimai = 500; // pakartojimų skaičius int n = 256; // mėginių skaičius ledcSetup (0, 25000, 8); // nustatyti pwm frequecny = 25000 Hz esant 8 bitų raiškai ledcAttachPin (25, 0); // nustatyti pwm ant 25 kaiščio ledcWrite (0, 128); // nustatyti pusę darbo ciklo (didžiausias triukšmas) uždelsimas (3000); // laukti nusistovėjimo laiko float snrPWM [pakartojimai]; // PWM plūdės snr masyvas snrDAC [pakartojimai]; // DAC „snrs“masyvas, skirtas (int i = 0; i <pakartojimai; i ++) {// ciklas per pakartojimus (int k = 1; k <(n+1); k ++) {// kilpas virš mėginių adc0 = ads.readADC_SingleEnded (0); // gauti skaitymą M = Mp + (adc0 - Mp) / k; // apskaičiuoti riedėjimo vidurkį Mp = M; // nustatyti ankstesnį vidurkį S = Sp + (adc0 - Mp) * (adc0 - M); // skaičiuoti riedėjimo dispersiją Sp = S; // nustatyti ankstesnę dispersiją} // snr dB dB snrPWM = 20 * log10 (3.3 / (sqrt (S / n) *.0625 *.001)); // atstatyti reikšmes M = 0; Mp = 0; S = 0; Sp = 0; } ledcDetachPin (25); // atjungti PWM nuo 25 kaiščio dacWrite (25, 128); // rašyti į DAC uždelsimą (3000); // laukti, kol atsiskaitys (int i = 0; i <pakartojimai; i ++) {// tas pats kaip PWM kilpa (int k = 1; k <(n+1); k ++) {adc0 = ads.readADC_SingleEnded (0); M = Mp + (adc0 - Mp) / k; Mp = M; S = Sp + (adc0 - Mp) * (adc0 - M); Sp = S; } snrDAC = 20 * log10 (3,3 / (kv. (S / n) *.0625 *.001)); M = 0; Mp = 0; S = 0; Sp = 0; } // brėžti SNR viename grafike, skirtas (int i = 1; i <pakartojimai; i ++) {Serial.print ("PWM_SNR (dB):"); Serijinis atspaudas (snrPWM ); Serial.print (","); Serial.print ("ESP32_SNR (dB):"); Serijinis.println (snrDAC ); }} void loop (void) {}

3 žingsnis: integralus netiesiškumas ir diferencialinis netiesiškumas

Integralus netiesiškumas ir diferencialinis netiesiškumas
Integralus netiesiškumas ir diferencialinis netiesiškumas

Integruotas netiesiškumas yra maždaug matas, kiek yra nukrypimų tarp jūsų DAC išėjimo įtampos ir tiesios linijos. Kuo šis didesnis, tuo blogiau…

Diferencialinis netiesiškumas yra maždaug matas, kiek pastebėtas įtampos pokytis (iš vieno kodo į kitą) nukrypsta nuo to, ko būtų galima tikėtis iš tiesios linijos.

Rezultatai čia buvo tikrai įdomūs. Visų pirma, abu turi mažiau nei 0,5 lsb klaidą (esant 8 bitų skiriamai gebai), o tai yra gerai, tačiau PWM turi daug geresnį vientisumą. Abi turi skirtingą netiesiškumą, tačiau ESP32 DAC turi labai keistų šuolių. Be to, PWM metodas turi tam tikrą klaidų struktūrą. Iš esmės jis kintamai viršija ir sumažina teisingą įtampą.

Įtariu, kad tai keista apvalinimo klaida, kaip ESP32 sukuriamas 8 bitų PWM signalas.

Vienas iš būdų tai ištaisyti yra greitai pereiti tarp dviejų gretimų kodų (pvz., 128, 129) naudojant PWM. Naudojant analoginį žemo dažnio filtrą, klaidų vidurkis bus lygus nuliui. Aš tai imitavau programinėje įrangoje ir visos klaidos išnyko. Dabar PWM metodas turi tiesiškumą, kuris yra tikslus 16 bitų!

Toliau pateikiamas bet koks duomenų generavimo kodas. Išvestis serijiniame monitoriuje bus.csv formatu. Tiesiog nukopijuokite jį į teksto failą tolesniam apdorojimui.

#įtraukti

#įtraukti „Adafruit_ADS1115“skelbimus; / * Naudokite tai 16 bitų versijai */ int16_t adc0; void setup (void) {Serial.begin (115200); ads.setGain (GAIN_ONE); // 2x stiprinimas +/- 2.048V 1 bitas = 1mV 0.0625mV ads.begin (); ledcSetup (0, 25000, 8); ledcAttachPin (25, 0); Serial.println ("Tikimasi, pastebėtas"); ledcWrite (0, 2); vėlavimas (3000); už (int i = 2; i <255; i ++) {ledcWrite (0, i); vėlavimas (100); adc0 = ads.readADC_SingleEnded (0); tikimasi plūdės = (i / 256,0 * 3,3) / 4,096 * 32767; Serial.print (tikimasi); Serial.print (","); Serial.println (adc0); }} void loop (void) {}

4 žingsnis: pralaidumas

Pralaidumas
Pralaidumas

Aš čia apibrėžsiu pralaidumą kaip dažnį, kuriuo DAC išvestis sumažėja 3dB. Tai yra susitarimas ir tam tikru mastu savavališkas. Pavyzdžiui, 6 dB taške DAC vis tiek perduos signalą, kurio amplitudė bus tik ~ 50%.

Norėdami tai išmatuoti, mes vis dažniau perduodame sinusines bangas iš DAC į ADC ir matuojame jų standartinį nuokrypį. Nenuostabu, kad 3dB taškas yra 30 Hz dažniu (1/(2*pi*5000*1e-6)).

ESP32 gali atlikti 1 mega mėginį per sekundę. Tai „ESP32“laimėjimas iš rankų. Jo amplitudė visiškai nesumažėja 100 Hz dažnių juostos pločio bandymo srityje.

Žemiau pateiktas kodas gali patikrinti PWM DAC pralaidumą.

#įtraukti

#įtraukti „Adafruit_ADS1115“skelbimus; / * Naudokite tai 16 bitų versijai */ int16_t adc0; int16_t adc1; void setup (void) {float M; plūdė Mp = 0; plūdė S = 0; plūdė Sp = 0; Serial.begin (115200); ads.setGain (GAIN_ONE); // 1x padidinimas +/- 4,096V 1 bitas = 2mV 0,125 m skelbimai.begin (); ledcSetup (0, 25000, 8); ledcAttachPin (25, 0); vėlavimas (5000); Serial.println („Dažnis, amplitudė“); for (int i = 1; i <100; i ++) {unsigned long start = milis (); nepasirašytas ilgas T = milis (); Sp = 0; S = 0; M = 0; Mp = 0; int k = 1; plūdės norma; tuo tarpu ((T - pradžia) <1000) {int out = 24 * sin (2 * PI * i * (T - pradžia) / 1000,0) + 128; ledcWrite (0, išėjimas); adc0 = ads.readADC_SingleEnded (0); M = Mp + (adc0 - Mp) / k; Mp = M; S = Sp + (adc0 - Mp) * (adc0 - M); Sp = S; T = milis (); k ++; } jei (i == 1) {norma = kv. (S / k); } Serijinis atspaudas (i); Serial.print (","); Serijinis.println (kv. (S / k) / norma, 3); k = 0; }} void loop (void) {}

Ir šis kodas patikrins ESP32 pralaidumą. Būtinai nuimkite kondensatorių, nes abiejų metodų rezultatai bus vienodi.

#įtraukti

#įtraukti „Adafruit_ADS1115“skelbimus; / * Naudokite tai 16 bitų versijai */ int16_t adc0; int16_t adc1; void setup (void) {float M; plūdė Mp = 0; plūdė S = 0; plūdė Sp = 0; Serial.begin (115200); ads.setGain (GAIN_ONE); // 1x padidinimas +/- 4,096V 1 bitas = 2mV 0,125 m skelbimai.begin (); vėlavimas (5000); Serial.println („Dažnis, amplitudė“); for (int i = 1; i <100; i ++) {unsigned long start = milis (); nepasirašytas ilgas T = milis (); Sp = 0; S = 0; M = 0; Mp = 0; int k = 1; plūdės norma; tuo tarpu ((T - pradžia) <1000) {int out = 24 * sin (2 * PI * i * (T - pradžia) / 1000,0) + 128; dacWrite (25, išėjimas); adc0 = ads.readADC_SingleEnded (0); M = Mp + (adc0 - Mp) / k; Mp = M; S = Sp + (adc0 - Mp) * (adc0 - M); Sp = S; T = milis (); k ++; } jei (i == 1) {norma = kv. (S / k); } Serijinis atspaudas (i); Serial.print (","); Serijinis.println (kv. (S / k) / norma, 3); k = 0; }} void loop (void) {}

5 žingsnis: uždarykite mintis

Naujasis DAC dizainas laimi tiesiškumu ir triukšmu, bet praranda pralaidumą. Priklausomai nuo jūsų taikymo, vienas iš šių rodiklių gali būti svarbesnis už kitą. Taikydami šias testavimo procedūras, turėtumėte sugebėti objektyviai priimti tokį sprendimą!

Taip pat manau, kad čia verta pažymėti, kad kadangi PWM išvestis yra mažo triukšmo, turint išskirtinį tiesiškumą, turėtų būti įmanoma sukurti daug didesnės skiriamosios gebos DAC su PWM išvestimi (galbūt net 16 bitų tikslumu). Tai užtruks šiek tiek darbo. Iki tol linkiu jums atsisveikinti!

Rekomenduojamas: