porres / pd-else

ELSE - EL Locus Solus' Externals for Pure Data
Do What The F*ck You Want To Public License
290 stars 36 forks source link

add compiled band limited oscillators #1288

Open porres opened 2 years ago

porres commented 2 years ago

hopefully with support for phase modulation and hard sync

@timothyschoen is also interested in this one

porres commented 2 years ago

why not @brbrofsvl? :)

porres commented 2 years ago

I've also noticed that the PolyBLEP oscillators don't take negative frequencies yet.

I noticed the object doesn't do that, but you're saying it can't. Why? Can't phase just run backwards?

if you'd like I could create a very minimal copy of pd-creb's impulse shape?

Looks good, you already have a working version of creb in plain C, right? Where is it?

I think BLIT might be more suited for this than polyBLEP.

why though?

porres commented 2 years ago

bandlimited wavetables are another entire topic/implementation imo (personally I've been wanting to implement this one.. I think serum uses a variation of it http://www.mp3-tech.org/programmer/docs/resampler.pdf)

looks complicated, let me know if you want to collaborate with this one for ELSE ;)

porres commented 2 years ago

@timothyschoen, creb's seems to be miniBLEP, not BLIT, for reference: http://www.martin-finke.de/blog/articles/audio-plugins-018-polyblep-oscillator/

timothyschoen commented 2 years ago

I see I already "fixed" negative frequencies, by doing fabs(frequency). I think this is not a correct solution though?

On this old commit you can find the creb code converted to C:

https://github.com/timothyschoen/pd-else/blob/435cc07f274357a930cf4397b3f4a6dde6fb014d/Classes/Source/blosc%7E.c

Good to know, about creb using minBLEP. The difference is that minBLEP is supposed to be more precise whereas polyBLEP is faster, so the old version I linked is also still a valid option (although the license is not to your liking). Personally I think that having a very fast "good enough" object is very useful, especially when an oversampled version is also included. Also, the code for my new version is much cleaner.

porres commented 2 years ago

I see I already "fixed" negative frequencies, by doing fabs(frequency). I think this is not a correct solution though?

nope, it needs to run backwards

porres commented 2 years ago

On this old commit you can find the creb code converted to C:

https://github.com/timothyschoen/pd-else/blob/435cc07f274357a930cf4397b3f4a6dde6fb014d/Classes/Source/blosc%7E.c

but this is not actually creb's original, right? I don't see the bipolar impulse. I thought you had somewhere the plain original just converted to C, do you?

timothyschoen commented 2 years ago

but this is not actually creb's original, right? I don't see the bipolar impulse. I thought you had somewhere the plain original just converted to C, do you?

It might be missing some things, but I can reconstruct that pretty easily if you're interested.

nope, it needs to run backwards

I'll look into this tomorrow, I think I just have to fix the phase wrapping function.

porres commented 2 years ago

It might be missing some things, but I can reconstruct that pretty easily if you're interested.

Please :)

porres commented 2 years ago

I'll look into this tomorrow, I think I just have to fix the phase wrapping function.

check how I do it in my non band limited oscillators

timothyschoen commented 2 years ago

Pull request has been sent!

timothyschoen commented 2 years ago

I see that one of the pulse waves is already in there, it's only missing pulse2. It uses the same processing function, but with different variables. You can set it up like this:

      x->x_ctl.c_phase_inc_scale *= 2;
      x->x_ctl.c_scale = 1.0;
      x->x_ctl.c_scale_update = -1.0;
      dsp_add(blosc_perform_pulse, 4, &x->x_ctl, sp[0]->s_n, sp[0]->s_vec, sp[1]->s_vec);
porres commented 2 years ago

what do you mean? I was hoping you'd send me the original blosc~ code in plain C with the adaption you've made.

timothyschoen commented 2 years ago

Here you go!

blosc~.c.zip

timothyschoen commented 2 years ago

https://user-images.githubusercontent.com/44585538/180656772-71bcdbaf-6d0c-47c1-8165-c8b8a5f26b27.mov

4 sawteeth head-to-head

porres commented 2 years ago

cool :) so, blosc~ is creb's, blosc~ is yours with polybleb, right?

I'm still thinking what I should do with the old ones like [bl.saw~]... I really want the new ones to have this name, so I'll either delete the old ones or rename them (probably best)

timothyschoen commented 2 years ago

Correct!

Personally, I'd leave the old bl.* objects the way they are, and replace the normal oscillators with band-limited oscillators. There's really no situation I could think of where you'd want non-bandlimited oscillators. Max also uses band-limited oscillators as the default, a big advantage is that beginners can create synths without having to think about this stuff. Also, if you want a non-bandlimited oscillator, why not simply create them with a phasor~? The performance of the polyBLEP oscillators is also good enough to serve as a default oscillator.

