Download free music MP3s on genuine quality, the world’s largest online music catalogue, powered by your scrobbles. Free listening, videos, photos, The world’s largest online music catalogue, powered by your scrobbles. Free listening, videos, photos, stats, charts, biographies and concerts. stats, charts, biographies and concerts.
Saturday, April 12, 2025
Raspberry Pi Pico Synth_Dexed – Revisited
I thought it was time I took another look at my Raspberry Pi Pico Synth_Dexed. I've a couple of main aims with coming back to this project: Update the build for the latest Pico SDK and Synth_Dexed. See what is involved in getting it running…
I thought it was time I took another look at my Raspberry Pi Pico Synth_Dexed. I've a couple of main aims with coming back to this project:
Update the build for the latest Pico SDK and Synth_Dexed.
See what is involved in getting it running on an RP2350.
See if a simple I2C display can be added and possibly an encoder or other controls.
Actually document the architecture!
The current hardware is described in detail in Raspberry Pi Pico Synth_Dexed? – Part 5 and supports serial and USB MIDI, I2S or PWM audio output, voice selection (over MIDI) and up to 16 note polyphony if using an overclocked (to 250MHz) RP2040 based Pico and lower sample rate.
Warning! I strongly recommend using old or second hand equipment for your experiments. I am not responsible for any damage to expensive instruments!
If you are new to microcontrollers, see the Getting Started pages.
Core Updates
Since I first put the PicoDexed together, V2 of the Raspberry Pi Pico SDK has been released. There aren't many changes, but as noted by okyeron, an additional include file is required in main.c.
But as I was updating things, I also found a number of changes to Synth_Dexed too that broke the build. The most irritating of which was including a definition of DEXED_SAMPLE_RATE which now clashes with my own definition. I've gone through and changed a number of DEXED_ definitions to PICODEXED_ to avoid that in the future too.
A few other changes have also been introduced, which have necessitated an update to my diff file for Synth_Dexed/src/Dexed.cpp.
But on the whole, there was nothing major in the end. This has all been uploaded to GitHub as a v0.02.
PicoDexed Architecture
I had to go back and attempt to reacquaint myself with what I'd done last time, so as part of that I've drawn out a rough architecture diagram as shown below.
This expands on the design notes I've already written up in Part 3.
The key principles are as follows:
Core 0 is used for all IO and is largely driven by MIDI events received over serial or USB.
Core 1 is used for all audio processing and is run continually using the Pico's audio driver (either I2S or PWM) to use a callback function to fill a buffer with samples to be played. The samples come from Synth_Dexed.
All synthesis parameters (including keyup/down events for playing notes) is handled within picoDexed in response to the MIDIMessageHandler receiving MIDI messages from the MIDIParser.
Looking at this, I should be able to include some additional IO handling in the main Process loop of picoDexed that runs on core 0.
I2C Displays
Hunting around for libraries to support an SSD1306 display with the Pico SDK, so far I've found four options:
pico-examples - has an example app that can put simple text or an image on an SSD1306. Note this isn't created as a library that could be used however - it is all in a single example.
sharkis/pico-ssd1306 - what appears to be a couple of files that can be included in your own code. It is pretty low-level with minimal options for any text or graphics and there is no documentation or licensing information as far as I can see.
daschr/pico-ssd1306 - a higher level interface that provides basic graphics primitives and simple font support. MIT license. Again a couple of files to include in your project.
Harbys/pico-ssd1306 - the most complete support I've found so far. What I'd consider to be a "proper" library with what seems to be good documentation and a wide range of usage options.
Whilst tempted to go with the "proper" library, it might be a little over the top for what I really need right now, and I don't want to include an additional third-party GitHub link in my code at this time.
So I'm going to try daschr's pico-ssd1306 as I can just grab the files, maintain the license information, and include it directly into my code.
To include this code in the build I've done the following:
Created a libs area and copied in the files: ssd1306.c, ssd1306.h, font.h
The first is a more complete library, the second more "bare bones". The last seems more of an example rather than a reusable object.
I was initially inclined towards the second which seemed likely to be easier to integrate into my own code, but as it was pretty low level and required a fair bit of glue around it.
I've had to change how voices are selected slightly to ensure the display, MIDI BANKSEL/PC and encoder can stay reasonably intuitive.
I've used the following logic:
IF BANKSEL/PC both received then treat as Bank=0-7; Voice=0-31.
IF PC on its own, then treat as Voice=0-127 across Banks 0 to 3.
IF UI changes voices, then treat as Bank=0-7; Voice=0-31.
In each case the display shows the current bank and voice number in 0-7/0-31 format.
So just to be clear, MIDI Program Select on its own now (so 0..128) will always only select from the first four banks of 32 voices each. This is a change from the previous version which would allow PC to select based on the currently selected banks and the three following banks.
The encoder will automatically switch from one bank to the next, and wrap around at either end, so is able to select all voices across all installed banks.
Raspberry Pi Pico PIO Use
One issue to keep an eye on is PIO state-machine use.
I'm still getting my head around PIO (I've just not really devoted any significant time to figuring it out yet) but as I understand things, each PIO instance has a 32 instruction memory which is shared across four state machines.
So if there are several programmes to run and they all combined fit in the 32 instruction memory, then they could all use the same PIO instance whilst being attached to different state machines.
But if there are two vastly different programs to be running then it may be that they have to be split across the two PIO instances. But there can still be up to four instance of each program, one for each state machine in a PIO instance.
The I2S audio driver uses PIO to implement I2S. As far as I can see which PIO to use is determined by the following definitions:
Expanding now on the table from Part 5, updated with the above, now gives the following GPIO usage map.
GP0
Debug UART TX
GP1
Debug UART RX (unused at present)
GP2
SDA (I2C bus 1) OLED display
GP3
SCL (I2C bus 1) OLED display
GP4
MIDI TX (unused at present)
GP5
MIDI RX
GP6
Rotary Encoder A
GP7
Rotary Encoder B
GP8
Rotary Encoder Switch (not used)
GP9
I2S Data (DATA, DIN)
GP10
I2S Bit Clock (BCK)
GP11
I2S "Left/Right" Clock (LCK, LRCK, LR_CLOCK)
GP20
Optional: PWM output
GP22
Optional: Mute pin for the Pimoroni Audio Pack (not used)
VSYS
5V power to DAC and OLED display (if required)
3V3_OUT
3V3 power to MIDI IN and encoder (if required)
GND
PicoDexed on a Breadboard
Closing Thoughts
I feel like this is really starting to get interesting now. I have a few choices to make now - do I attempt to go for a more complete menu system similar to MiniDexed, or do I stay with MIDI control and basic voice selection as it is now?
Future enhancements might include:
It will be interesting to see what supporting the RP2350 could bring.
It would be useful to be able to set the MIDI channel - either in menu, or perhaps more ideally in hardware somehow (e.g. switches, resistors on an ADC, etc).
Act as a USB host for USB MIDI devices.
In the video I've hooked it up to a serial MIDI controller and am just cycling through some of the voices showing how the UI works.
No comments:
Post a Comment