Using a variable/param to specify sample length on [data]

marde riasi's icon

I need to use a variable (or param) instead of a number to set the length of an array

This does not work "data: variable variable is not defined"

I am working with Daysi Seed (https://github.com/electro-smith/oopsy/tree/dev) So I need to use DATA and SAMPLE objects to play files. I can't use any other object (like buffer).

Graham Wakefield's icon

The [data] object is fixed size by design to avoid dynamic allocation in embedded contexts. See https://cycling74.com/forums/gen~-data-operator-length

So, if you need to work with sub-sections of a [data], it's better not to use [sample]. Instead, if you know the loop size in samples, you can multiply it by a phasor, and feed that into [peek <dataname> @interp linear], which will be equivalent to [sample]. Or similarly, you can look at using [wave].

Regarding Oopsy/Daisy: It's on the roadmap to look at dynamic loading of WAV files into [data], and I'll look at whether we can make the [data] object "fake" a length that corresponds to the WAV, so that e.g. [sample] works as expected. However I'm not sure whether this will be possible, and even if it is, you will still need to pre-define the maximum length of the [data]. Dynamic allocation is not at all likely to happen for a variety of reasons.

marde riasi's icon

I thought we could only use [sample] on Daysi, I will check the other objects

I am currently working on a MIDI-wav player. What I thought was:
1) using an SD card with folders of wav files (one file for each note, one folder for each "instrument")
2) On Daisy select the folder with some user interface
3) When selected the folder, set the [data] length (one for each .wav on that folder)
4) When changing the instrument, reset the [data] objects (or reset the whole patch) before changing the [data] lengths

But I am pretty sure you can only do this using external variables on C++ (not purely on Max gen~). There must be a function on C++ that asks what is the length of the .wav and send that information to the [data] object

For example (on C++):
reset();
folder = Piano; //you must set this with buttons before reset
Len = length(folder/A4.wav); //you get the length of the note A4
Data A4(Len); //this is the code for [data] on gen~, I don't know how you write it on oopsy/C++

Graham Wakefield's icon

That would be dynamically allocating the [data], which isn't possible (nor is it recommended for embedded DSP).

Right now, loading user-selected wav files isn't supported via Oopsy anyway -- at the moment the only way this can work is to preload all the instruments. This is of course a feature on the roadmap to be added, as I mentioned, but there's some technical hurdles to navigate first.

You can work around this if you want by digging into the C++ -- take a look at the genlib_daisy.h for the wav loading code, and genlib_daisy.cpp for how you might interact with a [data] object. It's not going to be simple though.

I'm also not sure that a wav per note is a good idea. I'd be suggesting storing an instrument in a single WAV file, much like a wavetable bank, and computing the offsets needed for each note. We've found there's some overhead and delay with loading many WAV files, so having a folder of tons of note files could be tricky. How many notes will you have per instrument? If you are going full 128-note range, that's a lot of files, and a lot of data... The Daisy has a lot of memory, but there's a performance cost to consider. I'm not sure how feasible this is.

Also, depending on what you're doing, you might consider a one-shot transient + looping wavetable approach, which would make the instrument data a lot smaller.