Very cool,
This is why I wish ChucK either had an Array UGen or if normal ChucK
arrays could be treated like UGens somehow. Coming from other
languages (Pd, Csound for example) one becomes very used to arrays (or
ftables) being part of the signal chain. Using LiSa as a workaround
is pretty rad. The ChucK wish-list keeps growing.
Later,
Kurt
2010/11/19 Kassen
Hey Lars!
this sounds interesting, but I can't follow your steps. Have you got an example of this idea?
Here we go; -----------8<----------------------------- LiSa l => dac; //more time here means more resolution //here more time actually prevents LiSa's interpolation from cleaning our intended dirt second => l.duration; //only calculating constants once (l.duration()/ samp) $ int => int NUM_SAMPS; 2.0 / NUM_SAMPS => float STEP_SIZE; //straight ramp from -1 to 1 for (int x; x< NUM_SAMPS; x++) { l.valueAt ( -1 + (x * STEP_SIZE) , x::samp); }
//get signal's range between 0 and 1. //slightly less, actually, to avoid edge-case glitches SinOsc signal => Gain mix => l; .49 => signal.gain; Step offset => mix; .5 => offset.next; //use the LiSa to map the signal to new values 1 => l.sync; //off we go. you should hear a pure sine here 1 => l.play; 5::second => now; //now we start crushing. 6 => int bits; //the "-1" is for above and minus zero //again we use a constant to minimise per-value processing Math.pow ( bits - 1, 2) => float QUANT; //cheap&dirty quantisation //we take the original value, multiply it by the number of steps in our chosen bit-depth //then round this by casting to int //finally dividing it again to get back in the original range //and putting the value back for (int x; x< NUM_SAMPS; x++) { l.valueAt ((l.valueAt(x::samp) * QUANT) $ int / QUANT , x::samp); }
//and there we go again 5::second => now; ---------------------------------------8<-------------------------------- I hacked this up quite quickly, there are bound to be some issues in the details, especially in the rounding. At the very least this should illustrate the technique of using LiSa as a waveshaper for arbitrary shapes. Note that "signal" is a placeholder for any signal you'd like to process, but it must not (initially) exceed the range of -1 to 1 (normal UGens conform to this, as should the ADC) or the result will wrap (that too might sound cool...). Of course using a oscillator here makes no sense; if a plain oscillator would do you are better off using a wavetable set to some suitably lo-fi single cycle wave instead of actual bitcrushing. Another likely issue here is that LiSa is trying to prevent the exact kind of artefact we are trying to create by using interpolation. I'm fairly sure the effect of that can be minimised by extending the size of the buffer and hence it's resolution. This might be a interesting element to play with. Hope this is at least a decent starting point for further experimentation. No warranties, no refunds, please mind your neighbours, pets and speakers. Have a noisy weekend! Kas. _______________________________________________ chuck-users mailing list chuck-users@lists.cs.princeton.edu https://lists.cs.princeton.edu/mailman/listinfo/chuck-users
-- -------------------------------------------------- www.kurtkotheimer.com --------------------------------------------------