I would leave the old bl.* oscillators in there because they might still perform slightly better when doing fm/sync/phasemod. If you replace default saw~ with the bandlimited saw though, you could also reduce the amount of oversampling, 4x would probably be enough.

edit: Or leave the old oscillators in, but with a "raw" prefix, like raw.square~

porres commented 2 years ago

There's really no situation I could think of where you'd want non-bandlimited oscillators.

LFOs

timothyschoen commented 2 years ago

Doesn't matter: If the frequency is very low, there will be so little aliasing that there won't be any "ripples" caused by the bandlimiting. The only benefit would be a small performance improvement.

porres commented 2 years ago

also, objects like [impulse~] are used as triggers, [pulse~] is gate...

timothyschoen commented 2 years ago

That's a good point

porres commented 2 years ago

there will be so little aliasing that there won't be any "ripples"

I never tested that, but it's something I'm not comfortable in doing knowing what I know (without test prooving). It doesn't seem elegant one way or another. Also, seems like you wanna use those for high frequencies as well, as in phase modulation and stuff.

SuperCollider has things like "LFSaw". I just thought I'd make these as default and name the band limited ones instead. I just think we need both and we have to distinct them one way or another.

porres commented 2 years ago

I guess people should be aware of this basic digital synthesis thing, that oscillators have to be band limited. It's not something I think it's too much to require from people using this kind of tool...

porres commented 2 years ago

@timothyschoen , your last commit for negative phase, somehow, screwed up phase modulation

timothyschoen commented 2 years ago

I also attempted to fix the 1 sample phase delay, I might have messed up there. I'll check it out

Edit: I see that the phase_dev variable just never gets used... whoops... PR coming soon

porres commented 2 years ago

I also attempted to fix the 1 sample phase delay, I might have messed up there. I'll check it out

let me know when this is ok so I can keep working on this

porres commented 2 years ago

made a simple last commit for some cosmetic changes, please keep it up with the current master

porres commented 2 years ago

I just broke bl.osc~ down into pieces, as bl.tri~ / bl.square~ / bl.saw~ / bl.saw2~ / bl.vsaw~

I also included bl.imp~ based on creb/blosc~, I just need help now figuring out how to implement hard sync and phase modulation in the new bl.imp~

porres commented 2 years ago

I just need help now figuring out how to implement hard sync and phase modulation in the new bl.imp~

next I should also work on bl.imp2~ for similar things and adapt it to have a pulse width parameter

timothyschoen commented 2 years ago

I see there's a new deadline, august 5th.

bl.imp2 should be very simple, the implementation is already there.

I think hard sync and phase modulation is difficult, but it can be done. As with the polyblep oscillators this will only strongly reduce aliasing. I'm trying to implement it right now, but it's not working yet.

Is august 5th also the deadline before which I should finish the [note] property box as well?

porres commented 2 years ago

I see there's a new deadline, august 5th.

not really :) this is flexible, but well, sorting bandlimited oscillators and providing an acceptable bicoeff is what's needed before an update.

[note]'s properties box would be great, and maybe simple to do it and I hope I can figure out how to do it myself, in other words, that you teach me later how it works... comments in the code should do the trick.

After that, I actually need help with bicoeff and the tcl/tk code is what's really challenging. I have another friend who might be able to help me with that.

porres commented 2 years ago

if all goes weel, I could also put number/number~ into the new release so we have it in plugdata right away as well. I've been working on number~ today. I wish to remove all dependencies from "iemguis.h".

timothyschoen commented 2 years ago

if all goes weel, I could also put number/number~ into the new release so we have it in plugdata right away as well. I've been working on number~ today. I wish to remove all dependencies from "iemguis.h".

agreed, that would be better. For [number~], it should be pretty simple to just copy the functions over.

The [number] code is unfortunately a bit messier, let me know if you need help with that. I left some of the fields in the object’s state empty so I could use more iemgui stuff, that should be cleaned up.

porres commented 2 years ago

For [number~], it should be pretty simple to just copy the functions over.

it's actually becoming a nightmare and I might restart from scratch :)

porres commented 2 years ago

I think hard sync and phase modulation is difficult, but it can be done (...) I'm trying to implement it right now, but it's not working yet.

@timothyschoen, how is that coming out?

timothyschoen commented 2 years ago

I didn't figure it out yet :(

I also don't have much time to look at it right now, if you're planning to release RC3 soon, you could also keep the original bl.imp~ for now...