Show HN: Porting Mutable Instruments to Arduino, RP2040

5 days ago 1

Ports of mutable intstruments eurorack code to arduino.

Current status, 15.05.2025:

  • braids works well
  • tides works well, or so I believe
  • rings is working well with a polyphony of 3
  • elements struggles a bit and I'm just favouring rings
  • plaits has voices that are not rendering properly but about 2/3s work fine.

This port was possible because of the work of Volker Boehm to bring MI modules to supercollider: https://github.com/v7b1/mi-UGens Very cool.

A simple sketch with no other io other than PWM pin 22 is located in BraidsEngines. It cycles through all voices with random parameters every 3 seoncds.

To use the sketch, copy the STMLIB and BRAIDS directories to you ~/Arduino/libraries folder, open the BraidsEngines sketch change

#define PWMOUT 22

to match whatever pin your using and

choose 250mHz overclocking (well, 200 should do it too, but, 250 is stable) and optimize. Then install it on your pico.

You should hear it step through the patches making small changes as it goes.

The STMLIB, BRAIDS and PLAITS directories can be placed in your Arduino/libraries/ folder and used as follows, for braids & plaits:

#define MI_SAMPLERATE 96000.f #define BLOCK_SIZE 32 // --> macro_oscillator.h ! #define SAMP_SCALE (float)(1.0 / 32756.0) #include <STMLIB.h> #include <BRAIDS.h> typedef struct { braids::MacroOscillator *osc; float samps[BLOCK_SIZE] ; int16_t buffer[BLOCK_SIZE]; uint8_t sync_buffer[BLOCK_SIZE]; } PROCESS_CB_DATA ; char shared_buffer[16384]; const size_t kBlockSize = BLOCK_SIZE; struct Unit { braids::Quantizer *quantizer; braids::SignatureWaveshaper *ws; bool last_trig; // resampler //SRC_STATE *src_state; PROCESS_CB_DATA pd; float *samples; float ratio; }; static long src_input_callback(void *cb_data, float **audio); struct Unit voices[1]; // plaits dsp #include <STMLIB.h> #include <PLAITS.h> plaits::Modulations modulations; plaits::Patch patch; plaits::Voice voice; char shared_buffer[16384]; stmlib::BufferAllocator allocator; //float a0 = (440.0 / 8.0) / kSampleRate; //48000.00; const size_t kBlockSize = plaits::kBlockSize; plaits::Voice::Frame outputPlaits[ plaits::kBlockSize]; struct Unit { plaits::Voice *voice_; plaits::Modulations modulations; plaits::Patch patch; float transposition_; float octave_; short trigger_connected; short trigger_toggle; char *shared_buffer; void *info_out; bool prev_trig; float sr; int sigvs; };

See the included sketches.

Curently, plaits is still a bit noisy but braids is really, really nice.

Read Entire Article