ESP32 audio-transceiver (deel 1): SD-kaart WAV-speler demo
op
ESP32-controllers zijn goede oplossingen die worden gebruikt in duizenden IoT-, smart home- en andere afstandsbedieningsprojecten. De ESP32 heeft ook een goede I2S-interface, die kan worden gebruikt om digitale audiosignalen uit te sturen en in te lezen. In combinatie met een I2S-DAC, een I2S-ADC en een SD-kaart zijn talloze verschillende audioprojecten mogelijk. Hier integreren we dit alles, samen met een nRF24-transceiver voor het zenden en ontvangen van (audio-)gegevens, op een soldeervriendelijke print. In het eerste deel van deze reeks artikelen presenteren we het blokschema, de schakeling en de demosoftware.
Kiezen voor ESP32
De populaire ESP32-controllers zijn betaalbaar, snel en eenvoudig te programmeren – bijvoorbeeld met de Arduino IDE. Uitgerust met WiFi worden ze gebruikt in duizenden IoT-, smart home- en andere afstandsbedieningsprojecten, en dat soort Elektor-projecten zijn nauwelijks te tellen. ESP32-controllers hebben echter ook een vrij goede I2S-interface aan boord, die audiostreams digitaal kan uitvoeren en inlezen (zie het kader I2S-interface). Wat u daarnaast nodig hebt voor het afspelen van audio is een I2S-DAC die de I2S-gegevens van de ESP32 neemt en omzet in een analoog signaal. Om omgekeerd audio te bemonsteren, hebt u een audio ADC met een I2S-interface nodig. Voor dit project hebben we een krachtige ESP32-S3-gebaseerde development-module samen met een I2S-ADC/DAC breakout-board op een carrierprint gezet. We integreerden ook een optie om een Nordic nRF24 draadloze module aan te sluiten om digitale (audio-)gegevens te verzenden en te ontvangen. Een SD-kaart, verschillende uitbreidingsconnectoren en diverse voedingsopties vervolledigen het project.
Gebruikssituaties
Dit board is voornamelijk bedoeld voor audiotoepassingen, maar u kunt het ook gebruiken om andere signalen en gegevens te samplen, uit te voeren, op te slaan, te transporteren en/of te ontvangen. Hier zijn enkele gebruikscenario’s, waarvan we er enkele zullen implementeren in volgende artikelen.
- Audiospeler die bestanden van een SD-kaart afspeelt (zie demo-software hieronder).
- Audiorecorder.
- Audioprocessor (audio samplen, iets met de gegevens doen en het uitvoeren)
- Draadloze audio zend-ontvanger via WiFi of ESP-NOW.
- Draadloze audio zend-ontvanger via Nordic nRF24.
- Datalogger: sensoren aangesloten via SPI/I2C, gegevens worden opgeslagen op SD-kaart.
- Draadloos sensorknooppunt: sensorwaarden verzenden via WiFi of nRF24.
- LF-signalen genereren of meten.
Belangrijkste blokken
U ziet de belangrijkste blokken en connectoren van de ESP32 audio-transceiver in figuur 1.
ESP32-S3-DevKit-C
Het brein van het project is het 44-pins ESP32-S3-DevKit-C-board [1]; het wordt in het midden van onze print geplaatst. In principe bevat het DevKit-C-board een ESP32-S3-WROOM-module (met een dual-core ESP32-S3-processor), maker-vriendelijke DIL-uitbreidingsconnectoren en twee USB-connectoren voor programmering en voeding (zie figuur◦2). Merk op dat er verschillende pin-compatibele S3 DevKit-Cvarianten op de markt zijn. Sommige hebben een WROOM-module met een PCB-printantenne, andere een WROOM-module met een connector voor een externe antenne. Deze laatste maakt het mogelijk om ons carrier board samen met de DevKit in een metalen behuizing te plaatsen en toch van de WiFi-functies van de ESP32 te profiteren.
en twee USB-aansluitingen voor programmering en voeding. Links een versie
met PCB-antenne en 1" breedte. Rechts de versie uit de Elektor-shop,
met 0,9" breedte en een connector voor een externe WiFi-antenne.
Omdat er S3-DevKit-C-varianten zijn met een breedte van 0,9" en 1", hebben we ons carrier board geschikt gemaakt voor beide, met een extra pinheader. Als u een 0,9" brede ESP32-S3-DevKit gebruikt, kunt u de buitenste pinheader (J3) ook gebruiken als uitbreidingsconnector.
Een S3-DevKit-C met printantenne is verkrijgbaar voor ongeveer €◦8; deze kan eenvoudig worden aangesloten en verwisseld. Het enige dat u moet solderen zijn twee rijen headers. We denken echter al na over een tweede versie van onze print, waar de S3-WROOM module rechtstreeks op wordt gesoldeerd, wat ruimte en enige kosten zal besparen.
I2S-DAC/ADC
Er zijn veel I2S breakout-boards voor het samplen en afspelen van audio op de markt. Uiteindelijk hebben we gekozen voor een Digilent I2S2 Pmod module [2], met daarop een Cirrus CS4344 DAC (tot 192◦kHz/24◦bit) en een Cirrus CS5343 ADC (tot 96◦kHz/24◦bit), beide aangesloten op stereo audio-jacks (figuur 3). Eigenlijk zijn het twee breakout-boards in één. Op de 2x6-connector zijn twee onafhankelijke I2S-interfaces toegankelijk, een voor de uitvoer en een voor de invoer van audio (zie kader I2S-interface). De VCC- en GND-pinnen voor de voeding zijn ook dubbel uitgevoerd. Het is een beetje ongebruikelijk dat deze 2x6-connector horizontaal staat, maar dat is onderdeel van de Pmod-connectorspecificatie van Digilent. Om deze module op onze print aan te sluiten, moet u een haakse 2x6-socket solderen.
en een Cirrus CS5343 ADC aan boord, beide aangesloten op stereo audio-connectoren.
De I2S2 Pmod-module is bij lange na niet het goedkoopste I2S-BoB dat u kunt kopen, maar de audiokwaliteit is behoorlijk goed en hij werkt uitstekend met de ESP32 als I2S-master. Er is ook geen configuratie nodig voordat u kunt beginnen met het afspelen of samplen van audio.
Op ons board is de 2x6 Pmod-connector gerouteerd naar GPIO35...GPIO40, plus GPIO47 en GPIO48. Natuurlijk is er niets op tegen om hier andere Pmod-modules aan te sluiten (stroomsensoren, audioversterkers...) of om uw eigen kleine uitbreidingsboard te maken met een 2x6-connector in het gebruikelijke 2,54mm-raster.
nRF24-transceiver
Naast de WiFi- en ESP-NOW-mogelijkheden van de ESP32 wilden we een derde optie bieden, die vooral gericht is op een zeer lage latentie bij het verzenden/ontvangen van een continue audiostroom. Nordic’s eigen draadloze protocol voor hun nRF24-transceivermodules is erg snel. U kunt pakketten in minder dan 1◦ms van zender naar ontvanger sturen. De nRF24-chips [3] worden ook gebruikt in veel IoT-projecten, omdat er vrij goedkope breakout-boards zijn die deze chip integreren en er bovendien goede (Arduino-) bibliotheken zijn. Vooral de modules met een nRF24, een antenneversterker en een antenneconnector zijn hun geld waard. Uit onze ervaringen blijkt dat het bereik binnen gebouwen beter is dan bij WiFi. Een voordeel is dat de chips in hun eigen 1MHz-brede kanalen zenden en niet precies in de WiFi-kanalen, waar altijd veel verkeer is. Een kleine tegenvaller is de maximale payload-grootte van 32◦bytes en de maximale gegevenssnelheid in praktische toepassingen, die ver onder de nominale gegevenssnelheid van 2◦Mbit/s ligt. Hier komen we in het volgende artikel op terug.
De nRF24 wordt benaderd via een SPI-interface plus twee digitale lijnen (Chip Enable en Interrupt). De 2x4-connector is min of meer gestandaardiseerd, dus u kunt een nRF24-module naar keuze gebruiken. We raden aan de E01-ML01DP5 van Ebyte [4] te gebruiken, die een SMA-antenneconnector en een geïntegreerde antenneversterker heeft (figuur 4). Onze carrierprint is voorbereid voor deze module, de antenneconnector komt precies aan de rand van deze print, zodat hij perfect in een plastic of metalen behuizing past.
een SMA-antenneaansluiting en een geïntegreerde antenneversterker.
Aangezien de 2x4-connector op onze print naar de SPI-interface van de ESP32 gaat, kunt u hier naar hartelust andere SPI-modules aansluiten, bijvoorbeeld een sensor.
SD-kaart-connector
Het board bevat een microSD-kaart-connector, die handige lokale opslag biedt voor geregistreerde data, configuratiebestanden of audio-inhoud. Deze is verbonden met de ESP32-S3 via de SPI-interface (MOSI, MISO, SCK en een extra CS-lijn), waardoor hij gemakkelijk te gebruiken is met de algemeen ondersteunde Arduino SD- of SdFat-bibliotheken. De socket is gemonteerd aan de bovenkant van het board en zo geplaatst dat hij gemakkelijk toegankelijk is. Ontkoppelcondensatoren worden dicht bij de voedingspinnen geplaatst voor stabiliteit tijdens schrijfoperaties. Aangezien de SD-kaart de SPI-bus deelt met andere periferie zoals de nRF24-module, is een juiste chip-select behandeling in de software essentieel om conflicten te voorkomen.
Uitbreidingsconnectoren
Het board heeft meerdere uitbreidingsconnectoren (J7...J10) die ongebruikte GPIO’s van de ESP32-S3 toegankelijk maken, waardoor extra sensoren of andere modules eenvoudig kunnen worden aangesloten. Deze connectoren zijn geschikt voor algemeen gebruik, maar ook ideaal voor gebruikersinterface-elementen zoals displays (bijvoorbeeld OLED via I2C), drukknoppen, LED’s of IR-ontvangers. Elke connector heeft voedings- en massapinnen om de bedrading te vereenvoudigen.
Voedingsopties
De print kan gevoed worden via een standaard DC-voedingsconnector of een printkroonsteen (steek 5,08◦mm), wat de nodige flexibiliteit biedt afhankelijk van de opstelling. Een lineaire regelaar van het type TLV76733 verlaagt de ingangsspanning (tot 16◦V) naar 3,3◦V waarmee de ESP32 en aangesloten periferie worden gevoed. Deze LDO kan tot 1◦A leveren en biedt een goede precisie (±1%), een lage ruststroom en beveiligingsfuncties zoals thermische beveiliging en stroombegrenzing. De hoge PSRR (70◦dB bij 1◦kHz) helpt het systeem stabiel te houden, zelfs met ruisende ingangen, en de lage dropout-panning zorgt voor een efficiënte werking, zelfs wanneer de ingangsspanning in de buurt van 3,3◦V komt.
Een andere mogelijkheid om het board te voeden is via een van de USB-connectoren van de S3-DeKit-C-module. Het is ook mogelijk om het board te voeden via de voedingsconnector en het tegelijkertijd via USB op de PC aan te sluiten – bijvoorbeeld om seriële gegevens te verzenden of te ontvangen.
Het schema
Aangezien we de aan te sluiten modules al hebben voorgesteld, is het schema gemakkelijk te begrijpen. Figuur 5 schetst een op een microcontroller gebaseerd systeem rond het ESP32-S3-DevKit-C development board. Voeding wordt geleverd via een 12V-ingang (connector J1), die wordt gestabiliseerd op 3,3◦V met behulp van een low-dropout spanningsregelaar (IC1). Deze gestabiliseerde 3,3V-lijn voedt het ESP32-S3-board en alle andere laagspanningscomponenten in de schakeling, waarbij verschillende ontkoppelcondensatoren (C1...C4) zorgen voor ruisonderdrukking en stabiliteit. De ESP32-S3 fungeert als de belangrijkste verwerkingseenheid en maakt via de GPIO’s verbinding met verschillende perifere componenten.
gebaseerd systeem rond het ESP32-S3-DevKit-C development board.
Draadloze communicatie wordt mogelijk gemaakt met de nRF24L01-module (MOD1), die via SPI-lijnen met de ESP32 communiceert: MISO, MOSI, SCK, CSN, CE en IRQ. Deze aansluitingen zijn beveiligd met 100Ω-weerstanden (R1...R3) en een ontkoppelcondensator (C6) voor stroomstabilisatie. Voor opslag bevat het ontwerp een MSD-11-A microSD-connector (J4) die is aangesloten via standaard SDIO/SPI-lijnen, met extra lijnen voor kaartdetectie en schrijfbeveiliging.
Het systeem ondersteunt uitbreiding van randapparatuur via meerdere GPIO-headers (J7...J10), die elk voeding, massa en signaallijnen leveren aan externe displaymodules, knoppen of apparaten. Een I2C-interface is beschikbaar via Grove- (J6) en Qwiic-compatibele (J5) connectoren, zodat digitale sensoren en modules eenvoudig kunnen worden geïntegreerd. Verder is er een Pmod-connector (MOD2), die een interface biedt voor Digilent-compatibele perifere modules.
De print
De layout van de print is georganiseerd rond de ESP32-S3-DevKitC (zie figuur 6). De connectoren bevinden zich aan de bovenzijde van de print, waaronder de voedingsaansluiting, printkroonsteen, Qwiic-connector en SD-kaartslot. De Pmod-connector bevindt zich aan de onderkant van de print om compatibiliteit met verschillende Pmod-modules mogelijk te maken. De nRF24-module is aan de rechterkant geplaatst en vier connectoren (J7...J10) zijn in het midden-rechts gemonteerd om extra GPIO-toegangsmogelijkheden voor externe modules te creëren. De I2C-printsporen zijn kort en smal, geschikt voor typische communicatiesnelheden, en de koperbanen voor de voeding zijn breder om de stroomverdeling aan te kunnen, met een massavlak dat het grootste deel van het board bedekt.
De behuizing
De print past in een aluminium behuizing met schuifdeksel van 100◦x◦97◦x◦40◦mm [5]. De print wordt in de rails van de behuizing geschoven; het deksel maakt het gemakkelijk om bij de interne onderdelen te komen als dat nodig is. Metalen behuizingen zijn handig voor mechanische bescherming en afscherming, maar ze blokkeren ook hoogfrequente signalen zoals WiFi en Bluetooth. Het metaal werkt als een kooi van Faraday, dus draadloze communicatie met de versie van de ESP32 DevKit met printantenne werkt niet – tenzij u een opening maakt. Daarom is het antennegebied van de ESP32-S3 aan de onderkant van de print geplaatst, zodat er een kleine uitsparing in de behuizing kan worden gemaakt om het signaal een in-/uitgang te bieden. Als u een ESP32 S3-DevKit met een antenneconnector gebruikt – bijvoorbeeld die uit de Elektor-shop – kunt een externe antenne op het voor- of achterpaneel van de metalen behuizing monteren.
De SMA-connector op de nRF24-module is zo geplaatst dat er een gat in de frontplaat kan worden geboord om de antenne extern te monteren (zie figuur 7).
in de frontplaat geboord kan worden om een externe antenne te monteren –
op deze manier blijft de module ook ingebouwd in een metalen behuizing bruikbaar.
Demo-software
Zoals gezegd zullen we in de volgende afleveringen enkele toepassingen en verdere ontwikkelingen presenteren. In de komende ‘draadloze’ editie van Elektor (september/oktober 2025) zullen we bijvoorbeeld software presenteren voor het zenden en ontvangen van audio. Maar we wilden dit artikel niet afsluiten zonder wat eerste demo-software.
Dit betreft een eenvoudige speler voor WAV-audiobestanden. U kunt de software downloaden van de Labs-pagina bij deze audio-transceiver [6]. Bij het opstarten leest de ESP32 de bestanden die zijn opgeslagen op een SD-kaart (geen submappen) en zet alle namen van de WAV-bestanden in een kleine lijst. Daarna wordt het eerste audiobestand uit die lijst afgespeeld. Met een druk op een knop, die is verbonden met GPIO7 van de ESP32 (op J8), wordt het huidige nummer gestopt en komt het volgende nummer aan de beurt. Figuur 8 toont een prototype met de knop. Voor het prototype hebben we geen SD-kaartconnector op de print gebruikt, maar een kleine externe SD-kaartmodule die via SPI is verbonden met de ESP32. Als connector voor de SPI-signalen hebben we de 2x4 ‘nRF24 socket’ gebruikt.
nummer te springen. Voor het prototype hebben we niet het SD-kaartslot
op de print gebruikt, maar een externe kleine SD-kaartmodule die via SPI is verbonden met de ESP32.
Als u de ESP32 via USB op een PC aansluit, kun u commando’s sturen vanuit een terminalprogramma. Een ‘b’ laat de software naar het volgende spoor springen; een ‘a’ naar het vorige. Overigens, omdat onze software (nog) geen MP3-nummers kan afspelen, kunt u een gratis converter zoals gebruiken om uw favoriete MP3-nummers om te zetten naar WAV-bestanden.
De demo-code is modulair. Misschien wel de meest interessante software-module is Stream_I2S.h, die het schrijven van de muziekbytes naar de I2S-interface afhandelt (zie het kader ESP32 I2S API). We hebben met opzet geen gebruik gemaakt van een van de krachtige grote audiobibliotheken – bijvoorbeeld de Arduino Audio Tools van Phil Schatzmann [8]. Ze kunnen flexibel gebruikt worden op veel hardwareplatforms, ze hebben een enorme hoeveelheid mogelijkheden en ze zijn erg goed gedocumenteerd. Aan de andere kant verbergen ze de ruwe muziekdata enigszins voor de gebruiker, en wij wilden laten zien hoe eenvoudig het is om te werken met de bytes die het audiosignaal vertegenwoordigen.
Naast onze eenvoudige Stream_I2S-bibliotheek is er een kleine bibliotheek SDCardFiles.h, die rechtstreeks gebaseerd is op de Arduino-standaardbibliotheken voor toegang tot SD-kaarten. Een zeer kleine Button.h-lib handelt het indrukken van knoppen af.
De belangrijkste lus van het hoofdprogramma is:
◦
uint8_t bBuffer[128];
...
◦
while (SDCardFiles_DataLeftToRead())
{
◦ ◦ ◦ SDCardFiles_ReadInBuffer(bBuffer, 128);
◦ ◦ ◦ I2S_WriteFromBuffer(bBuffer, 128);
◦
...
◦
}
◦
Eerst lezen we 128 bytes van de SD-kaart; daarna schrijven we deze 128 bytes naar de I2S-interface van de ESP32. Daarna hebben we genoeg tijd om te controleren of er op een knop is gedrukt of dat er een karakter is ontvangen via de seriële interface.
Beschouw deze software als een demonstratie van hoe eenvoudig het is om met audiodata te werken. Natuurlijk moet een echte speler worden aangevuld met een display en betere bedieningselementen zoals een draai-encoder.

In de volgende aflevering van deze reeks zullen we proberen om audiodata draadloos te verzenden en te ontvangen. Als voorproefje verwijzen we naar figuur 7, die een prototype van de draadloze ontvanger toont. Tot dan!
Noot van de redactie: Dit artikel (250384-01) verschijnt in de Elektor Circuit Special 2025.
Vragen over het audiotransceiverproject?
Als je vragen hebt over dit artikel of over het audiotransceiverproject in het algemeen, kun je een e-mail sturen naar de Elektor-redactie op editor@elektor.com.

Discussie (0 opmerking(en))