Work has been going well on my sampler engine. It’s really coming together now. I can say with some certainty that it will be released this summer – though I acknowledge that that is still very vague! I’ve actually been working on this project for nearly 2 years now – on an off as my full time project. It certainly feels like a long time, but has been enjoyable. A lot of this time as been spent learning how to actually program this properly, skills that I will take forward in anything that I do. The 2 main areas that I have tackled recently have been the library file format, and optimisation (and countless non-noteworthy fixes and improvements). I’ll go into some technical details of these 2 areas later on in this post.
The engine is quite versatile, and while it’s not really anything groundbreaking in terms of new features, I think this product has a lot to offer. It’s going to be the engine for new FrozenPlain libraries, and for that task I think it excels. It’s fast, modern and lightweight and contains all the features needed for multisampled instruments and creative sound design. It allows you to get straight to the point – the sounds and the playability. With the help of some excellent sound designers I’ll hopefully be able to release quite a few libraries for this engine. I’m getting excited to start using this in my music!
Library File Format
I’ve been working on a custom file format for this engine, which can contain a whole library into a single file. Packed inside it is all of the losslessly compressed audio, all the data on how the samples should be played, and various other info. The format is designed for speed and for portability. It’s based around data chunks, similar to the RIFF file format. Each data chunk has a header which contains the specifics of what the chunk contains. Then for the engine (which loads up these files), it’s usually just a matter of reading the chunk headers and copying the data chunk into RAM. For the audio files, we only want to load these when the instrument is selected – to save RAM, so this loading is done only when needed, and the loading is multithreaded for speed. A neat trick that can be done here is to share this sample pool across multiple instances of the plugin. So if you load up the engine multiple times in your DAW – they will all read from the same sample pool. Quite a lot of the work around loading libraries involved really going into the nitty gritty details of multithreaded programming, something that has to be done correctly, particularly for something like an audio plugin where we must be careful not to stall the audio thread.
The other area that I have spent quite a bit of time is on, is optimising the audio processing. Again, the solution here is quite often to do with multithreading. For this engine, there was an immediate obvious candidate for multithreading – the voices. Software synthesisers almost always have a concept of voices – which can be considered to be like a pipeline of audio processing (one or more are normally created per MIDI note pressed). These pipelines are not at all related to each other until they are mixed together towards the end. In the case of this engine they are mixed into 1 of 3 layers, and then those layers mixed into the master pipeline which applies the audio effects. You can see why they make good candidates for multithreading – not related to one another, and there are multiple of them doing the same thing. Changing that part to be multithreaded was the biggest gain for this engine, although just today I was working on a bug related to this so still some ironing out to do!