I’m trying to fix an esoteric problem with Sooperlooper keeping track of quantization over tempo changes when it’s also JACK transport master. It performs pretty well with time-stretching the loops, but it totally loses track of where the quantization boundaries are if you change the tempo. With loops, those milliseconds really add up after a few repetitions until things sound mega borked, so I rely heavily on the looper’s ability to not start recording until the next boundary even if I tap the button just a tad early like some kind of human or something.

(An aside, I’m almost positive this unmodified example code in jack_audio_driver.cpp is the problem. I will describe my hypothesis about exactly how the malfunction functions in another blog post — this one is reserved for describing my testing plan).

So, I spent all afternoon yesterday tediously trying to manually reproduce the issue, just to get it fresh in my mind again. I totally forgot about the quantization part of the problem and neglected to test it, and I was spinning my wheels running two instances of the engine (one with my changes and the other without) and manually connecting the GUI to either one, clicking buttons to set the settings. Having forgotten to test the quantization, I was confounded at the parity between the two versions’ performance as I tapped on the ‘t’ key at varying intervals. Yep, I forgot what bug I was even trying to fix. Lawl. What a mess.

I do actually do this for a living, so why the hell wouldn’t I have written some sort of test for it already?

“Eh, something something it’s a loopstation how would I test live audio and all that, it seems like more trouble than it’s worth.”

Okay. Fair enough. I am a green dev. So I’m trying to fix this minor malfunction in Sooperlooper, and I don’t know how to test it and I’m still learning C++ and reading the codebase and I have a day job and I’m not getting very far on this and I still wanna build my magical rig, so lately I’m also playing a lot with SuperCollider.

Hey! Supercollider is designed for audio and has its own internal timing mechanisms. It also talks OSC and MIDI. I can control Sooperlooper, I can send it audio, I can analyze the audio it returns! I have seen (and even partially understood!) code examples which do all of these things. And I need a beginner project.

This is perfect. I will write an automated test for this part of Sooperlooper in SuperCollider. I’ll bet you I can write the whole thing that way, even starting the engines. I can dispense with the GUI entirely. I can configure all the loops and settings, I can tell Sooperlooper to load files over OSC. Aw man, this is fucking RAD.

The timing is great. I’ve just recently started to understand busses and groups and how to route audio in SC, but I’m still looking for the exercise that will force me to understand how to wrangle the language toward a complex end goal. This is it.

Due to this realization, I’m very happy.

Just some notes to myself for later.

Sooperlooper builds if I do like the patch file in the AUR package for sooperlooper does, and change all the includes for sigc++/object.h to sigc++/trackable.h

I’m going to want to research why that is, and whether that change breaks the build on other platforms. For now, I’m gonna get it building so I can start playing with the bugs I actually intended to tackle.

I also have to use these options to ./configure:

CPPFLAGS=-std=c++11 ./configure \
--prefix=/usr \
--with-wxconfig-path=/usr/bin/wx-config-2.8