Thanks, added in Faust repo here: https://github.com/grame-cncm/faust/commit/71b8f236e0aaa89e172d90906fd18c26e29cfbad
Stéphane > Le 16 sept. 2025 à 15:52, ga <[email protected]> a écrit : > > Hello Stéphane and all, > > here is the finalized code. > ( Pickup paramter hidden, highpass removed, reverb replaced with > parameterless Dattorro default, > more clear parameter names and description, rearranged order of > convolution tabs and distortion > saves CPU, and a resonant EQ added for weak formants). > > From my side it could now be added to the examples, or used and > altered in any way. > > Gabriel > > > > [code] > > // Modulation synthesis with sparse convolution filter and distortions. > // ------------------------------------------------------------------- > // > // A "3D" oscillator oscillating on x,y,z axis, with the radius of x,y > used as waveform, > // very similar and related to FM / AM. > // > // The y axis oscillation is set by MIDI pitch, x and z are detuned by > simple just tuned ratios. > // Feedback acts on the individual sine oscillations (giving a > sawtooth like waveform). > // > // Three weighted copies with time varying shifts are summed in a > lossy integrator > // (sparse convolution), followed by a peak resonance filter and shaped by > // an internal pick-up like distortion and an asymmetric polynomial. > // > // The convolution tabs give a (variyng) triangle impulse response if > integrated twice, > // with a -12 dB/octave rolloff and regular notches. > // Here only one integrator is used. > // > // The envelope is hard wired to the oscillation amplitudes and the > rise time of the filter. > // > // An LFO is wired to pitch. > // > // A resonant EQ and the Dattoro Reverb from the Faust libary are > added as effect on the sum. > // > // > // Inspired by the history of sound synthesis, namely Trautonium, Mini > Moog, Phase Modulation Synthesis, > // Variophon Wind Instrument Synthesizer, Physical Modeling, and the > work of Thomas D. Rossing. > // > // References: > // Kot, Vítězslav. (2006). DIGITAL SOUND EFFECTS ECHO AND REVERB BASED > ON NON EXPONENTIALLY DECAYING COMB FILTER. > // https://en.wikipedia.org/wiki/Variophon > // Parker, Julian & Zavalishin, Vadim & Le Bivic, Efflam. (2016). > Reducing The Aliasing Of Nonlinear Waveshaping Using Continuous-Time > Convolution. > // Nicholas G. Horton, Thomas R. Moore. (2008). Modelling The Magnetic > Pickup Of An Electric Guitar. > // > https://www.musicdsp.org/en/latest/Effects/86-waveshaper-gloubi-boulga.html, > see comment from 2005-09-22 01:07:58 > // Frei, Beat. Digital Sound Generation I & II, ICST Zurich University > of the Arts > // Smith, J.O. Physical Audio Signal > Processing,http://ccrma.stanford.edu/~jos/pasp/, online book, 2010 > edition > > declare options "[midi:on][nvoices:8]"; > declare options "[-vec]"; > declare name "Paradigma_9"; > declare version "1.0"; > declare author "gabriel"; > > import("stdfaust.lib"); > > > // Frequency Ratios table > frtonum = waveform{1,16,9,6,5,4,7,3,8,5,7,15}; > frtodiv = waveform{1,15,8,5,4,3,5,2,5,3,4, 8}; > > // MIDI > // minimum velocity > minvelo = 1 / 32; > midigrp(x) = hgroup("[1]MIDI",x); > f = nentry("freq[hidden:1]",200,40,2000,0.1); > kmidi = nentry("key[hidden:1]",69,0,127,1); > bend = ba.semi2ratio(hslider("bend[hidden:1][midi:pitchwheel][style: > knob]",0,-2,2,0.01)); > gain = nentry("gain[hidden:1]",0.6,0,1,0.01)<:* : _*(1-minvelo):_+ minvelo; > master = hslider("volume[midi:ctrl 7]",0.6,0,1,0.01); > gate = button("gate[hidden:1]") ; > > // Oscillator Parameter > rtogrp(x) = hgroup("[2]Oscillator",x); > rto1sel = rtogrp(hslider("[1]x[style:knob]",-12,-36,36,1)); > rto2sel = rtogrp(hslider("[2]z[style:knob]",19,-36,36,1)); > fbka = rtogrp(hslider("[3]Feedback[style:knob]",0.15,0,1,0.01)<:*:*(1/ma.PI)); > detune = rtogrp(hslider("[4]Detune[style:knob]",0.125,0,0.5,0.005)/ma.SR); > > // LFO and Envelope Parameter > lfogrp(x) = hgroup("[3]Envelope & LFO",x); > enva = (lfogrp(ba.db2linear(hslider("[1]A[style:knob]",20,15,66,1) )/1000)); > envd = (lfogrp(ba.db2linear(hslider("[2]D[style:knob]",74,26,100,1) > )/1000)*envpscal); > envs = (lfogrp(hslider("[3]S[style:knob]",0,0,1,0.01) )); > envr = (lfogrp(ba.db2linear(hslider("[4]R[style:knob]",50,26,100,1) > )/1000)*envpscal); > lfof = lfogrp(hslider("[5]LFO Hz[style:knob]",3,0.1,12,0.1)); > lfvibra = lfogrp(hslider("[6]Vibrato[style:knob]",0.125,0,1,0.01))<:*; > > env = en.adsre(enva,envd*envpscal,envs,envr*envpscal,gate); > envg = env:_* gain; > > lfosn = qsin(mphasor(lfof/ma.SR)); > > // Triangular Filter Parameter > fltgrp(x) = hgroup("[4]Filter",x); > wid = fltgrp(hslider("[1]Rise[style:knob]",3,1,9,0.001)):2^_:1/_; > edge = fltgrp(hslider("[2]Fall[style:knob]",6,1,9,0.001)):2^_:1/_; > fiq = fltgrp(hslider("[3]Q[style:knob]",1,0.5,3.87,0.01))<:*; > drive = fltgrp(hslider("[4]Drive[style:knob]",-12,-12,30,0.1)):_/20.0:10^_; > > // Modulation Frequency Ratios > rto1oct = rto1sel / 12 : floor; > rto1semi = rto1sel + 36 : _% 12; > rto1a = frtonum, rto1semi : rdtable; > rto1b = frtodiv, rto1semi : rdtable; > rto1 = (rto1a/rto1b)*(2^rto1oct); > rto1r = min((1/ rto1),1); > > rto2oct = rto2sel / 12 : floor; > rto2semi = rto2sel + 36 : _% 12; > rto2a = frtonum, rto2semi : rdtable; > rto2b = frtodiv, rto2semi : rdtable; > rto2 = rto1*(rto2a/rto2b)*(2^rto2oct); > rto2r = min((1 / rto2),1); > > // Pitch > lg2f = ma.log2(f/440); > stretch = 0.0333*lg2f; > envpscal = ( - 3 * lg2f ):ba.db2linear; > fplus = f*bend + lfosn* lfvibra*f * 0.5/12*envg + stretch; > > w = f/ma.SR; > w2 = rto1 * w; > w3 = rto2 * w; > wplus = fplus/ma.SR; > > fbk1 = fbka*(0.5 -w)^4; > fbk2 = fbka*(0.5 - w2)^4*rto1r; > fbk3 = fbka*(0.5 - w3)^4*rto2r; > > // Modulation Reduction Per Frequency > redux1 = ((3.3 -((rto1+1)*w) )/3.3),0: max:_^3; > redux2 = ((3.3 -((rto2+1)*w) )/3.3),0: max:_^3; > modep = envg; > modep1 = envg * redux1 *rto1r * gain ; > modep2 = envg * redux2 *rto2r * gain ; > > // Sine Oscillator > wrap(n) = n-( floor( n +0.5)) ; > // Bhaskara I based approximate sine curve > qsincurve(x) = 1 - ( (x*x)<: *(1.2253517*16),(_<:*:* (-3.60562732*16)):>_ ); > qsin(x) = x+(0.5): wrap <: (abs:-(0.25):qsincurve),_:ma.copysign; > // Feedback Depth Reduction Curve > fbcurve (x)= x:abs:-(1) <:^(3):_,(x):ma.copysign; > > // Oscillator > mphasor(fw) = (+(fw) ~ (wrap)); > oscsn(fw, off) = mphasor(fw) + off:qsin:+~*(0.5); > osc1(fw, off) = ((fw),+(off):(oscsn)) ~ (*(fbk2):fi.pole(0.5):_*fbcurve(fw)); > > // 3D to 2D radius > oscy(fw, off) = (osc1(fw, off )*osc1(fw*rto2+2*detune,0.75 + > off)*modep2)*modep; > oscx(fw, off) = (osc1(fw*rto1+detune,0.25 + > off)*osc1(fw*rto2+2*detune,0.25 + off)*modep2)*modep1; > oscxy(fw, off) = (oscy(fw, off)<:*),(oscx(fw, off)<:*):+:sqrt; > > // Pick-Up like Distortion > // distance : > pickd = 0.25; > pickup(x, pickd) = x, > // normal for in < 1.2e-4 > ( x,(x^2:_+pickd:_^(3/2)):/ ), > // ILO: > ( pickd^(3/2) / ( sqrt(x*x + 1)):ma.neg:_+ pickd^(3/2) ): > // select > ba.if( (_:abs:_<= 1.2e-4), _, _ ):_*(pickd^(4/3)); > > // Basic Synthvoice, modulated Oscillations > synthvox(fw, ph2, ph3, g1, g2, g3) = (oscxy(fw, 0):_*g1), (oscxy(fw, > ph2):_*g2),(oscxy(fw, ph3):_*g3):>_ : fi.zero(1.0)<:_,(pickd):pickup; > > > // Triangle > // reduce width with frequency > widredux = w <:+:_^3:1.0-_; > // diff to max f in octaves, reduced for higher octaves > dwo = ( 0.25 / wid ):max(_, 1): ma.log2: ma.inv: _*widredux: ma.inv; > // falling edge > egderto = edge / wid; > wid2 = wid * (2^(dwo * (1-envg ))): > _* (2^(dwo * (1- gain ) )): > min( _, 0.25): max( _, 4 / (ma.SR/fplus)); > wid2e = edge: min( _, 0.25): max( _, 4 /(ma.SR/fplus)); > > fiw = wplus/wid2; > fiwtail = wplus/wid2e; > // triangle coefficients > apg0 = fiw; > apg1 = - apg0 - fiwtail; > apg2 = fiwtail; > // integration freq > igpole = 1.0-5.0/ma.SR; > resf = (fplus /( wid2 +wid2e) ): min( _, (0.249 * ma.SR)); > > // Asymmetric Shaper x - 0.15x²-0.15x³ > tubicclip = _:min(_, (1.19419)):max(_,(-1.86086)); > tubicilo(x) = x, > // normal for in < 1.2e-4 > ( x - 0.15*(x^2)-0.15*(x^3) ), > // ILO: > (( 0.5*(x^2) - 0.05*(x^3) - 0.0375*(x^4) ),(x <:_,_':- > :_<:(abs:max(_,1.2e-4)),(ma.signum):ma.copysign):/): > // select > ba.if( (_:abs:_<= 1.2e-4), _, _ ):fi.dcblockerat(10.0); > > > // Sound > process = synthvox(wplus, wid2, wid2e, apg0, apg1, apg2): > fi.dcblockerat(10.0): fi.pole(igpole) : fi.svf.peak( resf, fiq) : > _*drive: tubicclip: tubicilo:_*(1/drive); > effect = _ * master:preeq( lsf,lsgain, b1f, eqq2, eqg2, b2f, eqq3, > eqg3, hsf, hsgain) <:_,_:re.dattorro_rev_default; > > > > // > --------------------------------------------------------------------------------------------------------------- > // Resonant EQ for instrument corpus, based on SVF > eqgrp(x) = hgroup("[5]EQ",x); > lsgain = eqgrp(hslider("[1]Low Gain[style:knob]",3,-18,18,0.25)); > b1f = eqgrp(hslider("[2]Split F Low[style:knob]",-0.5,-1,1,0.05)) > :(2.0)^_:_*360; > b1gain = eqgrp(hslider("[3]Band 1 Gain[style:knob]",4.5,-18,18,0.25)); > b2f = eqgrp(hslider("[4]Split F > Hi[style:knob]",-0.5,-1,1,0.05)):(2.0)^_:_*720; > b2gain = eqgrp(hslider("[5]Band 2 Gain[style:knob]",4.5,-18,18,0.25)); > hsgain = eqgrp(hslider("[6]Hi Gain[style:knob]",-3,-18,18,0.25)); > > // Q and gain of middle bands are scaled simultanously, with > saturation curve on gain, > // max gain is reduced from the output. Bands are spaced in octaves by > default. > lsf = b1f *0.5; > hsf = b2f * 2; > gcurve( gain, gainrange) = abs(gain/gainrange) <:*:1-_:_+1:_*0.5; > qscal( gain, gainrange) = 1.414 * ( abs(gain/ gainrange)) :_+ 1.414; > eqq2 = qscal( b1gain, 18.0); > eqg2 = b1gain * gcurve( b1gain, 18.0); > eqq3 = qscal( b2gain, 18.0); > eqg3 = b2gain * gcurve( b2gain, 18.0); > eqredux = max( lsgain, eqg2):max(_, eqg3):max(_,hsgain):ba.db2linear: ma.inv; > > preeq( f1,g1,f2,q2,g2,f3,q3,g3,f4,g4) = _*eqredux:fi.svf.bell( f1, > 1.414, g1):fi.svf.bell( f2, q2, g2): fi.svf.bell( f3, q3, > g3):fi.svf.hs( f4, 1.414, g4); > > [/code] > > > On Thu, Sep 11, 2025 at 3:25 PM ga <[email protected]> wrote: >> >> Thanks, this would be a great solution. >> >> Meanwhile I collected the references for the relevant parts (below, if >> someone is interested ). >> The unfinished reverb will be omitted for simplicity and clarity, pickup >> replaced. >> I will take some time for the changes, if someone finds a part in the code >> the should be either more concise or >> more verbose, or a msitake, let me know. >> I also realized that I rewrote some things that seem to have equivalents in >> the library, I will most likely replace them. >> >> Gabriel >> >> // Modulation synthesis with sparse convolution filter and distortions. >> // ==================================================================== >> // >> // A "3D" oscillator oscillating on x,y,z axis, with the radius of x,y going >> // into a hyperbolic distortion. >> // >> // The y axis oscillation is set by MIDI pitch, x and z are detuned by >> simple just tuned ratios. >> // Feedback acts on the individual sine oscillations. >> // >> // >> // Three weighted copies with time varying shifts are summed in a lossy >> integrator >> // ( sparse convolution ), followed by a peak filter and shaped by an >> asymmetric polynomial. >> // >> // The convolution tabs would give a (variyng) triangle impulse response if >> integrated twice, >> // with a -12 dB/octave rolloff and varying regular notches. >> // Here only one integrator is used. >> // >> // >> // The envelope is hard wired to the oscillation amplitudes and the rise >> time of the filter. >> // >> // An LFO is wired to pitch. >> // >> // >> // Inspired by the history of sound synthesis, namely Trautonium, Mini Moog, >> Phase Modulation Synthesis, >> // Variophon Wind Instrument Synthesizer, Physical Modeling, and the work of >> Thams D. Rossing. >> // >> // References: >> // Kot, Vítězslav. (2006). DIGITAL SOUND EFFECTS ECHO AND REVERB BASED ON >> NON EXPONENTIALLY DECAYING COMB FILTER. >> // https://en.wikipedia.org/wiki/Variophon >> // Parker, Julian & Zavalishin, Vadim & Le Bivic, Efflam. (2016). Reducing >> The Aliasing Of Nonlinear Waveshaping Using Continuous-Time Convolution. >> // Nicholas G. Horton, Thomas R. Moore. (2008). Modelling The Magnetic >> Pickup Of An Electric Guitar. >> // >> https://www.musicdsp.org/en/latest/Effects/86-waveshaper-gloubi-boulga.html, >> see comment from 2005-09-22 01:07:58 >> // Frei, Beat. Digital Sound Generation I & II, ICST Zurich University of >> the Arts >> // Smith, J.O. Physical Audio Signal >> Processing,http://ccrma.stanford.edu/~jos/pasp/, online book, 2010 edition >> >> On Thu, Sep 11, 2025 at 10:57 AM Stéphane Letz <[email protected]> wrote: >>> >>> Hi Gabriel, >>> >>> I suggest we do it simple for now. If you can cleanup and document the DSP >>> code, then I can put in the examples/misc section: >>> https://faustdoc.grame.fr/examples/#misc >>> >>> Thanks. >>> >>> Stéphane >>> >>> >>>> Le 10 sept. 2025 à 18:43, ga <[email protected]> a écrit : >>>> >>>> Thanks >>>> >>>> I will look into installing Faust locally, I am bit deterred by the vast >>>> amount of dependencies >>>> and my little experience with installing such projects. >>>> >>>> I also don't have much experience with make and compiling and C, >>>> but I think faust2rpialsaconsole might be onther option I have to look into >>>> as running it on a Pi seems a reasonable solution for hardware. >>>> I do have a Pi 400, on which unfortunately the Patch OS which might be a >>>> good choice for OS does not run (or I didnt get it to run ). >>>> >>>> to 4) >>>> The code and concept is public and libre from my side, but maybe licenses >>>> of third parties have to be considered. >>>> >>>> So I reused and altered code from the Faust library ( by Julius Smith I >>>> think ) for the allpass delay, >>>> and the idea for the triangular filter was originally inspired by the >>>> historic Variophon triangular oscillator, etc. >>>> so at least a proper note with history and references would be desireable. >>>> Since the concept has a really long history with many sources and >>>> variants, and is floating on my desk since years, >>>> it's a bit difficult to be accurate in this regards, and to do this >>>> justice. >>>> >>>> The code also still needs some minor tweaks and cosmetic changes before it >>>> is released in a 'final' version. >>>> For instance it uses two SVFs in series at the moment with very similar >>>> corner frequencies, >>>> which could probably be replaced by a single SVF with a 'morphing' output. >>>> >>>> A previous version had roughly antialiased synched noise (windowed with a >>>> quarter sine wave) in a addition to the osciallator, >>>> to mimick a corpus impulse response, and to enhance piano and string >>>> reminiscent sounds. >>>> >>>> I now tried to replace this with short allpass delays but it sounds less >>>> convincing and "boxed", and setting >>>> the length of the allpass chain is also too arbitrary att the moment. >>>> >>>> Also noise has the interesting property that it has fluctuations, so a >>>> seed could be matched >>>> to produce a sequence that resembles the derivative (or 2nd derivative) of >>>> a real corpus impulse response. >>>> >>>> I would like to keep the paramter set to 4 though, as the idea for a >>>> hardware interface is to have >>>> two rows with 4 push and turn encoders each, one row for synth and one for >>>> EQ and other effects, >>>> with each encoder serving also as a button to select a set of 4 parameters >>>> that belong together, like ADSR. >>>> ( sketch : >>>> https://assets.steadyhq.com/production/post/c0d7b8ae-4d1f-4afa-afe8-8bcce17883ac/uploads/images/5prochhxdb/UI.jpg?auto=compress&w=800&fit=max&dpr=2&fm=webp) >>>> >>>> (Pressing two encoders in the corners simultanously could be used for >>>> saveing and laoding presets.) >>>> >>>> This is one reason why the noise was omitted in this version. >>>> >>>> Such a controller should be seperate from the computing hardware and be >>>> useful for many things, >>>> and could be easy to build from two I²C breakout boards from Adafruit, >>>> but I do not have the tools and funds for this at the moment, and it >>>> requires >>>> additional code for interfacing, which I do not have experience with. >>>> >>>> The idea defintively is to make it an all open source and somewhat >>>> flexible synth concept. >>>> >>>> An interesting aspect for me is that it touches and fuses many aspects of >>>> the history of synthesis, >>>> and synthesis approaches, starting with the Trautonium, modulation >>>> synthesis, subtractive, >>>> aspects and findings of physical modeling, etc, in a very compact but >>>> meaningful parameter set and combination. >>>> ( less paramter than a Mini Moog I think, from which it also borroughs of >>>> course). >>>> >>>> By this it is also a good simplified model to learn and teach I think, for >>>> instance you could >>>> examine what makes a sound "pianoide" and then expand on this with real >>>> pianos and real accurate modeling >>>> of real phyiscal forces etc., and then again examine their perceptual >>>> significance and compare to this "cartoon" >>>> version, and many similar things. >>>> >>>> I dont know whats the best way to publish this so others can contribute >>>> and expand on this. >>>> Maintaining and ovreseeing a project on Sourceforge or similar requires a >>>> lot of work and energy and experience >>>> which I do not have. >>>> So I am also looking for interested people I can hand this idea over, >>>> Including it with Faust examples would be interesting in this regards, >>>> but I am not sure it is fundamental and also simple enough for this, etc. >>>> >>>> Gabriel >>>> >>>> >>>> >>>> >>>> On Wed, Sep 10, 2025 at 3:14 PM Stéphane Letz <[email protected]> wrote: >>>> Hi, >>>> >>>> Thanks for this interesting code. For exporting the code, you have several >>>> options: >>>> >>>> 1) exporting the DSP for a standard plugin format. >>>> >>>> - you can possibly use the JUCE export for that, as an intermediate >>>> step: >>>> https://github.com/grame-cncm/faust/tree/master-dev/architecture/juce. For >>>> maximal flexibility the best would be to compile and install a local Faust >>>> version. >>>> >>>> - another option is to use the Fadeli project >>>> https://github.com/DISTRHO/Fadeli >>>> >>>> 2) you may find more info on this page >>>> https://faust.grame.fr/community/powered-by-faust >>>> >>>> 3) you can connect to the Faust developer/user community on Discord >>>> channel, see https://faust.grame.fr/community/help/ >>>> >>>> 4) You wrote « I am proposing the attached synthesis engine. » : Is the >>>> code public ? Are you interested to contribute it in the Faust examples: >>>> https://faustdoc.grame.fr/examples/ >>>> >>>> Thanks. >>>> >>>> Stéphane >>>> >>>> >>>>> Le 4 sept. 2025 à 11:53, ga <[email protected]> a écrit : >>>>> >>>>> Hello >>>>> I am proposing the attached synthesis engine. >>>>> It uses a "3D" oscillator that oscillates in x,y, z ( similar to FM / AM) >>>>> The radius of x,y is fed into a pickup distortion, which goes into a >>>>> triangular filter ( 3 phase offset copies going into an integrator) an >>>>> asymmetric distortion. >>>>> It has only 4× 4 parameter, including classic ADSR and LFO, envelope >>>>> hardwired to oscillation amplitudes. >>>>> Its capable of a variety of semi- realistic sounds. >>>>> Sound demo is here: >>>>> https://youtu.be/7CBhMcYDWac?feature=shared >>>>> >>>>> >>>>> I would need some help to streamline the code mor Faustian, >>>>> to export including GUI, and to export including the effect, >>>>> and maybe ideas how to port this to some small hardware, Pi or Daisy Pod >>>>> ( though I doubt it will run there ). as well as opinion on the method >>>>> and ideas. >>>>> >>>>> Code: >>>>> >>>>> declare options "[midi:on][nvoices:8]"; >>>>> declare options "[-vec]"; >>>>> declare name "Paradigma_9 v007"; >>>>> declare version "0.0.7"; >>>>> declare author "gabriel"; >>>>> declare copyright "https://steady.page/en/voxangelica/"; >>>>> declare license "DWTW"; >>>>> // a synthesizer with "philonic" 3D spin oscillator and triangular filter >>>>> import("stdfaust.lib"); >>>>> import("maths.lib"); >>>>> >>>>> // frequency ratios table >>>>> frtonum = waveform{1,16,9,6,5,4,7,3,8,5,7,15}; >>>>> frtodiv = waveform{1,15,8,5,4,3,5,2,5,3,4, 8}; >>>>> >>>>> // MIDI >>>>> midigrp(x) = hgroup("[1]MIDI",x); >>>>> f = nentry("freq",200,40,2000,0.1) ; >>>>> kmidi = nentry("key",69,0,127,1) ; >>>>> bend = ba.semi2ratio(hslider("bend[midi:pitchwheel][style: >>>>> knob]",0,-2,2,0.01)) ; >>>>> gain = nentry("gain",0.6,0,1,0.01)<:* ; >>>>> master = hslider("volume[midi:ctrl 7]",1,0,2,0.01) ; >>>>> gate = button("gate") ; >>>>> >>>>> // spin oscill params >>>>> rtogrp(x) = hgroup("[2]philonic",x); >>>>> rto1sel = rtogrp(hslider("[1]x[style:knob]",-12,-24,24,1)); >>>>> rto2sel = rtogrp(hslider("[2]z[style:knob]",19,-24,24,1)); >>>>> fbka = >>>>> rtogrp(hslider("[3]excentric[style:knob]",0.4,0,1,0.01)<:*:*(1/ma.PI)); >>>>> detune = rtogrp(hslider("[4]warble[style:knob]",0.125,0,0.5,0.005)/ma.SR); >>>>> pickd = >>>>> rtogrp(hslider("[5]distance[style:knob]",0.7,0.25,1,0.0625))<:*:si.smoo; >>>>> >>>>> // LFO and Envelope Parameter >>>>> lfogrp(x) = hgroup("[3]envelope & lfo",x); >>>>> enva = (lfogrp(ba.db2linear(hslider("[1]A[style:knob]",20,15,66,1) >>>>> )/1000)); >>>>> envd = (lfogrp(ba.db2linear(hslider("[2]D[style:knob]",74,26,100,1) >>>>> )/1000)*envpscal); >>>>> envs = (lfogrp(hslider("[3]S[style:knob]",0,0,1,0.01) )); >>>>> envr = (lfogrp(ba.db2linear(hslider("[4]R[style:knob]",50,26,100,1) >>>>> )/1000)*envpscal); >>>>> lfof = lfogrp(hslider("[5]LFO Hz[style:knob]",3,0.1,12,0.1)); >>>>> lfvibra = lfogrp(hslider("[6]Vibrato[style:knob]",0.125,0,2,0.01))<:*; >>>>> >>>>> env = en.adsre(enva,envd*envpscal,envs,envr*envpscal,gate); >>>>> envg = env:_* gain; >>>>> >>>>> lfosn = qsin(mphasor(lfof/ma.SR)); >>>>> >>>>> // Triangular Filter Parameter >>>>> fltgrp(x) = hgroup("[4]triangulation",x); >>>>> wid = fltgrp(hslider("[1]rise[style:knob]",4.89,1,9,0.001)):2^_:1/_; >>>>> edge = fltgrp(hslider("[2]fall[style:knob]",6,1,9,0.001)):2^_:1/_; >>>>> fiq = fltgrp(hslider("[3]q[style:knob]",1.18,0.5,3.87,0.01))<:*; >>>>> hpon = fltgrp(checkbox("[4]highpass")); >>>>> drive = fltgrp(hslider("[5]drive[style:knob]",0,-6,36,0.1)):_/20.0:10^_; >>>>> >>>>> rto1oct = rto1sel / 12 : floor; >>>>> rto1semi = rto1sel + 24 : _% 12; >>>>> rto1a = frtonum, rto1semi : rdtable; >>>>> rto1b = frtodiv, rto1semi : rdtable; >>>>> rto1 = (rto1a/rto1b)*(2^rto1oct); >>>>> rto1r = min((1/ rto1),1); >>>>> >>>>> rto2oct = rto2sel / 12 : floor; >>>>> rto2semi = rto2sel + 24 : _% 12; >>>>> rto2a = frtonum, rto2semi : rdtable; >>>>> rto2b = frtodiv, rto2semi : rdtable; >>>>> rto2 = rto1*(rto2a/rto2b)*(2^rto2oct); >>>>> rto2r = min((1 / rto2),1); >>>>> >>>>> // fve >>>>> lg2f = ma.log2(f/440); >>>>> stretch = 0.0333*lg2f; >>>>> envpscal = ( - 3 * lg2f ):ba.db2linear; >>>>> fplus = f*bend + lfosn* lfvibra*f * 0.5/12*envg + stretch; >>>>> >>>>> w = f/ma.SR; >>>>> w2 = rto1 * w; >>>>> w3 = rto2 * w; >>>>> wplus = fplus/ma.SR; >>>>> >>>>> fbk1 = fbka*(0.5 -w)^4; >>>>> fbk2 = fbka*(0.5 - w2)^4*rto1r; >>>>> fbk3 = fbka*(0.5 - w3)^4*rto2r; >>>>> >>>>> // modulation reduction per frequency >>>>> redux1 = ((3.3 -((rto1+1)*w) )/3.3),0: max:_^3; >>>>> redux2 = ((3.3 -((rto2+1)*w) )/3.3),0: max:_^3; >>>>> modep = envg; >>>>> modep1 = envg * redux1 *rto1r * gain ; >>>>> modep2 = envg * redux2 *rto2r * gain ; >>>>> >>>>> // sine oscillator >>>>> wrap(n) = n-( floor( n +0.5)) ; >>>>> qsincurve(x) = 1 - ( (x*x)<: *(1.2253517*16),(_<:*:* (-3.60562732*16)):>_ >>>>> ); >>>>> qsin(x) = x+(0.5): wrap <: (abs:-(0.25):qsincurve),_:ma.copysign; >>>>> // feedback depth reduction curve >>>>> fbcurve (x)= x:abs:-(1) <:^(3):_,(x):ma.copysign; >>>>> >>>>> // oscillator >>>>> mphasor(fw) = (+(fw) ~ (wrap)); >>>>> oscsn(fw, off) = mphasor(fw) + off:qsin:+~*(0.5); >>>>> osc1(fw, off) = ((fw),+(off):(oscsn)) ~ >>>>> (*(fbk2):fi.pole(0.5):_*fbcurve(fw)); >>>>> dcrem(x) = x <:_,_': -: +~*(0.999773243); >>>>> >>>>> // 3D >>>>> oscy(fw, off) = (osc1(fw, off )*osc1(fw*rto2+2*detune,0.75 + >>>>> off)*modep2)*modep; >>>>> oscx(fw, off) = (osc1(fw*rto1+detune,0.25 + >>>>> off)*osc1(fw*rto2+2*detune,0.25 + off)*modep2)*modep1; >>>>> oscxy(fw, off) = (oscy(fw, off)<:*),(oscx(fw, off)<:*):+:sqrt: >>>>> fi.zero(1.0);//dcrem; // >>>>> //oscxyb(fw, off) = (oscy(fw, off):fi.zero(1)) <:_,(_^2),((oscx(fw, >>>>> off):fi.zero(1):_^2)): _, (_+_):_,(_+0.1:_^(3/2)):_/_; >>>>> // with pickup >>>>> oscxyc(fw, off) = oscxy(fw, off) <:_,(_^2:_+pickd:_^(3/2)):/; >>>>> // >>>>> //synthvox(fw, ph2, ph3, g1, g2, g3) = (oscxy(fw, 0):_*g1), (oscxy(fw, >>>>> ph2):_*g2),(oscxy(fw, ph3):_*g3):>_ ; >>>>> synthvox(fw, ph2, ph3, g1, g2, g3) = (oscxyc(fw, 0):_*g1), (oscxyc(fw, >>>>> ph2):_*g2),(oscxyc(fw, ph3):_*g3):>_ ; >>>>> // triangulation >>>>> widredux = w <:+:_^3:1.0-_; >>>>> // diff to max f in octaves, reduced for higher octaves >>>>> dwo = ( 0.25 / wid ):max(_, 1): ma.log2: ma.inv: _*widredux: ma.inv; >>>>> //edge = 1/7; // falling triangle edge, >>>>> egderto = edge / wid; >>>>> wid2 = wid * (2^(dwo * (1-envg ))): >>>>> _* (2^(dwo * (1- gain ) )): >>>>> min( _, 0.25): max( _, 4 / (ma.SR/fplus)); >>>>> wid2e = edge: min( _, 0.25): max( _, 4 /(ma.SR/fplus)); >>>>> >>>>> fiw = wplus/wid2; >>>>> fiwtail = wplus/wid2e; >>>>> // triangle coefficients >>>>> apg0 = fiw; >>>>> apg1 = - apg0 - fiwtail; >>>>> apg2 = fiwtail; >>>>> // integration freq >>>>> igpole = 1.0-5.0/ma.SR; >>>>> resf = (fplus /( wid2 +wid2e) ): min( _, (0.249 * ma.SR)); >>>>> >>>>> // shaper >>>>> // x - 0.15x²-0.15x³ >>>>> tubicclip = _:min(_, (1.19419)):max(_,(-1.86086)); >>>>> //tubic(x) = x - 0.15*(x^2)-0.15*(x^3); >>>>> tubicilo(x) = x, >>>>> // normal for in < 1.2e-4 >>>>> ( x - 0.15*(x^2)-0.15*(x^3) ), >>>>> // ILO: >>>>> (( 0.5*(x^2) - 0.05*(x^3) - 0.0375*(x^4) ),(x <:_,_':- >>>>> :_<:(abs:max(_,1.2e-4)),(ma.signum):ma.copysign):/): >>>>> // select >>>>> ba.if( (_:abs:_<= 1.2e-4), _, _ ):dcrem; >>>>> // >>>>> superfbp = 1 - sin( 2 * ma.PI * w ); >>>>> >>>>> // make sound >>>>> process = synthvox(wplus, wid2, wid2e, apg0, apg1, apg2): >>>>> fi.dcblockerat(10.0): fi.pole(igpole) : fi.svf.peak( resf, fiq) <: >>>>> ba.if( hpon, fi.svf.hp( fplus/(wid+wid):min(_, ma.SR*0.249), >>>>> 0.707 ),_): >>>>> _*drive: tubicclip: tubicilo:_*(1/drive); >>>>> effect = _ * master:rev; >>>>> >>>>> // >>>>> ############################################################################################### >>>>> // CIELverb >>>>> ###################################################################################### >>>>> // minimalist reverb >>>>> // >>>>> // UI >>>>> revgrp(x) = hgroup("[5]reverb",x); >>>>> sizem = >>>>> revgrp(hslider("[1]size[style:knob]",0,-1.5,1.5,0.02)):(2.0)^_:_*16.7:si.smoo; >>>>> revt = revgrp(hslider("[2]revTime[style:knob]",60,40,80,0.1)): >>>>> ba.db2linear:_*0.001; >>>>> bright = revgrp(hslider("[4]brightness[style:knob]",90,52,112,0.1)): >>>>> ba.midikey2hz; >>>>> earlyl = revgrp(hslider("[5]early/late[style:knob]",0,0,1,0.01)); >>>>> drywet = revgrp(hslider("[6]dry/wet[style:knob]",0.5,0,1,0.01)) <:*; >>>>> >>>>> // reverb settings >>>>> // change revt with size >>>>> revtadapt = revt * ( 0.161*(sizem^3)/(6*sizem^2 )); >>>>> // diffusion delay times >>>>> revd0 = ma.SR * (sizem / 334); >>>>> revd1 = revd0 * 1 / ( 2 - log(2)); >>>>> revd2 = revd0 * 1 / ( 3 - log(2)); >>>>> revd3 = revd0 * 1 / ( 4 - log(2)); >>>>> revgn = 10^(-3*(( sizem/ 334 )/revtadapt)); >>>>> // diffusion allpass coeficients >>>>> revc = 0.707;//0.61803; // >>>>> revc1 = -revc * 10^(-3*(( revd1/ ma.SR )/revtadapt)); >>>>> revc2 = -revc * 10^(-3*(( revd2/ ma.SR )/revtadapt)); >>>>> revc3 = -revc * 10^(-3*(( revd3/ ma.SR )/revtadapt)); >>>>> // post (early) >>>>> revdp = revd3 * 1 / ( 4 - log(2)); >>>>> postd1 = revdp * 1 / ( 2 - log(2)); >>>>> postd2 = postd1 * 1 / ( 3 - log(2)); >>>>> postd3 = postd2 * 1 / ( 4 - log(2)); >>>>> postc = 0.382;//1/3;//0.61803; // >>>>> postc1 = -postc * 10^(-3*(( postd1/ ma.SR )/(revtadapt * 1 / ( 4 - >>>>> log(2))))); >>>>> postc2 = -postc * 10^(-3*(( postd2/ ma.SR )/(revtadapt * 1 / ( 4 - >>>>> log(2))))); >>>>> postc3 = -postc * 10^(-3*(( postd2/ ma.SR )/(revtadapt * 1 / ( 4 - >>>>> log(2))))); >>>>> >>>>> // left right delay time offsets >>>>> postdlroff = ma.SR * 0.15 /334 ; >>>>> >>>>> lfo1 = os.oscsin(0.13)*8.0; >>>>> apcomblp(maxdel,N,g) = (+ <: >>>>> (de.fdelay1a(maxdel,N-1.5)<:_,_':+:_*0.5),*(g)) ~ *(-g) : mem,_ : +; >>>>> // post diffusion (early reflections, placed after reverb loop) >>>>> postdiff( in ) = in <: >>>>> (apcomblp( 4096, postd1, postc1): apcomblp( 4096, postd2 + >>>>> postdlroff, postc2): apcomblp( 4096, postd3 - postdlroff*0.382, postc3)), >>>>> (apcomblp( 4096, postd1 + postdlroff, postc1) :apcomblp( >>>>> 4096, postd2 - postdlroff*0.382, postc2): apcomblp( 4096, postd3, >>>>> postc3)); >>>>> >>>>> // feedback filter >>>>> dampp = sin( 2 * ma.PI * bright/ma.SR); >>>>> fidamp = _*(dampp) : +~*(1-dampp) <:_,_':+:_*0.5: *(revgn); >>>>> >>>>> >>>>> // reverb >>>>> rev = _<: +~ (apcomblp( 4096, revd1 - lfo1, revc1):apcomblp( 4096, revd2 >>>>> + lfo1, revc2): apcomblp( 4096, revd3,revc3): de.fdelay1a( 4096, revd0 >>>>> ):fidamp ),_:(_*drywet:postdiff),((_*(1-drywet))<:_,_):route(4, 4, >>>>> (1,1),(2,3),(3,2),(4,4)):>(_+_),(_+_); >>>>> >>>>> // END REVERB >>>>> ############################################################################ >>>>> >>>>> _______________________________________________ >>>>> Faudiostream-users mailing list >>>>> [email protected] >>>>> https://lists.sourceforge.net/lists/listinfo/faudiostream-users >>>> >>> _______________________________________________ Faudiostream-users mailing list [email protected] https://lists.sourceforge.net/lists/listinfo/faudiostream-users
