├── LICENSE.txt ├── MSPd.h ├── Makefile ├── PenroseOscil.c ├── PenroseOscil.h ├── PenroseRand.c ├── PenroseRand.h ├── README.txt ├── ampdb-help.pd ├── ampdb.pd ├── bloscbank.c ├── bthresher~-help.pd ├── bthresher~.c ├── burrow~-help.pd ├── burrow~.c ├── cavoc27~-help.pd ├── cavoc27~.c ├── cavoc~-help.pd ├── cavoc~.c ├── centerring~-help.pd ├── centerring~.c ├── codepend~-help.pd ├── codepend~.c ├── convert.c ├── crossx~-help.pd ├── crossx~.c ├── dentist~-help.pd ├── dentist~.c ├── disarrain~-help.pd ├── disarrain~.c ├── disarray~-help.pd ├── disarray~.c ├── drown~-help.pd ├── drown~.c ├── ether~-help.pd ├── ether~.c ├── examples ├── 13et.scale ├── 24et.scale ├── 4th.scale ├── Piano.aif ├── blue3.scale ├── m3M3.scale ├── m3chord.scale ├── octfifth.scale ├── scale1.pl ├── scale2.pl ├── scale3.pl ├── scale4.pl ├── scale5.pl ├── scale6.pl ├── scale7.pl └── test.scale ├── fft.c ├── fft4.c ├── fftease-meta.pd ├── fftease-system-help.pd ├── fftease-system.pd ├── fftease.h ├── fftease_setup.c ├── fold.c ├── leaker~-help.pd ├── leaker~.c ├── leanconvert.c ├── leanunconvert.c ├── limit_fftsize.c ├── makewindows.c ├── manual └── code-notes.rtf ├── mindwarp~-help.pd ├── mindwarp~.c ├── morphine~-help.pd ├── morphine~.c ├── multyq~-help.pd ├── multyq~.c ├── overlapadd.c ├── power_of_two.c ├── presidency~-help.pd ├── presidency~.c ├── pvcompand~-help.pd ├── pvcompand~.c ├── pvgrain~-help.pd ├── pvgrain~.c ├── pvharm~-help.pd ├── pvharm~.c ├── pvoc~-help.pd ├── pvoc~.c ├── pvtuner.h ├── pvtuner~-help.pd ├── pvtuner~.c ├── pvwarp~-help.pd ├── pvwarp~.c ├── qsortE.c ├── reanimator~-help.pd ├── reanimator~.c ├── resent~-help.pd ├── resent~.c ├── residency_buffer~.c ├── residency~-help.pd ├── residency~.c ├── scrape~-help.pd ├── scrape~.c ├── shapee~-help.pd ├── shapee~.c ├── swinger~-help.pd ├── swinger~.c ├── taint~-help.pd ├── taint~.c ├── thresher~-help.pd ├── thresher~.c ├── unconvert.c ├── vacancy~-help.pd ├── vacancy~.c ├── xsyn~-help.pd └── xsyn~.c /LICENSE.txt: -------------------------------------------------------------------------------- 1 | This software is released under the MIT License, as described here: 2 | http://www.opensource.org/licenses/mit-license.php 3 | and here: http://tinyurl.com/y6u53r 4 | 5 | -EL 6 | 7 | ******************************************************************* 8 | 9 | FFTease is Copyright (c) 1999-2008 Eric Lyon and Christopher Penrose 10 | 11 | Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 16 | -------------------------------------------------------------------------------- /MSPd.h: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | 6 | /* choose your poison */ 7 | 8 | #define MSP (0) 9 | #define PD (!MSP) 10 | /* for compiling under XP */ 11 | 12 | 13 | #ifndef PIOVERTWO 14 | #define PIOVERTWO 1.5707963268 15 | #define TWOPI 6.2831853072 16 | #endif 17 | 18 | #if MSP 19 | #include "ext.h" 20 | #include "z_dsp.h" 21 | #include "buffer.h" 22 | #include "ext_obex.h" 23 | #define t_floatarg double 24 | #endif 25 | 26 | #if PD 27 | #include "m_pd.h" 28 | #define t_floatarg float 29 | #endif 30 | 31 | /* because Max and Pd have different ideas of what A_FLOAT is, use t_floatarg 32 | to force consistency. Otherwise functions that look good will fail on some 33 | hardware. Also note that Pd messages cannot accept arguments of type A_LONG. */ 34 | 35 | 36 | 37 | 38 | 39 | -------------------------------------------------------------------------------- /PenroseOscil.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include "PenroseOscil.h" 3 | 4 | 5 | float frequencyToIncrement( float samplingRate, float frequency, int bufferLength ) { 6 | 7 | return (frequency / samplingRate) * (float) bufferLength; 8 | } 9 | 10 | void makeSineBuffer( float *buffer, int bufferLength ) { 11 | 12 | int i; 13 | 14 | float myTwoPi = 8. * atan(1.); 15 | 16 | for ( i=0; i <= bufferLength; i++ ) 17 | *(buffer+i) = sin( myTwoPi * ((float) i / (float) bufferLength) ); 18 | 19 | return; 20 | } 21 | 22 | 23 | float bufferOscil( float *phase, float increment, float *buffer, 24 | int bufferLength ) 25 | { 26 | 27 | float sample; 28 | 29 | while ( *phase > bufferLength ) 30 | *phase -= bufferLength; 31 | 32 | while ( *phase < 0. ) 33 | *phase += bufferLength; 34 | 35 | sample = *( buffer + (int) (*phase) ); 36 | 37 | *phase += increment; 38 | 39 | return sample; 40 | } 41 | -------------------------------------------------------------------------------- /PenroseOscil.h: -------------------------------------------------------------------------------- 1 | 2 | float frequencyToIncrement( float samplingRate, float frequency, 3 | int bufferLength ); 4 | 5 | void makeSineBuffer( float *buffer, int bufferLength ); 6 | 7 | float bufferOscil( float *phase, float increment, float *buffer, 8 | int bufferLength ); 9 | -------------------------------------------------------------------------------- /PenroseRand.c: -------------------------------------------------------------------------------- 1 | #include "PenroseRand.h" 2 | 3 | float rrand(int *seed) 4 | { 5 | int i = ((*seed = *seed * 1103515245 + 12345)>>16) & 077777; 6 | return((float)i/16384. - 1.); 7 | } 8 | 9 | float prand(int *seed) 10 | { 11 | int i = ((*seed = *seed * 1103515245 + 12345)>>16) & 077777; 12 | return((float)i/32768.); 13 | } 14 | -------------------------------------------------------------------------------- /PenroseRand.h: -------------------------------------------------------------------------------- 1 | 2 | float rrand(int *seed); 3 | float prand(int *seed); 4 | -------------------------------------------------------------------------------- /README.txt: -------------------------------------------------------------------------------- 1 | FFTease 2.5 by Eric Lyon and Christopher Penrose 2 | 3 | This is the third release of FFTease, a set of live spectral sound processors for Max/MSP and Pd. This Pd distribution is compiled for Linux, OS X, and Windows. Move the appropriate set of binaries from "bin" to the Pd "extra" folder. Move the contents of "help" to the Pd "doc/5.reference" directory. You are now ready to use FFTease. 4 | 5 | Caveat: these objects are CPU intensive. A few of these objects in a patch could push your computer to its limits. Be very careful with playback volume as some of the objects produce dramatically different (lower or higher) overall levels. 6 | 7 | The FFT size, which must be a power of 2, is calculated relative to the Pd block size. It is recommended to use FFTease externals in a sub-patch that contains a block~ object, granting you control of the local block size, and thus FFT size. A larger block size results in a larger FFT size. Don't expect a great savings in CPU usage with smaller block sizes. But do expect increased CPU load as you crank the block size up. A block size of 256, with a default overlap of 4 gives an FFT size of 1024 that works acceptably well in many cases. With some of these objects, an even smaller block size/FFT size can actually work better. See the abstraction "fftease-system.pd" for more information on how to control these parameters. 8 | 9 | Acknowledgements: This work draws heavily on the phase vocoder code presented by F. Richard Moore in his classic "Elements of Computer Music." Additional inspiration was derived from work on cross synthesis and noise reduction by Mark Dolson at CARL in the mid-1980s. We also wish to thank Miller Puckette and David Zicarelli for designing and implementing the framework under which FFTease is presented. 10 | 11 | The authors would like to warmly acknowledge the support of the following institutions: Brown University, Dartmouth College, IAMAS, Keio University, the University of Manchester, and Queen's University Belfast. 12 | 13 | FFTease is copyright 2000-2009 Eric Lyon and Christopher Penrose. FFTease is released under the MIT license. 14 | 15 | Eric Lyon 16 | e.lyon@qub.ac.uk 17 | 18 | Christopher Penrose 19 | penrose@silvertone.princeton.edu 20 | -------------------------------------------------------------------------------- /ampdb-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 111 157 450 300 10; 2 | #X obj 102 144 ampdb; 3 | #X floatatom 102 119 5 0 0 0 - - -; 4 | #X obj 105 94 hsl 128 15 -150 0 0 0 empty empty empty -2 -8 0 10 -262144 5 | -1 -1 0 1; 6 | #X floatatom 102 178 10 0 0 0 - - -; 7 | #X text 46 49 convert negative decibels (dB) to amplitude between 0 8 | and 1; 9 | #X text 166 117 input range is roughly -150 to 0; 10 | #X text 179 178 output range is 0 to 1; 11 | #X connect 0 0 3 0; 12 | #X connect 1 0 0 0; 13 | #X connect 2 0 1 0; 14 | -------------------------------------------------------------------------------- /ampdb.pd: -------------------------------------------------------------------------------- 1 | #N canvas 945 219 212 299 10; 2 | #X obj 32 107 pow; 3 | #X obj 32 64 t b f; 4 | #X msg 32 83 10; 5 | #X obj 54 170 /; 6 | #X obj 32 127 t b f; 7 | #X msg 32 148 1; 8 | #X obj 32 41 * -0.05; 9 | #X obj 32 19 inlet; 10 | #X obj 54 193 outlet; 11 | #X connect 0 0 4 0; 12 | #X connect 1 0 2 0; 13 | #X connect 1 1 0 1; 14 | #X connect 2 0 0 0; 15 | #X connect 3 0 8 0; 16 | #X connect 4 0 5 0; 17 | #X connect 4 1 3 1; 18 | #X connect 5 0 3 0; 19 | #X connect 6 0 1 0; 20 | #X connect 7 0 6 0; 21 | -------------------------------------------------------------------------------- /bloscbank.c: -------------------------------------------------------------------------------- 1 | #include "fftease.h" void bloscbank( float *S, float *O, int D, float iD, float *lf, float *la, float *index, float *tab, int len, float synt, int lo, int hi ) { int amp,freq,chan, i; float a,ainc,f,finc,address; for ( chan = lo; chan < hi; chan++ ) { freq = ( amp = ( chan << 1 ) ) + 1; if ( S[amp] > synt ){ finc = ( S[freq] - ( f = lf[chan] ) )* iD; ainc = ( S[amp] - ( a = la[chan] ) )* iD; address = index[chan]; for ( i = 0; i < D ; i++ ) { O[i] += a*tab[ (int) address ]; address += f; while ( address >= len ) address -= len; while ( address < 0 ) address += len; a += ainc; f += finc; } lf[chan] = S[freq]; la[chan] = S[amp]; index[chan] = address; } } } -------------------------------------------------------------------------------- /bthresher~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 609 64 625 468 10; 2 | #N canvas 0 22 478 328 bthresher-block 0; 3 | #X obj 177 189 block~ 256; 4 | #X obj 188 161 outlet~; 5 | #X obj 344 173 outlet; 6 | #X obj 188 40 inlet~; 7 | #X obj 266 65 inlet; 8 | #X obj 344 69 inlet; 9 | #X obj 391 101 inlet; 10 | #X obj 188 117 bthresher~ 0.1 0.97 4 1; 11 | #X connect 3 0 7 0; 12 | #X connect 4 0 7 1; 13 | #X connect 5 0 7 2; 14 | #X connect 6 0 7 0; 15 | #X connect 7 0 1 0; 16 | #X connect 7 1 2 0; 17 | #X restore 154 133 pd bthresher-block; 18 | #X obj 154 206 dac~; 19 | #X obj 154 34 noise~; 20 | #N canvas 613 44 522 372 messages 0; 21 | #X obj 32 248 outlet; 22 | #N canvas 314 293 617 400 individual-bin-control 0; 23 | #X obj 23 363 outlet; 24 | #X obj 220 97 pack f f f; 25 | #X floatatom 220 48 5 0 0 1 bin_number - -; 26 | #X floatatom 252 62 5 0 0 1 damping_factor - -; 27 | #X floatatom 285 78 5 0 0 1 threshold - -; 28 | #X text 23 29 format:; 29 | #X msg 153 241 0 0.968693 0.124173 1 0.968693 0.124173 2 0.968693 0.124173 30 | 3 0.968693 0.124173 4 0.968693 0.124173 5 0.93 0.01 6 0.93 0.01 7 0.93 31 | 0.01 8 0.93 0.01 9 0.93 0.01 10 0.93 0.01 11 0.93 0.01 12 0.93 0.1 32 | 13 0.93 0.1 14 0.93 0.1 15 0.93 0.1 16 0.93 0.1 17 0.968693 0.124173 33 | 18 0.968693 0.124173 19 0.968693 0.124173 20 0.968693 0.124173; 34 | #X msg 23 56 bin 5 0.93 0.01; 35 | #X text 23 41 bin # \, damping \, threshold; 36 | #X msg 220 139 bin \$1 \$2 \$3; 37 | #X text 153 223 or send raw data controlling many bins from a list 38 | ; 39 | #X text 23 17 affect a single bin; 40 | #X text 219 31 construct bin message from components; 41 | #X connect 1 0 9 0; 42 | #X connect 2 0 1 0; 43 | #X connect 3 0 1 1; 44 | #X connect 4 0 1 2; 45 | #X connect 6 0 0 0; 46 | #X connect 7 0 0 0; 47 | #X connect 9 0 0 0; 48 | #X restore 32 20 pd individual-bin-control; 49 | #N canvas 0 22 498 348 global-bin-control 0; 50 | #X msg 253 203 alldamp \$1; 51 | #X msg 221 105 allthresh \$1; 52 | #X floatatom 221 73 5 0 0 0 - allthresh -; 53 | #X floatatom 253 181 5 0 0 0 - alldamp -; 54 | #X obj 221 238 outlet; 55 | #X obj 62 90 vsl 15 128 0 0.2 0 0 allthresh allthresh-init allthresh 56 | 0 -8 0 8 -117632 -1 -1 6985 1; 57 | #X obj 117 90 vsl 15 128 0 1.1 0 0 alldamp alldamp-init alldamp 0 -8 58 | 0 8 -117632 -1 -1 11084 1; 59 | #X connect 0 0 4 0; 60 | #X connect 1 0 4 0; 61 | #X connect 2 0 1 0; 62 | #X connect 3 0 0 0; 63 | #X restore 69 113 pd global-bin-control; 64 | #N canvas 0 22 494 344 random-bin-control 0; 65 | #X obj 8 105 outlet; 66 | #X text 4 33 format: min max; 67 | #X msg 8 50 rthreshold 0.05 0.7; 68 | #X msg 149 49 rdamper 0.8 0.999; 69 | #X connect 2 0 0 0; 70 | #X connect 3 0 0 0; 71 | #X restore 60 78 pd random-bin-control; 72 | #X text 222 21 <- start here; 73 | #N canvas 444 60 502 352 system 0; 74 | #X obj 26 268 outlet; 75 | #X text 122 87 arg must be power of 2; 76 | #X obj 26 19 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1 77 | ; 78 | #X msg 26 43 mute \$1; 79 | #X msg 124 103 overlap 4; 80 | #X msg 124 122 overlap 2; 81 | #X text 193 124 <- cuts CPU demand in half; 82 | #X text 197 105 <- default; 83 | #X msg 134 252 fftinfo; 84 | #X msg 140 185 winfac 1; 85 | #X text 136 166 relative size of input window to FFT; 86 | #X msg 210 186 winfac 2; 87 | #X connect 2 0 3 0; 88 | #X connect 3 0 0 0; 89 | #X connect 4 0 0 0; 90 | #X connect 5 0 0 0; 91 | #X connect 8 0 0 0; 92 | #X connect 9 0 0 0; 93 | #X connect 11 0 0 0; 94 | #X restore 83 158 pd system; 95 | #X msg 197 189 dump; 96 | #X text 195 172 with a list message; 97 | #X text 195 145 output current state; 98 | #X text 196 159 which can then be reloaded; 99 | #X connect 1 0 0 0; 100 | #X connect 2 0 0 0; 101 | #X connect 3 0 0 0; 102 | #X connect 5 0 0 0; 103 | #X connect 6 0 0 0; 104 | #X restore 275 97 pd messages; 105 | #X msg 79 242 \; pd dsp \$1; 106 | #X obj 79 221 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 1 107 | ; 108 | #X obj 154 163 *~ 0.2; 109 | #X floatatom 194 70 5 0 0 0 - scale-thresh -; 110 | #X floatatom 234 95 5 0 0 0 - scale-damping -; 111 | #X obj 191 268 hsl 128 15 0 2 0 0 scale-thresh slider-init scale-thresh 112 | -2 -6 0 8 -258369 -1 -1 6350 1; 113 | #X obj 191 302 hsl 128 15 0 2 0 0 scale-damping slider-init scale-damping 114 | -2 -6 0 8 -258369 -1 -1 6350 1; 115 | #N canvas 137 230 511 492 capture 0; 116 | #X obj 8 12 inlet; 117 | #X text 20 173 clear; 118 | #X msg 8 237 0 0.960032 0.11 1 0.960032 0.11 2 0.960032 0.11 3 0.960032 119 | 0.11 4 0.960032 0.11 5 0.960032 0.11 6 0.960032 0.11 7 0.960032 0.11 120 | 8 0.960032 0.11 9 0.960032 0.11 10 0.960032 0.11 11 0.960032 0.11 12 121 | 0.960032 0.11 13 0.960032 0.11 14 0.960032 0.11 15 0.960032 0.11 16 122 | 0.960032 0.11 17 0.960032 0.11 18 0.960032 0.11 19 0.960032 0.11 0 123 | 0.838661 0.383391 1 0.85394 0.349312 2 0.963181 0.277742 3 0.863287 124 | 0.111771 4 0.871333 0.331876 5 0.940383 0.510999 6 0.94973 0.125378 125 | 7 0.992569 0.100742 8 0.80563 0.290001 9 0.943857 0.0718399 10 0.971641 126 | 0.17489 11 0.928632 0.356374 12 0.871212 0.144183 13 0.933891 0.516592 127 | 14 0.918071 0.480113 15 0.851894 0.330705 16 0.97568 0.339909 17 0.98587 128 | 0.380415 18 0.859807 0.39325 19 0.839784 0.422369 0 0.838661 0.383391 129 | 1 0.85394 0.349312 2 0.963181 0.277742 3 0.863287 0.111771 4 0.871333 130 | 0.331876 5 0.940383 0.510999 6 0.94973 0.125378 7 0.992569 0.100742 131 | 8 0.80563 0.290001 9 0.943857 0.0718399 10 0.971641 0.17489 11 0.928632 132 | 0.356374 12 0.871212 0.144183 13 0.933891 0.516592 14 0.918071 0.480113 133 | 15 0.851894 0.330705 16 0.97568 0.339909 17 0.98587 0.380415 18 0.859807 134 | 0.39325 19 0.839784 0.422369; 135 | #X msg 23 191 set; 136 | #X text 82 15 capture (some) list output from 'dump' message; 137 | #X msg 8 59 add2 \$1 \$2 \$3 \$4 \$5 \$6 \$7 \$8 \$9 \$10 \$11 \$12 138 | \$13 \$14 \$15 \$16 \$17 \$18 \$19 \$20 \$21 \$22 \$23 \$24 \$25 \$26 139 | \$27 \$28 \$29 \$30 \$31 \$32 \$33 \$34 \$35 \$36 \$37 \$38 \$39 \$40 140 | \$41 \$42 \$43 \$44 \$45 \$46 \$47 \$48 \$49 \$50 \$51 \$52 \$53 \$54 141 | \$55 \$56 \$57 \$58 \$59 \$60; 142 | #X text 86 118 The "dump" message outputs the current state of bthresher~ 143 | as a series of triplets [bin# \, damp factor \, threshold]. This data 144 | can be captured as a list and reloaded to itself or any other bthresher~ 145 | unit. In this example we only show the first twenty triplets. Since 146 | there are potentially as many as N/2 triplets where N is the FFT size 147 | \, you would need to modify this subpatch to capture all the information 148 | of the current state of bthresher~. (A version of Pd with the "prepend" 149 | object would make your life easier here.); 150 | #X connect 0 0 5 0; 151 | #X connect 3 0 2 0; 152 | #X connect 5 0 2 0; 153 | #X restore 275 159 pd capture; 154 | #N canvas 0 22 470 320 initialize 0; 155 | #X obj 38 150 s slider-init; 156 | #X msg 38 85 1; 157 | #X obj 38 51 loadbang; 158 | #X obj 142 150 s allthresh-init; 159 | #X obj 265 150 s alldamp-init; 160 | #X msg 265 83 0.96; 161 | #X msg 142 83 0.11; 162 | #X obj 142 41 inlet; 163 | #X connect 1 0 0 0; 164 | #X connect 2 0 1 0; 165 | #X connect 2 0 6 0; 166 | #X connect 2 0 5 0; 167 | #X connect 5 0 4 0; 168 | #X connect 6 0 3 0; 169 | #X connect 7 0 1 0; 170 | #X connect 7 0 6 0; 171 | #X connect 7 0 5 0; 172 | #X restore 399 270 pd initialize; 173 | #X text 364 97 <- click me to learn more; 174 | #X obj 399 245 loadbang; 175 | #X text 50 336 bthresher~ extends the thresher~ model to allow independent 176 | control over the parameters of each individual bin. You can also randomly 177 | set damping and threshold values \, and can dump the current values 178 | (to possibly send as input to another bthresher~ unit). It is recommended 179 | that you familiarize yourself with thresher~ before exploring the more 180 | complicated bthresher~.; 181 | #X text 182 52 threshold scale factor; 182 | #X text 237 80 damping scale factor; 183 | #X text 351 160 <- state captured here; 184 | #X connect 0 0 6 0; 185 | #X connect 0 1 11 0; 186 | #X connect 2 0 0 0; 187 | #X connect 3 0 0 3; 188 | #X connect 5 0 4 0; 189 | #X connect 6 0 1 0; 190 | #X connect 6 0 1 1; 191 | #X connect 7 0 0 1; 192 | #X connect 8 0 0 2; 193 | #X connect 14 0 12 0; 194 | -------------------------------------------------------------------------------- /burrow~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 579 109 517 612 10; 2 | #N canvas 590 312 458 308 burrow-block 0; 3 | #X obj 160 154 burrow~; 4 | #X obj 160 39 inlet~; 5 | #X obj 174 72 inlet~; 6 | #X obj 189 99 inlet; 7 | #X obj 204 120 inlet; 8 | #X obj 160 209 outlet~; 9 | #X obj 270 186 block~ 256; 10 | #X obj 303 124 inlet; 11 | #X connect 0 0 5 0; 12 | #X connect 1 0 0 0; 13 | #X connect 2 0 0 1; 14 | #X connect 3 0 0 2; 15 | #X connect 4 0 0 3; 16 | #X connect 7 0 0 0; 17 | #X restore 93 227 pd burrow-block; 18 | #X obj 93 42 noise~; 19 | #X obj 118 82 noise~; 20 | #X obj 118 129 bp~ 500 50; 21 | #X text 90 25 sound to filter; 22 | #X text 115 66 sound to provide filter shape; 23 | #X obj 93 269 *~ 1; 24 | #X obj 93 304 dac~; 25 | #X msg 352 411 \; pd dsp \$1; 26 | #X obj 352 394 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 27 | 1; 28 | #X floatatom 116 251 5 0 0 0 - burrow-gain -; 29 | #X obj 151 313 hsl 128 15 0 0.2 0 0 burrow-gain empty output_gain -2 30 | -6 0 8 -182539 -1 -1 3175 1; 31 | #X floatatom 143 150 5 0 0 0 - burrow-threshold -; 32 | #X floatatom 168 170 5 0 0 0 - burrow-multiplier -; 33 | #N canvas 0 22 505 427 messages 0; 34 | #X obj 162 351 outlet; 35 | #X msg 162 253 invert \$1; 36 | #X obj 162 227 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 37 | 1; 38 | #X text 59 49 When invert is turned on \, the spectrum of the filter 39 | sound becomes the shape of the filter. Although this might seem more 40 | intuitive \, and thus a better candidate for default behavior \, recall 41 | that the external is called "burrow~" which is what it does.; 42 | #N canvas 380 158 454 304 system 0; 43 | #X obj 201 186 outlet; 44 | #X msg 93 128 overlap \$1; 45 | #X msg 84 96 2; 46 | #X msg 118 96 4; 47 | #X obj 298 44 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1 48 | ; 49 | #X msg 298 70 mute \$1; 50 | #X msg 302 132 fftinfo; 51 | #X msg 145 47 2; 52 | #X msg 179 47 4; 53 | #X msg 154 79 winfac \$1; 54 | #X msg 109 46 1; 55 | #X text 25 235 Try different combos of window factor and overlap. Lower 56 | overlap requires less CPU.; 57 | #X connect 1 0 0 0; 58 | #X connect 2 0 1 0; 59 | #X connect 3 0 1 0; 60 | #X connect 4 0 5 0; 61 | #X connect 5 0 0 0; 62 | #X connect 6 0 0 0; 63 | #X connect 7 0 9 0; 64 | #X connect 8 0 9 0; 65 | #X connect 9 0 0 0; 66 | #X connect 10 0 9 0; 67 | #X restore 182 305 pd system; 68 | #X connect 1 0 0 0; 69 | #X connect 2 0 1 0; 70 | #X connect 4 0 0 0; 71 | #X restore 193 197 pd messages; 72 | #X obj 153 348 hsl 128 15 0.0001 0.01 0 0 burrow-threshold empty threshold 73 | -2 -6 0 8 -182539 -1 -1 3720 1; 74 | #X obj 154 381 hsl 128 15 0.001 1 0 0 burrow-multiplier empty multiplier 75 | -2 -6 0 8 -182539 -1 -1 114 1; 76 | #X floatatom 150 103 5 0 0 0 - bp-center-freq -; 77 | #X obj 154 412 hsl 128 15 100 1500 0 0 bp-center-freq empty center-freq 78 | -2 -6 0 8 -182539 -1 -1 8164 1; 79 | #X floatatom 205 103 5 0 0 0 - bp-resonance -; 80 | #X obj 153 442 hsl 128 15 10 100 0 0 bp-resonance empty resonance -2 81 | -6 0 8 -182539 -1 -1 12700 1; 82 | #X text 12 476 The sound in the leftmost inlet gets filtered by the 83 | spectrum of the sound in the next inlet \, except that by default this 84 | spectrum is cut out from (or burrows into) the source sound. We use 85 | noise sources here to highlight the effect but it is recommended to 86 | use much more interesting sounds as one or both of the inputs. In this 87 | example \, with bandpassed noise as the filter sound \, the result 88 | is to create a notch in the source noise \, similar but inverse to 89 | the shape of the bandpass peak band.; 90 | #N canvas 0 22 462 312 init 0; 91 | #X obj 92 140 unpack f f f f f; 92 | #X obj 92 95 loadbang; 93 | #X obj 92 195 outlet; 94 | #X obj 110 234 outlet; 95 | #X obj 131 276 outlet; 96 | #X obj 165 256 outlet; 97 | #X obj 213 246 outlet; 98 | #X obj 197 71 inlet; 99 | #X msg 92 117 0.05 0.003 0.01 100 1000; 100 | #X connect 0 0 2 0; 101 | #X connect 0 1 3 0; 102 | #X connect 0 2 4 0; 103 | #X connect 0 3 5 0; 104 | #X connect 0 4 6 0; 105 | #X connect 1 0 8 0; 106 | #X connect 7 0 8 0; 107 | #X connect 8 0 0 0; 108 | #X restore 94 381 pd init; 109 | #X obj 94 364 bng 15 250 50 0 empty empty empty 0 -6 0 8 -262144 -1 110 | -1; 111 | #X connect 0 0 6 0; 112 | #X connect 1 0 0 0; 113 | #X connect 2 0 3 0; 114 | #X connect 3 0 0 1; 115 | #X connect 6 0 7 0; 116 | #X connect 6 0 7 1; 117 | #X connect 9 0 8 0; 118 | #X connect 10 0 6 1; 119 | #X connect 12 0 0 2; 120 | #X connect 13 0 0 3; 121 | #X connect 14 0 0 4; 122 | #X connect 17 0 3 1; 123 | #X connect 19 0 3 2; 124 | #X connect 22 0 11 0; 125 | #X connect 22 1 15 0; 126 | #X connect 22 2 16 0; 127 | #X connect 22 3 20 0; 128 | #X connect 22 4 18 0; 129 | #X connect 23 0 22 0; 130 | -------------------------------------------------------------------------------- /cavoc27~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 323 304 466 316 10; 2 | #N canvas 0 22 462 312 cavoc27-block 0; 3 | #X obj 141 110 cavoc27~ 0.05 200 4 1; 4 | #X obj 141 61 inlet~; 5 | #X obj 141 156 outlet~; 6 | #X obj 255 78 inlet; 7 | #X obj 142 212 block~ 256; 8 | #X text 89 187 args: density \, holdtime \, overlap \, winfac; 9 | #X connect 0 0 2 0; 10 | #X connect 1 0 0 0; 11 | #X connect 3 0 0 0; 12 | #X restore 146 109 pd cavoc27-block; 13 | #N canvas 0 22 478 328 messages 0; 14 | #X obj 111 220 outlet; 15 | #N canvas 0 22 466 316 rules 0; 16 | #X obj 15 181 outlet; 17 | #X msg 2 36 rule 1 0 1 0 0 0 1 0 0 1 2 1 0 2 0 2 0 0 1 0 2 0 2 1 2 18 | 1 1; 19 | #X msg 9 58 rule 0 2 1 0 0 1 0 0 0 1 1 2 0 1 2 1 1 1 1 0 0 0 1 1 0 20 | 1 1; 21 | #X msg 28 88 rule 2 2 0 1 0 2 1 1 0 2 1 2 0 1 1 2 0 2 2 1 2 1 1 2 0 22 | 0 0; 23 | #X connect 1 0 0 0; 24 | #X connect 2 0 0 0; 25 | #X connect 3 0 0 0; 26 | #X restore 111 134 pd rules; 27 | #N canvas 520 382 466 316 messages 0; 28 | #X obj 59 290 outlet; 29 | #X msg 308 110 interpolate \$1; 30 | #X obj 308 87 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 1 31 | ; 32 | #X msg 199 241 hold_time \$1; 33 | #X floatatom 199 212 5 0 0 0 - - -; 34 | #X floatatom 305 211 5 0 0 0 - - -; 35 | #X msg 305 242 density \$1; 36 | #X msg 61 37 retune 0.5 2; 37 | #X obj 89 68 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 1 38 | ; 39 | #X msg 89 92 capture_spectrum \$1; 40 | #X connect 1 0 0 0; 41 | #X connect 2 0 1 0; 42 | #X connect 3 0 0 0; 43 | #X connect 4 0 3 0; 44 | #X connect 5 0 6 0; 45 | #X connect 6 0 0 0; 46 | #X connect 7 0 0 0; 47 | #X connect 8 0 9 0; 48 | #X connect 9 0 0 0; 49 | #X restore 180 134 pd messages; 50 | #X obj 273 135 fftease-system; 51 | #X connect 1 0 0 0; 52 | #X connect 2 0 0 0; 53 | #X connect 3 0 0 0; 54 | #X restore 253 81 pd messages; 55 | #X obj 146 208 dac~; 56 | #X msg 287 201 \; pd dsp \$1; 57 | #X obj 287 176 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 58 | 1; 59 | #X obj 200 147 hsl 128 15 0 0.01 0 0 empty empty output_gain -2 -6 60 | 0 10 -245150 -1 -1 0 1; 61 | #N canvas 0 22 462 312 example-input-spectrum 0; 62 | #X obj 114 228 outlet~; 63 | #X obj 62 124 phasor~ 100; 64 | #X obj 145 124 phasor~ 125; 65 | #X obj 231 125 phasor~ 150; 66 | #X obj 114 175 *~ 0.333; 67 | #X text 26 89 this gets sampled when "capture_spectrum" is on; 68 | #X connect 1 0 4 0; 69 | #X connect 2 0 4 0; 70 | #X connect 3 0 4 0; 71 | #X connect 4 0 0 0; 72 | #X restore 146 48 pd example-input-spectrum; 73 | #X text 341 82 <- info; 74 | #X floatatom 197 168 5 0 0 0 - - -; 75 | #X obj 146 185 *~ 0.001; 76 | #X text 21 256 27 rule cellular automata (CA). New rules lists have 77 | 27 values (0 \, 1 \, or 2). Start with VERY low gain. See cavoc~ for 78 | a simpler implementation of CA-generated spectra.; 79 | #X connect 0 0 9 0; 80 | #X connect 1 0 0 1; 81 | #X connect 4 0 3 0; 82 | #X connect 5 0 8 0; 83 | #X connect 6 0 0 0; 84 | #X connect 8 0 9 1; 85 | #X connect 9 0 2 0; 86 | #X connect 9 0 2 1; 87 | -------------------------------------------------------------------------------- /cavoc~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 674 329 486 336 10; 2 | #N canvas 172 264 478 328 cavoc-block 0; 3 | #X obj 161 176 block~ 256; 4 | #X obj 167 155 outlet~; 5 | #X obj 292 69 inlet; 6 | #X obj 167 111 cavoc~ 0.05 150 4 1; 7 | #X text 133 127 args: density holdtime \, overlap \, window factor 8 | ; 9 | #X connect 2 0 3 0; 10 | #X connect 3 0 1 0; 11 | #X restore 29 72 pd cavoc-block; 12 | #X obj 29 143 dac~; 13 | #X msg 29 208 \; pd dsp \$1; 14 | #X obj 29 186 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1 15 | ; 16 | #X floatatom 80 96 5 0 0 0 - gain -; 17 | #X obj 32 261 hsl 128 15 0 1 0 0 gain gain-init gain -2 -6 0 8 -261127 18 | -1 -1 0 1; 19 | #N canvas 773 396 486 336 messages 0; 20 | #X obj 120 243 outlet; 21 | #N canvas 321 426 474 324 rules 0; 22 | #X obj 55 273 outlet; 23 | #X msg 59 71 rule 1 1 1 1 0 0 0 0; 24 | #X msg 213 72 rule 1 0 1 0 1 0 1 0; 25 | #X msg 203 122 rule 0 0 0 0 0 1 0 1; 26 | #X msg 203 149 rule 0 1 1 0 1 0 0 1; 27 | #X msg 203 194 rule 0 0 0 0 1 1 1 1; 28 | #X msg 90 34 rule 1 1 0 1 0 1 0 0; 29 | #X msg 265 23 rule 1 1 0 1 0 1 1 0; 30 | #X msg 300 51 rule 1 1 0 0 1 1 0 0; 31 | #X msg 294 94 rule 0 0 1 0 1 0 1 1; 32 | #X msg 204 234 rule 0 0 0 1 1 0 0 0; 33 | #X msg 244 265 rule 1 0 0 1 1 0 0 1; 34 | #X text 38 301 rules define CA evolution of spectrum; 35 | #X connect 1 0 0 0; 36 | #X connect 2 0 0 0; 37 | #X connect 3 0 0 0; 38 | #X connect 4 0 0 0; 39 | #X connect 5 0 0 0; 40 | #X connect 6 0 0 0; 41 | #X connect 7 0 0 0; 42 | #X connect 8 0 0 0; 43 | #X connect 9 0 0 0; 44 | #X connect 10 0 0 0; 45 | #X connect 11 0 0 0; 46 | #X restore 250 227 pd rules; 47 | #N canvas 687 59 486 336 system 0; 48 | #X obj 209 277 outlet; 49 | #X msg 132 162 fftinfo; 50 | #X msg 64 181 mute \$1; 51 | #X obj 64 154 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1 52 | ; 53 | #X msg 215 121 overlap \$1; 54 | #X msg 249 161 winfac \$1; 55 | #X floatatom 215 91 5 0 0 0 - - -; 56 | #X floatatom 249 142 5 0 0 0 - - -; 57 | #X text 243 240 default: overlap=4 \, winfac=1; 58 | #X connect 1 0 0 0; 59 | #X connect 2 0 0 0; 60 | #X connect 3 0 2 0; 61 | #X connect 4 0 0 0; 62 | #X connect 5 0 0 0; 63 | #X connect 6 0 4 0; 64 | #X connect 7 0 5 0; 65 | #X restore 41 177 pd system; 66 | #X floatatom 292 77 5 0 0 0 - - -; 67 | #X msg 291 101 density \$1; 68 | #X msg 251 44 0.05; 69 | #X msg 105 126 retune 0.5 2; 70 | #X msg 303 42 0.2; 71 | #X floatatom 316 163 5 0 0 0 - - -; 72 | #X msg 316 181 hold_time \$1; 73 | #X text 311 228 <- CA rules; 74 | #X text 220 149 hold time (in ms) for each step of CA; 75 | #X text 109 21 density is percent of bins turned on at start of CA 76 | ; 77 | #X text 96 102 reset phase "tunings"; 78 | #X connect 1 0 0 0; 79 | #X connect 2 0 0 0; 80 | #X connect 3 0 4 0; 81 | #X connect 4 0 0 0; 82 | #X connect 5 0 4 0; 83 | #X connect 6 0 0 0; 84 | #X connect 7 0 3 0; 85 | #X connect 8 0 9 0; 86 | #X connect 9 0 0 0; 87 | #X restore 29 38 pd messages; 88 | #X obj 29 115 *~ 0.025; 89 | #X text 27 290 cavoc~ is an 8 rule cellular automaton that generates 90 | spectra. Start with very low gain.; 91 | #X connect 0 0 7 0; 92 | #X connect 3 0 2 0; 93 | #X connect 4 0 7 1; 94 | #X connect 6 0 0 0; 95 | #X connect 7 0 1 0; 96 | #X connect 7 0 1 1; 97 | -------------------------------------------------------------------------------- /centerring~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 281 24 648 434 10; 2 | #N canvas 376 316 462 312 centerring-block 0; 3 | #X obj 163 128 centerring~; 4 | #X obj 233 219 block~ 256; 5 | #X obj 152 180 outlet~; 6 | #X obj 141 63 inlet~; 7 | #X obj 337 89 inlet; 8 | #X obj 195 67 inlet; 9 | #X obj 242 66 inlet; 10 | #X obj 290 71 inlet; 11 | #X connect 0 0 2 0; 12 | #X connect 3 0 0 0; 13 | #X connect 4 0 0 0; 14 | #X connect 5 0 0 1; 15 | #X connect 6 0 0 2; 16 | #X connect 7 0 0 3; 17 | #X restore 167 141 pd centerring-block; 18 | #X obj 167 195 *~ 1; 19 | #X obj 167 230 dac~; 20 | #X floatatom 190 176 5 0 0 0 - centerring-gain -; 21 | #X msg 333 242 \; pd dsp \$1; 22 | #X obj 333 225 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 23 | 1; 24 | #X obj 18 207 hsl 128 15 0 0.1 0 0 centerring-gain empty output_gain 25 | -2 -6 0 8 -79789 -1 -1 800 1; 26 | #X obj 81 51 phasor~ 150; 27 | #N canvas 0 22 474 324 messages 0; 28 | #X obj 159 192 outlet; 29 | #X msg 154 138 zerophases; 30 | #X msg 263 138 randphases; 31 | #X msg 71 101 seed \$1; 32 | #X floatatom 70 71 5 0 0 0 - - -; 33 | #X msg 117 65 1974; 34 | #X obj 320 168 fftease-system; 35 | #X connect 1 0 0 0; 36 | #X connect 2 0 0 0; 37 | #X connect 3 0 0 0; 38 | #X connect 4 0 3 0; 39 | #X connect 5 0 3 0; 40 | #X connect 6 0 0 0; 41 | #X restore 319 108 pd messages; 42 | #X floatatom 193 54 5 0 0 0 - cr-base-frequency -; 43 | #X obj 18 240 hsl 128 15 0.1 20 0 0 cr-base-frequency empty base_frequency 44 | -2 -6 0 8 -79789 -1 -1 900 1; 45 | #X floatatom 251 59 5 0 0 0 - cr-bandwidth -; 46 | #X obj 16 271 hsl 128 15 0.1 20 0 0 cr-bandwidth empty bandwidth -2 47 | -6 0 8 -79789 -1 -1 7700 1; 48 | #X floatatom 329 42 5 0 0 0 - cr-freq-constant -; 49 | #X obj 15 305 hsl 128 15 0.1 20 0 0 cr-freq-constant empty frequency_constant 50 | -2 -6 0 8 -79789 -1 -1 6300 1; 51 | #X obj 9 99 loadbang; 52 | #X msg 9 125 0.1 1 0.15 1; 53 | #X obj 9 157 unpack f f f f; 54 | #X text 171 294 centerring~ performs frequency independent amplitude 55 | modulation upon the spectral magnitudes of input signals. The effect 56 | is somewhat akin to flanging. The base frequency is used to derive 57 | the frequency of an oscillator associated with each frequency band. 58 | The frequency bandwidth and constant control the deviation of a particular 59 | frequency band's modulation oscillator frequency.; 60 | #X floatatom 81 30 5 0 0 0 - - -; 61 | #X connect 0 0 1 0; 62 | #X connect 1 0 2 0; 63 | #X connect 1 0 2 1; 64 | #X connect 3 0 1 1; 65 | #X connect 5 0 4 0; 66 | #X connect 7 0 0 0; 67 | #X connect 8 0 0 4; 68 | #X connect 9 0 0 1; 69 | #X connect 11 0 0 2; 70 | #X connect 13 0 0 3; 71 | #X connect 15 0 16 0; 72 | #X connect 16 0 17 0; 73 | #X connect 17 0 6 0; 74 | #X connect 17 1 10 0; 75 | #X connect 17 2 12 0; 76 | #X connect 17 3 14 0; 77 | #X connect 19 0 7 0; 78 | -------------------------------------------------------------------------------- /codepend~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 281 24 668 454 10; 2 | #X obj 167 237 *~ 1; 3 | #X obj 167 289 dac~; 4 | #X floatatom 190 218 5 0 0 0 - centerring-gain -; 5 | #X msg 333 284 \; pd dsp \$1; 6 | #X obj 333 267 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 7 | 1; 8 | #X obj 17 207 hsl 128 15 0 4 0 0 centerring-gain empty output_gain 9 | -2 -6 0 8 -79789 -1 -1 317 1; 10 | #N canvas 0 22 519 354 messages 0; 11 | #X obj 132 268 outlet; 12 | #X text 30 194 turn on invert; 13 | #X msg 132 175 pad \$1; 14 | #X obj 132 146 ampdb; 15 | #X floatatom 132 116 5 -200 -12 0 - - -; 16 | #X text 221 177 is turned on; 17 | #X obj 9 195 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1 18 | ; 19 | #X msg 9 217 invert \$1; 20 | #X text 221 163 pad affects the gain only when "invert"; 21 | #X obj 184 233 fftease-system; 22 | #X connect 2 0 0 0; 23 | #X connect 3 0 2 0; 24 | #X connect 4 0 3 0; 25 | #X connect 6 0 7 0; 26 | #X connect 7 0 0 0; 27 | #X connect 9 0 0 0; 28 | #X restore 448 167 pd messages; 29 | #X obj 18 240 hsl 128 15 0.15 1 0 0 cod-scaling-exponent empty scaling_exponent 30 | -2 -6 0 8 -88868 -1 -1 2241 1; 31 | #N canvas 376 316 470 320 codepend-block 0; 32 | #X obj 233 219 block~ 256; 33 | #X obj 163 185 outlet~; 34 | #X obj 163 38 inlet~; 35 | #X obj 269 107 inlet; 36 | #X obj 201 81 inlet; 37 | #X obj 221 98 inlet; 38 | #X obj 163 128 codepend~; 39 | #X obj 182 65 inlet~; 40 | #X connect 2 0 6 0; 41 | #X connect 3 0 6 0; 42 | #X connect 4 0 6 2; 43 | #X connect 5 0 6 3; 44 | #X connect 6 0 1 0; 45 | #X connect 7 0 6 1; 46 | #X restore 167 183 pd codepend-block; 47 | #X obj 252 142 ampdb; 48 | #X floatatom 252 122 5 0 0 0 - cod-inverse-threshold -; 49 | #X floatatom 252 164 5 0 0 0 - - -; 50 | #N canvas 990 218 504 393 playsound1 0; 51 | #X obj 31 194 soundfiler; 52 | #X obj 31 160 openpanel; 53 | #X msg 31 177 read -resize \$1 codepend-sound1; 54 | #N canvas 0 22 450 300 graph1 0; 55 | #X array codepend-sound1 501762 float 2; 56 | #X coords 0 1 501761 -1 200 140 1; 57 | #X restore 237 13 graph; 58 | #X msg 31 131 bang; 59 | #X obj 227 284 outlet~; 60 | #X obj 227 268 tabplay~ codepend-sound1; 61 | #X msg 227 244 bang; 62 | #X obj 348 228 spigot; 63 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 64 | 1; 65 | #X text 63 132 open the sound; 66 | #X text 133 244 then play it; 67 | #X text 304 190 loop if you like; 68 | #X connect 1 0 2 0; 69 | #X connect 2 0 0 0; 70 | #X connect 4 0 1 0; 71 | #X connect 6 0 5 0; 72 | #X connect 6 1 8 0; 73 | #X connect 7 0 6 0; 74 | #X connect 8 0 7 0; 75 | #X connect 9 0 8 1; 76 | #X restore 167 22 pd playsound1; 77 | #N canvas 990 218 508 397 playsound2 0; 78 | #X obj 31 194 soundfiler; 79 | #X obj 31 160 openpanel; 80 | #X msg 31 131 bang; 81 | #X obj 227 284 outlet~; 82 | #X msg 227 244 bang; 83 | #X obj 348 228 spigot; 84 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 85 | 1; 86 | #X text 63 132 open the sound; 87 | #X text 133 244 then play it; 88 | #X text 304 190 loop if you like; 89 | #X text 316 205 comment; 90 | #X msg 31 177 read -resize \$1 codepend-sound2; 91 | #N canvas 0 22 450 300 graph2 0; 92 | #X array codepend-sound2 4e+06 float 2; 93 | #X coords 0 1 4e+06 -1 200 140 1; 94 | #X restore 216 15 graph; 95 | #X obj 227 268 tabplay~ codepend-sound2; 96 | #X connect 1 0 11 0; 97 | #X connect 2 0 1 0; 98 | #X connect 4 0 13 0; 99 | #X connect 5 0 4 0; 100 | #X connect 6 0 5 1; 101 | #X connect 11 0 0 0; 102 | #X connect 13 0 3 0; 103 | #X connect 13 1 5 0; 104 | #X restore 195 40 pd playsound2; 105 | #X floatatom 224 90 5 0 0 0 - cod-scaling-exponent -; 106 | #X obj 19 278 hsl 128 15 -90 0 0 0 cod-inverse-threshold empty inverse_threshold 107 | -2 -6 0 8 -88868 -1 -1 7620 1; 108 | #X text 296 137 but only when "invert" is turned on); 109 | #X text 224 72 scaling exponent (lower values increase distortion) 110 | ; 111 | #X text 294 31 <- load and loop two soundfiles to hear effect; 112 | #X msg 14 123 0.1 0.3 -36; 113 | #X obj 14 139 unpack f f f; 114 | #X obj 14 107 loadbang; 115 | #X text 293 121 inverse threshold (lower values intensify effect; 116 | #X text 31 316 codepend~ is a classic "block convolution" processor. 117 | It performs a complex multiply upon the spectra of two input signals. 118 | Multiplication of spectra can cause significant drops in the amplitude 119 | of the output signal. The invert message causes codepend~ to perform 120 | complex division of the input spectra rather than multiplication. This 121 | can cause huge amplitude gains. A "pad" message is provided to allow 122 | for empirical amplitude balancing between the normal and "invert" states. 123 | ; 124 | #X connect 0 0 1 0; 125 | #X connect 0 0 1 1; 126 | #X connect 2 0 0 1; 127 | #X connect 4 0 3 0; 128 | #X connect 6 0 8 4; 129 | #X connect 8 0 0 0; 130 | #X connect 9 0 11 0; 131 | #X connect 10 0 9 0; 132 | #X connect 11 0 8 3; 133 | #X connect 12 0 8 0; 134 | #X connect 13 0 8 1; 135 | #X connect 14 0 8 2; 136 | #X connect 19 0 20 0; 137 | #X connect 20 0 5 0; 138 | #X connect 20 1 7 0; 139 | #X connect 20 2 15 0; 140 | #X connect 21 0 19 0; 141 | -------------------------------------------------------------------------------- /convert.c: -------------------------------------------------------------------------------- 1 | #include "fftease.h" /* S is a spectrum in rfft format, i.e., it contains N real values arranged as real followed by imaginary values, except for first two values, which are real parts of 0 and Nyquist frequencies; convert first changes these into N/2+1 PAIRS of magnitude and phase values to be stored in output array C; the phases are then unwrapped and successive phase differences are used to compute estimates of the instantaneous frequencies for each phase vocoder analysis channel; decimation rate D and sampling rate R are used to render these frequency values directly in Hz. */ void convert(float *S, float *C, int N2, float *lastphase, float fundamental, float factor ) { float phase, phasediff; int real, imag, amp, freq; float a, b; int i; /* float myTWOPI, myPI; */ /* double sin(), cos(), atan(), hypot();*/ /* myTWOPI = 8.*atan(1.); myPI = 4.*atan(1.); */ for ( i = 0; i <= N2; i++ ) { imag = freq = ( real = amp = i<<1 ) + 1; a = ( i == N2 ? S[1] : S[real] ); b = ( i == 0 || i == N2 ? 0. : S[imag] ); C[amp] = hypot( a, b ); if ( C[amp] == 0. ) phasediff = 0.; else { phasediff = ( phase = -atan2( b, a ) ) - lastphase[i]; lastphase[i] = phase; while ( phasediff > PI ) phasediff -= TWOPI; while ( phasediff < -PI ) phasediff += TWOPI; } C[freq] = phasediff*factor + i*fundamental; } } -------------------------------------------------------------------------------- /crossx~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 684 407 470 320 10; 2 | #X obj 25 189 dac~; 3 | #N canvas 0 22 470 320 rich-harmonic-source 0; 4 | #X obj 127 232 outlet~; 5 | #X obj 127 125 phasor~ 100; 6 | #X obj 212 126 phasor~ 125; 7 | #X obj 296 125 phasor~ 150; 8 | #X obj 127 183 *~ 0.3; 9 | #X floatatom 127 67 5 0 0 0 - - -; 10 | #X obj 212 99 * 1.25; 11 | #X obj 296 100 * 1.5; 12 | #X obj 130 34 hsl 128 15 60 600 0 0 empty empty empty -2 -6 0 8 -154413 13 | -1 -1 8900 1; 14 | #X connect 1 0 4 0; 15 | #X connect 2 0 4 0; 16 | #X connect 3 0 4 0; 17 | #X connect 4 0 0 0; 18 | #X connect 5 0 6 0; 19 | #X connect 5 0 1 0; 20 | #X connect 5 0 7 0; 21 | #X connect 6 0 2 0; 22 | #X connect 7 0 3 0; 23 | #X connect 8 0 5 0; 24 | #X restore 25 23 pd rich-harmonic-source; 25 | #X floatatom 91 66 5 0 0 0 - - -; 26 | #N canvas 179 221 657 470 vocal-source 0; 27 | #X text 13 300 try a vocal sound or other sound with strong formant 28 | structure; 29 | #X obj 31 194 soundfiler; 30 | #X obj 31 160 openpanel; 31 | #N canvas 0 22 450 300 graph1 0; 32 | #X array crossx-sound1 4e+06 float 2; 33 | #X coords 0 1 4e+06 -1 200 140 1; 34 | #X restore 237 13 graph; 35 | #X msg 31 131 bang; 36 | #X obj 227 284 outlet~; 37 | #X msg 227 244 bang; 38 | #X obj 348 228 spigot; 39 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 40 | 1; 41 | #X text 63 132 open the sound; 42 | #X text 133 244 then play it; 43 | #X text 304 190 loop if you like; 44 | #X msg 31 177 read -resize \$1 crossx-sound1; 45 | #X obj 227 268 tabplay~ crossx-sound1; 46 | #X connect 2 0 12 0; 47 | #X connect 4 0 2 0; 48 | #X connect 6 0 13 0; 49 | #X connect 7 0 6 0; 50 | #X connect 8 0 7 1; 51 | #X connect 12 0 1 0; 52 | #X connect 13 0 5 0; 53 | #X connect 13 1 7 0; 54 | #X restore 58 45 pd vocal-source; 55 | #X msg 186 229 \; pd dsp \$1; 56 | #X obj 186 208 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 57 | 1; 58 | #X obj 25 160 *~ 1; 59 | #X floatatom 48 141 5 0 0 0 - - -; 60 | #X text 90 143 <- might need large amplitude; 61 | #X text 96 155 but watch for sudden spikes!; 62 | #X text 133 70 <- synthesis advancement threshold; 63 | #N canvas 172 351 466 316 crossx-block 0; 64 | #X obj 161 178 outlet~; 65 | #X obj 161 49 inlet~; 66 | #X obj 219 100 inlet; 67 | #X obj 283 102 inlet; 68 | #X obj 161 213 block~ 256; 69 | #X obj 190 80 inlet~; 70 | #X obj 161 132 crossx~ 4; 71 | #X connect 1 0 6 0; 72 | #X connect 2 0 6 2; 73 | #X connect 3 0 6 0; 74 | #X connect 5 0 6 1; 75 | #X connect 6 0 0 0; 76 | #X restore 25 88 pd crossx-block; 77 | #N canvas 0 22 458 308 messages 0; 78 | #X obj 56 233 outlet; 79 | #X msg 56 175 autonorm \$1; 80 | #X text 56 66 frame normalization to tame amplitude spikes; 81 | #X obj 209 217 fftease-system; 82 | #N canvas 0 22 458 308 rescale-autonorm 0; 83 | #X obj 93 30 inlet; 84 | #X obj 61 92 t b b; 85 | #X msg 61 115 1; 86 | #X msg 108 118 0.05; 87 | #X obj 108 144 s output-gain; 88 | #X obj 96 221 outlet; 89 | #X obj 197 49 inlet; 90 | #X obj 226 102 t b b; 91 | #X obj 243 237 s output-gain; 92 | #X msg 313 130 0; 93 | #X msg 243 211 5; 94 | #X obj 261 174 pipe 100; 95 | #X connect 0 0 1 0; 96 | #X connect 1 0 2 0; 97 | #X connect 1 1 3 0; 98 | #X connect 2 0 5 0; 99 | #X connect 3 0 4 0; 100 | #X connect 6 0 7 0; 101 | #X connect 7 0 11 0; 102 | #X connect 7 1 9 0; 103 | #X connect 9 0 5 0; 104 | #X connect 10 0 8 0; 105 | #X connect 11 0 10 0; 106 | #X restore 56 122 pd rescale-autonorm; 107 | #X obj 56 93 bng 15 250 50 0 empty empty on 0 -6 0 8 -262144 -1 -1 108 | ; 109 | #X obj 184 94 bng 15 250 50 0 empty empty off 0 -6 0 8 -262144 -1 -1 110 | ; 111 | #X connect 1 0 0 0; 112 | #X connect 3 0 0 0; 113 | #X connect 4 0 1 0; 114 | #X connect 5 0 4 0; 115 | #X connect 6 0 4 1; 116 | #X restore 143 88 pd messages; 117 | #X obj 48 118 r output-gain; 118 | #X text 96 170 a compressor could be useful here; 119 | #X obj 215 51 hsl 128 15 0 0.05 0 0 empty empty empty -2 -6 0 8 -191432 120 | -1 -1 700 1; 121 | #X text 26 262 crossx~ is related to xsyn~ but uses a threshold to 122 | determine whether to perform spectral multiplication or maintain the 123 | last calculated amplitude/phase pair. crossx~ is also somewhat less 124 | CPU intensive.; 125 | #X connect 1 0 11 0; 126 | #X connect 2 0 11 2; 127 | #X connect 3 0 11 1; 128 | #X connect 5 0 4 0; 129 | #X connect 6 0 0 0; 130 | #X connect 6 0 0 1; 131 | #X connect 7 0 6 1; 132 | #X connect 11 0 6 0; 133 | #X connect 12 0 11 3; 134 | #X connect 13 0 7 0; 135 | #X connect 15 0 2 0; 136 | -------------------------------------------------------------------------------- /dentist~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 71 582 526 376 10; 2 | #N canvas 0 22 482 332 dentist-block 0; 3 | #X obj 322 150 block~ 256; 4 | #X obj 185 65 inlet~; 5 | #X obj 257 67 inlet; 6 | #X obj 185 174 outlet~; 7 | #X obj 221 264 snapshot~; 8 | #X obj 199 229 metro 80; 9 | #X msg 201 204 1; 10 | #X obj 310 287 outlet; 11 | #X obj 84 188 loadbang; 12 | #X obj 185 112 dentist~ 8000; 13 | #X obj 271 218 s dentist-stored-teeth; 14 | #X connect 1 0 9 0; 15 | #X connect 2 0 9 0; 16 | #X connect 4 0 7 0; 17 | #X connect 5 0 4 0; 18 | #X connect 6 0 5 0; 19 | #X connect 8 0 6 0; 20 | #X connect 9 0 3 0; 21 | #X connect 9 1 4 0; 22 | #X connect 9 2 10 0; 23 | #X restore 126 106 pd dentist-block; 24 | #X msg 263 173 \; pd dsp \$1; 25 | #X obj 263 147 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 26 | 1; 27 | #X obj 126 180 dac~; 28 | #N canvas 639 41 688 619 messages 0; 29 | #X obj 70 447 outlet; 30 | #X msg 271 50 ramptime \$1; 31 | #X obj 271 26 nbx 5 14 -1e+37 1e+37 0 0 empty empty empty 0 -6 0 10 32 | -262144 -1 -1 1000 256; 33 | #X msg 271 4 1000; 34 | #X obj 271 -17 loadbang; 35 | #X msg 186 431 toothcount \$1; 36 | #X msg 95 234 topfreq \$1; 37 | #X floatatom 95 212 5 0 0 0 - - -; 38 | #X text 94 196 highest frequency for bin selection; 39 | #X text 330 26 interpolation time between distributions; 40 | #X text 89 57 set distribution; 41 | #X msg 330 330 interpolate_singles \$1; 42 | #X obj 330 303 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 43 | 1; 44 | #X msg 70 75 scramble; 45 | #X obj 299 430 hsl 128 15 0 127 0 0 toothcount empty toothcount -2 46 | -6 0 8 -85171 -1 -1 5300 1; 47 | #X text 220 448 this sets the number of bins within a fixed random 48 | distribution. must be greater than zero to hear sound.; 49 | #X obj 70 487 fftease-system; 50 | #X msg 186 389 10; 51 | #N canvas 643 146 878 628 data-storage 0; 52 | #X obj 260 105 outlet; 53 | #X msg 260 -66 setstate 30 31 32 33 34 35; 54 | #X msg 260 -49 setstate 7 9 11 13; 55 | #X text 250 -92 set a particular bin distribution; 56 | #X msg 260 -32 setstate 16 20 7 10 24 12 2 23 3; 57 | #X msg 260 64 showstate; 58 | #X text 337 64 list current bin selections; 59 | #X obj 80 140 r dentist-stored-teeth; 60 | #X obj 80 167 print; 61 | #X text 128 170 <- replace with [prepend set] -> [messagebox] if you 62 | have a "prepend" in your Pd distribution. Otherwise we just print to 63 | the Pd window.; 64 | #X text 241 141 <- from the dentist~ list outlet; 65 | #X connect 5 0 0 0; 66 | #X connect 7 0 8 0; 67 | #X restore 143 339 pd data-storage; 68 | #X obj 186 369 loadbang; 69 | #X obj 186 410 nbx 5 14 -1e+37 1e+37 0 0 empty toothcount empty 0 -6 70 | 0 12 -262144 -1 -1 50 256; 71 | #X obj 70 17 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1 72 | ; 73 | #X obj 70 36 metro 1000; 74 | #X text 89 15 do it repeatedly; 75 | #X text 286 275 turn OFF to make toothcount changes instantaneous; 76 | #X connect 1 0 0 0; 77 | #X connect 2 0 1 0; 78 | #X connect 3 0 2 0; 79 | #X connect 4 0 3 0; 80 | #X connect 5 0 0 0; 81 | #X connect 6 0 0 0; 82 | #X connect 7 0 6 0; 83 | #X connect 11 0 0 0; 84 | #X connect 12 0 11 0; 85 | #X connect 13 0 0 0; 86 | #X connect 16 0 0 0; 87 | #X connect 17 0 20 0; 88 | #X connect 18 0 0 0; 89 | #X connect 19 0 17 0; 90 | #X connect 20 0 5 0; 91 | #X connect 21 0 22 0; 92 | #X connect 22 0 13 0; 93 | #X restore 233 80 pd messages; 94 | #X obj 126 150 *~ 2; 95 | #X obj 61 228 hsl 128 15 0 4 0 0 gain empty gain -2 -6 0 8 -208862 96 | -1 -1 12700 1; 97 | #X text 316 81 <- open me; 98 | #X obj 126 66 noise~; 99 | #X floatatom 233 131 5 0 0 0 - - -; 100 | #X text 279 131 sync; 101 | #X text 72 272 dentist~ punches out all but a select set of partials. 102 | The argument is the maximum frequency from which to select partials. 103 | ; 104 | #X floatatom 149 130 5 0 0 0 - gain -; 105 | #X connect 0 0 5 0; 106 | #X connect 0 1 9 0; 107 | #X connect 2 0 1 0; 108 | #X connect 4 0 0 1; 109 | #X connect 5 0 3 0; 110 | #X connect 5 0 3 1; 111 | #X connect 8 0 0 0; 112 | #X connect 12 0 5 1; 113 | -------------------------------------------------------------------------------- /disarrain~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 717 430 516 403 10; 2 | #N canvas 1009 566 462 312 disarrain-block 0; 3 | #X obj 137 111 disarrain~ 4000; 4 | #X obj 137 177 outlet~; 5 | #X obj 237 173 outlet; 6 | #X obj 137 66 inlet~; 7 | #X obj 53 247 block~ 256; 8 | #X obj 205 217 snapshot~; 9 | #X obj 324 189 metro 100; 10 | #X msg 325 162 1; 11 | #X obj 327 125 loadbang; 12 | #X obj 205 242 outlet; 13 | #X obj 316 74 inlet; 14 | #X connect 0 0 1 0; 15 | #X connect 0 1 5 0; 16 | #X connect 0 2 2 0; 17 | #X connect 3 0 0 0; 18 | #X connect 5 0 9 0; 19 | #X connect 6 0 5 0; 20 | #X connect 7 0 6 0; 21 | #X connect 8 0 7 0; 22 | #X connect 10 0 0 0; 23 | #X restore 63 80 pd disarrain-block; 24 | #X obj 63 11 phasor~ 174; 25 | #X obj 63 241 *~ 0.05; 26 | #X floatatom 123 132 5 0 0 0 - - -; 27 | #X obj 63 286 dac~; 28 | #X obj 110 199 hsl 128 15 0 0.5 0 0 empty empty empty -2 -6 0 8 -258444 29 | -1 -1 3000 1; 30 | #X floatatom 107 220 5 0 0 0 - - -; 31 | #X msg 285 258 \; pd dsp \$1; 32 | #X obj 285 237 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 33 | 1; 34 | #X text 51 333 disarrain~ is a modified version of disarray~ that interpolates 35 | between different spectral reorderings.; 36 | #N canvas 476 454 458 308 messages 0; 37 | #X obj 209 234 outlet; 38 | #X obj 303 202 fftease-system; 39 | #N canvas 904 74 603 462 main-messages 0; 40 | #X obj 8 407 outlet; 41 | #X floatatom 38 65 5 0 0 0 - - -; 42 | #X msg 77 148 forcefade \$1; 43 | #X obj 78 122 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 1 44 | ; 45 | #X floatatom 99 216 5 0 0 0 - - -; 46 | #X msg 99 242 fadetime \$1; 47 | #X floatatom 218 283 5 0 0 0 - - -; 48 | #X msg 218 309 topfreq \$1; 49 | #X msg 195 391 killfade; 50 | #X msg 38 91 switch_count \$1; 51 | #X msg 8 28 reset_shuffle; 52 | #X text 123 29 make new reordering; 53 | #X text 153 93 number of bins to reorder (at 0 there is no bin swapping) 54 | ; 55 | #X text 167 151 permit override of current fade for instantaneous changes 56 | ; 57 | #X text 297 312 top frequency to be shuffled; 58 | #X text 270 391 immediately end current crossfade; 59 | #X text 195 241 crossfade interpolation time; 60 | #X msg 99 194 3000; 61 | #X obj 99 172 loadbang; 62 | #X connect 1 0 9 0; 63 | #X connect 2 0 0 0; 64 | #X connect 3 0 2 0; 65 | #X connect 4 0 5 0; 66 | #X connect 5 0 0 0; 67 | #X connect 6 0 7 0; 68 | #X connect 7 0 0 0; 69 | #X connect 8 0 0 0; 70 | #X connect 9 0 0 0; 71 | #X connect 10 0 0 0; 72 | #X connect 17 0 4 0; 73 | #X connect 18 0 17 0; 74 | #X restore 31 31 pd main-messages; 75 | #N canvas 752 371 590 315 data 0; 76 | #X obj 89 237 outlet; 77 | #X msg 48 83 isetstate 73 109 187 113 3 2 1 30 96 4 7; 78 | #X msg 105 119 setstate 0 20 23 42 2 18 6 7 38 14 10 27 12 8 4 19 16 79 | 5 36 9 15 40 39 45 24 25 28 17 33 13 43 29 34 21 32 35 22 37 46 1 26 80 | 3 41 44 11 31 30 47 48 49; 81 | #X text 138 160 instant recall; 82 | #X text 51 67 recall a mapping you like; 83 | #X msg 194 188 showstate; 84 | #X text 269 189 output current remapping as a list; 85 | #X connect 1 0 0 0; 86 | #X connect 2 0 0 0; 87 | #X connect 5 0 0 0; 88 | #X restore 5 145 pd data; 89 | #X text 151 32 <- now go here; 90 | #X text 58 144 <- if you find a setting you like and wish to store 91 | it; 92 | #X connect 1 0 0 0; 93 | #X connect 2 0 0 0; 94 | #X connect 3 0 0 0; 95 | #X restore 184 53 pd messages; 96 | #X obj 184 111 print; 97 | #X text 229 113 prints current reordering; 98 | #X text 124 146 crossfade sync; 99 | #X text 277 56 <- start here; 100 | #X connect 0 0 2 0; 101 | #X connect 0 1 3 0; 102 | #X connect 0 2 11 0; 103 | #X connect 1 0 0 0; 104 | #X connect 2 0 4 0; 105 | #X connect 2 0 4 1; 106 | #X connect 5 0 6 0; 107 | #X connect 6 0 2 1; 108 | #X connect 8 0 7 0; 109 | #X connect 10 0 0 1; 110 | -------------------------------------------------------------------------------- /disarray~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 863 421 559 421 10; 2 | #X obj 174 83 phasor~ 300; 3 | #N canvas 0 22 478 328 disarray_block 0; 4 | #X obj 107 116 disarray~ 3000 0 4 1; 5 | #X obj 107 59 inlet~; 6 | #X obj 186 65 inlet; 7 | #X obj 107 186 outlet~; 8 | #X obj 295 170 print; 9 | #X obj 188 206 block~ 256; 10 | #X connect 0 0 3 0; 11 | #X connect 0 1 4 0; 12 | #X connect 1 0 0 0; 13 | #X connect 2 0 0 0; 14 | #X restore 174 133 pd disarray_block; 15 | #X obj 174 179 *~ 0.2; 16 | #X obj 174 216 dac~; 17 | #N canvas 673 80 659 338 messages 0; 18 | #X obj 172 305 outlet; 19 | #X obj 136 33 bng 15 250 50 0 empty empty empty 0 -6 0 8 -262144 -1 20 | -1; 21 | #X floatatom 304 138 5 0 0 0 - - -; 22 | #X msg 304 163 topfreq \$1; 23 | #X msg 184 130 switch_count \$1; 24 | #X floatatom 184 104 5 0 0 0 - - -; 25 | #X msg 415 201 showstate; 26 | #X obj 421 277 fftease-system; 27 | #X msg 184 81 40; 28 | #X obj 184 54 loadbang; 29 | #X msg 304 112 4000; 30 | #X obj 304 88 loadbang; 31 | #X text 344 137 top frequency to scramble; 32 | #X text 222 73 number of bins to scramble; 33 | #X text 418 182 report current scramble; 34 | #X text 160 30 get new distribution; 35 | #N canvas 887 617 454 304 data 0; 36 | #X obj 8 226 outlet; 37 | #X msg 8 104 35 89 192 56 132 187 141 82 51 87 156 43 103 37 80 122 38 | 107 1 109 209 81; 39 | #X text 11 80 load your own data as a list; 40 | #X text 62 139 use the data reported from "showstate" as a start; 41 | #X connect 1 0 0 0; 42 | #X restore 405 245 pd data; 43 | #X connect 1 0 0 0; 44 | #X connect 2 0 3 0; 45 | #X connect 3 0 0 0; 46 | #X connect 4 0 0 0; 47 | #X connect 5 0 4 0; 48 | #X connect 6 0 0 0; 49 | #X connect 7 0 0 0; 50 | #X connect 8 0 5 0; 51 | #X connect 9 0 8 0; 52 | #X connect 10 0 2 0; 53 | #X connect 11 0 10 0; 54 | #X connect 16 0 0 0; 55 | #X restore 288 90 pd messages; 56 | #X msg 26 166 \; pd dsp \$1; 57 | #X obj 26 143 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 1 58 | ; 59 | #X text 286 75 open for controls:; 60 | #X text 36 283 disarray~ reorders the weights of spectral components 61 | below a specified top frequency.; 62 | #X connect 0 0 1 0; 63 | #X connect 1 0 2 0; 64 | #X connect 2 0 3 0; 65 | #X connect 2 0 3 1; 66 | #X connect 4 0 1 1; 67 | #X connect 6 0 5 0; 68 | -------------------------------------------------------------------------------- /drown~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 1012 277 466 316 10; 2 | #N canvas 0 22 470 320 drown-block 0; 3 | #X obj 178 165 drown~ 0.001 0.1 4 1; 4 | #X obj 178 195 outlet~; 5 | #X obj 178 124 inlet~; 6 | #X obj 245 123 inlet; 7 | #X obj 313 125 inlet; 8 | #X obj 371 129 inlet; 9 | #X obj 178 232 block~ 256; 10 | #X connect 0 0 1 0; 11 | #X connect 2 0 0 0; 12 | #X connect 3 0 0 1; 13 | #X connect 4 0 0 2; 14 | #X connect 5 0 0 0; 15 | #X restore 18 93 pd drown-block; 16 | #X obj 18 140 dac~; 17 | #X msg 24 256 \; pd dsp \$1; 18 | #X obj 24 233 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1 19 | ; 20 | #X floatatom 49 49 5 0 0 0 - threshold -; 21 | #X floatatom 80 65 5 0 0 0 - noise-gain -; 22 | #N canvas 730 185 462 312 sound-source 0; 23 | #X obj 127 102 osc~ 350; 24 | #X obj 127 194 outlet~; 25 | #X obj 249 107 noise~; 26 | #X obj 127 155 *~ 0.1; 27 | #X obj 249 143 *~ 0.03; 28 | #X text 58 103 signal ->; 29 | #X text 298 110 <- add noise; 30 | #X connect 0 0 3 0; 31 | #X connect 2 0 4 0; 32 | #X connect 3 0 1 0; 33 | #X connect 4 0 1 0; 34 | #X restore 18 7 pd sound-source; 35 | #N canvas 928 509 470 320 messages 0; 36 | #X obj 231 210 outlet; 37 | #N canvas 0 22 458 308 init 0; 38 | #X obj 333 21 loadbang; 39 | #X obj 333 71 unpack f f; 40 | #X obj 333 103 s drown-s1; 41 | #X obj 362 129 s drown-s2; 42 | #X msg 333 48 0.01 1; 43 | #X connect 0 0 4 0; 44 | #X connect 1 0 2 0; 45 | #X connect 1 1 3 0; 46 | #X connect 4 0 1 0; 47 | #X restore 89 104 pd init; 48 | #X obj 231 180 fftease-system; 49 | #X connect 2 0 0 0; 50 | #X restore 163 77 pd messages; 51 | #X obj 26 173 hsl 128 15 0 0.02 0 0 threshold drown-s1 threshold -2 52 | -6 0 8 -189148 -1 -1 6800 1; 53 | #X obj 26 211 hsl 128 15 0 1 0 0 noise-gain drown-s2 noise-gain -2 54 | -6 0 8 -189148 -1 -1 0 1; 55 | #X text 160 210 <- reduce noise here; 56 | #X text 160 172 <- threshold to block noise; 57 | #X text 103 265 threshold-based noise reduction; 58 | #X connect 0 0 1 0; 59 | #X connect 0 0 1 1; 60 | #X connect 3 0 2 0; 61 | #X connect 4 0 0 1; 62 | #X connect 5 0 0 2; 63 | #X connect 6 0 0 0; 64 | #X connect 7 0 0 3; 65 | -------------------------------------------------------------------------------- /ether~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 281 24 660 446 10; 2 | #X obj 167 237 *~ 1; 3 | #X obj 167 289 dac~; 4 | #X floatatom 190 218 5 0 0 0 - centerring-gain -; 5 | #X msg 333 284 \; pd dsp \$1; 6 | #X obj 333 267 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 7 | 1; 8 | #X obj 17 207 hsl 128 15 0 4 0 0 centerring-gain empty output_gain 9 | -2 -6 0 8 -79789 -1 -1 1900 1; 10 | #N canvas 0 22 511 346 messages 0; 11 | #X obj 132 268 outlet; 12 | #X msg 34 232 fftinfo; 13 | #X msg 132 74 mute \$1; 14 | #X obj 132 41 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1 15 | ; 16 | #X msg 25 101 overlap \$1; 17 | #X msg 25 54 2; 18 | #X msg 55 71 4; 19 | #X text 208 216 turn on invert; 20 | #X text 221 177 is turned on; 21 | #X obj 187 217 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 22 | 1; 23 | #X msg 187 239 invert \$1; 24 | #X text 221 163 pad affects the gain only when "invert"; 25 | #X connect 1 0 0 0; 26 | #X connect 2 0 0 0; 27 | #X connect 3 0 2 0; 28 | #X connect 4 0 0 0; 29 | #X connect 5 0 4 0; 30 | #X connect 6 0 4 0; 31 | #X connect 9 0 10 0; 32 | #X connect 10 0 0 0; 33 | #X restore 448 167 pd messages; 34 | #X obj 18 241 hsl 128 15 0 256 0 0 eth-composite-index empty composite_index 35 | -2 -6 0 8 -88868 -1 -1 0 1; 36 | #N canvas 990 218 500 389 playsound1 0; 37 | #X obj 31 194 soundfiler; 38 | #X obj 31 160 openpanel; 39 | #X msg 31 131 bang; 40 | #X obj 227 284 outlet~; 41 | #X msg 227 244 bang; 42 | #X obj 348 228 spigot; 43 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 44 | 1; 45 | #X text 63 132 open the sound; 46 | #X text 133 244 then play it; 47 | #X text 304 190 loop if you like; 48 | #X text 316 205 comment; 49 | #X msg 31 177 read -resize \$1 ether-sound1; 50 | #X obj 227 268 tabplay~ ether-sound1; 51 | #N canvas 0 0 450 300 graph1 0; 52 | #X array ether-sound1 449212 float 2; 53 | #X coords 0 1 449211 -1 200 140 1; 54 | #X restore 244 30 graph; 55 | #X connect 1 0 11 0; 56 | #X connect 2 0 1 0; 57 | #X connect 4 0 12 0; 58 | #X connect 5 0 4 0; 59 | #X connect 6 0 5 1; 60 | #X connect 11 0 0 0; 61 | #X connect 12 0 3 0; 62 | #X connect 12 1 5 0; 63 | #X restore 167 97 pd playsound1; 64 | #N canvas 936 488 508 397 playsound2 0; 65 | #X obj 31 194 soundfiler; 66 | #X obj 31 160 openpanel; 67 | #X msg 31 131 bang; 68 | #X obj 227 284 outlet~; 69 | #X msg 227 244 bang; 70 | #X obj 348 228 spigot; 71 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 72 | 1; 73 | #X text 63 132 open the sound; 74 | #X text 133 244 then play it; 75 | #X text 304 190 loop if you like; 76 | #X text 316 205 comment; 77 | #X msg 31 177 read -resize \$1 ether-sound2; 78 | #N canvas 0 0 450 300 graph2 0; 79 | #X array ether-sound2 1.764e+06 float 2; 80 | #X coords 0 1 1.764e+06 -1 200 140 1; 81 | #X restore 236 17 graph; 82 | #X obj 227 268 tabplay~ ether-sound2; 83 | #X connect 1 0 11 0; 84 | #X connect 2 0 1 0; 85 | #X connect 4 0 13 0; 86 | #X connect 5 0 4 0; 87 | #X connect 6 0 5 1; 88 | #X connect 11 0 0 0; 89 | #X connect 13 0 3 0; 90 | #X connect 13 1 5 0; 91 | #X restore 198 116 pd playsound2; 92 | #X floatatom 229 159 5 0 0 0 - eth-composite-index -; 93 | #X text 286 101 <- load and loop two soundfiles to hear effect; 94 | #X obj 14 107 loadbang; 95 | #X text 31 316; 96 | #X text 23 318 ether~ selects portions of two input signals and creates 97 | a composite output spectrum based upon the amplitude of the inputs. 98 | The loudest band of the two inputs will be selected. Sending the inverse 99 | message will reverse this behavior selecting the weakest. The composite 100 | index is a scalar for the selection of the second input. Useful values 101 | will vary according to the amplitude characteristics of the input signals. 102 | Try values greater than 0 and less than 100 But higher values may be 103 | effective depending upon the input signals.; 104 | #N canvas 376 316 474 324 ether-block 0; 105 | #X obj 233 219 block~ 256; 106 | #X obj 163 185 outlet~; 107 | #X obj 163 38 inlet~; 108 | #X obj 269 107 inlet; 109 | #X obj 201 81 inlet; 110 | #X obj 181 60 inlet~; 111 | #X obj 163 128 ether~; 112 | #X connect 2 0 6 0; 113 | #X connect 3 0 6 0; 114 | #X connect 4 0 6 2; 115 | #X connect 5 0 6 1; 116 | #X connect 6 0 1 0; 117 | #X restore 167 183 pd ether-block; 118 | #X text 270 159 composite index; 119 | #X msg 14 123 0.1 1; 120 | #X obj 14 139 unpack f f; 121 | #X connect 0 0 1 0; 122 | #X connect 0 0 1 1; 123 | #X connect 2 0 0 1; 124 | #X connect 4 0 3 0; 125 | #X connect 6 0 15 3; 126 | #X connect 8 0 15 0; 127 | #X connect 9 0 15 1; 128 | #X connect 10 0 15 2; 129 | #X connect 12 0 17 0; 130 | #X connect 15 0 0 0; 131 | #X connect 17 0 18 0; 132 | #X connect 18 0 5 0; 133 | #X connect 18 1 7 0; 134 | -------------------------------------------------------------------------------- /examples/13et.scale: -------------------------------------------------------------------------------- 1 | 27.5000 2 | 29.0061 3 | 30.5946 4 | 32.2702 5 | 34.0375 6 | 35.9016 7 | 37.8678 8 | 39.9416 9 | 42.1291 10 | 44.4363 11 | 46.8699 12 | 49.4368 13 | 52.1443 14 | 55.0000 15 | 58.0121 16 | 61.1892 17 | 64.5403 18 | 68.0749 19 | 71.8031 20 | 75.7355 21 | 79.8833 22 | 84.2581 23 | 88.8726 24 | 93.7398 25 | 98.8736 26 | 104.2885 27 | 110.0000 28 | 116.0243 29 | 122.3785 30 | 129.0807 31 | 136.1499 32 | 143.6063 33 | 151.4710 34 | 159.7665 35 | 168.5163 36 | 177.7453 37 | 187.4797 38 | 197.7472 39 | 208.5771 40 | 220.0000 41 | 232.0485 42 | 244.7569 43 | 258.1613 44 | 272.2998 45 | 287.2126 46 | 302.9421 47 | 319.5330 48 | 337.0326 49 | 355.4906 50 | 374.9594 51 | 395.4944 52 | 417.1541 53 | 440.0000 54 | 464.0971 55 | 489.5138 56 | 516.3226 57 | 544.5996 58 | 574.4251 59 | 605.8842 60 | 639.0661 61 | 674.0652 62 | 710.9811 63 | 749.9187 64 | 790.9889 65 | 834.3082 66 | 880.0000 67 | 928.1941 68 | 979.0277 69 | 1032.6452 70 | 1089.1991 71 | 1148.8503 72 | 1211.7683 73 | 1278.1321 74 | 1348.1304 75 | 1421.9622 76 | 1499.8375 77 | 1581.9777 78 | 1668.6164 79 | 1760.0000 80 | 1856.3883 81 | 1958.0554 82 | 2065.2904 83 | 2178.3983 84 | 2297.7006 85 | 2423.5366 86 | 2556.2642 87 | 2696.2608 88 | 2843.9244 89 | 2999.6750 90 | 3163.9554 91 | 3337.2329 92 | 3520.0000 93 | 3712.7766 94 | 3916.1108 95 | 4130.5808 96 | 4356.7965 97 | 4595.4012 98 | 4847.0733 99 | 5112.5285 100 | 5392.5216 101 | 5687.8488 102 | 5999.3500 103 | 6327.9109 104 | 6674.4657 105 | 7040.0000 106 | 7425.5532 107 | 7832.2216 108 | 8261.1616 109 | 8713.5930 110 | 9190.8024 111 | 9694.1465 112 | 10225.0569 113 | 10785.0432 114 | 11375.6977 115 | 11998.7000 116 | 12655.8217 117 | 13348.9314 118 | 14080.0000 119 | 14851.1064 120 | 15664.4432 121 | 16522.3233 122 | 17427.1861 123 | 18381.6047 124 | 19388.2931 125 | 20450.1138 126 | 21570.0863 127 | -------------------------------------------------------------------------------- /examples/24et.scale: -------------------------------------------------------------------------------- 1 | 27.5000 2 | 28.3058 3 | 29.1352 4 | 29.9890 5 | 30.8677 6 | 31.7722 7 | 32.7032 8 | 33.6615 9 | 34.6478 10 | 35.6631 11 | 36.7081 12 | 37.7837 13 | 38.8909 14 | 40.0305 15 | 41.2034 16 | 42.4108 17 | 43.6535 18 | 44.9327 19 | 46.2493 20 | 47.6045 21 | 48.9994 22 | 50.4352 23 | 51.9131 24 | 53.4343 25 | 55.0000 26 | 56.6116 27 | 58.2705 28 | 59.9779 29 | 61.7354 30 | 63.5444 31 | 65.4064 32 | 67.3229 33 | 69.2957 34 | 71.3262 35 | 73.4162 36 | 75.5675 37 | 77.7817 38 | 80.0609 39 | 82.4069 40 | 84.8216 41 | 87.3071 42 | 89.8653 43 | 92.4986 44 | 95.2090 45 | 97.9989 46 | 100.8704 47 | 103.8262 48 | 106.8685 49 | 110.0000 50 | 113.2232 51 | 116.5409 52 | 119.9559 53 | 123.4708 54 | 127.0888 55 | 130.8128 56 | 134.6459 57 | 138.5913 58 | 142.6524 59 | 146.8324 60 | 151.1349 61 | 155.5635 62 | 160.1219 63 | 164.8138 64 | 169.6432 65 | 174.6141 66 | 179.7307 67 | 184.9972 68 | 190.4180 69 | 195.9977 70 | 201.7409 71 | 207.6523 72 | 213.7370 73 | 220.0000 74 | 226.4465 75 | 233.0819 76 | 239.9117 77 | 246.9417 78 | 254.1776 79 | 261.6256 80 | 269.2918 81 | 277.1826 82 | 285.3047 83 | 293.6648 84 | 302.2698 85 | 311.1270 86 | 320.2437 87 | 329.6276 88 | 339.2864 89 | 349.2282 90 | 359.4614 91 | 369.9944 92 | 380.8361 93 | 391.9954 94 | 403.4818 95 | 415.3047 96 | 427.4741 97 | 440.0000 98 | 452.8930 99 | 466.1638 100 | 479.8234 101 | 493.8833 102 | 508.3552 103 | 523.2511 104 | 538.5836 105 | 554.3653 106 | 570.6094 107 | 587.3295 108 | 604.5396 109 | 622.2540 110 | 640.4874 111 | 659.2551 112 | 678.5728 113 | 698.4565 114 | 718.9228 115 | 739.9888 116 | 761.6722 117 | 783.9909 118 | 806.9636 119 | 830.6094 120 | 854.9481 121 | 880.0000 122 | 905.7860 123 | 932.3275 124 | 959.6468 125 | 987.7666 126 | 1016.7104 127 | 1046.5023 128 | 1077.1671 129 | 1108.7305 130 | 1141.2188 131 | 1174.6591 132 | 1209.0792 133 | 1244.5079 134 | 1280.9748 135 | 1318.5102 136 | 1357.1455 137 | 1396.9129 138 | 1437.8456 139 | 1479.9777 140 | 1523.3443 141 | 1567.9817 142 | 1613.9271 143 | 1661.2188 144 | 1709.8962 145 | 1760.0000 146 | 1811.5719 147 | 1864.6550 148 | 1919.2936 149 | 1975.5332 150 | 2033.4207 151 | 2093.0045 152 | 2154.3342 153 | 2217.4610 154 | 2282.4376 155 | 2349.3181 156 | 2418.1584 157 | 2489.0159 158 | 2561.9496 159 | 2637.0205 160 | 2714.2911 161 | 2793.8259 162 | 2875.6912 163 | 2959.9554 164 | 3046.6887 165 | 3135.9635 166 | 3227.8542 167 | 3322.4376 168 | 3419.7924 169 | 3520.0000 170 | 3623.1439 171 | 3729.3101 172 | 3838.5872 173 | 3951.0664 174 | 4066.8415 175 | 4186.0090 176 | 4308.6685 177 | 4434.9221 178 | 4564.8752 179 | 4698.6363 180 | 4836.3168 181 | 4978.0317 182 | 5123.8992 183 | 5274.0409 184 | 5428.5821 185 | 5587.6517 186 | 5751.3824 187 | 5919.9108 188 | 6093.3774 189 | 6271.9270 190 | 6455.7085 191 | 6644.8752 192 | 6839.5849 193 | 7040.0000 194 | 7246.2877 195 | 7458.6202 196 | 7677.1744 197 | 7902.1328 198 | 8133.6830 199 | 8372.0181 200 | 8617.3369 201 | 8869.8442 202 | 9129.7505 203 | 9397.2726 204 | 9672.6337 205 | 9956.0635 206 | 10247.7984 207 | 10548.0818 208 | 10857.1642 209 | 11175.3034 210 | 11502.7648 211 | 11839.8215 212 | 12186.7548 213 | 12543.8540 214 | 12911.4169 215 | 13289.7503 216 | 13679.1697 217 | 14080.0000 218 | 14492.5755 219 | 14917.2404 220 | 15354.3489 221 | 15804.2656 222 | 16267.3660 223 | 16744.0362 224 | 17234.6739 225 | 17739.6884 226 | 18259.5009 227 | 18794.5451 228 | 19345.2674 229 | 19912.1270 230 | 20495.5968 231 | 21096.1636 232 | 21714.3284 233 | -------------------------------------------------------------------------------- /examples/4th.scale: -------------------------------------------------------------------------------- 1 | 27.5000 2 | 36.6667 3 | 48.8889 4 | 65.1852 5 | 86.9136 6 | 115.8848 7 | 154.5130 8 | 206.0174 9 | 274.6898 10 | 366.2531 11 | 488.3375 12 | 651.1166 13 | 868.1555 14 | 1157.5407 15 | 1543.3876 16 | 2057.8501 17 | 2743.8002 18 | 3658.4002 19 | 4877.8670 20 | 6503.8226 21 | 8671.7635 22 | 11562.3514 23 | 15416.4685 24 | 20555.2913 25 | -------------------------------------------------------------------------------- /examples/Piano.aif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pd-projects/fftease/9b83b3271d9f79055c08007e1a72c3dd4ca08a58/examples/Piano.aif -------------------------------------------------------------------------------- /examples/blue3.scale: -------------------------------------------------------------------------------- 1 | 27.5000 2 | 33.6875 3 | 41.2672 4 | 50.5523 5 | 61.9266 6 | 75.8601 7 | 92.9286 8 | 113.8375 9 | 139.4509 10 | 170.8274 11 | 209.2635 12 | 256.3478 13 | 314.0261 14 | 384.6820 15 | 471.2354 16 | 577.2634 17 | 707.1477 18 | 866.2559 19 | 1061.1635 20 | 1299.9252 21 | 1592.4084 22 | 1950.7003 23 | 2389.6079 24 | 2927.2697 25 | 3585.9054 26 | 4392.7341 27 | 5381.0992 28 | 6591.8465 29 | 8075.0120 30 | 9891.8897 31 | 12117.5649 32 | 14844.0170 33 | 18183.9208 34 | -------------------------------------------------------------------------------- /examples/m3M3.scale: -------------------------------------------------------------------------------- 1 | 27.5000 2 | 33.0000 3 | 41.2500 4 | 49.5000 5 | 61.8750 6 | 74.2500 7 | 92.8125 8 | 111.3750 9 | 139.2188 10 | 167.0625 11 | 208.8281 12 | 250.5938 13 | 313.2422 14 | 375.8906 15 | 469.8633 16 | 563.8359 17 | 704.7949 18 | 845.7539 19 | 1057.1924 20 | 1268.6309 21 | 1585.7886 22 | 1902.9463 23 | 2378.6829 24 | 2854.4194 25 | 3568.0243 26 | 4281.6292 27 | 5352.0364 28 | 6422.4437 29 | 8028.0547 30 | 9633.6656 31 | 12042.0820 32 | 14450.4984 33 | 18063.1230 34 | 21675.7476 35 | -------------------------------------------------------------------------------- /examples/m3chord.scale: -------------------------------------------------------------------------------- 1 | 27.5000 2 | 33.0000 3 | 36.6667 4 | 44.0000 5 | 48.8889 6 | 55.0000 7 | 66.0000 8 | 73.3333 9 | 88.0000 10 | 97.7778 11 | 110.0000 12 | 132.0000 13 | 146.6667 14 | 176.0000 15 | 195.5556 16 | 220.0000 17 | 264.0000 18 | 293.3333 19 | 352.0000 20 | 391.1111 21 | 440.0000 22 | 528.0000 23 | 586.6667 24 | 704.0000 25 | 782.2222 26 | 880.0000 27 | 1056.0000 28 | 1173.3333 29 | 1408.0000 30 | 1564.4444 31 | 1760.0000 32 | 2112.0000 33 | 2346.6667 34 | 2816.0000 35 | 3128.8889 36 | 3520.0000 37 | 4224.0000 38 | 4693.3333 39 | 5632.0000 40 | 6257.7778 41 | 7040.0000 42 | 8448.0000 43 | 9386.6667 44 | 11264.0000 45 | 12515.5556 46 | 14080.0000 47 | 16896.0000 48 | 18773.3333 49 | 22528.0000 50 | 25031.1111 51 | -------------------------------------------------------------------------------- /examples/octfifth.scale: -------------------------------------------------------------------------------- 1 | 27.5000 2 | 41.2500 3 | 55.0000 4 | 82.5000 5 | 110.0000 6 | 165.0000 7 | 220.0000 8 | 330.0000 9 | 440.0000 10 | 660.0000 11 | 880.0000 12 | 1320.0000 13 | 1760.0000 14 | 2640.0000 15 | 3520.0000 16 | 5280.0000 17 | 7040.0000 18 | 10560.0000 19 | 14080.0000 20 | 21120.0000 21 | -------------------------------------------------------------------------------- /examples/scale1.pl: -------------------------------------------------------------------------------- 1 | #!/usr/local/bin/perl 2 | 3 | # -*-Perl-*- 4 | 5 | $file = "m3M3.scale"; 6 | 7 | open(OUT, ">$file"); 8 | 9 | $base = 27.5; 10 | 11 | @ints = (1.2, 1.25); 12 | $phs = 0; 13 | 14 | while( $base < 22050 ){ 15 | printf OUT "%.4f\n", $base; 16 | $base *= $ints[$phs++]; 17 | $phs %= 2; 18 | } 19 | close $file; 20 | print "wrote to $file\n"; 21 | -------------------------------------------------------------------------------- /examples/scale2.pl: -------------------------------------------------------------------------------- 1 | #!/usr/local/bin/perl 2 | 3 | # -*-Perl-*- 4 | 5 | $file = "4th.scale"; 6 | 7 | open(OUT, ">$file"); 8 | 9 | $base = 27.5; 10 | 11 | @ints = (1.2, 1.25); 12 | $phs = 0; 13 | 14 | while( $base < 22050 ){ 15 | printf OUT "%.4f\n", $base; 16 | $base *= 1.33333333333; 17 | } 18 | close $file; 19 | print "wrote to $file\n"; 20 | -------------------------------------------------------------------------------- /examples/scale3.pl: -------------------------------------------------------------------------------- 1 | #!/usr/local/bin/perl 2 | 3 | # -*-Perl-*- 4 | 5 | $file = "blue3.scale"; 6 | 7 | open(OUT, ">$file"); 8 | 9 | $base = 27.5; 10 | 11 | while( $base < 22050 ){ 12 | printf OUT "%.4f\n", $base; 13 | $base *= 1.225; 14 | } 15 | close $file; 16 | print "wrote to $file\n"; 17 | -------------------------------------------------------------------------------- /examples/scale4.pl: -------------------------------------------------------------------------------- 1 | #!/usr/local/bin/perl 2 | 3 | # -*-Perl-*- 4 | 5 | $file = "13et.scale"; 6 | 7 | open(OUT, ">$file"); 8 | 9 | $base = 27.5; 10 | $mult = 2 ** (1/13); 11 | while( $base < 22050 ){ 12 | printf OUT "%.4f\n", $base; 13 | $base *= $mult; 14 | } 15 | close $file; 16 | print "wrote to $file\n"; 17 | -------------------------------------------------------------------------------- /examples/scale5.pl: -------------------------------------------------------------------------------- 1 | #!/usr/local/bin/perl 2 | 3 | # -*-Perl-*- 4 | 5 | $file = "24et.scale"; 6 | 7 | open(OUT, ">$file"); 8 | 9 | $base = 27.5; 10 | $mult = 2 ** (1/24); 11 | while( $base < 22050 ){ 12 | printf OUT "%.4f\n", $base; 13 | $base *= $mult; 14 | } 15 | close $file; 16 | print "wrote to $file\n"; 17 | -------------------------------------------------------------------------------- /examples/scale6.pl: -------------------------------------------------------------------------------- 1 | #!/usr/local/bin/perl 2 | 3 | # -*-Perl-*- 4 | 5 | $file = "octfifth.scale"; 6 | 7 | open(OUT, ">$file"); 8 | 9 | $base = 27.5; 10 | 11 | @ints = (1.5, 4/3); 12 | $phs = 0; 13 | 14 | while( $base < 22050 ){ 15 | printf OUT "%.4f\n", $base; 16 | $base *= $ints[$phs++]; 17 | $phs %= 2; 18 | } 19 | close $file; 20 | print "wrote to $file\n"; 21 | -------------------------------------------------------------------------------- /examples/scale7.pl: -------------------------------------------------------------------------------- 1 | #!/usr/local/bin/perl 2 | 3 | # -*-Perl-*- 4 | 5 | $file = "m3chord.scale"; 6 | 7 | open(OUT, ">$file"); 8 | 9 | $base = 27.5; 10 | 11 | @ints = (1.2, 9/8, 1.2, 9/8, 9/8); 12 | @ints = (1, 1.2, 4/3, 1.2 * (4/3), 16/9); 13 | $phs = 0; 14 | 15 | 16 | $octmult = 1; 17 | while( $val < 22050 ){ 18 | for $i (0..$#ints){ 19 | $val = $base * $ints[$i] * $octmult; 20 | printf OUT "%.4f\n", $val; 21 | } 22 | $octmult *= 2; 23 | } 24 | close $file; 25 | print "wrote to $file\n"; 26 | -------------------------------------------------------------------------------- /examples/test.scale: -------------------------------------------------------------------------------- 1 | 10. 2 | 11. 3 | 12 4 | 13 5 | 17 6 | -------------------------------------------------------------------------------- /fft.c: -------------------------------------------------------------------------------- 1 | #include "fftease.h" /* If forward is true, rfft replaces 2*N real data points in x with N complex values representing the positive frequency half of their Fourier spectrum, with x[1] replaced with the real part of the Nyquist frequency value. If forward is false, rfft expects x to contain a positive frequency spectrum arranged as before, and replaces it with 2*N real values. N MUST be a power of 2. */ void rfft( float *x, int N, int forward ) { float c1,c2, h1r,h1i, h2r,h2i, wr,wi, wpr,wpi, temp, theta; float xr,xi; int i, i1,i2,i3,i4, N2p1; static int first = 1; /*float PI, TWOPI;*/ void cfft(); if ( first ) { first = 0; } theta = PI/N; wr = 1.; wi = 0.; c1 = 0.5; if ( forward ) { c2 = -0.5; cfft( x, N, forward ); xr = x[0]; xi = x[1]; } else { c2 = 0.5; theta = -theta; xr = x[1]; xi = 0.; x[1] = 0.; } wpr = -2.*pow( sin( 0.5*theta ), 2. ); wpi = sin( theta ); N2p1 = (N<<1) + 1; for ( i = 0; i <= N>>1; i++ ) { i1 = i<<1; i2 = i1 + 1; i3 = N2p1 - i2; i4 = i3 + 1; if ( i == 0 ) { h1r = c1*(x[i1] + xr ); h1i = c1*(x[i2] - xi ); h2r = -c2*(x[i2] + xi ); h2i = c2*(x[i1] - xr ); x[i1] = h1r + wr*h2r - wi*h2i; x[i2] = h1i + wr*h2i + wi*h2r; xr = h1r - wr*h2r + wi*h2i; xi = -h1i + wr*h2i + wi*h2r; } else { h1r = c1*(x[i1] + x[i3] ); h1i = c1*(x[i2] - x[i4] ); h2r = -c2*(x[i2] + x[i4] ); h2i = c2*(x[i1] - x[i3] ); x[i1] = h1r + wr*h2r - wi*h2i; x[i2] = h1i + wr*h2i + wi*h2r; x[i3] = h1r - wr*h2r + wi*h2i; x[i4] = -h1i + wr*h2i + wi*h2r; } wr = (temp = wr)*wpr - wi*wpi + wr; wi = wi*wpr + temp*wpi + wi; } if ( forward ) x[1] = xr; else cfft( x, N, forward ); } /* cfft replaces float array x containing NC complex values (2*NC float values alternating real, imagininary, etc.) by its Fourier transform if forward is true, or by its inverse Fourier transform if forward is false, using a recursive Fast Fourier transform method due to Danielson and Lanczos. NC MUST be a power of 2. */ void cfft( float *x, int NC, int forward ) { float wr,wi, wpr,wpi, theta, scale; int mmax, ND, m, i,j, delta; void bitreverse(); ND = NC<<1; bitreverse( x, ND ); for ( mmax = 2; mmax < ND; mmax = delta ) { delta = mmax<<1; theta = TWOPI/( forward? mmax : -mmax ); wpr = -2.*pow( sin( 0.5*theta ), 2. ); wpi = sin( theta ); wr = 1.; wi = 0.; for ( m = 0; m < mmax; m += 2 ) { register float rtemp, itemp; for ( i = m; i < ND; i += delta ) { j = i + mmax; rtemp = wr*x[j] - wi*x[j+1]; itemp = wr*x[j+1] + wi*x[j]; x[j] = x[i] - rtemp; x[j+1] = x[i+1] - itemp; x[i] += rtemp; x[i+1] += itemp; } wr = (rtemp = wr)*wpr - wi*wpi + wr; wi = wi*wpr + rtemp*wpi + wi; } } /* scale output */ scale = forward ? 1./ND : 2.; { register float *xi=x, *xe=x+ND; while ( xi < xe ) *xi++ *= scale; } } /* bitreverse places float array x containing N/2 complex values into bit-reversed order */ void bitreverse( float *x, int N ) { float rtemp,itemp; int i,j, m; for ( i = j = 0; i < N; i += 2, j += m ) { if ( j > i ) { rtemp = x[j]; itemp = x[j+1]; /* complex exchange */ x[j] = x[i]; x[j+1] = x[i+1]; x[i] = rtemp; x[i+1] = itemp; } for ( m = N>>1; m >= 2 && j >= m; m >>= 1 ) j -= m; } } -------------------------------------------------------------------------------- /fft4.c: -------------------------------------------------------------------------------- 1 | #include #include "fftease.h" void init_rdft(int n, int *ip, float *w) { int nw, nc; void makewt(int nw, int *ip, float *w); void makect(int nc, int *ip, float *c); nw = n >> 2; makewt(nw, ip, w); nc = n >> 2; makect(nc, ip, w + nw); return; } void rdft(int n, int isgn, float *a, int *ip, float *w) { int j, nw, nc; float xi; void bitrv2(int n, int *ip, float *a), cftsub(int n, float *a, float *w), rftsub(int n, float *a, int nc, float *c); nw = ip[0]; nc = ip[1]; if (isgn < 0) { a[1] = 0.5 * (a[1] - a[0]); a[0] += a[1]; for (j = 3; j <= n - 1; j += 2) { a[j] = -a[j]; } if (n > 4) { rftsub(n, a, nc, w + nw); bitrv2(n, ip + 2, a); } cftsub(n, a, w); for (j = 1; j <= n - 1; j += 2) { a[j] = -a[j]; } } else { if (n > 4) { bitrv2(n, ip + 2, a); } cftsub(n, a, w); if (n > 4) { rftsub(n, a, nc, w + nw); } xi = a[0] - a[1]; a[0] += a[1]; a[1] = xi; } } void bitrv2(int n, int *ip, float *a) { int j, j1, k, k1, l, m, m2; float xr, xi; ip[0] = 0; l = n; m = 1; while ((m << 2) < l) { l >>= 1; for (j = 0; j <= m - 1; j++) { ip[m + j] = ip[j] + l; } m <<= 1; } if ((m << 2) > l) { for (k = 1; k <= m - 1; k++) { for (j = 0; j <= k - 1; j++) { j1 = (j << 1) + ip[k]; k1 = (k << 1) + ip[j]; xr = a[j1]; xi = a[j1 + 1]; a[j1] = a[k1]; a[j1 + 1] = a[k1 + 1]; a[k1] = xr; a[k1 + 1] = xi; } } } else { m2 = m << 1; for (k = 1; k <= m - 1; k++) { for (j = 0; j <= k - 1; j++) { j1 = (j << 1) + ip[k]; k1 = (k << 1) + ip[j]; xr = a[j1]; xi = a[j1 + 1]; a[j1] = a[k1]; a[j1 + 1] = a[k1 + 1]; a[k1] = xr; a[k1 + 1] = xi; j1 += m2; k1 += m2; xr = a[j1]; xi = a[j1 + 1]; a[j1] = a[k1]; a[j1 + 1] = a[k1 + 1]; a[k1] = xr; a[k1 + 1] = xi; } } } } void cftsub(int n, float *a, float *w) { int j, j1, j2, j3, k, k1, ks, l, m; float wk1r, wk1i, wk2r, wk2i, wk3r, wk3i; float x0r, x0i, x1r, x1i, x2r, x2i, x3r, x3i; l = 2; while ((l << 1) < n) { m = l << 2; for (j = 0; j <= l - 2; j += 2) { j1 = j + l; j2 = j1 + l; j3 = j2 + l; x0r = a[j] + a[j1]; x0i = a[j + 1] + a[j1 + 1]; x1r = a[j] - a[j1]; x1i = a[j + 1] - a[j1 + 1]; x2r = a[j2] + a[j3]; x2i = a[j2 + 1] + a[j3 + 1]; x3r = a[j2] - a[j3]; x3i = a[j2 + 1] - a[j3 + 1]; a[j] = x0r + x2r; a[j + 1] = x0i + x2i; a[j2] = x0r - x2r; a[j2 + 1] = x0i - x2i; a[j1] = x1r - x3i; a[j1 + 1] = x1i + x3r; a[j3] = x1r + x3i; a[j3 + 1] = x1i - x3r; } if (m < n) { wk1r = w[2]; for (j = m; j <= l + m - 2; j += 2) { j1 = j + l; j2 = j1 + l; j3 = j2 + l; x0r = a[j] + a[j1]; x0i = a[j + 1] + a[j1 + 1]; x1r = a[j] - a[j1]; x1i = a[j + 1] - a[j1 + 1]; x2r = a[j2] + a[j3]; x2i = a[j2 + 1] + a[j3 + 1]; x3r = a[j2] - a[j3]; x3i = a[j2 + 1] - a[j3 + 1]; a[j] = x0r + x2r; a[j + 1] = x0i + x2i; a[j2] = x2i - x0i; a[j2 + 1] = x0r - x2r; x0r = x1r - x3i; x0i = x1i + x3r; a[j1] = wk1r * (x0r - x0i); a[j1 + 1] = wk1r * (x0r + x0i); x0r = x3i + x1r; x0i = x3r - x1i; a[j3] = wk1r * (x0i - x0r); a[j3 + 1] = wk1r * (x0i + x0r); } k1 = 1; ks = -1; for (k = (m << 1); k <= n - m; k += m) { k1++; ks = -ks; wk1r = w[k1 << 1]; wk1i = w[(k1 << 1) + 1]; wk2r = ks * w[k1]; wk2i = w[k1 + ks]; wk3r = wk1r - 2 * wk2i * wk1i; wk3i = 2 * wk2i * wk1r - wk1i; for (j = k; j <= l + k - 2; j += 2) { j1 = j + l; j2 = j1 + l; j3 = j2 + l; x0r = a[j] + a[j1]; x0i = a[j + 1] + a[j1 + 1]; x1r = a[j] - a[j1]; x1i = a[j + 1] - a[j1 + 1]; x2r = a[j2] + a[j3]; x2i = a[j2 + 1] + a[j3 + 1]; x3r = a[j2] - a[j3]; x3i = a[j2 + 1] - a[j3 + 1]; a[j] = x0r + x2r; a[j + 1] = x0i + x2i; x0r -= x2r; x0i -= x2i; a[j2] = wk2r * x0r - wk2i * x0i; a[j2 + 1] = wk2r * x0i + wk2i * x0r; x0r = x1r - x3i; x0i = x1i + x3r; a[j1] = wk1r * x0r - wk1i * x0i; a[j1 + 1] = wk1r * x0i + wk1i * x0r; x0r = x1r + x3i; x0i = x1i - x3r; a[j3] = wk3r * x0r - wk3i * x0i; a[j3 + 1] = wk3r * x0i + wk3i * x0r; } } } l = m; } if (l < n) { for (j = 0; j <= l - 2; j += 2) { j1 = j + l; x0r = a[j] - a[j1]; x0i = a[j + 1] - a[j1 + 1]; a[j] += a[j1]; a[j + 1] += a[j1 + 1]; a[j1] = x0r; a[j1 + 1] = x0i; } } } void rftsub(int n, float *a, int nc, float *c) { int j, k, kk, ks; float wkr, wki, xr, xi, yr, yi; ks = (nc << 2) / n; kk = 0; for (k = (n >> 1) - 2; k >= 2; k -= 2) { j = n - k; kk += ks; wkr = 0.5 - c[kk]; wki = c[nc - kk]; xr = a[k] - a[j]; xi = a[k + 1] + a[j + 1]; yr = wkr * xr - wki * xi; yi = wkr * xi + wki * xr; a[k] -= yr; a[k + 1] -= yi; a[j] += yr; a[j + 1] -= yi; } } void makewt(int nw, int *ip, float *w) { void bitrv2(int n, int *ip, float *a); int nwh, j; float delta, x, y; ip[0] = nw; ip[1] = 1; if (nw > 2) { nwh = nw >> 1; delta = atan(1.0) / nwh; w[0] = 1; w[1] = 0; w[nwh] = cos(delta * nwh); w[nwh + 1] = w[nwh]; for (j = 2; j <= nwh - 2; j += 2) { x = cos(delta * j); y = sin(delta * j); w[j] = x; w[j + 1] = y; w[nw - j] = y; w[nw - j + 1] = x; } bitrv2(nw, ip + 2, w); } } void makect(int nc, int *ip, float *c) { int nch, j; float delta; ip[1] = nc; if (nc > 1) { nch = nc >> 1; delta = atan(1.0) / nch; c[0] = 0.5; c[nch] = 0.5 * cos(delta * nch); for (j = 1; j <= nch - 1; j++) { c[j] = 0.5 * cos(delta * j); c[nc - j] = 0.5 * sin(delta * j); } } } -------------------------------------------------------------------------------- /fftease-meta.pd: -------------------------------------------------------------------------------- 1 | #N canvas 15 49 200 200 10; 2 | #N canvas 25 49 420 300 META 1; 3 | #X text 13 41 NAME fftease; 4 | #X text 10 25 AUTHOR Eric Lyon and Christopher Penrose; 5 | #X text 10 10 VERSION 2.5.2.git20121005; 6 | #X text 10 60 LICENSE MIT; 7 | #X restore 10 10 pd META; 8 | -------------------------------------------------------------------------------- /fftease-system-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 629 262 450 300 10; 2 | #X obj 123 118 fftease-system; 3 | #X text 37 31 [fftease-system] is a support object for the FFTease 4 | library. It is used for sending standard control messages to configure 5 | various objects. Open the object itself for more information:; 6 | -------------------------------------------------------------------------------- /fftease-system.pd: -------------------------------------------------------------------------------- 1 | #N canvas 724 87 493 474 10; 2 | #X obj 174 207 outlet; 3 | #X msg 174 167 overlap \$1; 4 | #X msg 161 122 2; 5 | #X msg 202 121 4; 6 | #X msg 235 120 8; 7 | #X msg 297 165 winfac \$1; 8 | #X msg 282 120 1; 9 | #X msg 323 119 2; 10 | #X msg 355 118 4; 11 | #X msg 36 175 fftinfo; 12 | #X msg 102 155 mute \$1; 13 | #X obj 102 120 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 14 | 1; 15 | #X text 45 27 FFT size is overlap times the fftease subpatch block 16 | size (256 in our examples). With a blocksize of 256 and overlap 4 your 17 | FFT size is 1024 Higher overlap generally gives higher quality \, but 18 | CPU load is proportional to overlap \, so if you double the overlap 19 | \, you double the CPU load.; 20 | #X text 33 245 winfac determines the ratio between the FFT size and 21 | an input window that funnels samples into the FFT. Roughly speaking 22 | \, smaller window sizes (minimum is 1) give tighter temporal response 23 | \, but higher sizes can improve frequency performance \, especially 24 | with lower FFT sizes.; 25 | #X text 29 337 It is recommended that overlap and winfac only be used 26 | when the DACs are off. They can potentially crash Pd when the DACs 27 | are active.; 28 | #X connect 1 0 0 0; 29 | #X connect 2 0 1 0; 30 | #X connect 3 0 1 0; 31 | #X connect 4 0 1 0; 32 | #X connect 5 0 0 0; 33 | #X connect 6 0 5 0; 34 | #X connect 7 0 5 0; 35 | #X connect 8 0 5 0; 36 | #X connect 9 0 0 0; 37 | #X connect 10 0 0 0; 38 | #X connect 11 0 10 0; 39 | -------------------------------------------------------------------------------- /fftease.h: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | 6 | 7 | /* 8 | The new improved fftease.h 9 | */ 10 | 11 | #define getbytes t_getbytes 12 | #define freebytes t_freebytes 13 | #define resizebytes t_resizebytes 14 | 15 | #define FFTEASE_ANNOUNCEMENT "- a member of FFTease 2.52" 16 | 17 | #ifndef PI 18 | #define PI 3.141592653589793115997963468544185161590576171875 19 | #endif 20 | 21 | #ifndef TWOPI 22 | #define TWOPI 6.28318530717958623199592693708837032318115234375 23 | #endif 24 | 25 | #define MAX_N (16384) 26 | #define MAX_N2 (MAX_N/2) 27 | #define MAX_Nw (MAX_N * 4) 28 | 29 | void convert(float *S, float *C, int N2, float *lastphase, float fundamental, float factor ); 30 | void unconvert( float *C, float *S, int N2, float *lastphase, float fundamental, float factor ); 31 | void rfft( float *x, int N, int forward ); 32 | void cfft( float *x, int NC, int forward ); 33 | void bitreverse( float *x, int N ); 34 | void fold( float *I, float *W, int Nw, float *O, int N, int n ); 35 | void init_rdft(int n, int *ip, float *w); 36 | void rdft(int n, int isgn, float *a, int *ip, float *w); 37 | void bitrv2(int n, int *ip, float *a); 38 | void cftsub(int n, float *a, float *w); 39 | void rftsub(int n, float *a, int nc, float *c); 40 | void makewt(int nw, int *ip, float *w); 41 | void makect(int nc, int *ip, float *c); 42 | void leanconvert( float *S, float *C, int N2 ); 43 | void leanunconvert( float *C, float *S, int N2 ); 44 | void makewindows( float *H, float *A, float *S, int Nw, int N, int I ); 45 | void makehamming( float *H, float *A, float *S, int Nw, int N, int I,int odd ); 46 | void makehanning( float *H, float *A, float *S, int Nw, int N, int I,int odd ); 47 | void overlapadd( float *I, int N, float *W, float *O, int Nw, int n ); 48 | void bloscbank( float *S, float *O, int D, float iD, float *lf, float *la, 49 | float *bindex, float *tab, int len, float synt, int lo, int hi ); 50 | 51 | float randf( float min, float max ); 52 | int randi( int min, int max ); 53 | int power_of_two(int test); 54 | 55 | 56 | void freebytes2(void *fatso, size_t nbytes); 57 | void *getbytes2(size_t nbytes); 58 | void *resizebytes2(void *old, size_t oldsize, size_t newsize); 59 | void limit_fftsize(int *N, int *Nw, char *OBJECT_NAME); 60 | 61 | /* THE FUNCTIONS */ 62 | -------------------------------------------------------------------------------- /fftease_setup.c: -------------------------------------------------------------------------------- 1 | void fftease_setup(void) 2 | { 3 | post("Loaded FFTease Library"); 4 | printf("Loaded FFTease Library(2)"); 5 | } 6 | -------------------------------------------------------------------------------- /fold.c: -------------------------------------------------------------------------------- 1 | #include "fftease.h" /* * multiply current input I by window W (both of length Nw); * using modulus arithmetic, fold and rotate windowed input * into output array O of (FFT) length N according to current * input time n */ void fold( float *I, float *W, int Nw, float *O, int N, int n ) { int i; for ( i = 0; i < N; i++ ) O[i] = 0.; while ( n < 0 ) n += N; n %= N; for ( i = 0; i < Nw; i++ ) { O[n] += I[i]*W[i]; if ( ++n == N ) n = 0; } } -------------------------------------------------------------------------------- /leaker~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 718 386 500 440 10; 2 | #N canvas 0 22 462 312 leaker-block 0; 3 | #X obj 194 143 outlet~; 4 | #X obj 198 186 block~ 256; 5 | #X obj 194 112 leaker~ 4 1; 6 | #X obj 165 52 inlet~; 7 | #X obj 212 52 inlet~; 8 | #X obj 280 60 inlet; 9 | #X obj 329 97 inlet; 10 | #X connect 2 0 0 0; 11 | #X connect 3 0 2 0; 12 | #X connect 4 0 2 1; 13 | #X connect 5 0 2 2; 14 | #X connect 6 0 2 0; 15 | #X restore 96 168 pd leaker-block; 16 | #X msg 255 182 \; pd dsp \$1; 17 | #X obj 255 159 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 18 | 1; 19 | #X obj 96 221 dac~; 20 | #X floatatom 162 113 5 0 1 0 - xfade -; 21 | #X obj 100 254 hsl 128 15 0 1 0 0 xfade empty xfade -2 -6 0 8 -260372 22 | -1 -1 10400 1; 23 | #N canvas 0 22 466 316 messages 1; 24 | #X msg 40 116 upsieve; 25 | #X msg 52 138 downsieve; 26 | #X msg 69 163 randsieve; 27 | #X obj 40 262 outlet; 28 | #X obj 105 220 fftease-system; 29 | #X text 43 90 select sieve characteristic:; 30 | #X connect 0 0 3 0; 31 | #X connect 1 0 3 0; 32 | #X connect 2 0 3 0; 33 | #X connect 4 0 3 0; 34 | #X restore 196 141 pd messages; 35 | #X text 237 254 <- spectral crossfade here; 36 | #X obj 16 215 loadbang; 37 | #X msg 16 238 0.5; 38 | #N canvas 990 218 520 409 playsound1 0; 39 | #X obj 31 194 soundfiler; 40 | #X obj 31 160 openpanel; 41 | #N canvas 0 22 450 300 graph1 0; 42 | #X array leaker-sound1 4e+06 float 2; 43 | #X coords 0 1 4e+06 -1 200 140 1; 44 | #X restore 237 13 graph; 45 | #X msg 31 131 bang; 46 | #X obj 227 284 outlet~; 47 | #X msg 227 244 bang; 48 | #X obj 348 228 spigot; 49 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 50 | 1; 51 | #X text 63 132 open the sound; 52 | #X text 133 244 then play it; 53 | #X text 304 190 loop if you like; 54 | #X msg 31 177 read -resize \$1 leaker-sound1; 55 | #X obj 227 268 tabplay~ leaker-sound1; 56 | #X connect 1 0 11 0; 57 | #X connect 3 0 1 0; 58 | #X connect 5 0 12 0; 59 | #X connect 6 0 5 0; 60 | #X connect 7 0 6 1; 61 | #X connect 11 0 0 0; 62 | #X connect 12 0 4 0; 63 | #X connect 12 1 6 0; 64 | #X restore 96 37 pd playsound1; 65 | #N canvas 990 218 516 405 playsound2 0; 66 | #X obj 31 194 soundfiler; 67 | #X obj 31 160 openpanel; 68 | #X msg 31 131 bang; 69 | #X obj 227 284 outlet~; 70 | #X msg 227 244 bang; 71 | #X obj 348 228 spigot; 72 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 73 | 1; 74 | #X text 63 132 open the sound; 75 | #X text 133 244 then play it; 76 | #X text 304 190 loop if you like; 77 | #N canvas 0 22 450 300 graph2 0; 78 | #X array leaker-sound2 2.499e+06 float 2; 79 | #X coords 0 1 2.499e+06 -1 200 140 1; 80 | #X restore 216 15 graph; 81 | #X msg 31 177 read -resize \$1 leaker-sound2; 82 | #X obj 227 268 tabplay~ leaker-sound2; 83 | #X connect 1 0 11 0; 84 | #X connect 2 0 1 0; 85 | #X connect 4 0 12 0; 86 | #X connect 5 0 4 0; 87 | #X connect 6 0 5 1; 88 | #X connect 11 0 0 0; 89 | #X connect 12 0 3 0; 90 | #X connect 12 1 5 0; 91 | #X restore 129 55 pd playsound2; 92 | #X text 38 317 leaker~ combines two input sounds \, with the spectral 93 | contribution of each sound determined by an internally maintained sieve 94 | and a threshold selection value. At value 0 \, only sound 1 is heard 95 | and at value 1 \, only sound 2 is heard. At intermediate values \, 96 | parts of each spectrum are aggregated according to the sieve structure 97 | which may be specified as upsieve \, downsieve or randsieve.; 98 | #X connect 0 0 3 0; 99 | #X connect 0 0 3 1; 100 | #X connect 2 0 1 0; 101 | #X connect 4 0 0 2; 102 | #X connect 6 0 0 3; 103 | #X connect 8 0 9 0; 104 | #X connect 9 0 5 0; 105 | #X connect 10 0 0 0; 106 | #X connect 11 0 0 1; 107 | -------------------------------------------------------------------------------- /leanconvert.c: -------------------------------------------------------------------------------- 1 | #include "fftease.h" void leanconvert( float *S, float *C, int N2 ) { int real, imag, amp, phase; float a, b; int i; double hypot(), atan2(); for ( i = 0; i <= N2; i++ ) { imag = phase = ( real = amp = i<<1 ) + 1; a = ( i == N2 ? S[1] : S[real] ); b = ( i == 0 || i == N2 ? 0. : S[imag] ); C[amp] = hypot( a, b ); C[phase] = -atan2( b, a ); } } -------------------------------------------------------------------------------- /leanunconvert.c: -------------------------------------------------------------------------------- 1 | #include "fftease.h" /* unconvert essentially undoes what convert does, i.e., it turns N2+1 PAIRS of amplitude and frequency values in C into N2 PAIR of complex spectrum data (in rfft format) in output array S; sampling rate R and interpolation factor I are used to recompute phase values from frequencies */ void leanunconvert( float *C, float *S, int N2 ) { double cos(), sin(); int real, imag, amp, phase; register int i; for ( i = 0; i <= N2; i++ ) { imag = phase = ( real = amp = i<<1 ) + 1; S[real] = *(C+amp) * cos( *(C+phase) ); if ( i != N2 ) S[imag] = -*(C+amp) * sin( *(C+phase) ); } } -------------------------------------------------------------------------------- /limit_fftsize.c: -------------------------------------------------------------------------------- 1 | #include "fftease.h" extern void post(const char *fmt, ...); void limit_fftsize(int *N, int *Nw, char *OBJECT_NAME) { if(*N > MAX_N){ // post("%s: N set to maximum FFT size of %d",OBJECT_NAME,MAX_N); *N = MAX_N; } if(*Nw > MAX_Nw){ // post("%s: Nw set to maximum window size of %d",OBJECT_NAME,MAX_Nw); *Nw = MAX_Nw; } } -------------------------------------------------------------------------------- /makewindows.c: -------------------------------------------------------------------------------- 1 | #include "fftease.h" void makewindows( float *H, float *A, float *S, int Nw, int N, int I ) { int i ; float sum ; for ( i = 0 ; i < Nw ; i++ ) H[i] = A[i] = S[i] = 0.54 - 0.46*cos( TWOPI*i/(Nw - 1) ) ; if ( Nw > N ) { float x ; x = -(Nw - 1)/2. ; for ( i = 0 ; i < Nw ; i++, x += 1. ) if ( x != 0. ) { A[i] *= N*sin( PI*x/N )/(PI*x) ; if ( I ) S[i] *= I*sin( PI*x/I )/(PI*x) ; } } for ( sum = i = 0 ; i < Nw ; i++ ) sum += A[i] ; for ( i = 0 ; i < Nw ; i++ ) { float afac = 2./sum ; float sfac = Nw > N ? 1./afac : afac ; A[i] *= afac ; S[i] *= sfac ; } if ( Nw <= N && I ) { for ( sum = i = 0 ; i < Nw ; i += I ) sum += S[i]*S[i] ; for ( sum = 1./sum, i = 0 ; i < Nw ; i++ ) S[i] *= sum ; } } void makehamming( float *H, float *A, float *S, int Nw, int N, int I, int odd ) { int i; float sum ; if (odd) { for ( i = 0 ; i < Nw ; i++ ) H[i] = A[i] = S[i] = sqrt(0.54 - 0.46*cos( TWOPI*i/(Nw - 1) )); } else { for ( i = 0 ; i < Nw ; i++ ) H[i] = A[i] = S[i] = 0.54 - 0.46*cos( TWOPI*i/(Nw - 1) ); } if ( Nw > N ) { float x ; x = -(Nw - 1)/2. ; for ( i = 0 ; i < Nw ; i++, x += 1. ) if ( x != 0. ) { A[i] *= N*sin( PI*x/N )/(PI*x) ; if ( I ) S[i] *= I*sin( PI*x/I )/(PI*x) ; } } for ( sum = i = 0 ; i < Nw ; i++ ) sum += A[i] ; for ( i = 0 ; i < Nw ; i++ ) { float afac = 2./sum ; float sfac = Nw > N ? 1./afac : afac ; A[i] *= afac ; S[i] *= sfac ; } if ( Nw <= N && I ) { for ( sum = i = 0 ; i < Nw ; i += I ) sum += S[i]*S[i] ; for ( sum = 1./sum, i = 0 ; i < Nw ; i++ ) S[i] *= sum ; } } void makehanning( float *H, float *A, float *S, int Nw, int N, int I, int odd ) { int i; float sum ; if (odd) { for ( i = 0 ; i < Nw ; i++ ) H[i] = A[i] = S[i] = sqrt(0.5 * (1. + cos(PI + TWOPI * i / (Nw - 1)))); } else { for ( i = 0 ; i < Nw ; i++ ) H[i] = A[i] = S[i] = 0.5 * (1. + cos(PI + TWOPI * i / (Nw - 1))); } if ( Nw > N ) { float x ; x = -(Nw - 1)/2. ; for ( i = 0 ; i < Nw ; i++, x += 1. ) if ( x != 0. ) { A[i] *= N*sin( PI*x/N )/(PI*x) ; if ( I ) S[i] *= I*sin( PI*x/I )/(PI*x) ; } } for ( sum = i = 0 ; i < Nw ; i++ ) sum += A[i] ; for ( i = 0 ; i < Nw ; i++ ) { float afac = 2./sum ; float sfac = Nw > N ? 1./afac : afac ; A[i] *= afac ; S[i] *= sfac ; } if ( Nw <= N && I ) { for ( sum = i = 0 ; i < Nw ; i += I ) sum += S[i]*S[i] ; for ( sum = 1./sum, i = 0 ; i < Nw ; i++ ) S[i] *= sum ; } } -------------------------------------------------------------------------------- /manual/code-notes.rtf: -------------------------------------------------------------------------------- 1 | {\rtf1\mac\ansicpg10000\cocoartf824\cocoasubrtf230 2 | {\fonttbl\f0\fswiss\fcharset77 Helvetica;\f1\fnil\fcharset77 LucidaGrande;} 3 | {\colortbl;\red255\green255\blue255;} 4 | \margl1440\margr1440\vieww9000\viewh8400\viewkind0 5 | \pard\tx720\tx1440\tx2160\tx2880\tx3600\tx4320\tx5040\tx5760\tx6480\tx7200\tx7920\tx8640\ql\qnatural\pardirnatural 6 | 7 | \f0\fs24 \cf0 notes:\ 8 | \ 9 | improved memory cleaning in resident\ 10 | \ 11 | disabled residency_buffer if no argument given\ 12 | \ 13 | fixed dentist factor of two bug for bin number\ 14 | \ 15 | 30.11.05\ 16 | \ 17 | gave presidency an "int" function to avoid int error\ 18 | \ 19 | fixed potential memory bug in all objects and recompiled for OS X. Now must reinstall code for Pd and Windows FFTease.\ 20 | \ 21 | \ 22 | removed FFTease Lite from helpfiles and 23 | \f1 FFTease-objectlist.txt\ 24 | \ 25 | 31.11.05\ 26 | \ 27 | compiled stuff for windows:\ 28 | removed "old memory" message from hacked miller code in reanimator\ 29 | \ 30 | fixed residency_buffer:\ 31 | added overlap\ 32 | fixed problem with initiating sampling\ 33 | \ 34 | added residency_buffer helpfile gain slider\ 35 | residency_buffer: return 0 instead of return if no argument\ 36 | \ 37 | residency: modified helpfile\ 38 | \ 39 | resent:\ 40 | fixed no sync out bug when mute is on\ 41 | \ 42 | scrape: fixed helpfile\ 43 | \ 44 | swinger: fixed helpfile\ 45 | \ 46 | dentist: fixed sync bug on mute\ 47 | \ 48 | disarray: fixed mute bug, helpfile\ 49 | \ 50 | drown: fixed mute bug\ 51 | } -------------------------------------------------------------------------------- /mindwarp~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 61 22 766 791 10; 2 | #X obj 384 435 dac~; 3 | #X floatatom 124 121 5 0.1 3 2 transpose transpose -; 4 | #X msg 500 486 \; pd dsp \$1; 5 | #X obj 500 467 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 6 | 1; 7 | #X obj 85 512 hsl 128 15 0.1 4 0 0 empty empty empty -2 -6 0 8 -261285 8 | -1 -1 1600 1; 9 | #N canvas 0 22 494 344 messages 0; 10 | #X obj 154 185 outlet; 11 | #X obj 154 136 fftease-system; 12 | #X connect 1 0 0 0; 13 | #X restore 210 338 pd messages; 14 | #X obj 227 512 hsl 128 15 0 0.01 0 0 empty empty empty -2 -6 0 8 -227712 15 | -1 -1 0 1; 16 | #X obj 224 538 s thresh; 17 | #X obj 82 538 s transpose; 18 | #X obj 82 460 loadbang; 19 | #X msg 82 491 1; 20 | #N canvas 0 22 550 400 mindwarp-block 0; 21 | #X obj 27 158 outlet~; 22 | #X obj 27 42 inlet~; 23 | #X obj 73 14 inlet; 24 | #X obj 120 49 inlet; 25 | #X obj 213 69 inlet; 26 | #X text 107 105 args: warp factor \, shape width \, overlap \, winfac 27 | ; 28 | #X obj 27 85 mindwarp~ 1 16; 29 | #X obj 28 183 block~ 256; 30 | #X connect 1 0 6 0; 31 | #X connect 2 0 6 1; 32 | #X connect 3 0 6 2; 33 | #X connect 4 0 6 0; 34 | #X connect 6 0 0 0; 35 | #X restore 96 364 pd mindwarp-block; 36 | #N canvas 1171 182 470 320 pvoc-block 0; 37 | #X obj 102 141 pvoc~; 38 | #X obj 102 199 outlet~; 39 | #X obj 102 50 inlet~; 40 | #X obj 117 94 inlet; 41 | #X obj 233 94 inlet; 42 | #X obj 270 115 block~ 256; 43 | #X obj 164 95 inlet; 44 | #X connect 0 0 1 0; 45 | #X connect 2 0 0 0; 46 | #X connect 3 0 0 1; 47 | #X connect 4 0 0 0; 48 | #X connect 6 0 0 2; 49 | #X restore 96 194 pd pvoc-block; 50 | #X text 176 274 warp factor; 51 | #X floatatom 172 316 5 1 16 0 - - -; 52 | #N canvas 990 218 520 409 playsound 0; 53 | #X obj 31 194 soundfiler; 54 | #X obj 31 160 openpanel; 55 | #X msg 31 131 bang; 56 | #X obj 227 284 outlet~; 57 | #X msg 227 244 bang; 58 | #X obj 348 228 spigot; 59 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 60 | 1; 61 | #X text 63 132 open the sound; 62 | #X text 133 244 then play it; 63 | #X text 304 190 loop if you like; 64 | #X text 316 205 comment; 65 | #N canvas 0 22 450 300 graph3 0; 66 | #X array mindwarp-sound1 302338 float 2; 67 | #X coords 0 1 302337 -1 200 140 1; 68 | #X restore 231 21 graph; 69 | #X obj 227 268 tabplay~ mindwarp-sound1; 70 | #X msg 31 177 read -resize \$1 mindwarp-sound1; 71 | #X connect 1 0 13 0; 72 | #X connect 2 0 1 0; 73 | #X connect 4 0 12 0; 74 | #X connect 5 0 4 0; 75 | #X connect 6 0 5 1; 76 | #X connect 12 0 3 0; 77 | #X connect 12 1 5 0; 78 | #X connect 13 0 0 0; 79 | #X restore 96 38 pd playsound; 80 | #N canvas 0 22 494 344 messages 0; 81 | #X obj 154 185 outlet; 82 | #X obj 302 145 fftease-system; 83 | #X floatatom 65 105 5 0 0 0 - - -; 84 | #X msg 65 126 highfreq \$1; 85 | #X floatatom 201 94 5 0 0 0 - - -; 86 | #X msg 201 112 lowfreq \$1; 87 | #X msg 65 83 8000; 88 | #X obj 65 61 loadbang; 89 | #X msg 201 73 0; 90 | #X obj 201 51 loadbang; 91 | #X connect 1 0 0 0; 92 | #X connect 2 0 3 0; 93 | #X connect 3 0 0 0; 94 | #X connect 4 0 5 0; 95 | #X connect 5 0 0 0; 96 | #X connect 6 0 2 0; 97 | #X connect 7 0 6 0; 98 | #X connect 8 0 4 0; 99 | #X connect 9 0 8 0; 100 | #X restore 182 174 pd messages; 101 | #X msg 384 314 set mindwarp-raw; 102 | #X obj 384 409 receive~ mindwarp-warped; 103 | #X msg 384 333 set mindwarp-pvoc; 104 | #X msg 384 352 set mindwarp-warped; 105 | #X obj 129 396 send~ mindwarp-warped; 106 | #X obj 119 228 send~ mindwarp-pvoc; 107 | #X obj 108 73 send~ mindwarp-raw; 108 | #X text 380 290 select listening point:; 109 | #X text 503 314 original sound; 110 | #X text 511 335 pvoc transposed; 111 | #X text 523 352 post-pvoc formant-adjusted; 112 | #X text 82 577 mindwarp~ performs spectral envelope warping. It can 113 | be used to correct for the formant shifting effects of pitch-scaling. 114 | The warp factor is tuned to warp spectra to compensate for directly 115 | corresponding pitch-scaling values. For example \, if you have pitch-scaled 116 | a signal by a factor of two \, increasing its frequency content by 117 | an octave \, by providing mindwarp~ with a warp factor of 2 and the 118 | pitch-scaled signal \, mindwarp~ will restore the spectral formant 119 | of the signal to an estimation of the shape present in the original 120 | unscaled signal. Currently \, warp factor values are restricted to 121 | the range [1/16 ... 16.]. mindwarp~ utilizes frequency shaping to perform 122 | its duty. It can be fun to decorrelate the warp factor from the transposition 123 | factor.; 124 | #X text 190 32 <- first load a soundfile here; 125 | #X floatatom 153 156 5 0 0 0 - - -; 126 | #X floatatom 134 275 5 0.1 20 0 - - -; 127 | #X obj 134 252 r transpose; 128 | #X text 214 316 shape width; 129 | #X obj 153 137 r thresh; 130 | #X msg 224 476 1e-05; 131 | #X obj 172 296 r shapewidth; 132 | #N canvas 0 22 454 304 init 0; 133 | #X obj 95 88 loadbang; 134 | #X msg 95 116 16; 135 | #X obj 95 155 s shapewidth; 136 | #X obj 198 155 s transpose; 137 | #X msg 198 120 1; 138 | #X connect 0 0 1 0; 139 | #X connect 0 0 4 0; 140 | #X connect 1 0 2 0; 141 | #X connect 4 0 3 0; 142 | #X restore 501 518 pd init; 143 | #X connect 1 0 12 1; 144 | #X connect 3 0 2 0; 145 | #X connect 4 0 8 0; 146 | #X connect 5 0 11 3; 147 | #X connect 6 0 7 0; 148 | #X connect 9 0 10 0; 149 | #X connect 9 0 35 0; 150 | #X connect 10 0 4 0; 151 | #X connect 11 0 21 0; 152 | #X connect 12 0 11 0; 153 | #X connect 12 0 22 0; 154 | #X connect 14 0 11 2; 155 | #X connect 15 0 12 0; 156 | #X connect 15 0 23 0; 157 | #X connect 16 0 12 3; 158 | #X connect 17 0 18 0; 159 | #X connect 18 0 0 0; 160 | #X connect 18 0 0 1; 161 | #X connect 19 0 18 0; 162 | #X connect 20 0 18 0; 163 | #X connect 30 0 12 2; 164 | #X connect 31 0 11 1; 165 | #X connect 32 0 31 0; 166 | #X connect 34 0 30 0; 167 | #X connect 35 0 6 0; 168 | #X connect 36 0 14 0; 169 | -------------------------------------------------------------------------------- /morphine~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 831 409 575 413 10; 2 | #N canvas 0 22 454 304 morphine-block 0; 3 | #X obj 48 204 block~ 512; 4 | #X obj 152 114 morphine~; 5 | #X obj 152 69 inlet~; 6 | #X obj 201 71 inlet~; 7 | #X obj 260 73 inlet; 8 | #X obj 314 81 inlet; 9 | #X obj 152 202 outlet~; 10 | #X connect 1 0 6 0; 11 | #X connect 2 0 1 0; 12 | #X connect 3 0 1 1; 13 | #X connect 4 0 1 2; 14 | #X connect 5 0 1 0; 15 | #X restore 149 150 pd morphine-block; 16 | #N canvas 990 218 520 409 playsound1 0; 17 | #X obj 31 194 soundfiler; 18 | #X obj 31 160 openpanel; 19 | #N canvas 0 22 450 300 graph1 0; 20 | #X array morphine-sound1 4e+06 float 2; 21 | #X coords 0 1 4e+06 -1 200 140 1; 22 | #X restore 237 13 graph; 23 | #X msg 31 131 bang; 24 | #X obj 227 284 outlet~; 25 | #X msg 227 244 bang; 26 | #X obj 348 228 spigot; 27 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 28 | 1; 29 | #X msg 31 177 read -resize \$1 morphine-sound1; 30 | #X obj 227 268 tabplay~ morphine-sound1; 31 | #X text 316 205 comment; 32 | #X text 63 132 1 open the sound; 33 | #X text 109 245 2 then play it; 34 | #X text 304 190 3 loop if you like; 35 | #X connect 1 0 8 0; 36 | #X connect 3 0 1 0; 37 | #X connect 5 0 9 0; 38 | #X connect 6 0 5 0; 39 | #X connect 7 0 6 1; 40 | #X connect 8 0 0 0; 41 | #X connect 9 0 4 0; 42 | #X connect 9 1 6 0; 43 | #X restore 149 18 pd playsound1; 44 | #N canvas 990 218 520 409 playsound2 0; 45 | #X obj 31 194 soundfiler; 46 | #X obj 31 160 openpanel; 47 | #N canvas 0 22 450 300 graph1 0; 48 | #X array morphine-sound2 2.5137e+06 float 2; 49 | #X coords 0 1 2.5137e+06 -1 200 140 1; 50 | #X restore 237 13 graph; 51 | #X msg 31 131 bang; 52 | #X obj 227 284 outlet~; 53 | #X msg 227 244 bang; 54 | #X obj 348 228 spigot; 55 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 56 | 1; 57 | #X text 316 205 comment; 58 | #X text 63 132 1 open the sound; 59 | #X text 109 245 2 then play it; 60 | #X text 304 190 3 loop if you like; 61 | #X obj 227 268 tabplay~ morphine-sound2; 62 | #X msg 31 177 read -resize \$1 morphine-sound2; 63 | #X connect 1 0 13 0; 64 | #X connect 3 0 1 0; 65 | #X connect 5 0 12 0; 66 | #X connect 6 0 5 0; 67 | #X connect 7 0 6 1; 68 | #X connect 12 0 4 0; 69 | #X connect 12 1 6 0; 70 | #X connect 13 0 0 0; 71 | #X restore 187 42 pd playsound2; 72 | #X floatatom 225 119 5 0 0 0 - - -; 73 | #X text 223 81 morph index; 74 | #N canvas 643 138 458 308 messages 0; 75 | #X obj 100 164 outlet; 76 | #X msg 100 126 transition \$1; 77 | #X obj 103 78 hsl 128 15 -30 0 0 0 empty empty empty -2 -6 0 8 -110787 78 | -1 -1 10900 1; 79 | #X text 61 49 exponential transition scalar; 80 | #X floatatom 100 106 5 0 0 0 - - -; 81 | #X obj 35 26 loadbang; 82 | #X msg 35 49 -5; 83 | #X obj 177 148 fftease-system; 84 | #X connect 1 0 0 0; 85 | #X connect 2 0 4 0; 86 | #X connect 4 0 1 0; 87 | #X connect 5 0 6 0; 88 | #X connect 6 0 2 0; 89 | #X connect 7 0 0 0; 90 | #X restore 295 134 pd messages; 91 | #X msg 27 233 \; pd dsp \$1; 92 | #X obj 27 216 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1 93 | ; 94 | #X obj 149 209 *~ 1; 95 | #X obj 149 261 dac~; 96 | #X obj 175 170 hsl 128 15 0 1 0 0 empty empty empty -2 -6 0 8 -110787 97 | -1 -1 6700 1; 98 | #X floatatom 172 190 5 0 0 0 - - -; 99 | #X obj 228 97 hsl 128 15 0 1 0 0 empty empty empty -2 -6 0 8 -110787 100 | -1 -1 9400 1; 101 | #X text 251 18 <- load sounds here; 102 | #X text 289 41 <- and here; 103 | #X text 23 291 morphine~ performs spectral morphing \, creating a new 104 | spectrum from its two inputs. Values between 0 and 1 are the useful 105 | range for the morph index. The progression depends upon the exponential 106 | transition scaling value. Progressively smaller negative values will 107 | widen the transition space between the two sounds. Larger FFT sizes 108 | \, such as 4096 \, produce smoother results.; 109 | #X text 310 170 gain; 110 | #X connect 0 0 8 0; 111 | #X connect 1 0 0 0; 112 | #X connect 2 0 0 1; 113 | #X connect 3 0 0 2; 114 | #X connect 5 0 0 3; 115 | #X connect 7 0 6 0; 116 | #X connect 8 0 9 0; 117 | #X connect 8 0 9 1; 118 | #X connect 10 0 11 0; 119 | #X connect 11 0 8 1; 120 | #X connect 12 0 3 0; 121 | -------------------------------------------------------------------------------- /multyq~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 224 36 657 848 10; 2 | #X msg 360 574 \; pd dsp \$1; 3 | #X obj 360 548 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 4 | 1; 5 | #X obj 136 366 dac~; 6 | #X obj 180 295 nbx 5 14 -1e+37 1e+37 0 0 empty out-gain empty 0 -6 7 | 0 10 -262144 -1 -1 0.0551181 256; 8 | #X obj 29 394 hsl 128 15 60 600 0 0 cf1 empty cf1 -2 -6 0 8 -235882 9 | -1 -1 5400 1; 10 | #X obj 49 151 noise~; 11 | #N canvas 0 22 502 352 multyq-block 0; 12 | #X obj 71 352 block~ 256; 13 | #X obj 28 95 inlet~; 14 | #X obj 193 169 inlet; 15 | #X obj 72 299 outlet~; 16 | #X obj 72 256 multyq~ 4 1; 17 | #X obj 249 239 inlet; 18 | #X obj 66 143 inlet; 19 | #X obj 72 182 inlet; 20 | #X obj 78 217 inlet; 21 | #X obj 110 142 inlet; 22 | #X obj 116 181 inlet; 23 | #X obj 122 216 inlet; 24 | #X text 67 105 [cf \, bw \, gain] triplets; 25 | #X obj 182 141 inlet~; 26 | #X obj 199 189 inlet; 27 | #X connect 1 0 4 0; 28 | #X connect 2 0 4 8; 29 | #X connect 4 0 3 0; 30 | #X connect 5 0 4 0; 31 | #X connect 6 0 4 1; 32 | #X connect 7 0 4 2; 33 | #X connect 8 0 4 3; 34 | #X connect 9 0 4 4; 35 | #X connect 10 0 4 5; 36 | #X connect 11 0 4 6; 37 | #X connect 13 0 4 7; 38 | #X connect 14 0 4 9; 39 | #X restore 136 261 pd multyq-block; 40 | #X floatatom 146 7 5 0 0 2 - cf1 -; 41 | #X floatatom 156 22 5 0 0 2 - bw1 -; 42 | #X floatatom 166 37 5 0 0 2 - gain1 -; 43 | #X obj 30 433 hsl 128 15 0.01 0.5 0 0 bw1 empty bw1 -2 -6 0 8 -235882 44 | -1 -1 7000 1; 45 | #X obj 30 471 hsl 128 15 0 20 0 0 gain1 empty gain1 -2 -6 0 8 -235882 46 | -1 -1 7900 1; 47 | #X obj 136 314 *~ 0.05; 48 | #X obj 190 595 hsl 128 15 0 1 0 0 out-gain empty out-gain -2 -6 0 8 49 | -44646 -1 -1 700 1; 50 | #X obj 31 518 hsl 128 15 600 2000 0 0 cf2 empty cf2 -2 -6 0 8 -235882 51 | -1 -1 2300 1; 52 | #X obj 31 557 hsl 128 15 0.01 0.5 0 0 bw2 empty bw2 -2 -6 0 8 -235882 53 | -1 -1 8100 1; 54 | #X obj 31 595 hsl 128 15 -1 20 0 0 gain2 empty gain2 -2 -6 0 8 -235882 55 | -1 -1 6600 1; 56 | #X floatatom 176 56 5 0 0 2 - cf2 -; 57 | #X floatatom 186 73 5 0 0 2 - bw2 -; 58 | #X floatatom 196 92 5 0 0 2 - gain2 -; 59 | #X obj 206 111 phasor~ 2; 60 | #X obj 206 134 *~ 2000; 61 | #X obj 206 157 +~ 1500; 62 | #X obj 246 452 hsl 128 15 0.01 0.5 0 0 bw3 empty bw3 -2 -6 0 8 -125810 63 | -1 -1 3900 1; 64 | #X obj 247 485 hsl 128 15 -1 20 0 0 gain3 empty gain3 -2 -6 0 8 -125810 65 | -1 -1 5400 1; 66 | #X floatatom 216 185 5 0 0 0 - bw3 -; 67 | #X floatatom 226 213 5 0 0 0 - gain3 -; 68 | #X obj 236 238 fftease-system; 69 | #X text 29 643 multyq~ is a four band equalizer. Gain values below 70 | 0 create notches rather than peaks \, but only go as far as -1.0. Bandwidth 71 | is from 0 to 1.0. Only three bands are used in this example \, but 72 | cpu usage is the same regardless of how many are used. As the filter 73 | is FFT-based \, its performance is spotty in the low frequency range. 74 | ; 75 | #X connect 1 0 0 0; 76 | #X connect 3 0 12 1; 77 | #X connect 5 0 6 0; 78 | #X connect 6 0 12 0; 79 | #X connect 7 0 6 1; 80 | #X connect 8 0 6 2; 81 | #X connect 9 0 6 3; 82 | #X connect 12 0 2 0; 83 | #X connect 12 0 2 1; 84 | #X connect 17 0 6 4; 85 | #X connect 18 0 6 5; 86 | #X connect 19 0 6 6; 87 | #X connect 20 0 21 0; 88 | #X connect 21 0 22 0; 89 | #X connect 22 0 6 7; 90 | #X connect 25 0 6 8; 91 | #X connect 26 0 6 9; 92 | #X connect 27 0 6 10; 93 | -------------------------------------------------------------------------------- /overlapadd.c: -------------------------------------------------------------------------------- 1 | /* * input I is a folded spectrum of length N; output O and * synthesis window W are of length Nw--overlap-add windowed, * unrotated, unfolded input data into output O */ #include "fftease.h" void overlapadd( float *I, int N, float *W, float *O, int Nw, int n ) { int i ; while ( n < 0 ) n += N ; n %= N ; for ( i = 0 ; i < Nw ; i++ ) { O[i] += I[n]*W[i] ; if ( ++n == N ) n = 0 ; } } -------------------------------------------------------------------------------- /power_of_two.c: -------------------------------------------------------------------------------- 1 | 2 | int power_of_two(int test) 3 | { 4 | int limit = 8192; 5 | int compare = 1; 6 | // post("testing what we thing is an int:%d",test); 7 | do { 8 | if(test == compare){ 9 | // post("good power of 2 found!"); 10 | return 1; 11 | } 12 | compare *= 2; 13 | } while (compare <= limit); 14 | 15 | return 0; 16 | } 17 | // we think the above function is shadowed somewhere else 18 | 19 | int fftease_power_of_two(int test) 20 | { 21 | int limit = 8192; 22 | int compare = 1; 23 | // post("testing what we thing is an int:%d",test); 24 | do { 25 | if(test == compare){ 26 | // post("good power of 2 found!"); 27 | return 1; 28 | } 29 | compare *= 2; 30 | } while (compare <= limit); 31 | 32 | return 0; 33 | } 34 | -------------------------------------------------------------------------------- /presidency~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 58 237 555 452 10; 2 | #N canvas 431 336 551 457 messages 0; 3 | #X obj 34 383 outlet; 4 | #X floatatom 42 228 5 0 0 2 - size -; 5 | #X msg 42 259 size \$1; 6 | #X obj 34 87 bng 15 250 50 0 empty trigger trigger_sampling 0 -6 0 7 | 8 -262144 -1 -1; 8 | #X obj 64 139 s playsound; 9 | #X obj 34 115 t b b; 10 | #X msg 34 166 acquire_sample; 11 | #X msg 85 230 10000; 12 | #X obj 280 367 fftease-system; 13 | #X text 45 210 resize memory (but with DACs off to be safe); 14 | #X obj 291 266 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 15 | 1; 16 | #X obj 320 265 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 17 | 1; 18 | #X obj 349 265 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 19 | 1; 20 | #X obj 291 239 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 21 | 1; 22 | #N canvas 0 22 462 312 init 0; 23 | #X msg 33 61 playthrough 1; 24 | #X obj 33 34 loadbang; 25 | #X obj 33 103 outlet; 26 | #X obj 233 93 loadbang; 27 | #X msg 233 114 1; 28 | #X obj 233 136 s speed-slider; 29 | #X msg 137 61 verbose 0; 30 | #X msg 169 142 1; 31 | #X obj 169 164 s transpose-slider; 32 | #X connect 0 0 2 0; 33 | #X connect 1 0 0 0; 34 | #X connect 1 0 6 0; 35 | #X connect 3 0 4 0; 36 | #X connect 3 0 7 0; 37 | #X connect 4 0 5 0; 38 | #X connect 6 0 2 0; 39 | #X connect 7 0 8 0; 40 | #X restore 111 335 pd init; 41 | #N canvas 260 69 789 579 frequency-boundaries 0; 42 | #X msg 283 158 high_freq \$1; 43 | #X obj 286 120 hsl 128 15 500 8000 0 0 empty empty empty -2 -6 0 8 44 | -155632 -1 -1 0 1; 45 | #X floatatom 283 140 5 0 0 0 - - -; 46 | #X text 280 102 highest frequency to resynthesize; 47 | #X text 9 364 note: these relate to frequencies in the original sound. 48 | If you transpose the resynthesis \, you will go outside these ranges. 49 | ; 50 | #X obj 4 318 outlet; 51 | #X obj 7 117 hsl 128 15 0 1000 0 0 empty empty empty -2 -6 0 8 -155632 52 | -1 -1 0 1; 53 | #X floatatom 4 138 5 0 0 0 - - -; 54 | #X msg 4 167 low_freq \$1; 55 | #X obj 7 117 hsl 128 15 0 1000 0 0 empty empty empty -2 -6 0 8 -155632 56 | -1 -1 0 1; 57 | #X text -1 98 lowest frequency to resynthesize; 58 | #X connect 0 0 5 0; 59 | #X connect 1 0 2 0; 60 | #X connect 2 0 0 0; 61 | #X connect 6 0 7 0; 62 | #X connect 7 0 8 0; 63 | #X connect 8 0 5 0; 64 | #X restore 64 287 pd frequency-boundaries; 65 | #N canvas 24 525 634 358 random-behavior 0; 66 | #X obj 46 95 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1 67 | ; 68 | #X obj 46 149 random 1000; 69 | #X obj 46 187 * 0.001; 70 | #X obj 190 101 random 1000; 71 | #X obj 190 139 * 0.001; 72 | #X obj 190 169 * 3; 73 | #X obj 190 196 + 0.05; 74 | #X obj 190 46 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1 75 | ; 76 | #X obj 190 73 metro 233; 77 | #X obj 46 57 inlet; 78 | #X obj 46 243 spigot; 79 | #X obj 83 221 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 1 80 | ; 81 | #X obj 190 243 spigot; 82 | #X obj 227 221 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 83 | 1; 84 | #X obj 344 101 random 1000; 85 | #X obj 344 139 * 0.001; 86 | #X obj 344 73 metro 233; 87 | #X obj 344 243 spigot; 88 | #X obj 381 221 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 89 | 1; 90 | #X obj 344 169 * 2; 91 | #X obj 344 196 - 1; 92 | #X obj 344 50 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1 93 | ; 94 | #X obj 190 19 inlet; 95 | #X obj 344 18 inlet; 96 | #X obj 344 268 s speed-slider; 97 | #X obj 190 268 s transpose-slider; 98 | #X obj 46 268 s position-slider; 99 | #X obj 479 183 loadbang; 100 | #X msg 479 205 1; 101 | #X obj 46 121 metro 650; 102 | #X connect 0 0 29 0; 103 | #X connect 1 0 2 0; 104 | #X connect 2 0 10 0; 105 | #X connect 3 0 4 0; 106 | #X connect 4 0 5 0; 107 | #X connect 5 0 6 0; 108 | #X connect 6 0 12 0; 109 | #X connect 7 0 8 0; 110 | #X connect 8 0 3 0; 111 | #X connect 9 0 0 0; 112 | #X connect 10 0 26 0; 113 | #X connect 11 0 10 1; 114 | #X connect 12 0 25 0; 115 | #X connect 13 0 12 1; 116 | #X connect 14 0 15 0; 117 | #X connect 15 0 19 0; 118 | #X connect 16 0 14 0; 119 | #X connect 17 0 24 0; 120 | #X connect 18 0 17 1; 121 | #X connect 19 0 20 0; 122 | #X connect 20 0 17 0; 123 | #X connect 21 0 16 0; 124 | #X connect 22 0 7 0; 125 | #X connect 23 0 21 0; 126 | #X connect 27 0 28 0; 127 | #X connect 28 0 18 0; 128 | #X connect 28 0 13 0; 129 | #X connect 28 0 11 0; 130 | #X connect 29 0 1 0; 131 | #X restore 291 288 pd random-behavior; 132 | #X text 36 10 Load a valid soundfile in sound-source \, then hit the 133 | sampling trigger below. The resulting recording is stored as a series 134 | of FFT frames inside presidency~ available for arbitrary time-access. 135 | ; 136 | #X connect 1 0 2 0; 137 | #X connect 2 0 0 0; 138 | #X connect 3 0 5 0; 139 | #X connect 5 0 6 0; 140 | #X connect 5 1 4 0; 141 | #X connect 6 0 0 0; 142 | #X connect 7 0 2 0; 143 | #X connect 8 0 0 0; 144 | #X connect 10 0 16 0; 145 | #X connect 11 0 16 1; 146 | #X connect 12 0 16 2; 147 | #X connect 13 0 10 0; 148 | #X connect 13 0 11 0; 149 | #X connect 13 0 12 0; 150 | #X connect 14 0 0 0; 151 | #X connect 15 0 0 0; 152 | #X restore 252 214 pd messages; 153 | #X floatatom 156 134 5 0 0 2 speed speed -; 154 | #N canvas 0 22 530 380 sound-source 0; 155 | #X text 13 300 try a vocal sound or other sound with strong formant 156 | structure; 157 | #X obj 31 194 soundfiler; 158 | #X obj 31 160 openpanel; 159 | #N canvas 0 22 450 300 graph1 0; 160 | #X array presidency-sound1 441202 float 2; 161 | #X coords 0 1 441201 -1 200 140 1; 162 | #X restore 237 13 graph; 163 | #X msg 31 131 bang; 164 | #X obj 227 284 outlet~; 165 | #X msg 227 244 bang; 166 | #X obj 348 228 spigot; 167 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 168 | 1; 169 | #X text 63 132 open the sound; 170 | #X text 133 244 then play it; 171 | #X text 304 190 loop if you like; 172 | #X obj 227 268 tabplay~ presidency-sound1; 173 | #X msg 31 177 read -resize \$1 presidency-sound1; 174 | #X obj 227 219 r playsound; 175 | #X connect 2 0 13 0; 176 | #X connect 4 0 2 0; 177 | #X connect 6 0 12 0; 178 | #X connect 7 0 6 0; 179 | #X connect 8 0 7 1; 180 | #X connect 12 0 5 0; 181 | #X connect 12 1 7 0; 182 | #X connect 13 0 1 0; 183 | #X connect 14 0 6 0; 184 | #X restore 124 95 pd sound-source; 185 | #X msg 301 272 \; pd dsp \$1; 186 | #X obj 301 246 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 187 | 1; 188 | #X floatatom 188 163 5 0 1 2 position position -; 189 | #X obj 28 47 vsl 15 128 -2 2 0 0 speed speed-slider speed 0 -8 0 8 190 | -253906 -1 -1 9525 1; 191 | #X obj 60 47 vsl 15 128 0 1 0 0 position position-slider position 0 192 | -8 0 8 -4094 -1 -1 0 1; 193 | #X text 333 214 <- ask me what I can do; 194 | #X floatatom 220 194 5 0 1 2 transpose transpose -; 195 | #X obj 35 216 vsl 15 128 0.1 2 0 0 transpose transpose-slider transpose 196 | 0 -8 0 8 -231210 -1 -1 6016 1; 197 | #X msg 29 13 0; 198 | #N canvas 81 500 498 348 presidency-block 0; 199 | #X obj 28 42 inlet~; 200 | #X obj 89 42 inlet~; 201 | #X obj 150 42 inlet~; 202 | #X obj 313 66 inlet; 203 | #X obj 28 140 outlet~; 204 | #X obj 28 169 block~ 256; 205 | #X text 103 171 FFT size is block~ size times overlap; 206 | #X obj 28 99 presidency~ 5000 0 4000 4 1; 207 | #X obj 212 42 inlet~; 208 | #X text 39 120 args: size \, minfreq \, maxfreq \, overlap \, window 209 | factor; 210 | #X obj 323 279 outlet; 211 | #X obj 323 251 snapshot~; 212 | #X obj 378 213 metro 50; 213 | #X msg 378 192 1; 214 | #X obj 378 156 loadbang; 215 | #X connect 0 0 7 0; 216 | #X connect 1 0 7 1; 217 | #X connect 2 0 7 2; 218 | #X connect 3 0 7 0; 219 | #X connect 7 0 4 0; 220 | #X connect 7 1 11 0; 221 | #X connect 8 0 7 3; 222 | #X connect 11 0 10 0; 223 | #X connect 12 0 11 0; 224 | #X connect 13 0 12 0; 225 | #X connect 14 0 13 0; 226 | #X restore 124 246 pd presidency-block; 227 | #X text 128 372 presidency~ follows the residency~ model but uses an 228 | oscillator bank for resynthesis and offers independent control of speed 229 | \, location and transposition of playback.; 230 | #X text 237 94 <- first load a sound here; 231 | #X floatatom 252 271 5 0 0 0 - - -; 232 | #X text 212 272 sync; 233 | #X obj 214 31 hsl 128 15 0 1 0 0 presidency-gain empty gain -2 -6 0 234 | 8 -67648 -1 -1 0 1; 235 | #X obj 124 322 dac~; 236 | #X obj 124 284 *~ 0.25; 237 | #X floatatom 168 268 5 0 0 3 - presidency-gain -; 238 | #X text 59 14 freeze frame; 239 | #X connect 0 0 12 4; 240 | #X connect 1 0 12 1; 241 | #X connect 2 0 12 0; 242 | #X connect 4 0 3 0; 243 | #X connect 5 0 12 2; 244 | #X connect 9 0 12 3; 245 | #X connect 11 0 6 0; 246 | #X connect 12 0 19 0; 247 | #X connect 12 1 15 0; 248 | #X connect 19 0 18 1; 249 | #X connect 19 0 18 0; 250 | #X connect 20 0 19 1; 251 | -------------------------------------------------------------------------------- /pvcompand~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 854 454 487 362 10; 2 | #N canvas 0 22 458 308 pvcompand-block 0; 3 | #X obj 231 190 block~ 256; 4 | #X obj 231 133 pvcompand~; 5 | #X obj 231 86 inlet~; 6 | #X obj 296 94 inlet; 7 | #X obj 362 117 inlet; 8 | #X obj 231 159 outlet~; 9 | #X connect 1 0 5 0; 10 | #X connect 2 0 1 0; 11 | #X connect 3 0 1 1; 12 | #X connect 4 0 1 0; 13 | #X restore 121 99 pd pvcompand-block; 14 | #X obj 121 139 dac~; 15 | #N canvas 0 22 466 316 messages 0; 16 | #X obj 203 227 outlet; 17 | #X obj 281 174 fftease-system; 18 | #N canvas 181 394 454 304 init 0; 19 | #X obj 97 48 loadbang; 20 | #X obj 97 182 outlet; 21 | #X obj 262 124 s compandslider; 22 | #X msg 262 97 -6; 23 | #X text 105 152 attempt to preserve overall amplitude; 24 | #X msg 97 130 normalize \$1; 25 | #X obj 97 103 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 1 26 | ; 27 | #X msg 97 83 1; 28 | #X connect 0 0 3 0; 29 | #X connect 0 0 7 0; 30 | #X connect 3 0 2 0; 31 | #X connect 5 0 1 0; 32 | #X connect 6 0 5 0; 33 | #X connect 7 0 6 0; 34 | #X restore 203 153 pd init; 35 | #X connect 1 0 0 0; 36 | #X connect 2 0 0 0; 37 | #X restore 242 69 pd messages; 38 | #X msg 211 165 \; pd dsp \$1; 39 | #X obj 211 143 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 40 | 1; 41 | #X floatatom 181 78 5 0 0 0 - compand-factor -; 42 | #X obj 123 229 hsl 128 15 -60 60 0 0 compand-factor compandslider compand-factor 43 | -2 -6 0 8 -258842 -1 -1 5115 1; 44 | #X text 256 230 -> expansion; 45 | #X text 17 230 compression <-; 46 | #X text 23 258 pvcompand~ either expands or compresses the differences 47 | between the amplitudes of the spectral frames. The threshold is interpreted 48 | as dB and useful ranges are from about -60 to +60. Positive values 49 | increase the "peakiness" of the sound and negative values tend to whiten 50 | the spectrum.; 51 | #N canvas 179 221 661 474 sound-source 0; 52 | #X text 13 300 try a vocal sound or other sound with strong formant 53 | structure; 54 | #X obj 31 194 soundfiler; 55 | #X obj 31 160 openpanel; 56 | #N canvas 0 22 450 300 graph1 0; 57 | #X array pvcompand-sound1 4e+06 float 2; 58 | #X coords 0 1 4e+06 -1 200 140 1; 59 | #X restore 237 13 graph; 60 | #X msg 31 131 bang; 61 | #X obj 227 284 outlet~; 62 | #X msg 227 244 bang; 63 | #X obj 348 228 spigot; 64 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 65 | 1; 66 | #X text 63 132 open the sound; 67 | #X text 133 244 then play it; 68 | #X text 304 190 loop if you like; 69 | #X obj 227 268 tabplay~ pvcompand-sound1; 70 | #X msg 31 177 read -resize \$1 pvcompand-sound1; 71 | #X connect 2 0 13 0; 72 | #X connect 4 0 2 0; 73 | #X connect 6 0 12 0; 74 | #X connect 7 0 6 0; 75 | #X connect 8 0 7 1; 76 | #X connect 12 0 5 0; 77 | #X connect 12 1 7 0; 78 | #X connect 13 0 1 0; 79 | #X restore 121 38 pd sound-source; 80 | #X text 232 39 <- first load sound here; 81 | #X connect 0 0 1 0; 82 | #X connect 0 0 1 1; 83 | #X connect 2 0 0 2; 84 | #X connect 4 0 3 0; 85 | #X connect 5 0 0 1; 86 | #X connect 10 0 0 0; 87 | -------------------------------------------------------------------------------- /pvgrain~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 772 607 490 340 10; 2 | #N canvas 0 22 482 332 pvgrain-block 0; 3 | #X obj 9 110 outlet; 4 | #X obj 9 15 inlet~; 5 | #X obj 94 15 inlet; 6 | #X obj 8 140 block~ 256; 7 | #X text 12 90 args: grains/frame \, odds \, topfreq \, overlap \, window-factor 8 | ; 9 | #X obj 9 68 pvgrain~ 4 0.01 2000 4 2; 10 | #X connect 1 0 5 0; 11 | #X connect 2 0 5 0; 12 | #X connect 5 0 0 0; 13 | #X restore 13 103 pd pvgrain-block; 14 | #X obj 220 158 dac~; 15 | #X obj 13 172 print; 16 | #X msg 110 242 \; pd dsp \$1; 17 | #X obj 110 221 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 18 | 1; 19 | #N canvas 368 141 902 629 messages 0; 20 | #X obj 111 523 outlet; 21 | #X msg 105 115 probability \$1; 22 | #X obj 108 68 hsl 128 15 0 0.1 0 0 empty empty empty -2 -6 0 8 -43542 23 | -1 -1 1270 1; 24 | #X floatatom 105 94 5 0 0 0 - - -; 25 | #X obj 198 179 hsl 128 15 200 10000 0 0 empty empty empty -2 -6 0 8 26 | -43542 -1 -1 2333 1; 27 | #X floatatom 195 205 5 0 0 0 - - -; 28 | #X msg 195 226 topfreq \$1; 29 | #X obj 439 388 hsl 128 15 0 20 0 0 empty empty empty -2 -6 0 8 -43542 30 | -1 -1 5080 1; 31 | #X floatatom 436 414 5 0 0 0 - - -; 32 | #X msg 436 435 framegrains \$1; 33 | #X obj 105 1 loadbang; 34 | #X obj 283 284 hsl 128 15 0 1500 0 0 empty empty empty -2 -6 0 8 -43542 35 | -1 -1 423 1; 36 | #X floatatom 280 310 5 0 0 0 - - -; 37 | #X msg 280 331 bottomfreq \$1; 38 | #X obj 105 40 unpack f f f f; 39 | #X msg 105 21 0.01 2000 50 8; 40 | #X obj 300 492 fftease-system; 41 | #X text 436 363 maximum data grains per FFT frame; 42 | #X text 197 157 top frequency to listen to in source sound; 43 | #X text 283 263 ditto for bottom frequency; 44 | #X text 221 48 odds for a grain appearing from an active bin; 45 | #X connect 1 0 0 0; 46 | #X connect 2 0 3 0; 47 | #X connect 3 0 1 0; 48 | #X connect 4 0 5 0; 49 | #X connect 5 0 6 0; 50 | #X connect 6 0 0 0; 51 | #X connect 7 0 8 0; 52 | #X connect 8 0 9 0; 53 | #X connect 9 0 0 0; 54 | #X connect 10 0 15 0; 55 | #X connect 11 0 12 0; 56 | #X connect 12 0 13 0; 57 | #X connect 13 0 0 0; 58 | #X connect 14 0 2 0; 59 | #X connect 14 1 4 0; 60 | #X connect 14 2 11 0; 61 | #X connect 14 3 7 0; 62 | #X connect 15 0 14 0; 63 | #X connect 16 0 0 0; 64 | #X restore 120 62 pd messages; 65 | #X obj 50 129 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1 66 | ; 67 | #X obj 13 149 spigot; 68 | #X text 69 131 see amp/freq info; 69 | #X text 42 277 spectral granular (re)synthesis; 70 | #N canvas 0 22 478 328 resynth-engine 0; 71 | #X obj 12 28 inlet; 72 | #N canvas 0 22 450 300 graph1 0; 73 | #X array piano-sample 46383 float 2; 74 | #X coords 0 1 46382 -1 200 140 1; 75 | #X restore 215 4 graph; 76 | #X obj 17 242 soundfiler; 77 | #X msg 17 205 read -resize examples/Piano.aif piano-sample; 78 | #X obj 17 169 loadbang; 79 | #N canvas 578 40 566 745 choir 0; 80 | #X obj 79 103 inlet; 81 | #X obj 79 141 t l b; 82 | #X obj 25 199 float; 83 | #X obj 25 228 + 1; 84 | #X obj 25 252 % 8; 85 | #X floatatom 25 276 5 0 0 0 - - -; 86 | #X obj 47 367 pack f f f; 87 | #X obj 79 315 unpack f f; 88 | #X obj 47 395 route 0 1 2 3 4 5 6 7; 89 | #X obj 112 343 / 261; 90 | #X text 156 345 <- piano sample base frequency; 91 | #N canvas 74 88 1066 749 playit 0; 92 | #X obj 21 47 unpack f f; 93 | #X obj 21 222 outlet~; 94 | #X floatatom 131 120 5 0 0 0 - - -; 95 | #X floatatom 88 118 5 0 0 0 - - -; 96 | #X obj 21 119 impulse~; 97 | #X obj 21 146 *~; 98 | #X obj 21 80 t b f; 99 | #X obj 21 182 player~ piano-sample; 100 | #X obj 21 8 inlet; 101 | #X connect 0 0 6 0; 102 | #X connect 0 1 2 0; 103 | #X connect 2 0 7 1; 104 | #X connect 3 0 5 1; 105 | #X connect 4 0 5 0; 106 | #X connect 5 0 7 0; 107 | #X connect 6 0 4 0; 108 | #X connect 6 1 3 0; 109 | #X connect 7 0 1 0; 110 | #X connect 8 0 0 0; 111 | #X restore 47 430 pd playit; 112 | #X obj 123 595 outlet~; 113 | #X obj 123 572 *~ 0.25; 114 | #N canvas 74 88 1062 745 playit 0; 115 | #X obj 21 47 unpack f f; 116 | #X obj 21 222 outlet~; 117 | #X floatatom 131 120 5 0 0 0 - - -; 118 | #X floatatom 88 118 5 0 0 0 - - -; 119 | #X obj 21 119 impulse~; 120 | #X obj 21 146 *~; 121 | #X obj 21 80 t b f; 122 | #X obj 21 182 player~ piano-sample; 123 | #X obj 21 8 inlet; 124 | #X connect 0 0 6 0; 125 | #X connect 0 1 2 0; 126 | #X connect 2 0 7 1; 127 | #X connect 3 0 5 1; 128 | #X connect 4 0 5 0; 129 | #X connect 5 0 7 0; 130 | #X connect 6 0 4 0; 131 | #X connect 6 1 3 0; 132 | #X connect 7 0 1 0; 133 | #X connect 8 0 0 0; 134 | #X restore 64 451 pd playit; 135 | #N canvas 74 88 1062 745 playit 0; 136 | #X obj 21 47 unpack f f; 137 | #X obj 21 222 outlet~; 138 | #X floatatom 131 120 5 0 0 0 - - -; 139 | #X floatatom 88 118 5 0 0 0 - - -; 140 | #X obj 21 119 impulse~; 141 | #X obj 21 146 *~; 142 | #X obj 21 80 t b f; 143 | #X obj 21 182 player~ piano-sample; 144 | #X obj 21 8 inlet; 145 | #X connect 0 0 6 0; 146 | #X connect 0 1 2 0; 147 | #X connect 2 0 7 1; 148 | #X connect 3 0 5 1; 149 | #X connect 4 0 5 0; 150 | #X connect 5 0 7 0; 151 | #X connect 6 0 4 0; 152 | #X connect 6 1 3 0; 153 | #X connect 7 0 1 0; 154 | #X connect 8 0 0 0; 155 | #X restore 83 472 pd playit; 156 | #N canvas 74 88 1062 745 playit 0; 157 | #X obj 21 47 unpack f f; 158 | #X obj 21 222 outlet~; 159 | #X floatatom 131 120 5 0 0 0 - - -; 160 | #X floatatom 88 118 5 0 0 0 - - -; 161 | #X obj 21 119 impulse~; 162 | #X obj 21 146 *~; 163 | #X obj 21 80 t b f; 164 | #X obj 21 182 player~ piano-sample; 165 | #X obj 21 8 inlet; 166 | #X connect 0 0 6 0; 167 | #X connect 0 1 2 0; 168 | #X connect 2 0 7 1; 169 | #X connect 3 0 5 1; 170 | #X connect 4 0 5 0; 171 | #X connect 5 0 7 0; 172 | #X connect 6 0 4 0; 173 | #X connect 6 1 3 0; 174 | #X connect 7 0 1 0; 175 | #X connect 8 0 0 0; 176 | #X restore 101 493 pd playit; 177 | #N canvas 74 88 1062 745 playit 0; 178 | #X obj 21 47 unpack f f; 179 | #X obj 21 222 outlet~; 180 | #X floatatom 131 120 5 0 0 0 - - -; 181 | #X floatatom 88 118 5 0 0 0 - - -; 182 | #X obj 21 119 impulse~; 183 | #X obj 21 146 *~; 184 | #X obj 21 80 t b f; 185 | #X obj 21 182 player~ piano-sample; 186 | #X obj 21 8 inlet; 187 | #X connect 0 0 6 0; 188 | #X connect 0 1 2 0; 189 | #X connect 2 0 7 1; 190 | #X connect 3 0 5 1; 191 | #X connect 4 0 5 0; 192 | #X connect 5 0 7 0; 193 | #X connect 6 0 4 0; 194 | #X connect 6 1 3 0; 195 | #X connect 7 0 1 0; 196 | #X connect 8 0 0 0; 197 | #X restore 118 421 pd playit; 198 | #N canvas 74 88 1062 745 playit 0; 199 | #X obj 21 47 unpack f f; 200 | #X obj 21 222 outlet~; 201 | #X floatatom 131 120 5 0 0 0 - - -; 202 | #X floatatom 88 118 5 0 0 0 - - -; 203 | #X obj 21 119 impulse~; 204 | #X obj 21 146 *~; 205 | #X obj 21 80 t b f; 206 | #X obj 21 182 player~ piano-sample; 207 | #X obj 21 8 inlet; 208 | #X connect 0 0 6 0; 209 | #X connect 0 1 2 0; 210 | #X connect 2 0 7 1; 211 | #X connect 3 0 5 1; 212 | #X connect 4 0 5 0; 213 | #X connect 5 0 7 0; 214 | #X connect 6 0 4 0; 215 | #X connect 6 1 3 0; 216 | #X connect 7 0 1 0; 217 | #X connect 8 0 0 0; 218 | #X restore 135 442 pd playit; 219 | #N canvas 74 88 1062 745 playit 0; 220 | #X obj 21 47 unpack f f; 221 | #X obj 21 222 outlet~; 222 | #X floatatom 131 120 5 0 0 0 - - -; 223 | #X floatatom 88 118 5 0 0 0 - - -; 224 | #X obj 21 119 impulse~; 225 | #X obj 21 146 *~; 226 | #X obj 21 80 t b f; 227 | #X obj 21 182 player~ piano-sample; 228 | #X obj 21 8 inlet; 229 | #X connect 0 0 6 0; 230 | #X connect 0 1 2 0; 231 | #X connect 2 0 7 1; 232 | #X connect 3 0 5 1; 233 | #X connect 4 0 5 0; 234 | #X connect 5 0 7 0; 235 | #X connect 6 0 4 0; 236 | #X connect 6 1 3 0; 237 | #X connect 7 0 1 0; 238 | #X connect 8 0 0 0; 239 | #X restore 154 463 pd playit; 240 | #N canvas 74 88 1062 745 playit 0; 241 | #X obj 21 47 unpack f f; 242 | #X obj 21 222 outlet~; 243 | #X floatatom 131 120 5 0 0 0 - - -; 244 | #X floatatom 88 118 5 0 0 0 - - -; 245 | #X obj 21 119 impulse~; 246 | #X obj 21 146 *~; 247 | #X obj 21 80 t b f; 248 | #X obj 21 182 player~ piano-sample; 249 | #X obj 21 8 inlet; 250 | #X connect 0 0 6 0; 251 | #X connect 0 1 2 0; 252 | #X connect 2 0 7 1; 253 | #X connect 3 0 5 1; 254 | #X connect 4 0 5 0; 255 | #X connect 5 0 7 0; 256 | #X connect 6 0 4 0; 257 | #X connect 6 1 3 0; 258 | #X connect 7 0 1 0; 259 | #X connect 8 0 0 0; 260 | #X restore 172 484 pd playit; 261 | #X connect 0 0 1 0; 262 | #X connect 1 0 7 0; 263 | #X connect 1 1 2 0; 264 | #X connect 2 0 3 0; 265 | #X connect 3 0 4 0; 266 | #X connect 4 0 2 1; 267 | #X connect 4 0 5 0; 268 | #X connect 5 0 6 0; 269 | #X connect 6 0 8 0; 270 | #X connect 7 0 6 1; 271 | #X connect 7 1 9 0; 272 | #X connect 8 0 11 0; 273 | #X connect 8 1 14 0; 274 | #X connect 8 2 15 0; 275 | #X connect 8 3 16 0; 276 | #X connect 8 4 17 0; 277 | #X connect 8 5 18 0; 278 | #X connect 8 6 19 0; 279 | #X connect 8 7 20 0; 280 | #X connect 9 0 6 2; 281 | #X connect 11 0 13 0; 282 | #X connect 13 0 12 0; 283 | #X connect 14 0 13 0; 284 | #X connect 15 0 13 0; 285 | #X connect 16 0 13 0; 286 | #X connect 17 0 13 0; 287 | #X connect 18 0 13 0; 288 | #X connect 19 0 13 0; 289 | #X connect 20 0 13 0; 290 | #X restore 12 97 pd choir; 291 | #X obj 12 121 outlet~; 292 | #X text 13 269 this is one example of what you can do with the analysis 293 | data; 294 | #X obj 12 63 spigot; 295 | #X obj 49 44 inlet; 296 | #X obj 113 27 loadbang; 297 | #X msg 113 47 0; 298 | #X connect 0 0 8 0; 299 | #X connect 3 0 2 0; 300 | #X connect 4 0 3 0; 301 | #X connect 5 0 6 0; 302 | #X connect 8 0 5 0; 303 | #X connect 9 0 8 1; 304 | #X connect 10 0 11 0; 305 | #X connect 11 0 8 1; 306 | #X restore 220 119 pd resynth-engine; 307 | #N canvas 408 408 482 332 sound-source 0; 308 | #X obj -34 240 outlet~; 309 | #X obj -34 215 *~ 0.3; 310 | #X floatatom -34 72 5 0 0 0 - - -; 311 | #X obj 149 119 * 1.5; 312 | #X floatatom 51 142 5 0 0 0 - - -; 313 | #X floatatom 149 143 5 0 0 0 - - -; 314 | #X obj 51 161 phasor~ 586.6; 315 | #X obj 149 161 phasor~ 660; 316 | #X obj -34 161 phasor~ 440; 317 | #X obj 51 119 * 1.25; 318 | #X msg -34 41 440; 319 | #X obj -34 15 loadbang; 320 | #X text -18 262 a soundfile or live mic would be more interesting here 321 | ; 322 | #X connect 1 0 0 0; 323 | #X connect 2 0 3 0; 324 | #X connect 2 0 8 0; 325 | #X connect 2 0 9 0; 326 | #X connect 3 0 5 0; 327 | #X connect 4 0 6 0; 328 | #X connect 5 0 7 0; 329 | #X connect 6 0 1 0; 330 | #X connect 7 0 1 0; 331 | #X connect 8 0 1 0; 332 | #X connect 9 0 4 0; 333 | #X connect 10 0 2 0; 334 | #X connect 11 0 10 0; 335 | #X restore 13 41 pd sound-source; 336 | #N canvas 180 51 470 320 what's-going-on-here? 0; 337 | #X text 18 26 Input sound is analyzed and a certain number of bin snapshots 338 | are taken \, based on the probability and framegrains parameters. Each 339 | bin grain snapshot is sent out as a list with two members: [amplitude 340 | \, frequency]. In this example the grain data is used to drive a sample 341 | player. One could easily replace this with a synth or even drive an 342 | external MIDI synth. This is something like a pitch-follower except 343 | that it follows the entire spectrum (limited by the topfreq parameter) 344 | rather than just looking for the fundamental. Since this is based on 345 | FFT analysis the resolution is worse for lower frequencies. Frequency 346 | resolution can be improved by upping the FFT size.; 347 | #X restore 269 203 pd what's-going-on-here?; 348 | #X obj 334 96 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 1 349 | ; 350 | #X text 356 98 <- turn me on; 351 | #X text 204 64 <- check me out; 352 | #X connect 0 0 7 0; 353 | #X connect 0 0 10 0; 354 | #X connect 4 0 3 0; 355 | #X connect 5 0 0 1; 356 | #X connect 6 0 7 1; 357 | #X connect 7 0 2 0; 358 | #X connect 10 0 1 0; 359 | #X connect 10 0 1 1; 360 | #X connect 11 0 0 0; 361 | #X connect 13 0 10 1; 362 | -------------------------------------------------------------------------------- /pvharm~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 768 40 466 316 10; 2 | #N canvas 0 22 466 316 pvharm-block 0; 3 | #X obj 22 81 pvharm~ 0 3000 4 1; 4 | #X obj 22 130 outlet~; 5 | #X obj 22 20 inlet~; 6 | #X obj 22 156 block~ 256; 7 | #X obj 62 41 inlet; 8 | #X obj 102 41 inlet; 9 | #X obj 143 41 inlet; 10 | #X obj 216 65 inlet; 11 | #X text 32 106 args: lowfreq \, highfreq \, overlap \, window-factor 12 | ; 13 | #X connect 0 0 1 0; 14 | #X connect 2 0 0 0; 15 | #X connect 4 0 0 1; 16 | #X connect 5 0 0 2; 17 | #X connect 6 0 0 3; 18 | #X connect 7 0 0 0; 19 | #X restore 70 134 pd pvharm-block; 20 | #X obj 70 200 dac~; 21 | #X obj 70 177 *~ 0.1; 22 | #X obj 70 53 phasor~ 300; 23 | #X floatatom 95 80 5 0 0 1 transpose1 - -; 24 | #X floatatom 120 97 5 0 0 1 transpose2 - -; 25 | #X floatatom 145 114 5 0 0 1 synth-threshold - -; 26 | #N canvas 587 239 474 324 messages 0; 27 | #X obj 61 259 outlet; 28 | #X msg 61 121 highfreq \$1; 29 | #X floatatom 61 100 5 0 0 0 - - -; 30 | #X floatatom 118 168 5 0 0 0 - - -; 31 | #X msg 118 189 lowfreq \$1; 32 | #X obj 165 228 fftease-system; 33 | #X obj 64 72 hsl 128 15 500 5000 0 0 empty empty empty -2 -6 0 8 -184257 34 | -1 -1 3500 1; 35 | #X obj 121 144 hsl 128 15 0 450 0 0 empty empty empty -2 -6 0 8 -184257 36 | -1 -1 5700 1; 37 | #X text 29 37 synthesis frequency boundaries; 38 | #X connect 1 0 0 0; 39 | #X connect 2 0 1 0; 40 | #X connect 3 0 4 0; 41 | #X connect 4 0 0 0; 42 | #X connect 5 0 0 0; 43 | #X connect 6 0 2 0; 44 | #X connect 7 0 3 0; 45 | #X restore 292 118 pd messages; 46 | #X obj 13 136 *~ 0.3; 47 | #X msg 163 206 \; pd dsp \$1; 48 | #X obj 110 155 hsl 128 15 0 0.2 0 0 empty empty empty -2 -6 0 8 -184257 49 | -1 -1 3500 1; 50 | #X obj 163 180 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 51 | 1; 52 | #X floatatom 70 30 5 0 0 0 - - -; 53 | #X text 18 254 pvharm~ provides basic harmonizing with two transpositions 54 | of the input internally calculated and mixed to the output; 55 | #N canvas 578 326 1043 702 init 0; 56 | #X obj 56 175 outlet; 57 | #X obj 104 171 outlet; 58 | #X obj 157 173 outlet; 59 | #X obj 230 177 outlet; 60 | #X obj 179 21 loadbang; 61 | #X msg 179 43 165 1.25 1.5 0.01; 62 | #X obj 179 64 unpack f f f f; 63 | #X connect 4 0 5 0; 64 | #X connect 5 0 6 0; 65 | #X connect 6 0 0 0; 66 | #X connect 6 1 1 0; 67 | #X connect 6 2 2 0; 68 | #X connect 6 3 3 0; 69 | #X restore 369 -6 pd init; 70 | #X text 244 156 gain; 71 | #X connect 0 0 2 0; 72 | #X connect 2 0 1 0; 73 | #X connect 2 0 1 1; 74 | #X connect 3 0 0 0; 75 | #X connect 3 0 8 0; 76 | #X connect 4 0 0 1; 77 | #X connect 5 0 0 2; 78 | #X connect 6 0 0 3; 79 | #X connect 7 0 0 4; 80 | #X connect 8 0 2 0; 81 | #X connect 10 0 2 1; 82 | #X connect 11 0 9 0; 83 | #X connect 12 0 3 0; 84 | #X connect 14 0 12 0; 85 | #X connect 14 1 4 0; 86 | #X connect 14 2 5 0; 87 | #X connect 14 3 6 0; 88 | -------------------------------------------------------------------------------- /pvoc~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas -2 462 686 439 10; 2 | #N canvas 0 22 502 352 pvocblock 0; 3 | #X obj 27 158 outlet~; 4 | #X obj 27 42 inlet~; 5 | #X obj 80 13 inlet; 6 | #X obj 134 46 inlet; 7 | #X obj 213 69 inlet; 8 | #X text 145 87 args: lo-freq \, hi-freq \, overlap \, window-factor 9 | ; 10 | #X obj 27 85 pvoc~ 0 8000 4 4; 11 | #X obj 27 182 block~ 256; 12 | #X connect 1 0 6 0; 13 | #X connect 2 0 6 1; 14 | #X connect 3 0 6 2; 15 | #X connect 4 0 6 0; 16 | #X connect 6 0 0 0; 17 | #X restore 203 144 pd pvocblock; 18 | #X obj 203 203 dac~; 19 | #X floatatom 229 68 5 0.1 3 2 transpose transpose -; 20 | #X floatatom 255 99 5 0 0 2 thresh thresh -; 21 | #X msg 44 193 \; pd dsp \$1; 22 | #X obj 44 174 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1 23 | ; 24 | #X obj 80 285 hsl 128 15 0.1 4 0 0 empty empty empty -2 -6 0 8 -261285 25 | -1 -1 1931 1; 26 | #N canvas 242 216 504 402 messages 1; 27 | #X obj 70 293 outlet; 28 | #X floatatom 70 82 5 0 0 0 - - -; 29 | #X msg 70 112 highfreq \$1; 30 | #X floatatom 182 175 5 0 0 0 - - -; 31 | #X msg 182 204 lowfreq \$1; 32 | #X msg 70 53 8000; 33 | #X obj 70 27 loadbang; 34 | #X msg 182 154 0; 35 | #X obj 182 132 loadbang; 36 | #X obj 212 267 fftease-system; 37 | #X obj 161 48 hsl 128 15 500 8000 0 0 empty empty empty -2 -6 0 8 -68760 38 | -1 -1 6900 1; 39 | #X obj 256 148 hsl 128 15 0 1000 0 0 empty empty empty -2 -6 0 8 -68760 40 | -1 -1 0 1; 41 | #X text 149 22 maximum frequency to synthesize; 42 | #X text 252 124 minimum; 43 | #X connect 1 0 2 0; 44 | #X connect 2 0 0 0; 45 | #X connect 3 0 4 0; 46 | #X connect 4 0 0 0; 47 | #X connect 5 0 1 0; 48 | #X connect 6 0 5 0; 49 | #X connect 7 0 3 0; 50 | #X connect 8 0 7 0; 51 | #X connect 9 0 0 0; 52 | #X connect 10 0 1 0; 53 | #X connect 11 0 3 0; 54 | #X restore 282 116 pd messages; 55 | #X obj 222 285 hsl 128 15 0 0.05 0 0 empty empty empty -2 -6 0 8 -227712 56 | -1 -1 300 1; 57 | #X obj 219 311 s thresh; 58 | #X obj 77 311 s transpose; 59 | #X obj 77 233 loadbang; 60 | #X msg 77 264 1; 61 | #X obj 311 144 hsl 128 15 0 1 0 0 empty empty empty -2 -6 0 8 -43049 62 | -1 -1 5400 1; 63 | #X obj 203 170 *~ 0.01; 64 | #X text 444 143 gain; 65 | #N canvas 639 439 639 490 sndfile 0; 66 | #X text 13 300 try a vocal sound or other sound with strong formant 67 | structure; 68 | #X obj 31 194 soundfiler; 69 | #X obj 31 160 openpanel; 70 | #N canvas 0 22 450 300 graph1 0; 71 | #X array pvoc-sound1 4e+06 float 2; 72 | #X coords 0 1 4e+06 -1 200 140 1; 73 | #X restore 237 13 graph; 74 | #X msg 31 131 bang; 75 | #X obj 227 284 outlet~; 76 | #X msg 227 244 bang; 77 | #X obj 348 228 spigot; 78 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 79 | 1; 80 | #X text 63 132 open the sound; 81 | #X text 133 244 then play it; 82 | #X text 304 190 loop if you like; 83 | #X obj 227 268 tabplay~ pvoc-sound1; 84 | #X msg 31 177 read -resize \$1 pvoc-sound1; 85 | #X connect 2 0 13 0; 86 | #X connect 4 0 2 0; 87 | #X connect 6 0 12 0; 88 | #X connect 7 0 6 0; 89 | #X connect 8 0 7 1; 90 | #X connect 12 0 5 0; 91 | #X connect 12 1 7 0; 92 | #X connect 13 0 1 0; 93 | #X restore 203 31 pd sndfile; 94 | #X msg 219 249 0.001; 95 | #X text 286 27 <- load a soundfile here; 96 | #X text 75 345 pvoc~ allows you to change the pitch of the input sound 97 | without changing its speed. Optional arguments: low frequency to synthesize 98 | \, high frequency to synthesize. These parameters \, together with 99 | the pvoc~ block size will determine CPU load.; 100 | #X connect 0 0 14 0; 101 | #X connect 2 0 0 1; 102 | #X connect 3 0 0 2; 103 | #X connect 5 0 4 0; 104 | #X connect 6 0 10 0; 105 | #X connect 7 0 0 3; 106 | #X connect 8 0 9 0; 107 | #X connect 11 0 12 0; 108 | #X connect 11 0 17 0; 109 | #X connect 12 0 6 0; 110 | #X connect 13 0 14 1; 111 | #X connect 14 0 1 0; 112 | #X connect 14 0 1 1; 113 | #X connect 16 0 0 0; 114 | #X connect 17 0 8 0; 115 | -------------------------------------------------------------------------------- /pvtuner.h: -------------------------------------------------------------------------------- 1 | #define MAXTONES (1024) 2 | #define BASE_FREQ (27.5) /* low A */ 3 | #define DIATONIC 0 4 | #define EASTERN 1 5 | #define MINOR 2 6 | #define EQ12 3 7 | #define PENTATONIC 4 8 | #define MAJOR_ADDED_SIXTH 5 9 | #define MINOR_ADDED_SIXTH 6 10 | #define MAJOR_SEVENTH_CHORD 7 11 | #define MINOR_SEVENTH_CHORD 8 12 | #define DOMINANT_SEVENTH_CHORD 9 13 | #define EQ8 10 14 | #define PENTACLUST 11 15 | #define QUARTERCLUST 12 16 | #define EQ5 13 17 | #define SLENDRO 14 18 | #define PELOG 15 19 | #define IMPORTED_SCALE 16 20 | 21 | #define DEFAULT_VECTOR_SIZE 512 22 | static t_class *pvtuner_class; 23 | 24 | typedef struct _pvtuner 25 | { 26 | t_object x_obj; 27 | t_float x_f; 28 | int R; 29 | int N; 30 | int N2; 31 | int Nw; 32 | int Nw2; 33 | int D; 34 | int i; 35 | int inCount; 36 | float *Wanal; 37 | float *Wsyn; 38 | float *input; 39 | float *Hwin; 40 | float *buffer; 41 | float *channel; 42 | float *output; 43 | // for convert 44 | float *c_lastphase_in; 45 | float *c_lastphase_out; 46 | float c_fundamental; 47 | float c_factor_in; 48 | float c_factor_out; 49 | 50 | // for oscbank 51 | int NP; 52 | float P; 53 | int L; 54 | int first; 55 | float Iinv; 56 | float *lastamp; 57 | float *lastfreq; 58 | float *bindex; 59 | float *table; 60 | float myPInc; 61 | float ffac; 62 | // 63 | int lo_bin; 64 | int hi_bin; 65 | float topfreq; 66 | float synt; 67 | float myPI; 68 | float TWOmyPI; 69 | // for fast fft 70 | float mult; 71 | float *trigland; 72 | int *bitshuffle; 73 | // 74 | float *prebuffer; 75 | float *postbuffer; 76 | // 77 | int bypass_state; 78 | int pitch_connected; 79 | int synt_connected; 80 | // TUNING 81 | float *pitchgrid ; 82 | float pbase ; 83 | int scale_steps; 84 | short current_scale; 85 | short mute; 86 | // 87 | float TWOPIoL; 88 | float user_lofreq; 89 | float user_hifreq; 90 | int vector_size; 91 | float funda; 92 | float curfreq; 93 | int overlap; 94 | int window_factor; 95 | float tabscale; 96 | int quality; 97 | int scale_len; 98 | } t_pvtuner; 99 | 100 | 101 | float closestf(float test, float *arr) ; 102 | void pvtuner_diatonic( t_pvtuner *x ); 103 | void pvtuner_eastern( t_pvtuner *x ); 104 | void pvtuner_minor( t_pvtuner *x ); 105 | void pvtuner_eq12( t_pvtuner *x ); 106 | void pvtuner_pentatonic( t_pvtuner *x ); 107 | void pvtuner_major_added_sixth( t_pvtuner *x ); 108 | void pvtuner_minor_added_sixth( t_pvtuner *x ); 109 | void pvtuner_major_seventh_chord( t_pvtuner *x ); 110 | void pvtuner_minor_seventh_chord( t_pvtuner *x ); 111 | void pvtuner_dominant_seventh_chord( t_pvtuner *x ); 112 | void pvtuner_eq8( t_pvtuner *x ); 113 | void pvtuner_pentaclust( t_pvtuner *x ); 114 | void pvtuner_quarterclust( t_pvtuner *x ); 115 | void pvtuner_eq5( t_pvtuner *x ); 116 | void pvtuner_slendro( t_pvtuner *x ); 117 | void pvtuner_pelog( t_pvtuner *x ); 118 | void pvtuner_update_imported( t_pvtuner *x ); 119 | 120 | 121 | -------------------------------------------------------------------------------- /pvtuner~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 189 203 449 413 10; 2 | #N canvas 0 22 502 352 tuneblock 0; 3 | #X obj 33 21 inlet~; 4 | #X obj 97 20 inlet; 5 | #X obj 161 25 inlet; 6 | #X obj 242 56 inlet; 7 | #X obj 33 203 outlet~; 8 | #X obj 33 102 pvtuner~ 0 5000; 9 | #X obj 147 208 block~ 256; 10 | #X connect 0 0 5 0; 11 | #X connect 1 0 5 1; 12 | #X connect 2 0 5 2; 13 | #X connect 3 0 5 0; 14 | #X connect 5 0 4 0; 15 | #X restore 24 141 pd tuneblock; 16 | #X obj 24 3 noise~; 17 | #X floatatom 50 71 5 0.1 2 1 transpose - -; 18 | #X obj 24 242 dac~; 19 | #X msg 81 239 \; pd dsp \$1; 20 | #X obj 81 216 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1 21 | ; 22 | #N canvas 154 403 400 321 messages 0; 23 | #X obj 21 216 outlet; 24 | #N canvas 0 22 536 459 built-in-scales 0; 25 | #X msg 11 30 major_seventh_chord; 26 | #X msg 41 49 minor_seventh_chord; 27 | #X msg 113 88 minor_added_sixth; 28 | #X msg 84 68 major_added_sixth; 29 | #X msg 320 8 pelog; 30 | #X msg 324 36 slendro; 31 | #X obj 46 312 outlet; 32 | #X msg 296 97 eq5; 33 | #X msg 302 117 eq8; 34 | #X msg 309 138 eq12; 35 | #X msg -1 11 dominant_seventh_chord; 36 | #X msg 276 181 minor; 37 | #X msg 284 208 pentatonic; 38 | #X msg 282 233 eastern; 39 | #X msg 255 261 pentaclust; 40 | #X msg 270 282 quarterclust; 41 | #X connect 0 0 6 0; 42 | #X connect 1 0 6 0; 43 | #X connect 2 0 6 0; 44 | #X connect 3 0 6 0; 45 | #X connect 4 0 6 0; 46 | #X connect 5 0 6 0; 47 | #X connect 7 0 6 0; 48 | #X connect 8 0 6 0; 49 | #X connect 9 0 6 0; 50 | #X connect 10 0 6 0; 51 | #X connect 11 0 6 0; 52 | #X connect 12 0 6 0; 53 | #X connect 13 0 6 0; 54 | #X connect 14 0 6 0; 55 | #X connect 15 0 6 0; 56 | #X restore 21 27 pd built-in-scales; 57 | #N canvas 520 357 631 434 more-scales 0; 58 | #X msg 77 94 27.5 41.25 55 82.5 110 165 220 330 440 660 880 1320 1760 59 | 2640 3520 5280 7040 10560 14080 21120; 60 | #X text 80 78 define scale as ordered list of numbers; 61 | #X obj 77 371 outlet; 62 | #X msg 165 148 import_scale examples/blue3.scale; 63 | #X text 161 130 you can even load a file \, but be sure to use a full 64 | pathname; 65 | #X msg 165 170 import_scale examples/13et.scale; 66 | #X msg 165 190 import_scale examples/24et.scale; 67 | #X msg 165 210 import_scale examples/4th.scale; 68 | #X msg 165 230 import_scale examples/blue3.scale; 69 | #X msg 165 250 import_scale examples/m3chord.scale; 70 | #X msg 165 270 import_scale examples/m3M3.scale; 71 | #X msg 165 290 import_scale examples/octfifth.scale; 72 | #X msg 165 310 import_scale examples/test.scale; 73 | #X text 217 337 There are also included perl scripts for generating 74 | the scale files: examples/scale*.pl; 75 | #X connect 0 0 2 0; 76 | #X connect 3 0 2 0; 77 | #X connect 5 0 2 0; 78 | #X connect 6 0 2 0; 79 | #X connect 7 0 2 0; 80 | #X connect 8 0 2 0; 81 | #X connect 9 0 2 0; 82 | #X connect 10 0 2 0; 83 | #X connect 11 0 2 0; 84 | #X connect 12 0 2 0; 85 | #X restore 48 48 pd more-scales; 86 | #X obj 130 154 fftease-system; 87 | #N canvas 968 224 694 704 frequency-management 0; 88 | #X obj 37 509 outlet; 89 | #X msg 37 122 toptune \$1; 90 | #X msg 187 129 topfreq \$1; 91 | #X floatatom 37 93 5 0 0 0 - - -; 92 | #X floatatom 187 98 5 0 0 0 - - -; 93 | #X obj 160 31 hsl 200 15 500 9000 0 0 empty empty empty -2 -6 0 8 -126035 94 | -1 -1 0 1; 95 | #X obj 157 57 t f f; 96 | #X msg 258 181 frequency_range 500 2000; 97 | #X msg 258 207 frequency_range 0 6000; 98 | #X text 45 106 highest tuned freq; 99 | #X text 191 114 highest synthesized freq; 100 | #X text 256 166 set synthesize range; 101 | #X msg 155 471 basefreq \$1; 102 | #X floatatom 155 454 5 0 0 0 - - -; 103 | #X obj 158 433 hsl 128 15 27.5 500 0 0 empty empty empty -2 -6 0 8 104 | -261681 -1 -1 0 1; 105 | #X msg 155 406 27.5; 106 | #X obj 155 381 loadbang; 107 | #X text 190 409 set base frequency for scale; 108 | #X obj 40 12 hsl 200 15 500 9000 0 0 empty empty empty -2 -6 0 8 -126035 109 | -1 -1 0 1; 110 | #X connect 1 0 0 0; 111 | #X connect 2 0 0 0; 112 | #X connect 3 0 1 0; 113 | #X connect 4 0 2 0; 114 | #X connect 5 0 6 0; 115 | #X connect 6 0 3 0; 116 | #X connect 6 1 4 0; 117 | #X connect 7 0 0 0; 118 | #X connect 8 0 0 0; 119 | #X connect 12 0 0 0; 120 | #X connect 13 0 12 0; 121 | #X connect 14 0 13 0; 122 | #X connect 15 0 14 0; 123 | #X connect 16 0 15 0; 124 | #X connect 18 0 3 0; 125 | #X restore 56 73 pd frequency-management; 126 | #X msg 109 116 binfo; 127 | #X connect 1 0 0 0; 128 | #X connect 2 0 0 0; 129 | #X connect 3 0 0 0; 130 | #X connect 4 0 0 0; 131 | #X connect 5 0 0 0; 132 | #X restore 103 115 pd messages; 133 | #X obj 167 26 loadbang; 134 | #X msg 50 42 1; 135 | #X obj 71 163 hsl 128 15 0 1 0 0 empty empty empty -2 -6 0 8 -123336 136 | -1 -1 0 1; 137 | #X floatatom 68 181 5 0 0 0 - - -; 138 | #X floatatom 76 91 5 0 0 1 synth-threshold - -; 139 | #X msg 167 47 0.001; 140 | #X text 188 116 <- check it; 141 | #X obj 24 199 *~ 0.01; 142 | #X text 27 295 pvtuner~ tunes sounds to scales.; 143 | #X connect 0 0 14 0; 144 | #X connect 1 0 0 0; 145 | #X connect 2 0 0 1; 146 | #X connect 5 0 4 0; 147 | #X connect 6 0 0 3; 148 | #X connect 7 0 8 0; 149 | #X connect 7 0 12 0; 150 | #X connect 8 0 2 0; 151 | #X connect 9 0 10 0; 152 | #X connect 10 0 14 1; 153 | #X connect 11 0 0 2; 154 | #X connect 12 0 11 0; 155 | #X connect 14 0 3 0; 156 | #X connect 14 0 3 1; 157 | -------------------------------------------------------------------------------- /pvwarp~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 36 232 566 392 10; 2 | #N canvas 0 22 462 312 pvwarp-block 0; 3 | #X obj 185 146 pvwarp~ 0 4000 4 2; 4 | #X obj 185 187 outlet~; 5 | #X obj 158 250 block~ 256; 6 | #X obj 185 88 inlet~; 7 | #X obj 339 83 inlet; 8 | #X obj 265 47 inlet; 9 | #X obj 283 70 inlet; 10 | #X obj 321 52 inlet; 11 | #X connect 0 0 1 0; 12 | #X connect 3 0 0 0; 13 | #X connect 4 0 0 0; 14 | #X connect 5 0 0 7; 15 | #X connect 6 0 0 8; 16 | #X connect 7 0 0 9; 17 | #X restore 121 125 pd pvwarp-block; 18 | #N canvas 595 467 629 326 messages 0; 19 | #X obj 182 294 outlet; 20 | #X msg 99 77 bottomfreq \$1; 21 | #X floatatom 99 54 5 0 0 0 - - -; 22 | #X floatatom 253 68 5 0 0 0 - - -; 23 | #X msg 253 87 topfreq \$1; 24 | #X msg 301 178 autofunc 0.1 2; 25 | #X obj 301 158 loadbang; 26 | #X text 254 50 highest freq to synthesize; 27 | #X text 98 38 lowest freq; 28 | #N canvas 430 531 673 333 init 0; 29 | #X msg 66 47 automate 1; 30 | #X obj 66 17 loadbang; 31 | #X text 159 28 this tells Pd to ignore its control inlets and take 32 | the warp function exclusively from its internally generated states. 33 | This is because otherwise we'd have to deal with sending lots of data 34 | to the inlets.; 35 | #X text 78 125 FYI - the inlets are as follows: signal in \, CF1 \, 36 | BW1 \, warpfac1 \, CF2 \, BW2 \, warpfac2 \, transposition \, synthesis 37 | threshold.; 38 | #X obj 22 268 outlet; 39 | #X obj 196 265 s warp-offset; 40 | #X obj 305 262 s warp-transpose; 41 | #X obj 429 262 s warp-threshold; 42 | #X obj 207 221 unpack f f f; 43 | #X msg 207 197 0 1 1e-05; 44 | #X obj 207 174 loadbang; 45 | #X connect 0 0 4 0; 46 | #X connect 1 0 0 0; 47 | #X connect 8 0 5 0; 48 | #X connect 8 1 6 0; 49 | #X connect 8 2 7 0; 50 | #X connect 9 0 8 0; 51 | #X connect 10 0 9 0; 52 | #X restore 290 231 pd init; 53 | #X obj 256 26 hsl 128 15 500 5000 0 0 empty empty empty -2 -6 0 8 -260204 54 | -1 -1 8700 1; 55 | #X obj 102 17 hsl 128 15 0 1000 0 0 empty empty empty -2 -6 0 8 -260204 56 | -1 -1 0 1; 57 | #X text 407 177 punch for a new warp function.; 58 | #X text 295 201 parameters are minimum warp and maximum warp.; 59 | #X obj 370 259 fftease-system; 60 | #X connect 1 0 0 0; 61 | #X connect 2 0 1 0; 62 | #X connect 3 0 4 0; 63 | #X connect 4 0 0 0; 64 | #X connect 5 0 0 0; 65 | #X connect 6 0 5 0; 66 | #X connect 9 0 0 0; 67 | #X connect 10 0 3 0; 68 | #X connect 11 0 2 0; 69 | #X connect 14 0 0 0; 70 | #X restore 258 109 pd messages; 71 | #X msg 44 193 \; pd dsp \$1; 72 | #X obj 44 174 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 1 73 | ; 74 | #X obj 121 160 dac~; 75 | #X floatatom 171 89 5 0 0 0 - transpose -; 76 | #X floatatom 146 72 5 0 0 0 - offset -; 77 | #X obj 201 196 hsl 128 15 0 1 0 0 offset empty offset -2 -6 0 8 -260204 78 | -1 -1 4200 1; 79 | #X obj 202 231 hsl 128 15 0.25 1.5 0 0 transpose empty transpose -2 80 | -6 0 8 -260204 -1 -1 7720 1; 81 | #X obj 201 264 hsl 128 15 0 0.05 0 0 threshold empty threshold -2 -6 82 | 0 8 -260204 -1 -1 0 1; 83 | #X floatatom 196 106 5 0 0 0 - threshold -; 84 | #X text 231 41 load a sound \, then warp away; 85 | #X text 339 262 synthesis threshold; 86 | #X text 334 196 offset for warping function; 87 | #X text 343 107 <- more info here; 88 | #N canvas 639 439 647 498 sound-source 0; 89 | #X text 13 300 try a vocal sound or other sound with strong formant 90 | structure; 91 | #X obj 31 194 soundfiler; 92 | #X obj 31 160 openpanel; 93 | #N canvas 0 22 450 300 graph1 0; 94 | #X array pvwarp-sound1 4e+06 float 2; 95 | #X coords 0 1 4e+06 -1 200 140 1; 96 | #X restore 237 13 graph; 97 | #X msg 31 131 bang; 98 | #X obj 227 284 outlet~; 99 | #X msg 227 244 bang; 100 | #X obj 348 228 spigot; 101 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 102 | 1; 103 | #X text 63 132 open the sound; 104 | #X text 133 244 then play it; 105 | #X text 304 190 loop if you like; 106 | #X obj 227 268 tabplay~ pvwarp-sound1; 107 | #X msg 31 177 read -resize \$1 pvwarp-sound1; 108 | #X connect 2 0 13 0; 109 | #X connect 4 0 2 0; 110 | #X connect 6 0 12 0; 111 | #X connect 7 0 6 0; 112 | #X connect 8 0 7 1; 113 | #X connect 12 0 5 0; 114 | #X connect 12 1 7 0; 115 | #X connect 13 0 1 0; 116 | #X restore 121 41 pd sound-source; 117 | #X text 80 304 Experimental spectrum warper. An internal frequency 118 | warping function is created either according to specification or with 119 | the autofunc message. Try it on vocal sounds.; 120 | #N canvas 0 22 454 304 rinit 0; 121 | #X obj 26 83 r warp-offset; 122 | #X obj 135 80 r warp-transpose; 123 | #X obj 256 79 r warp-threshold; 124 | #X obj 48 160 outlet; 125 | #X obj 109 171 outlet; 126 | #X obj 244 174 outlet; 127 | #X connect 0 0 3 0; 128 | #X connect 1 0 4 0; 129 | #X connect 2 0 5 0; 130 | #X restore 131 231 pd rinit; 131 | #X connect 0 0 4 0; 132 | #X connect 0 0 4 1; 133 | #X connect 1 0 0 4; 134 | #X connect 3 0 2 0; 135 | #X connect 5 0 0 2; 136 | #X connect 6 0 0 1; 137 | #X connect 10 0 0 3; 138 | #X connect 15 0 0 0; 139 | #X connect 17 0 7 0; 140 | #X connect 17 1 8 0; 141 | #X connect 17 2 9 0; 142 | -------------------------------------------------------------------------------- /qsortE.c: -------------------------------------------------------------------------------- 1 | /* Plug-compatible replacement for UNIX qsort. Copyright (C) 1989 Free Software Foundation, Inc. Written by Douglas C. Schmidt (schmidt@ics.uci.edu) This file is part of GNU CC. GNU QSORT is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2, or (at your option) any later version. GNU QSORT is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with GNU QSORT; see the file COPYING. If not, write to the Free the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ /* Synched up with: FSF 19.28. */ #ifdef sparc #include #endif #include /* Invoke the comparison function, returns either 0, < 0, or > 0. */ #define CMP(A,B) ((*cmp)((A),(B))) /* Byte-wise swap two items of size SIZE. */ #define SWAP(A,B,SIZE) do {int sz = (SIZE); char *a = (A); char *b = (B); \ do { char _temp = *a;*a++ = *b;*b++ = _temp;} while (--sz);} while (0) /* Copy SIZE bytes from item B to item A. */ #define COPY(A,B,SIZE) {int sz = (SIZE); do { *(A)++ = *(B)++; } while (--sz); } /* This should be replaced by a standard ANSI macro. */ #define BYTES_PER_WORD 8 /* The next 4 #defines implement a very fast in-line stack abstraction. */ #define STACK_SIZE (BYTES_PER_WORD * sizeof (long)) #define PUSH(LOW,HIGH) do {top->lo = LOW;top++->hi = HIGH;} while (0) #define POP(LOW,HIGH) do {LOW = (--top)->lo;HIGH = top->hi;} while (0) #define STACK_NOT_EMPTY (stack < top) /* Discontinue quicksort algorithm when partition gets below this size. This particular magic number was chosen to work best on a Sun 4/260. */ #define MAX_THRESH 4 /* requisite prototype */ int qsortE (char *base_ptr, int total_elems, int size, int (*cmp)()); /* Stack node declarations used to store unfulfilled partition obligations. */ typedef struct { char *lo; char *hi; } stack_node; /* Order size using quicksort. This implementation incorporates four optimizations discussed in Sedgewick: 1. Non-recursive, using an explicit stack of pointer that store the next array partition to sort. To save time, this maximum amount of space required to store an array of MAX_INT is allocated on the stack. Assuming a 32-bit integer, this needs only 32 * sizeof (stack_node) == 136 bits. Pretty cheap, actually. 2. Choose the pivot element using a median-of-three decision tree. This reduces the probability of selecting a bad pivot value and eliminates certain extraneous comparisons. 3. Only quicksorts TOTAL_ELEMS / MAX_THRESH partitions, leaving insertion sort to order the MAX_THRESH items within each partition. This is a big win, since insertion sort is faster for small, mostly sorted array segments. 4. The larger of the two sub-partitions is always pushed onto the stack first, with the algorithm then concentrating on the smaller partition. This *guarantees* no more than log (n) stack size is needed (actually O(1) in this case)! */ int qsortE (char *base_ptr, int total_elems, int size, int (*cmp)()) { /* Allocating SIZE bytes for a pivot buffer facilitates a better algorithm below since we can do comparisons directly on the pivot. */ char *pivot_buffer = (char *) malloc(size); int max_thresh = MAX_THRESH * size; if (total_elems > MAX_THRESH) { char *lo = base_ptr; char *hi = lo + size * (total_elems - 1); stack_node stack[STACK_SIZE]; /* Largest size needed for 32-bit int!!! */ stack_node *top = stack + 1; while (STACK_NOT_EMPTY) { char *left_ptr; char *right_ptr; { char *pivot = pivot_buffer; { /* Select median value from among LO, MID, and HI. Rearrange LO and HI so the three values are sorted. This lowers the probability of picking a pathological pivot value and skips a comparison for both the LEFT_PTR and RIGHT_PTR. */ char *mid = lo + size * ((hi - lo) / size >> 1); if (CMP (mid, lo) < 0) SWAP (mid, lo, size); if (CMP (hi, mid) < 0) SWAP (mid, hi, size); else goto jump_over; if (CMP (mid, lo) < 0) SWAP (mid, lo, size); jump_over: COPY (pivot, mid, size); pivot = pivot_buffer; } left_ptr = lo + size; right_ptr = hi - size; /* Here's the famous ``collapse the walls'' section of quicksort. Gotta like those tight inner loops! They are the main reason that this algorithm runs much faster than others. */ do { while (CMP (left_ptr, pivot) < 0) left_ptr += size; while (CMP (pivot, right_ptr) < 0) right_ptr -= size; if (left_ptr < right_ptr) { SWAP (left_ptr, right_ptr, size); left_ptr += size; right_ptr -= size; } else if (left_ptr == right_ptr) { left_ptr += size; right_ptr -= size; break; } } while (left_ptr <= right_ptr); } /* Set up pointers for next iteration. First determine whether left and right partitions are below the threshold size. If so, ignore one or both. Otherwise, push the larger partition's bounds on the stack and continue sorting the smaller one. */ if ((right_ptr - lo) <= max_thresh) { if ((hi - left_ptr) <= max_thresh) /* Ignore both small partitions. */ POP (lo, hi); else /* Ignore small left partition. */ lo = left_ptr; } else if ((hi - left_ptr) <= max_thresh) /* Ignore small right partition. */ hi = right_ptr; else if ((right_ptr - lo) > (hi - left_ptr)) /* Push larger left partition indices. */ { PUSH (lo, right_ptr); lo = left_ptr; } else /* Push larger right partition indices. */ { PUSH (left_ptr, hi); hi = right_ptr; } } } /* Once the BASE_PTR array is partially sorted by quicksort the rest is completely sorted using insertion sort, since this is efficient for partitions below MAX_THRESH size. BASE_PTR points to the beginning of the array to sort, and END_PTR points at the very last element in the array (*not* one beyond it!). */ #define MIN(X,Y) ((X) < (Y) ? (X) : (Y)) { char *end_ptr = base_ptr + size * (total_elems - 1); char *run_ptr; char *tmp_ptr = base_ptr; char *thresh = MIN (end_ptr, base_ptr + max_thresh); /* Find smallest element in first threshold and place it at the array's beginning. This is the smallest array element, and the operation speeds up insertion sort's inner loop. */ for (run_ptr = tmp_ptr + size; run_ptr <= thresh; run_ptr += size) if (CMP (run_ptr, tmp_ptr) < 0) tmp_ptr = run_ptr; if (tmp_ptr != base_ptr) SWAP (tmp_ptr, base_ptr, size); /* Insertion sort, running from left-hand-side up to `right-hand-side.' Pretty much straight out of the original GNU qsort routine. */ for (run_ptr = base_ptr + size; (tmp_ptr = run_ptr += size) <= end_ptr; ) { while (CMP (run_ptr, tmp_ptr -= size) < 0) ; if ((tmp_ptr += size) != run_ptr) { char *trav; for (trav = run_ptr + size; --trav >= run_ptr;) { char c = *trav; char *hi, *lo; for (hi = lo = trav; (lo -= size) >= tmp_ptr; hi = lo) *hi = *lo; *hi = c; } } } } return 1; } -------------------------------------------------------------------------------- /reanimator~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 17 365 720 517 10; 2 | #N canvas 132 212 480 321 reanimator-block 0; 3 | #X obj 15 170 block~ 256; 4 | #X obj 19 30 inlet~; 5 | #X obj 154 33 inlet~; 6 | #X obj 217 34 inlet; 7 | #X obj 19 105 outlet~; 8 | #X obj 86 105 outlet~; 9 | #X obj 154 106 outlet~; 10 | #X text 17 128 args: size of texture analysis(ms.) \, overlap factor 11 | \, window factor; 12 | #X obj 19 78 reanimator~ 5000 4 1; 13 | #X connect 1 0 8 0; 14 | #X connect 2 0 8 1; 15 | #X connect 3 0 8 0; 16 | #X connect 8 0 4 0; 17 | #X connect 8 1 5 0; 18 | #X connect 8 2 6 0; 19 | #X restore 96 87 pd reanimator-block; 20 | #N canvas 536 186 752 534 driver-sound 0; 21 | #X text 13 300 try a vocal sound or other sound with strong formant 22 | structure; 23 | #X obj 31 194 soundfiler; 24 | #X obj 31 160 openpanel; 25 | #N canvas 0 22 450 300 graph1 0; 26 | #X array reanimator-sound1 4e+06 float 2; 27 | #X coords 0 1 4e+06 -1 200 140 1; 28 | #X restore 237 13 graph; 29 | #X msg 31 131 bang; 30 | #X obj 227 284 outlet~; 31 | #X msg 227 244 bang; 32 | #X obj 348 228 spigot; 33 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 34 | 1; 35 | #X text 133 244 then play it; 36 | #X text 304 190 loop if you like; 37 | #X msg 31 177 read -resize \$1 reanimator-sound1; 38 | #X obj 227 268 tabplay~ reanimator-sound1; 39 | #X text 63 132 open the driver sound; 40 | #X connect 2 0 11 0; 41 | #X connect 4 0 2 0; 42 | #X connect 6 0 12 0; 43 | #X connect 7 0 6 0; 44 | #X connect 8 0 7 1; 45 | #X connect 11 0 1 0; 46 | #X connect 12 0 5 0; 47 | #X connect 12 1 7 0; 48 | #X restore 96 30 pd driver-sound; 49 | #N canvas 349 43 518 368 texture-sound 0; 50 | #X text 13 300 try a vocal sound or other sound with strong formant 51 | structure; 52 | #X obj 31 194 soundfiler; 53 | #X obj 31 160 openpanel; 54 | #N canvas 0 22 450 300 graph1 0; 55 | #X array reanimator-sound2 1.25363e+06 float 2; 56 | #X coords 0 1 1.25363e+06 -1 200 140 1; 57 | #X restore 237 13 graph; 58 | #X msg 31 131 bang; 59 | #X obj 227 284 outlet~; 60 | #X msg 227 244 bang; 61 | #X obj 348 228 spigot; 62 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 63 | 1; 64 | #X text 133 244 then play it; 65 | #X text 304 190 loop if you like; 66 | #X msg 31 177 read -resize \$1 reanimator-sound2; 67 | #X obj 227 268 tabplay~ reanimator-sound2; 68 | #X text 63 132 open the texture sound; 69 | #X connect 2 0 11 0; 70 | #X connect 4 0 2 0; 71 | #X connect 6 0 12 0; 72 | #X connect 7 0 6 0; 73 | #X connect 8 0 7 1; 74 | #X connect 11 0 1 0; 75 | #X connect 12 0 5 0; 76 | #X connect 12 1 7 0; 77 | #X restore 160 49 pd texture-sound; 78 | #X msg 499 356 \; pd dsp \$1; 79 | #X obj 499 337 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 80 | 1; 81 | #X obj 96 269 dac~; 82 | #X obj 160 150 snapshot~; 83 | #X floatatom 160 172 5 0 0 0 - - -; 84 | #X obj 324 167 snapshot~; 85 | #X floatatom 324 189 5 0 0 0 - - -; 86 | #X obj 324 134 metro 50; 87 | #X obj 324 113 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 88 | 1; 89 | #X text 324 201 analysis sync; 90 | #X text 158 184 matched frame; 91 | #N canvas 913 441 569 496 messages 0; 92 | #X obj 128 229 outlet; 93 | #X msg 24 181 analyze; 94 | #X msg 128 117 topbin \$1; 95 | #X floatatom 128 81 5 0 0 0 - - -; 96 | #X msg 206 117 inverse \$1; 97 | #X obj 206 84 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1 98 | ; 99 | #X text 189 163 texture sound must be playing during analysis; 100 | #X text 194 183 otherwise: crash!!!; 101 | #X text 223 84 matches with *least* good frame; 102 | #X text 128 39 top bin to match: lower means less CPU; 103 | #X text 128 54 different (perhaps worse) matching; 104 | #X obj 36 39 loadbang; 105 | #X msg 36 65 20; 106 | #X obj 231 213 fftease-system; 107 | #N canvas 0 22 454 304 more-info 0; 108 | #X text 18 60 How does this work? First load up a texture sound and 109 | play it into the right inlet of reanimator~. While the texture sound 110 | is playing \, send an "analyze" message and the texture sound will 111 | be captured (5 seconds worth in this example patch). Once you see the 112 | message "data acquisition completed" in the Pd window \, play any sound 113 | into the left inlet and reanimator~ will output the best match from 114 | the texture sound. If the input and output are the same sound \, the 115 | match should be identical. Otherwise the result is "texture mapping" 116 | the texture sound onto the driver sound. The key to effective use of 117 | reanimator~ is in smart selections of driver and texture sounds.; 118 | #X restore 382 225 pd more-info; 119 | #X text 5 163 get texture sample; 120 | #X connect 1 0 0 0; 121 | #X connect 2 0 0 0; 122 | #X connect 3 0 2 0; 123 | #X connect 4 0 0 0; 124 | #X connect 5 0 4 0; 125 | #X connect 11 0 12 0; 126 | #X connect 12 0 3 0; 127 | #X connect 13 0 0 0; 128 | #X restore 255 71 pd messages; 129 | #X text 51 287 reanimator performs spectral reanimation \, AKA audio 130 | texture mapping. An online paper descripts this process in greater 131 | detail. Essentially reanimator~ captures input from its rightmost inlet 132 | and uses this as material to reconstitute sound coming in on the left. 133 | Since this is done by searching all stored spectra \, there are limits 134 | to how much sound may be recorded before overloading your computer's 135 | CPU. Start with a small amount of sound \, say 5 seconds \, and gradually 136 | increase until you find your practical limit. Once the texture sound 137 | has been recorded \, it may be driven by unlimited amounts of material 138 | in the leftmost inlet. Your driver should have a clear rhythmic profile. 139 | A drum loop would be a good place to start.; 140 | #X text 80 470 http://tinyurl.com/9324v; 141 | #X text 57 450 more info below or google "spectral reanimation"; 142 | #X text 261 31 <- load sounds into both buffers; 143 | #X obj 122 202 hsl 128 15 0 4 0 0 empty empty empty -2 -6 0 8 -176298 144 | -1 -1 11100 1; 145 | #X floatatom 119 225 5 0 0 0 - - -; 146 | #X obj 96 246 *~ 1; 147 | #X text 165 223 gain; 148 | #X connect 0 0 21 0; 149 | #X connect 0 1 6 0; 150 | #X connect 0 2 8 0; 151 | #X connect 1 0 0 0; 152 | #X connect 2 0 0 1; 153 | #X connect 4 0 3 0; 154 | #X connect 6 0 7 0; 155 | #X connect 8 0 9 0; 156 | #X connect 10 0 8 0; 157 | #X connect 10 0 6 0; 158 | #X connect 11 0 10 0; 159 | #X connect 14 0 0 2; 160 | #X connect 19 0 20 0; 161 | #X connect 20 0 21 1; 162 | #X connect 21 0 5 0; 163 | #X connect 21 0 5 1; 164 | -------------------------------------------------------------------------------- /resent~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 309 443 478 328 10; 2 | #N canvas 0 22 522 372 sound-source 0; 3 | #X text 13 300 try a vocal sound or other sound with strong formant 4 | structure; 5 | #X obj 31 194 soundfiler; 6 | #X obj 31 160 openpanel; 7 | #N canvas 0 22 450 300 graph1 0; 8 | #X array resent-sound1 1.25363e+06 float 2; 9 | #X coords 0 1 1.25363e+06 -1 200 140 1; 10 | #X restore 237 13 graph; 11 | #X msg 31 131 bang; 12 | #X obj 227 284 outlet~; 13 | #X msg 227 244 bang; 14 | #X obj 348 228 spigot; 15 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 16 | 1; 17 | #X text 63 132 open the sound; 18 | #X text 133 244 then play it; 19 | #X text 304 190 loop if you like; 20 | #X obj 227 268 tabplay~ resent-sound1; 21 | #X msg 31 177 read -resize \$1 resent-sound1; 22 | #X connect 2 0 13 0; 23 | #X connect 4 0 2 0; 24 | #X connect 6 0 12 0; 25 | #X connect 7 0 6 0; 26 | #X connect 8 0 7 1; 27 | #X connect 12 0 5 0; 28 | #X connect 12 1 7 0; 29 | #X connect 13 0 1 0; 30 | #X restore 35 68 pd sound-source; 31 | #X msg 231 143 \; pd dsp \$1; 32 | #X obj 231 117 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 33 | 1; 34 | #N canvas 0 22 474 324 resent-block 1; 35 | #X obj 164 51 inlet~; 36 | #X obj 164 143 outlet~; 37 | #X obj 271 203 outlet; 38 | #X obj 162 183 block~ 256; 39 | #X obj 264 54 inlet; 40 | #X obj 164 98 resent~ 5000 4 1; 41 | #X obj 271 175 snapshot~; 42 | #X obj 326 137 metro 50; 43 | #X msg 326 116 1; 44 | #X obj 326 80 loadbang; 45 | #X connect 0 0 5 0; 46 | #X connect 4 0 5 0; 47 | #X connect 5 0 1 0; 48 | #X connect 5 1 6 0; 49 | #X connect 6 0 2 0; 50 | #X connect 7 0 6 0; 51 | #X connect 8 0 7 0; 52 | #X connect 9 0 8 0; 53 | #X restore 35 114 pd resent-block; 54 | #X obj 35 158 dac~; 55 | #N canvas 921 180 636 397 messages 0; 56 | #X obj 171 295 outlet; 57 | #X msg 171 112 acquire_sample; 58 | #N canvas 260 436 657 449 global-control 0; 59 | #X obj 82 351 outlet; 60 | #X msg 257 259 1 0; 61 | #X msg 299 259 -1 0; 62 | #X text 254 347 set speed and phase; 63 | #X msg 82 166 setspeed \$1; 64 | #X floatatom 82 140 5 0 0 0 - a -; 65 | #X msg 337 259 0 0; 66 | #X floatatom 206 66 5 0 0 0 - b -; 67 | #X msg 206 92 setphase \$1; 68 | #X obj 439 235 vsl 15 128 -2 2 0 0 a empty empty 0 -8 0 8 -236160 -1 69 | -1 0 1; 70 | #X obj 461 235 vsl 15 128 0 1 0 0 b empty empty 0 -8 0 8 -236160 -1 71 | -1 0 1; 72 | #X msg 257 327 ssap \$1 \$1; 73 | #X text 421 209 speed; 74 | #X text 460 373 phase; 75 | #X connect 1 0 11 0; 76 | #X connect 2 0 11 0; 77 | #X connect 4 0 0 0; 78 | #X connect 5 0 4 0; 79 | #X connect 6 0 11 0; 80 | #X connect 7 0 8 0; 81 | #X connect 8 0 0 0; 82 | #X connect 11 0 0 0; 83 | #X restore 197 151 pd global-control; 84 | #X text 281 112 record sample to FFT buffer; 85 | #X obj 320 255 fftease-system; 86 | #N canvas 0 22 454 304 init 0; 87 | #X msg 158 101 verbose 1; 88 | #X obj 158 76 loadbang; 89 | #X msg 235 148 playthrough 1; 90 | #X obj 235 125 loadbang; 91 | #X obj 178 210 outlet; 92 | #X connect 0 0 4 0; 93 | #X connect 1 0 0 0; 94 | #X connect 2 0 4 0; 95 | #X connect 3 0 2 0; 96 | #X restore 252 245 pd init; 97 | #N canvas 786 85 508 405 separate-bin-control 0; 98 | #X obj 50 296 outlet; 99 | #X obj 50 129 pack f f; 100 | #X floatatom 50 95 5 0 0 0 - - -; 101 | #X floatatom 101 96 5 0 0 0 - - -; 102 | #X text 48 79 bin #; 103 | #X text 99 81 bin speed; 104 | #X msg 187 122 linespeed 0 -1 511 1; 105 | #X text 164 105 startbin startspeed endbin endspeed; 106 | #X text 164 222 minspeed maxspeed; 107 | #X msg 162 265 randphase 0 1; 108 | #X msg 188 163 linephase 0 0 511 1; 109 | #X msg 165 237 randspeed 0.95 1.05; 110 | #X text 47 53 phase is bounded by 0-1; 111 | #X text 47 39 bin numbers are bounded by 0-(FFT_size/2 - 1); 112 | #X msg 50 168 bin \$1 \$2; 113 | #X text 45 327 The cool thing here is that each FFT bin can be set 114 | to a different speed.; 115 | #X connect 1 0 14 0; 116 | #X connect 2 0 1 0; 117 | #X connect 3 0 1 1; 118 | #X connect 6 0 0 0; 119 | #X connect 9 0 0 0; 120 | #X connect 10 0 0 0; 121 | #X connect 11 0 0 0; 122 | #X connect 14 0 0 0; 123 | #X restore 210 176 pd separate-bin-control; 124 | #X text 334 157 then control it; 125 | #X connect 1 0 0 0; 126 | #X connect 2 0 0 0; 127 | #X connect 4 0 0 0; 128 | #X connect 5 0 0 0; 129 | #X connect 6 0 0 0; 130 | #X restore 135 92 pd messages; 131 | #X text 28 212 resent~ follows the model of residency~ but allows independent 132 | control over each bin. It is recommended that you familiarize yourself 133 | with residency~ before working with the more complicated resent~.; 134 | #X floatatom 135 150 5 0 0 0 - - -; 135 | #X text 117 167 record sync; 136 | #X text 155 71 <- first load a sound; 137 | #X text 228 93 <- then see what else you can do; 138 | #X connect 0 0 3 0; 139 | #X connect 2 0 1 0; 140 | #X connect 3 0 4 0; 141 | #X connect 3 0 4 1; 142 | #X connect 3 1 7 0; 143 | #X connect 5 0 3 1; 144 | -------------------------------------------------------------------------------- /residency~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 230 215 591 546 10; 2 | #N canvas 0 22 490 340 residency-block 0; 3 | #X obj 28 42 inlet~; 4 | #X obj 92 44 inlet~; 5 | #X obj 156 44 inlet~; 6 | #X obj 229 46 inlet; 7 | #X obj 28 140 outlet~; 8 | #X obj 28 99 residency~ 5000 4 1; 9 | #X obj 28 169 block~ 256; 10 | #X text 39 120 args: buffer size \, overlap \, window factor; 11 | #X text 103 171 FFT size is block~ size times overlap; 12 | #X obj 232 235 snapshot~; 13 | #X obj 393 187 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 14 | 1; 15 | #X obj 232 264 outlet; 16 | #X msg 393 142 loadbang; 17 | #X msg 393 165 1; 18 | #X obj 394 205 metro 100; 19 | #X connect 0 0 5 0; 20 | #X connect 1 0 5 1; 21 | #X connect 2 0 5 2; 22 | #X connect 3 0 5 0; 23 | #X connect 5 0 4 0; 24 | #X connect 5 1 9 0; 25 | #X connect 9 0 11 0; 26 | #X connect 10 0 14 0; 27 | #X connect 12 0 13 0; 28 | #X connect 13 0 10 0; 29 | #X connect 14 0 9 0; 30 | #X restore 124 220 pd residency-block; 31 | #N canvas 449 46 676 438 messages 0; 32 | #X obj 119 302 outlet; 33 | #X floatatom 289 121 5 0 0 2 resize_memory size -; 34 | #X msg 289 151 size \$1; 35 | #X obj 119 70 bng 15 250 50 0 empty trigger trigger_sampling 0 -6 0 36 | 8 -262144 -1 -1; 37 | #X obj 149 122 s playsound; 38 | #X obj 119 98 t b b; 39 | #X msg 119 149 acquire_sample; 40 | #X text 36 10 Load a valid soundfile in sound-source \, then hit the 41 | sampling trigger below. The resulting recording is stored as a series 42 | of FFT frames inside residency~ available for arbitrary time-access. 43 | ; 44 | #X text 254 134 first turn off DACs to be safe; 45 | #X obj 274 264 fftease-system; 46 | #N canvas 0 22 642 503 init 0; 47 | #X msg 241 126 verbose 1; 48 | #X msg 140 126 playthrough 1; 49 | #X obj 140 99 loadbang; 50 | #X obj 140 36 loadbang; 51 | #X msg 140 57 1; 52 | #X obj 140 79 s speed-slider; 53 | #X obj 130 194 outlet; 54 | #X connect 0 0 6 0; 55 | #X connect 1 0 6 0; 56 | #X connect 2 0 1 0; 57 | #X connect 2 0 0 0; 58 | #X connect 3 0 4 0; 59 | #X connect 4 0 5 0; 60 | #X restore 233 231 pd init; 61 | #X connect 1 0 2 0; 62 | #X connect 2 0 0 0; 63 | #X connect 3 0 5 0; 64 | #X connect 5 0 6 0; 65 | #X connect 5 1 4 0; 66 | #X connect 6 0 0 0; 67 | #X connect 9 0 0 0; 68 | #X connect 10 0 0 0; 69 | #X restore 245 185 pd messages; 70 | #X floatatom 164 196 5 0 0 0 - speed -; 71 | #N canvas 0 22 514 364 sound-source 0; 72 | #X obj 227 222 r playsound; 73 | #X obj 31 194 soundfiler; 74 | #X obj 31 160 openpanel; 75 | #N canvas 0 22 450 300 graph1 0; 76 | #X array residency-sound1 4e+06 float 2; 77 | #X coords 0 1 4e+06 -1 200 140 1; 78 | #X restore 237 13 graph; 79 | #X msg 31 131 bang; 80 | #X obj 227 284 outlet~; 81 | #X msg 227 244 bang; 82 | #X obj 348 228 spigot; 83 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 84 | 1; 85 | #X text 133 244 then play it; 86 | #X text 304 190 loop if you like; 87 | #X msg 31 177 read -resize \$1 residency-sound1; 88 | #X obj 227 268 tabplay~ residency-sound1; 89 | #X text 63 132 open the sound; 90 | #X connect 0 0 6 0; 91 | #X connect 2 0 11 0; 92 | #X connect 4 0 2 0; 93 | #X connect 6 0 12 0; 94 | #X connect 7 0 6 0; 95 | #X connect 8 0 7 1; 96 | #X connect 11 0 1 0; 97 | #X connect 12 0 5 0; 98 | #X connect 12 1 7 0; 99 | #X restore 124 125 pd sound-source; 100 | #X obj 124 263 dac~; 101 | #X text 161 181 speed; 102 | #X msg 284 257 \; pd dsp \$1; 103 | #X obj 284 231 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 104 | 1; 105 | #X floatatom 204 168 5 0 1 2 position position -; 106 | #X obj 28 47 vsl 15 128 -2 2 0 0 speed speed-slider speed 0 -8 0 8 107 | -253906 -1 -1 6325 1; 108 | #X obj 60 47 vsl 15 128 0 1 0 0 position empty position 0 -8 0 8 -4094 109 | -1 -1 8000 1; 110 | #X text 329 185 <- ask me what I can do; 111 | #X floatatom 245 291 5 0 0 0 - - -; 112 | #X text 245 307 recording sync; 113 | #X text 112 352 residency~ is a spectral sampler. The first argument 114 | specifies how many milliseconds of sampling memory to use. Start conservatively. 115 | If you request more memory than is available \, you may experience 116 | difficulty.; 117 | #X connect 0 0 4 0; 118 | #X connect 0 0 4 1; 119 | #X connect 0 1 12 0; 120 | #X connect 1 0 0 3; 121 | #X connect 2 0 0 1; 122 | #X connect 3 0 0 0; 123 | #X connect 7 0 6 0; 124 | #X connect 8 0 0 2; 125 | -------------------------------------------------------------------------------- /scrape~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 153 350 531 534 10; 2 | #N canvas 0 22 462 312 scrape-block 0; 3 | #X obj 134 142 scrape~ 1000 4000 0.001 0.05 0.1 4 1; 4 | #X obj 126 237 block~ 256; 5 | #X obj 134 188 outlet~; 6 | #X obj 134 74 inlet~; 7 | #X obj 198 84 inlet; 8 | #X obj 239 84 inlet; 9 | #X obj 282 84 inlet; 10 | #X obj 324 85 inlet; 11 | #X obj 366 85 inlet; 12 | #X obj 421 94 inlet; 13 | #X connect 0 0 2 0; 14 | #X connect 3 0 0 0; 15 | #X connect 4 0 0 1; 16 | #X connect 5 0 0 2; 17 | #X connect 6 0 0 3; 18 | #X connect 7 0 0 4; 19 | #X connect 8 0 0 5; 20 | #X connect 9 0 0 0; 21 | #X restore 61 203 pd scrape-block; 22 | #N canvas 0 22 470 320 messages 0; 23 | #X obj 200 244 outlet; 24 | #X obj 200 212 fftease-system; 25 | #X connect 1 0 0 0; 26 | #X restore 161 182 pd messages; 27 | #N canvas 0 22 470 320 playsound 0; 28 | #X obj 31 194 soundfiler; 29 | #X obj 31 160 openpanel; 30 | #N canvas 0 22 450 300 graph1 0; 31 | #X array scrape-sound1 4e+06 float 2; 32 | #X coords 0 1 4e+06 -1 200 140 1; 33 | #X restore 237 13 graph; 34 | #X msg 31 131 bang; 35 | #X obj 227 284 outlet~; 36 | #X msg 227 244 bang; 37 | #X obj 348 228 spigot; 38 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 39 | 1; 40 | #X text 133 244 then play it; 41 | #X text 304 190 loop if you like; 42 | #X text 63 132 open the sound; 43 | #X msg 31 177 read -resize \$1 scrape-sound1; 44 | #X obj 227 268 tabplay~ scrape-sound1; 45 | #X connect 1 0 11 0; 46 | #X connect 3 0 1 0; 47 | #X connect 5 0 12 0; 48 | #X connect 6 0 5 0; 49 | #X connect 7 0 6 1; 50 | #X connect 11 0 0 0; 51 | #X connect 12 0 4 0; 52 | #X connect 12 1 6 0; 53 | #X restore 61 22 pd playsound; 54 | #X floatatom 77 53 5 0 0 1 knee - -; 55 | #X floatatom 94 75 5 0 0 1 cutoff - -; 56 | #X floatatom 111 97 5 0 0 1 threshold1 - -; 57 | #X floatatom 127 115 5 0 0 1 threshold2 - -; 58 | #X floatatom 144 135 5 0 0 1 weak_bin_multiplier - -; 59 | #X obj 61 240 dac~; 60 | #X msg 223 235 \; pd dsp \$1; 61 | #X obj 223 215 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 62 | 1; 63 | #X msg 287 14 1000 4000 0.001 0.05 0.1; 64 | #X obj 287 37 unpack f f f f f; 65 | #X obj 287 -7 loadbang; 66 | #X text 54 284 scrape~ is like drown~ except that it only operates 67 | between the frequencies specified by knee and cutoff to the Nyquist. 68 | Between knee and cutoff is a transition range to gradually increase 69 | the noise reduction. This is good if you just want to scrape some noise 70 | off the upper frequency range without affecting lower parts of the 71 | spectrum (much).; 72 | #X connect 0 0 8 0; 73 | #X connect 0 0 8 1; 74 | #X connect 1 0 0 6; 75 | #X connect 2 0 0 0; 76 | #X connect 3 0 0 1; 77 | #X connect 4 0 0 2; 78 | #X connect 5 0 0 3; 79 | #X connect 6 0 0 4; 80 | #X connect 7 0 0 5; 81 | #X connect 10 0 9 0; 82 | #X connect 11 0 12 0; 83 | #X connect 12 0 3 0; 84 | #X connect 12 1 4 0; 85 | #X connect 12 2 5 0; 86 | #X connect 12 3 6 0; 87 | #X connect 12 4 7 0; 88 | #X connect 13 0 11 0; 89 | -------------------------------------------------------------------------------- /shapee~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 263 477 494 344 10; 2 | #N canvas 657 88 510 360 messages 0; 3 | #X obj 160 251 outlet; 4 | #X obj 160 215 fftease-system; 5 | #X obj 308 200 loadbang; 6 | #X msg 308 235 16; 7 | #X obj 308 264 outlet; 8 | #X connect 1 0 0 0; 9 | #X connect 2 0 3 0; 10 | #X connect 3 0 4 0; 11 | #X restore 248 126 pd messages; 12 | #X obj 148 221 dac~; 13 | #X msg 210 242 \; pd dsp \$1; 14 | #X obj 210 212 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 15 | 1; 16 | #X floatatom 212 175 5 0 1 0 - - -; 17 | #N canvas 638 45 502 352 shapee-block 0; 18 | #X obj 150 160 outlet~; 19 | #X obj 150 66 inlet~; 20 | #X obj 229 70 inlet~; 21 | #X obj 411 78 inlet; 22 | #X obj 150 115 shapee~ 4 1; 23 | #X floatatom 279 149 5 0 0 0 - - -; 24 | #X obj 329 72 inlet; 25 | #X obj 154 253 block~ 512; 26 | #X connect 1 0 4 0; 27 | #X connect 2 0 4 1; 28 | #X connect 3 0 4 0; 29 | #X connect 4 0 0 0; 30 | #X connect 5 0 4 2; 31 | #X connect 6 0 4 2; 32 | #X restore 148 153 pd shapee-block; 33 | #X floatatom 214 98 5 0 0 0 - - -; 34 | #X text 258 99 shaping width; 35 | #N canvas 501 137 751 450 pitch-source 0; 36 | #X obj 31 194 soundfiler; 37 | #X obj 31 160 openpanel; 38 | #N canvas 0 22 450 300 graph1 0; 39 | #X array shapee-sound1 4e+06 float 2; 40 | #X coords 0 1 4e+06 -1 200 140 1; 41 | #X restore 237 13 graph; 42 | #X msg 31 131 bang; 43 | #X obj 227 284 outlet~; 44 | #X msg 227 244 bang; 45 | #X obj 348 228 spigot; 46 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 47 | 1; 48 | #X text 133 244 then play it; 49 | #X text 304 190 loop if you like; 50 | #X msg 31 177 read -resize \$1 shapee-sound1; 51 | #X obj 227 268 tabplay~ shapee-sound1; 52 | #X text 63 132 open the pitched sound; 53 | #X connect 1 0 10 0; 54 | #X connect 3 0 1 0; 55 | #X connect 5 0 11 0; 56 | #X connect 6 0 5 0; 57 | #X connect 7 0 6 1; 58 | #X connect 10 0 0 0; 59 | #X connect 11 0 4 0; 60 | #X connect 11 1 6 0; 61 | #X restore 148 25 pd pitch-source; 62 | #N canvas 0 22 495 403 formant-source 0; 63 | #X obj 31 194 soundfiler; 64 | #X obj 31 160 openpanel; 65 | #N canvas 0 22 450 300 graph1 0; 66 | #X array shapee-sound2 4e+06 float 2; 67 | #X coords 0 1 4e+06 -1 200 140 1; 68 | #X restore 237 13 graph; 69 | #X msg 31 131 bang; 70 | #X obj 227 284 outlet~; 71 | #X msg 227 244 bang; 72 | #X obj 348 228 spigot; 73 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 74 | 1; 75 | #X text 133 244 then play it; 76 | #X text 304 190 loop if you like; 77 | #X obj 227 268 tabplay~ shapee-sound2; 78 | #X msg 31 177 read -resize \$1 shapee-sound2; 79 | #X text 36 337 try a vocal sound or other sound with strong formant 80 | structure; 81 | #X text 63 132 open the formant sound; 82 | #X connect 1 0 11 0; 83 | #X connect 3 0 1 0; 84 | #X connect 5 0 10 0; 85 | #X connect 6 0 5 0; 86 | #X connect 7 0 6 1; 87 | #X connect 10 0 4 0; 88 | #X connect 10 1 6 0; 89 | #X connect 11 0 0 0; 90 | #X restore 181 49 pd formant-source; 91 | #X obj 320 160 hsl 128 15 0 2 0 0 empty empty empty -2 -6 0 8 -195520 92 | -1 -1 5200 1; 93 | #X text 321 146 gain; 94 | #X obj 148 188 *~ 0.1; 95 | #X text 40 287 shapee~ shapes the frequency evolution of one signal 96 | with that of another. The shape width controls the amount of the frequency 97 | shaping effect. Try to avoid sounds containing silence \, which can 98 | cause strong clicks.; 99 | #X connect 0 0 5 3; 100 | #X connect 0 1 6 0; 101 | #X connect 3 0 2 0; 102 | #X connect 4 0 12 1; 103 | #X connect 5 0 12 0; 104 | #X connect 6 0 5 2; 105 | #X connect 8 0 5 0; 106 | #X connect 9 0 5 1; 107 | #X connect 10 0 4 0; 108 | #X connect 12 0 1 0; 109 | #X connect 12 0 1 1; 110 | -------------------------------------------------------------------------------- /swinger~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 263 477 470 320 10; 2 | #N canvas 0 22 478 328 swinger-block 0; 3 | #X obj 150 160 outlet~; 4 | #X obj 150 66 inlet~; 5 | #X obj 229 70 inlet~; 6 | #X obj 293 82 inlet; 7 | #X obj 179 224 block~ 512; 8 | #X obj 150 115 swinger~ 4 1; 9 | #X connect 1 0 5 0; 10 | #X connect 2 0 5 1; 11 | #X connect 3 0 5 0; 12 | #X connect 5 0 0 0; 13 | #X restore 148 121 pd swinger-block; 14 | #N canvas 0 22 478 328 messages 0; 15 | #X obj 160 251 outlet; 16 | #X obj 160 227 fftease-system; 17 | #X connect 1 0 0 0; 18 | #X restore 255 94 pd messages; 19 | #X obj 148 189 dac~; 20 | #X obj 148 156 *~ 1; 21 | #X msg 210 210 \; pd dsp \$1; 22 | #X obj 210 180 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 23 | 1; 24 | #X floatatom 212 143 5 0 0 0 - - -; 25 | #X text 41 255 swinger~ replaces the phases of one signal (left) with 26 | those from another (right). The result often sounds like victory. A 27 | swinging trick: Don't connect any signal to the right inlet and listen 28 | to the result.; 29 | #N canvas 538 45 558 447 sound1 0; 30 | #X obj 31 194 soundfiler; 31 | #X obj 31 160 openpanel; 32 | #N canvas 0 22 450 300 graph1 0; 33 | #X array swinger-sound1 1.5435e+06 float 2; 34 | #X coords 0 1 1.5435e+06 -1 200 140 1; 35 | #X restore 237 13 graph; 36 | #X msg 31 131 bang; 37 | #X obj 227 284 outlet~; 38 | #X msg 227 244 bang; 39 | #X obj 348 228 spigot; 40 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 41 | 1; 42 | #X text 133 244 then play it; 43 | #X text 304 190 loop if you like; 44 | #X msg 31 177 read -resize \$1 swinger-sound1; 45 | #X obj 227 268 tabplay~ swinger-sound1; 46 | #X text 64 132 open the sound; 47 | #X connect 1 0 10 0; 48 | #X connect 3 0 1 0; 49 | #X connect 5 0 11 0; 50 | #X connect 6 0 5 0; 51 | #X connect 7 0 6 1; 52 | #X connect 10 0 0 0; 53 | #X connect 11 0 4 0; 54 | #X connect 11 1 6 0; 55 | #X restore 148 51 pd sound1; 56 | #N canvas 0 22 758 461 sound2 0; 57 | #X obj 161 265 soundfiler; 58 | #X obj 161 231 openpanel; 59 | #N canvas 0 22 450 300 graph1 0; 60 | #X array swinger-sound2 4e+06 float 2; 61 | #X coords 0 1 4e+06 -1 200 140 1; 62 | #X restore 367 84 graph; 63 | #X msg 161 202 bang; 64 | #X obj 357 355 outlet~; 65 | #X msg 357 315 bang; 66 | #X obj 478 299 spigot; 67 | #X obj 515 276 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 68 | 1; 69 | #X text 263 315 then play it; 70 | #X text 434 261 loop if you like; 71 | #X text 193 203 open the sound; 72 | #X obj 357 339 tabplay~ swinger-sound2; 73 | #X msg 161 248 read -resize \$1 swinger-sound2; 74 | #X connect 1 0 12 0; 75 | #X connect 3 0 1 0; 76 | #X connect 5 0 11 0; 77 | #X connect 6 0 5 0; 78 | #X connect 7 0 6 1; 79 | #X connect 11 0 4 0; 80 | #X connect 11 1 6 0; 81 | #X connect 12 0 0 0; 82 | #X restore 201 73 pd sound2; 83 | #X obj 314 128 hsl 128 15 0 1 0 0 empty empty empty -2 -6 0 8 -131603 84 | -1 -1 11500 1; 85 | #X text 334 151 gain; 86 | #X connect 0 0 3 0; 87 | #X connect 1 0 0 2; 88 | #X connect 3 0 2 0; 89 | #X connect 3 0 2 1; 90 | #X connect 5 0 4 0; 91 | #X connect 6 0 3 1; 92 | #X connect 8 0 0 0; 93 | #X connect 9 0 0 1; 94 | #X connect 10 0 6 0; 95 | -------------------------------------------------------------------------------- /swinger~.c: -------------------------------------------------------------------------------- 1 | #include "MSPd.h" 2 | #include "fftease.h" 3 | 4 | #if MSP 5 | void *swinger_class; 6 | #endif 7 | 8 | #if PD 9 | static t_class *swinger_class; 10 | #endif 11 | 12 | #define OBJECT_NAME "swinger~" 13 | 14 | typedef struct _swinger 15 | { 16 | #if MSP 17 | t_pxobject x_obj; 18 | #endif 19 | #if PD 20 | t_object x_obj; 21 | float x_f; 22 | #endif 23 | int R; 24 | int N; 25 | int N2; 26 | int Nw; 27 | int Nw2; 28 | int D; 29 | int i; 30 | int inCount; 31 | int *bitshuffle; 32 | 33 | float *Wanal; 34 | float *Wsyn; 35 | float *inputOne; 36 | float *inputTwo; 37 | float *Hwin; 38 | float *bufferOne; 39 | float *bufferTwo; 40 | float *channelOne; 41 | float *channelTwo; 42 | float *output; 43 | float mult; 44 | float *trigland; 45 | int overlap;//overlap factor 46 | int winfac;// window factor 47 | int vs;//last measurement of vector size 48 | short mute; 49 | 50 | } t_swinger; 51 | 52 | 53 | /* msp function prototypes */ 54 | 55 | void *swinger_new(t_symbol *s, int argc, t_atom *argv); 56 | t_int *swinger_perform(t_int *w); 57 | void swinger_dsp(t_swinger *x, t_signal **sp, short *count); 58 | void swinger_assist(t_swinger *x, void *b, long m, long a, char *s); 59 | void swinger_mute(t_swinger *x, t_floatarg state); 60 | void swinger_init(t_swinger *x, short initialized); 61 | void swinger_dsp_free(t_swinger *x); 62 | void swinger_overlap(t_swinger *x, t_floatarg o); 63 | void swinger_winfac(t_swinger *x, t_floatarg o); 64 | //int fftease_power_of_two(int p); 65 | void swinger_fftinfo(t_swinger *x); 66 | 67 | #if MSP 68 | 69 | void main(void) 70 | { 71 | setup((t_messlist **)&swinger_class, (method) swinger_new, (method)dsp_free, (short)sizeof(t_swinger), 72 | 0L, A_GIMME, 0); 73 | 74 | addmess((method)swinger_dsp, "dsp", A_CANT, 0); 75 | addmess((method)swinger_assist,"assist",A_CANT,0); 76 | addmess((method)swinger_mute,"mute",A_FLOAT,0); 77 | addmess((method)swinger_overlap,"overlap",A_FLOAT,0); 78 | addmess((method)swinger_winfac,"winfac",A_FLOAT,0); 79 | addmess((method)swinger_fftinfo,"fftinfo",0); 80 | dsp_initclass(); 81 | post("%s %s",OBJECT_NAME,FFTEASE_ANNOUNCEMENT); 82 | } 83 | #endif 84 | #if PD 85 | /* Pd Initialization */ 86 | void swinger_tilde_setup(void) 87 | { 88 | swinger_class = class_new(gensym("swinger~"), (t_newmethod)swinger_new, 89 | (t_method)swinger_dsp_free ,sizeof(t_swinger), 0,A_GIMME,0); 90 | CLASS_MAINSIGNALIN(swinger_class, t_swinger, x_f); 91 | class_addmethod(swinger_class, (t_method)swinger_dsp, gensym("dsp"), 0); 92 | class_addmethod(swinger_class, (t_method)swinger_mute, gensym("mute"), A_DEFFLOAT,0); 93 | class_addmethod(swinger_class, (t_method)swinger_overlap, gensym("overlap"), A_DEFFLOAT,0); 94 | class_addmethod(swinger_class, (t_method)swinger_winfac, gensym("winfac"), A_DEFFLOAT,0); 95 | class_addmethod(swinger_class, (t_method)swinger_fftinfo, gensym("fftinfo"),0); 96 | post("%s %s",OBJECT_NAME,FFTEASE_ANNOUNCEMENT); 97 | } 98 | #endif 99 | 100 | /* diagnostic messages for Max */ 101 | void swinger_fftinfo(t_swinger *x) 102 | { 103 | if( ! x->overlap ){ 104 | post("zero overlap!"); 105 | return; 106 | } 107 | post("%s: FFT size %d, hopsize %d, windowsize %d", OBJECT_NAME, x->N, x->N/x->overlap, x->Nw); 108 | } 109 | 110 | 111 | void swinger_mute(t_swinger *x, t_floatarg state) 112 | { 113 | x->mute = state; 114 | } 115 | 116 | void swinger_assist (t_swinger *x, void *b, long msg, long arg, char *dst) 117 | { 118 | 119 | if (msg == 1) { 120 | 121 | switch (arg) { 122 | 123 | case 0: sprintf(dst,"(signal) Signal to be Phase Replaced "); 124 | break; 125 | 126 | case 1: sprintf(dst,"(signal) Signal to Supply Phase Information "); 127 | break; 128 | } 129 | } 130 | 131 | else { 132 | 133 | if (msg == 2) 134 | sprintf(dst,"(signal) Swinger Output"); 135 | 136 | } 137 | } 138 | 139 | 140 | void *swinger_new(t_symbol *s, int argc, t_atom *argv) 141 | { 142 | #if MSP 143 | t_swinger *x = (t_swinger *) newobject(swinger_class); 144 | dsp_setup((t_pxobject *)x,2); 145 | outlet_new((t_pxobject *)x, "signal"); 146 | /* make sure that signal inlets and outlets have their own memory */ 147 | x->x_obj.z_misc |= Z_NO_INPLACE; 148 | #endif 149 | #if PD 150 | t_swinger *x = (t_swinger *)pd_new(swinger_class); 151 | inlet_new(&x->x_obj, &x->x_obj.ob_pd,gensym("signal"), gensym("signal")); 152 | outlet_new(&x->x_obj, gensym("signal")); 153 | #endif 154 | 155 | /* INITIALIZATIONS */ 156 | x->overlap = atom_getfloatarg(0,argc,argv); 157 | x->winfac = atom_getfloatarg(1,argc,argv); 158 | if(!x->winfac) 159 | x->winfac = 1; 160 | if(!x->overlap) 161 | x->overlap = 4; 162 | x->vs = sys_getblksize(); 163 | x->R = sys_getsr(); 164 | swinger_init(x,0); 165 | return (x); 166 | } 167 | 168 | void swinger_overlap(t_swinger *x, t_floatarg o) 169 | { 170 | if(!fftease_power_of_two(o)){ 171 | post("%f is not a power of two",o); 172 | return; 173 | } 174 | x->overlap = o; 175 | swinger_init(x,1); 176 | } 177 | 178 | void swinger_winfac(t_swinger *x, t_floatarg f) 179 | { 180 | if(!fftease_power_of_two(f)){ 181 | error("%f is not a power of two",f); 182 | return; 183 | } 184 | x->winfac = (int)f; 185 | swinger_init(x,1); 186 | } 187 | 188 | void swinger_init(t_swinger *x, short initialized) 189 | { 190 | int i; 191 | x->D = x->vs; 192 | x->N = x->vs * x->overlap; 193 | x->Nw = x->N * x->winfac; 194 | limit_fftsize(&x->N,&x->Nw,OBJECT_NAME); 195 | x->N2 = (x->N)>>1; 196 | x->Nw2 = (x->Nw)>>1; 197 | x->inCount = -(x->Nw); 198 | x->mult = 1. / (float) x->N; 199 | 200 | if(!initialized){ 201 | x->Wanal = (float *) getbytes( MAX_Nw * sizeof(float) ); 202 | x->Wsyn = (float *) getbytes( MAX_Nw * sizeof(float) ); 203 | x->Hwin = (float *) getbytes( MAX_Nw * sizeof(float) ); 204 | x->inputOne = (float *) getbytes( MAX_Nw * sizeof(float) ); 205 | x->inputTwo = (float *) getbytes( MAX_Nw * sizeof(float) ); 206 | x->bufferOne = (float *) getbytes( MAX_N * sizeof(float) ); 207 | x->bufferTwo = (float *) getbytes( MAX_N * sizeof(float) ); 208 | x->channelOne = (float *) getbytes( (MAX_N+2) * sizeof(float) ); 209 | x->channelTwo = (float *) getbytes( (MAX_N+2) * sizeof(float) ); 210 | x->output = (float *) getbytes( MAX_Nw * sizeof(float) ); 211 | x->bitshuffle = (int *) getbytes( MAX_N * 2 * sizeof( int ) ); 212 | x->trigland = (float *) getbytes( MAX_N * 2 * sizeof( float ) ); 213 | } 214 | memset((char *)x->inputOne,0,x->Nw * sizeof(float)); 215 | memset((char *)x->inputTwo,0,x->Nw * sizeof(float)); 216 | memset((char *)x->output,0,x->Nw * sizeof(float)); 217 | 218 | init_rdft(x->N, x->bitshuffle, x->trigland); 219 | makehanning(x->Hwin, x->Wanal, x->Wsyn, x->Nw, x->N, x->D, 1);// wants an ODD window 220 | 221 | } 222 | 223 | t_int *swinger_perform(t_int *w) 224 | { 225 | 226 | int n, 227 | i,j, 228 | inCount, 229 | R, 230 | N, 231 | N2, 232 | D, 233 | Nw, 234 | invert = 1, 235 | even, odd, 236 | *bitshuffle; 237 | 238 | float maxamp, 239 | threshMult = 1., 240 | mult, 241 | a1, b1, 242 | a2, b2, 243 | *inputOne, 244 | *inputTwo, 245 | *bufferOne, 246 | *bufferTwo, 247 | *output, 248 | *Wanal, 249 | *Wsyn, 250 | *channelOne, 251 | *channelTwo, 252 | *trigland; 253 | t_float *inOne, 254 | *inTwo, 255 | *out; 256 | 257 | /* get our inlets and outlets */ 258 | 259 | t_swinger *x = (t_swinger *) (w[1]); 260 | inOne = (t_float *)(w[2]); 261 | inTwo = (t_float *)(w[3]); 262 | 263 | out = (t_float *)(w[4]); 264 | n = (int)(w[5]); 265 | 266 | /* dereference structure */ 267 | 268 | inputOne = x->inputOne; 269 | inputTwo = x->inputTwo; 270 | bufferOne = x->bufferOne; 271 | bufferTwo = x->bufferTwo; 272 | inCount = x->inCount; 273 | R = x->R; 274 | N = x->N; 275 | N2 = x->N2; 276 | D = x->D; 277 | Nw = x->Nw; 278 | Wanal = x->Wanal; 279 | Wsyn = x->Wsyn; 280 | output = x->output; 281 | channelOne = x->channelOne; 282 | channelTwo = x->channelTwo; 283 | bitshuffle = x->bitshuffle; 284 | trigland = x->trigland; 285 | mult = x->mult; 286 | 287 | /* no computation if muted */ 288 | 289 | if(x->mute){ 290 | while(n--) 291 | *out++ = 0.0; 292 | return w+6; 293 | } 294 | 295 | inCount += D; 296 | 297 | for ( j = 0 ; j < Nw - D ; j++ ) { 298 | inputOne[j] = inputOne[j+D]; 299 | inputTwo[j] = inputTwo[j+D]; 300 | } 301 | 302 | for ( j = Nw-D; j < Nw; j++ ) { 303 | inputOne[j] = *inOne++; 304 | inputTwo[j] = *inTwo++; 305 | } 306 | 307 | /* apply hamming window and fold our window buffer into the fft buffer */ 308 | 309 | fold( inputOne, Wanal, Nw, bufferOne, N, inCount ); 310 | fold( inputTwo, Wanal, Nw, bufferTwo, N, inCount ); 311 | 312 | /* do an fft */ 313 | 314 | rdft( N, 1, bufferOne, bitshuffle, trigland ); 315 | rdft( N, 1, bufferTwo, bitshuffle, trigland ); 316 | 317 | /* use redundant coding for speed, even though moving the invert variable 318 | comparison outside of the for loop will give us only a minimal performance 319 | increase (hypot and atan2 are the most intensive portions of this code). 320 | consider adding a table lookup for atan2 instead. 321 | */ 322 | 323 | /* convert to polar coordinates from complex values */ 324 | 325 | for ( i = 0; i <= N2; i++ ) { 326 | odd = ( even = i<<1 ) + 1; 327 | 328 | a1 = ( i == N2 ? *(bufferOne+1) : *(bufferOne+even) ); 329 | b1 = ( i == 0 || i == N2 ? 0. : *(bufferOne+odd) ); 330 | 331 | a2 = ( i == N2 ? *(bufferTwo+1) : *(bufferTwo+even) ); 332 | b2 = ( i == 0 || i == N2 ? 0. : *(bufferTwo+odd) ); 333 | 334 | /* replace signal one's phases with those of signal two */ 335 | 336 | *(channelOne+even) = hypot( a1, b1 ); 337 | *(channelOne+odd) = -atan2( b2, a2 ); 338 | } 339 | 340 | for ( i = 0; i <= N2; i++ ) { 341 | 342 | odd = ( even = i<<1 ) + 1; 343 | 344 | *(bufferOne+even) = *(channelOne+even) * cos( *(channelOne+odd) ); 345 | 346 | if ( i != N2 ) 347 | *(bufferOne+odd) = -(*(channelOne+even)) * sin( *(channelOne+odd) ); 348 | } 349 | 350 | 351 | /* do an inverse fft */ 352 | 353 | rdft( N, -1, bufferOne, bitshuffle, trigland ); 354 | 355 | 356 | 357 | /* dewindow our result */ 358 | 359 | overlapadd( bufferOne, N, Wsyn, output, Nw, inCount); 360 | 361 | /* set our output and adjust our retaining output buffer */ 362 | 363 | for ( j = 0; j < D; j++ ) 364 | *out++ = output[j] * mult; 365 | 366 | for ( j = 0; j < Nw - D; j++ ) 367 | output[j] = output[j+D]; 368 | 369 | for ( j = Nw - D; j < Nw; j++ ) 370 | output[j] = 0.; 371 | 372 | 373 | /* restore state variables */ 374 | 375 | x->inCount = inCount % Nw; 376 | return (w+6); 377 | } 378 | 379 | void swinger_dsp_free( t_swinger *x ) 380 | { 381 | #if MSP 382 | dsp_free((t_pxobject *) x); 383 | #endif 384 | freebytes(x->trigland,0); 385 | freebytes(x->bitshuffle,0); 386 | freebytes(x->Wanal,0); 387 | freebytes(x->Wsyn,0); 388 | freebytes(x->Hwin,0); 389 | freebytes(x->inputOne,0); 390 | freebytes(x->inputTwo,0); 391 | freebytes(x->bufferOne,0); 392 | freebytes(x->bufferTwo,0); 393 | freebytes(x->channelOne,0); 394 | freebytes(x->channelTwo,0); 395 | freebytes(x->output,0); 396 | } 397 | 398 | void swinger_dsp(t_swinger *x, t_signal **sp, short *count) 399 | { 400 | if(x->vs != sp[0]->s_n || x->R != sp[0]->s_sr){ 401 | x->vs = sp[0]->s_n; 402 | x->R = sp[0]->s_sr; 403 | swinger_init(x,1); 404 | } 405 | dsp_add(swinger_perform, 5, x, 406 | sp[0]->s_vec,sp[1]->s_vec,sp[2]->s_vec,sp[0]->s_n); 407 | } 408 | 409 | -------------------------------------------------------------------------------- /taint~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 417 69 677 443 10; 2 | #X obj 167 237 *~ 1; 3 | #X obj 167 289 dac~; 4 | #X floatatom 190 218 5 0 0 0 - centerring-gain -; 5 | #X msg 18 330 \; pd dsp \$1; 6 | #X obj 18 313 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1 7 | ; 8 | #X obj 17 207 hsl 128 15 0 1.5 0 0 centerring-gain empty output_gain 9 | -2 -6 0 8 -79789 -1 -1 447 1; 10 | #N canvas 0 22 523 358 messages 0; 11 | #X obj 132 286 outlet; 12 | #X text 302 155 turn on invert; 13 | #X msg 132 223 pad \$1; 14 | #X floatatom 132 112 5 0 0 0 - - -; 15 | #X text 227 108 is turned on; 16 | #X obj 281 156 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 17 | 1; 18 | #X msg 281 178 invert \$1; 19 | #X text 227 94 pad affects the gain only when "invert"; 20 | #X obj 132 142 ampdb; 21 | #X obj 132 67 loadbang; 22 | #X msg 132 90 -32; 23 | #X floatatom 132 167 5 0 0 0 - - -; 24 | #X obj 257 256 fftease-system; 25 | #X connect 2 0 0 0; 26 | #X connect 3 0 8 0; 27 | #X connect 5 0 6 0; 28 | #X connect 6 0 0 0; 29 | #X connect 8 0 11 0; 30 | #X connect 9 0 10 0; 31 | #X connect 10 0 3 0; 32 | #X connect 11 0 2 0; 33 | #X connect 12 0 0 0; 34 | #X restore 448 167 pd messages; 35 | #X obj 18 240 hsl 128 15 0.15 1 0 0 cod-scaling-exponent empty scaling_exponent 36 | -2 -6 0 8 -88868 -1 -1 800 1; 37 | #X floatatom 236 121 5 0 0 0 - cod-inverse-threshold -; 38 | #X floatatom 236 163 5 0 0 0 - - -; 39 | #N canvas 990 218 508 397 playsound1 0; 40 | #X obj 31 194 soundfiler; 41 | #X obj 31 160 openpanel; 42 | #N canvas 0 22 450 300 graph1 0; 43 | #X array taint-sound1 17642 float 2; 44 | #X coords 0 1 17641 -1 200 140 1; 45 | #X restore 237 13 graph; 46 | #X msg 31 131 bang; 47 | #X obj 227 284 outlet~; 48 | #X msg 227 244 bang; 49 | #X obj 348 228 spigot; 50 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 51 | 1; 52 | #X text 63 132 open the sound; 53 | #X text 133 244 then play it; 54 | #X text 304 190 loop if you like; 55 | #X text 316 205 comment; 56 | #X msg 31 177 read -resize \$1 taint-sound1; 57 | #X obj 227 268 tabplay~ taint-sound1; 58 | #X connect 1 0 12 0; 59 | #X connect 3 0 1 0; 60 | #X connect 5 0 13 0; 61 | #X connect 6 0 5 0; 62 | #X connect 7 0 6 1; 63 | #X connect 12 0 0 0; 64 | #X connect 13 0 4 0; 65 | #X connect 13 1 6 0; 66 | #X restore 167 22 pd playsound1; 67 | #N canvas 990 218 512 401 playsound2 0; 68 | #X obj 31 194 soundfiler; 69 | #X obj 31 160 openpanel; 70 | #X msg 31 131 bang; 71 | #X obj 227 284 outlet~; 72 | #X msg 227 244 bang; 73 | #X obj 348 228 spigot; 74 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 75 | 1; 76 | #X text 63 132 open the sound; 77 | #X text 133 244 then play it; 78 | #X text 304 190 loop if you like; 79 | #X text 316 205 comment; 80 | #N canvas 0 22 450 300 graph2 0; 81 | #X array taint-sound2 133504 float 2; 82 | #X coords 0 1 133503 -1 200 140 1; 83 | #X restore 216 15 graph; 84 | #X msg 31 177 read -resize \$1 taint-sound2; 85 | #X obj 227 268 tabplay~ taint-sound2; 86 | #X connect 1 0 12 0; 87 | #X connect 2 0 1 0; 88 | #X connect 4 0 13 0; 89 | #X connect 5 0 4 0; 90 | #X connect 6 0 5 1; 91 | #X connect 12 0 0 0; 92 | #X connect 13 0 3 0; 93 | #X connect 13 1 5 0; 94 | #X restore 190 43 pd playsound2; 95 | #X floatatom 213 91 5 0.35 2 0 - cod-scaling-exponent -; 96 | #X obj 19 278 hsl 128 15 -90 0 0 0 cod-inverse-threshold empty inverse_threshold 97 | -2 -6 0 8 -88868 -1 -1 6100 1; 98 | #X text 280 136 but only when "invert" is turned on); 99 | #X text 213 73 scaling exponent (lower values increase distortion) 100 | ; 101 | #X text 294 31 <- load and loop two soundfiles to hear effect; 102 | #X msg 14 123 0.1 0.3 -36; 103 | #X obj 14 139 unpack f f f; 104 | #X obj 14 107 loadbang; 105 | #X text 275 120 inverse threshold (lower values intensify effect; 106 | #N canvas 376 316 478 328 taint-block 0; 107 | #X obj 163 185 outlet~; 108 | #X obj 163 38 inlet~; 109 | #X obj 269 107 inlet; 110 | #X obj 201 81 inlet; 111 | #X obj 221 98 inlet; 112 | #X obj 182 65 inlet~; 113 | #X obj 163 128 taint~; 114 | #X obj 233 219 block~ 512; 115 | #X connect 1 0 6 0; 116 | #X connect 2 0 6 0; 117 | #X connect 3 0 6 2; 118 | #X connect 4 0 6 3; 119 | #X connect 5 0 6 1; 120 | #X connect 6 0 0 0; 121 | #X restore 167 183 pd taint-block; 122 | #X obj 236 141 ampdb; 123 | #X text 221 262 taint~ multiplies the spectra of two input signals. 124 | Multiplication of spectra can cause significant drops in the amplitude 125 | of the output signal. The inverse option allows division of the input 126 | spectra. Division requires the use of a threshold to avert division 127 | by zero. Also \, signal division will cause massive amplitude gains. 128 | Be careful of your ears and equipment. Start the amplitude very low 129 | (-100dB) and slowly work up to an acceptable level. A pad is provided 130 | to balance gain between normal and invert options.; 131 | #X connect 0 0 1 0; 132 | #X connect 0 0 1 1; 133 | #X connect 2 0 0 1; 134 | #X connect 4 0 3 0; 135 | #X connect 6 0 21 4; 136 | #X connect 8 0 22 0; 137 | #X connect 9 0 21 3; 138 | #X connect 10 0 21 0; 139 | #X connect 11 0 21 1; 140 | #X connect 12 0 21 2; 141 | #X connect 17 0 18 0; 142 | #X connect 18 0 5 0; 143 | #X connect 18 1 7 0; 144 | #X connect 18 2 13 0; 145 | #X connect 19 0 17 0; 146 | #X connect 21 0 0 0; 147 | #X connect 22 0 9 0; 148 | -------------------------------------------------------------------------------- /thresher~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 112 22 568 570 10; 2 | #N canvas 0 22 474 324 threshblock 0; 3 | #X obj 197 47 inlet; 4 | #X obj 234 68 inlet; 5 | #X obj 161 29 inlet~; 6 | #X obj 161 111 outlet~; 7 | #X obj 339 87 block~ 256; 8 | #X obj 313 47 inlet; 9 | #X obj 161 87 thresher~ 0.1 0.99 4 1; 10 | #X connect 0 0 6 1; 11 | #X connect 1 0 6 2; 12 | #X connect 2 0 6 0; 13 | #X connect 5 0 6 0; 14 | #X connect 6 0 3 0; 15 | #X restore 64 79 pd threshblock; 16 | #X obj 66 223 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1 17 | ; 18 | #X obj 64 21 noise~; 19 | #X obj 249 206 vsl 15 128 1e-05 0.2 0 0 thresh b threshold 0 -8 0 8 20 | -73688 -1 -1 6350 1; 21 | #X obj 300 206 vsl 15 128 0.75 0.999 0 0 damp c damping_factor 0 -8 22 | 0 8 -258462 -1 -1 10201 1; 23 | #X obj 64 187 dac~; 24 | #X obj 64 138 *~ 0.1; 25 | #X msg 66 246 \; pd dsp \$1; 26 | #X obj 205 206 vsl 15 128 0 4 0 0 amp a amp 0 -8 0 8 -150784 -1 -1 27 | 2540 1; 28 | #N canvas 0 22 462 312 init 0; 29 | #X obj 31 29 loadbang; 30 | #X obj 32 71 unpack f f f; 31 | #X obj 33 99 s a; 32 | #X obj 43 108 s b; 33 | #X obj 53 118 s c; 34 | #X msg 31 51 0.8 0.1 0.95; 35 | #X connect 0 0 5 0; 36 | #X connect 1 0 2 0; 37 | #X connect 1 1 3 0; 38 | #X connect 1 2 4 0; 39 | #X connect 5 0 1 0; 40 | #X restore 67 286 pd init; 41 | #X obj 101 116 nbx 5 14 -1e+37 1e+37 0 0 empty amp empty 0 -6 0 10 42 | -262144 -1 -1 0.8 256; 43 | #X obj 126 60 nbx 5 14 -1e+37 1e+37 0 0 empty damp empty 0 -6 0 10 44 | -262144 -1 -1 0.950004 256; 45 | #X obj 95 44 nbx 5 14 -1e+37 1e+37 0 0 empty thresh empty 0 -6 0 10 46 | -262144 -1 -1 0.100005 256; 47 | #X text 113 20 <- something more interesting could go here.; 48 | #X obj 251 63 fftease-system; 49 | #X text 54 359 thresher~ sustains the amplitude and frequency in lower-energy 50 | FFT bins. The extent of this effect is controlled by the threshold 51 | parameter - at 0 all frames pass \, at higher values more frames are 52 | sustained. The damping factor controls the decay time - a value of 53 | 1 gives an infinite freeze. See also the somewhat more interesting 54 | bthresher~.; 55 | #X connect 0 0 6 0; 56 | #X connect 1 0 7 0; 57 | #X connect 2 0 0 0; 58 | #X connect 6 0 5 0; 59 | #X connect 6 0 5 1; 60 | #X connect 10 0 6 1; 61 | #X connect 11 0 0 2; 62 | #X connect 12 0 0 1; 63 | #X connect 14 0 0 3; 64 | -------------------------------------------------------------------------------- /unconvert.c: -------------------------------------------------------------------------------- 1 | #include "fftease.h" 2 | 3 | 4 | 5 | void unconvert( float *C, float *S, int N2, float *lastphase, float fundamental, float factor ) 6 | 7 | { 8 | int i, 9 | real, 10 | imag, 11 | amp, 12 | freq; 13 | float mag, 14 | phase; 15 | double sin(), cos(); 16 | 17 | for ( i = 0; i <= N2; i++ ) { 18 | 19 | imag = freq = ( real = amp = i<<1 ) + 1; 20 | 21 | if ( i == N2 ) 22 | real = 1; 23 | 24 | mag = C[amp]; 25 | lastphase[i] += C[freq] - i*fundamental; 26 | phase = lastphase[i]*factor; 27 | S[real] = mag*cos( phase ); 28 | 29 | if ( i != N2 ) 30 | S[imag] = -mag*sin( phase ); 31 | 32 | } 33 | 34 | } 35 | -------------------------------------------------------------------------------- /vacancy~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 606 96 689 455 10; 2 | #X obj 167 237 *~ 1; 3 | #X obj 167 289 dac~; 4 | #X floatatom 190 218 5 0 0 0 - centerring-gain -; 5 | #X msg 18 330 \; pd dsp \$1; 6 | #X obj 18 313 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1 7 | ; 8 | #X obj 17 207 hsl 128 15 0 1.5 0 0 centerring-gain empty output_gain 9 | -2 -6 0 8 -171124 -1 -1 847 1; 10 | #N canvas 785 535 531 366 messages 0; 11 | #X obj 132 268 outlet; 12 | #X text 291 182 turn on invert; 13 | #X obj 270 183 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 14 | 1; 15 | #X msg 270 205 invert \$1; 16 | #X obj 132 105 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 17 | 1; 18 | #X msg 132 127 swapphase \$1; 19 | #X obj 182 172 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 20 | 1; 21 | #X msg 182 194 rms \$1; 22 | #X obj 311 252 fftease-system; 23 | #X connect 2 0 3 0; 24 | #X connect 3 0 0 0; 25 | #X connect 4 0 5 0; 26 | #X connect 5 0 0 0; 27 | #X connect 6 0 7 0; 28 | #X connect 7 0 0 0; 29 | #X connect 8 0 0 0; 30 | #X restore 448 167 pd messages; 31 | #X floatatom 238 123 5 0 0 0 - vac-compositing-threshold -; 32 | #N canvas 990 218 520 409 playsound1 0; 33 | #X obj 31 194 soundfiler; 34 | #X obj 31 160 openpanel; 35 | #N canvas 0 22 450 300 graph1 0; 36 | #X array vacancy-sound1 1.09357e+06 float 2; 37 | #X coords 0 1 1.09357e+06 -1 200 140 1; 38 | #X restore 237 13 graph; 39 | #X msg 31 131 bang; 40 | #X obj 227 284 outlet~; 41 | #X msg 227 244 bang; 42 | #X obj 348 228 spigot; 43 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 44 | 1; 45 | #X text 63 132 open the sound; 46 | #X text 133 244 then play it; 47 | #X text 304 190 loop if you like; 48 | #X text 316 205 comment; 49 | #X msg 31 177 read -resize \$1 vacancy-sound1; 50 | #X obj 227 268 tabplay~ vacancy-sound1; 51 | #X connect 1 0 12 0; 52 | #X connect 3 0 1 0; 53 | #X connect 5 0 13 0; 54 | #X connect 6 0 5 0; 55 | #X connect 7 0 6 1; 56 | #X connect 12 0 0 0; 57 | #X connect 13 0 4 0; 58 | #X connect 13 1 6 0; 59 | #X restore 167 22 pd playsound1; 60 | #N canvas 990 218 524 413 playsound2 0; 61 | #X obj 31 194 soundfiler; 62 | #X obj 31 160 openpanel; 63 | #X msg 31 131 bang; 64 | #X obj 227 284 outlet~; 65 | #X msg 227 244 bang; 66 | #X obj 348 228 spigot; 67 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 68 | 1; 69 | #X text 63 132 open the sound; 70 | #X text 133 244 then play it; 71 | #X text 304 190 loop if you like; 72 | #X text 316 205 comment; 73 | #N canvas 0 22 450 300 graph2 0; 74 | #X array vacancy-sound2 1.764e+06 float 2; 75 | #X coords 0 1 1.764e+06 -1 200 140 1; 76 | #X restore 216 15 graph; 77 | #X msg 31 177 read -resize \$1 vacancy-sound2; 78 | #X obj 227 268 tabplay~ vacancy-sound2; 79 | #X connect 1 0 12 0; 80 | #X connect 2 0 1 0; 81 | #X connect 4 0 13 0; 82 | #X connect 5 0 4 0; 83 | #X connect 6 0 5 1; 84 | #X connect 12 0 0 0; 85 | #X connect 13 0 3 0; 86 | #X connect 13 1 5 0; 87 | #X restore 202 45 pd playsound2; 88 | #X text 294 31 <- load and loop two soundfiles to hear effect; 89 | #X obj 14 107 loadbang; 90 | #N canvas 376 316 482 332 vacancy-block 0; 91 | #X obj 163 185 outlet~; 92 | #X obj 163 38 inlet~; 93 | #X obj 269 107 inlet; 94 | #X obj 214 87 inlet; 95 | #X obj 188 64 inlet~; 96 | #X obj 233 219 block~ 512; 97 | #X obj 163 128 vacancy~; 98 | #X connect 1 0 6 0; 99 | #X connect 2 0 6 0; 100 | #X connect 3 0 6 2; 101 | #X connect 4 0 6 1; 102 | #X connect 6 0 0 0; 103 | #X restore 167 183 pd vacancy-block; 104 | #X text 280 124 compositing threshold; 105 | #X obj 16 242 hsl 128 15 -90 90 0 0 vac-compositing-threshold empty 106 | compositing_threshold -2 -6 0 8 -171124 -1 -1 3810 1; 107 | #X text 221 262 vacancy~ performs spectral compositing. The threshold 108 | controls the compositing and is specified in dB. Useful values lie 109 | in the range from -90 dB to 90 dB. Threshold inversion is available 110 | via the invert message. The threshold can also track the current RMS 111 | value of of the signal. In RMS tracking mode \, the useful threshold 112 | range will be somewhat different depending upon the character of the 113 | input signals. Phases will be derived from the left input unless phase 114 | swapping is specified. In this case phases will be taken from the right 115 | input signal when the threshold test is true.; 116 | #X msg 14 123 0.1 -36; 117 | #X obj 14 139 unpack f f; 118 | #X connect 0 0 1 0; 119 | #X connect 0 0 1 1; 120 | #X connect 2 0 0 1; 121 | #X connect 4 0 3 0; 122 | #X connect 6 0 12 3; 123 | #X connect 7 0 12 2; 124 | #X connect 8 0 12 0; 125 | #X connect 9 0 12 1; 126 | #X connect 11 0 16 0; 127 | #X connect 12 0 0 0; 128 | #X connect 16 0 17 0; 129 | #X connect 17 0 5 0; 130 | #X connect 17 1 14 0; 131 | -------------------------------------------------------------------------------- /xsyn~-help.pd: -------------------------------------------------------------------------------- 1 | #N canvas 236 558 603 436 10; 2 | #X obj 25 136 dac~; 3 | #N canvas 0 22 470 320 rich-harmonic-source 0; 4 | #X obj 127 232 outlet~; 5 | #X obj 127 125 phasor~ 100; 6 | #X obj 212 126 phasor~ 125; 7 | #X obj 296 125 phasor~ 150; 8 | #X obj 127 183 *~ 0.3; 9 | #X floatatom 127 67 5 0 0 0 - - -; 10 | #X obj 212 99 * 1.25; 11 | #X obj 296 100 * 1.5; 12 | #X obj 130 34 hsl 128 15 60 600 0 0 empty empty empty -2 -6 0 8 -154413 13 | -1 -1 6350 1; 14 | #X msg 127 11 330; 15 | #X obj 127 -18 loadbang; 16 | #X connect 1 0 4 0; 17 | #X connect 2 0 4 0; 18 | #X connect 3 0 4 0; 19 | #X connect 4 0 0 0; 20 | #X connect 5 0 6 0; 21 | #X connect 5 0 1 0; 22 | #X connect 5 0 7 0; 23 | #X connect 6 0 2 0; 24 | #X connect 7 0 3 0; 25 | #X connect 8 0 5 0; 26 | #X connect 9 0 8 0; 27 | #X connect 10 0 9 0; 28 | #X restore 25 23 pd rich-harmonic-source; 29 | #N canvas 473 320 623 326 vocal-source 0; 30 | #X obj 31 194 soundfiler; 31 | #X obj 31 160 openpanel; 32 | #N canvas 0 22 450 300 graph1 0; 33 | #X array xsyn-sound1 4e+06 float 2; 34 | #X coords 0 1 4e+06 -1 200 140 1; 35 | #X restore 237 13 graph; 36 | #X msg 31 131 bang; 37 | #X obj 227 284 outlet~; 38 | #X msg 227 244 bang; 39 | #X obj 348 228 spigot; 40 | #X obj 385 205 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 1 41 | 1; 42 | #X text 63 132 open the sound; 43 | #X text 133 244 then play it; 44 | #X text 304 190 loop if you like; 45 | #X obj 227 268 tabplay~ xsyn-sound1; 46 | #X msg 31 177 read -resize \$1 xsyn-sound1; 47 | #X connect 1 0 12 0; 48 | #X connect 3 0 1 0; 49 | #X connect 5 0 11 0; 50 | #X connect 6 0 5 0; 51 | #X connect 7 0 6 1; 52 | #X connect 11 0 4 0; 53 | #X connect 11 1 6 0; 54 | #X connect 12 0 0 0; 55 | #X restore 68 46 pd vocal-source; 56 | #X msg 34 242 \; pd dsp \$1; 57 | #X obj 34 221 tgl 15 0 empty empty empty 0 -6 0 8 -262144 -1 -1 0 1 58 | ; 59 | #N canvas 172 351 466 316 xsyn-block 0; 60 | #X obj 161 178 outlet~; 61 | #X obj 161 49 inlet~; 62 | #X obj 283 102 inlet; 63 | #X obj 161 213 block~ 256; 64 | #X obj 205 72 inlet~; 65 | #X obj 161 132 xsyn~ 4; 66 | #X connect 1 0 5 0; 67 | #X connect 2 0 5 0; 68 | #X connect 4 0 5 1; 69 | #X connect 5 0 0 0; 70 | #X restore 25 88 pd xsyn-block; 71 | #X obj 111 68 fftease-system; 72 | #X text 34 284 xsyn~ filters the first input with the second input 73 | \, creating a spectral cross synthesis effect.; 74 | #X connect 1 0 5 0; 75 | #X connect 2 0 5 1; 76 | #X connect 4 0 3 0; 77 | #X connect 5 0 0 0; 78 | #X connect 5 0 0 1; 79 | #X connect 6 0 5 2; 80 | -------------------------------------------------------------------------------- /xsyn~.c: -------------------------------------------------------------------------------- 1 | #include "MSPd.h" 2 | #include "fftease.h" 3 | 4 | #if MSP 5 | void *xsyn_class; 6 | #endif 7 | 8 | #if PD 9 | static t_class *xsyn_class; 10 | #endif 11 | 12 | #define OBJECT_NAME "xsyn~" 13 | 14 | typedef struct _xsyn 15 | { 16 | #if MSP 17 | t_pxobject x_obj; 18 | #endif 19 | #if PD 20 | t_object x_obj; 21 | float x_f; 22 | #endif 23 | 24 | int R; 25 | int N; 26 | int N2; 27 | int Nw; 28 | int Nw2; 29 | int D; 30 | int i; 31 | float *input1; 32 | float *buffer1; 33 | float *channel1; 34 | 35 | 36 | float *input2; 37 | float *buffer2; 38 | float *channel2; 39 | // 40 | int inCount; 41 | float *Hwin; 42 | float *Wanal; 43 | float *Wsyn; 44 | float *output; 45 | /* xsyn vars */ 46 | 47 | float *c_lastphase_in1; 48 | float *c_lastphase_in2; 49 | float *c_lastphase_out; 50 | float c_fundamental; 51 | float c_factor_in; 52 | float c_factor_out; 53 | 54 | // float *filter ; 55 | // for fast fft 56 | float mult; 57 | float *trigland; 58 | int *bitshuffle; 59 | int overlap;//overlap factor 60 | int winfac;//window factor 61 | int vs;//vector size 62 | short mute;//flag 63 | } t_xsyn; 64 | 65 | void *xsyn_new(t_symbol *s, int argc, t_atom *argv); 66 | t_int *offset_perform(t_int *w); 67 | t_int *xsyn_perform(t_int *w); 68 | void xsyn_dsp(t_xsyn *x, t_signal **sp, short *count); 69 | void xsyn_assist(t_xsyn *x, void *b, long m, long a, char *s); 70 | void xsyn_dsp_free( t_xsyn *x ); 71 | void xsyn_init(t_xsyn *x, short initialized); 72 | void xsyn_mute(t_xsyn *x, t_floatarg toggle); 73 | void xsyn_fftinfo(t_xsyn *x); 74 | void xsyn_overlap(t_xsyn *x, t_floatarg f); 75 | void xsyn_winfac(t_xsyn *x, t_floatarg f); 76 | 77 | void xsyn_dsp_free( t_xsyn *x ) 78 | { 79 | #if MSP 80 | dsp_free( (t_pxobject *) x); 81 | #endif 82 | freebytes(x->c_lastphase_in1,0); 83 | freebytes(x->c_lastphase_in2,0); 84 | freebytes(x->c_lastphase_out,0); 85 | freebytes(x->trigland,0); 86 | freebytes(x->bitshuffle,0); 87 | freebytes(x->Wanal,0); 88 | freebytes(x->Wsyn,0); 89 | freebytes(x->Hwin,0); 90 | freebytes(x->input1,0); 91 | freebytes(x->buffer1,0); 92 | freebytes(x->channel1,0); 93 | freebytes(x->input2,0); 94 | freebytes(x->buffer2,0); 95 | freebytes(x->channel2,0); 96 | freebytes(x->output,0); 97 | } 98 | 99 | #if MSP 100 | void main(void) 101 | { 102 | setup((t_messlist **)&xsyn_class, (method) xsyn_new, (method)xsyn_dsp_free, 103 | (short)sizeof(t_xsyn), 0, A_GIMME, 0); 104 | addmess((method)xsyn_dsp, "dsp", A_CANT, 0); 105 | addmess((method)xsyn_assist,"assist",A_CANT,0); 106 | addmess((method)xsyn_mute,"mute",A_FLOAT,0); 107 | addmess((method)xsyn_overlap,"overlap",A_FLOAT,0); 108 | addmess((method)xsyn_winfac,"winfac",A_DEFFLOAT,0); 109 | addmess((method)xsyn_fftinfo,"fftinfo",0); 110 | dsp_initclass(); 111 | post("%s %s",OBJECT_NAME,FFTEASE_ANNOUNCEMENT); 112 | } 113 | #endif 114 | 115 | #if PD 116 | void xsyn_tilde_setup(void) 117 | { 118 | xsyn_class = class_new(gensym("xsyn~"), (t_newmethod)xsyn_new, 119 | (t_method)xsyn_dsp_free ,sizeof(t_xsyn), 0,A_GIMME,0); 120 | CLASS_MAINSIGNALIN(xsyn_class, t_xsyn, x_f); 121 | class_addmethod(xsyn_class, (t_method)xsyn_dsp, gensym("dsp"), 0); 122 | class_addmethod(xsyn_class, (t_method)xsyn_assist, gensym("assist"), 0); 123 | class_addmethod(xsyn_class, (t_method)xsyn_mute, gensym("mute"), A_DEFFLOAT,0); 124 | class_addmethod(xsyn_class, (t_method)xsyn_overlap, gensym("overlap"), A_DEFFLOAT,0); 125 | class_addmethod(xsyn_class,(t_method)xsyn_winfac,gensym("winfac"),A_FLOAT,0); 126 | class_addmethod(xsyn_class,(t_method)xsyn_fftinfo,gensym("fftinfo"),0); 127 | post("%s %s",OBJECT_NAME,FFTEASE_ANNOUNCEMENT); 128 | } 129 | #endif 130 | 131 | void xsyn_mute(t_xsyn *x, t_floatarg toggle) 132 | { 133 | x->mute = (short)toggle; 134 | } 135 | 136 | void xsyn_overlap(t_xsyn *x, t_floatarg f) 137 | { 138 | int i = (int) f; 139 | if(!fftease_power_of_two(i)){ 140 | error("%f is not a power of two",f); 141 | return; 142 | } 143 | x->overlap = i; 144 | xsyn_init(x,1); 145 | } 146 | 147 | void xsyn_winfac(t_xsyn *x, t_floatarg f) 148 | { 149 | int i = (int)f; 150 | 151 | if(!fftease_power_of_two(i)){ 152 | error("%f is not a power of two",f); 153 | return; 154 | } 155 | x->winfac = i; 156 | xsyn_init(x,2); 157 | } 158 | 159 | void xsyn_fftinfo(t_xsyn *x) 160 | { 161 | if( ! x->overlap ){ 162 | post("zero overlap!"); 163 | return; 164 | } 165 | post("%s: FFT size %d, hopsize %d, windowsize %d", OBJECT_NAME, x->N, x->N/x->overlap, x->Nw); 166 | } 167 | 168 | 169 | void xsyn_assist (t_xsyn *x, void *b, long msg, long arg, char *dst) 170 | { 171 | if (msg==1) { 172 | switch (arg) { 173 | case 0: 174 | sprintf(dst,"(signal) Input 1 "); 175 | break; 176 | case 1: 177 | sprintf(dst,"(signal) Input 2 "); 178 | break; 179 | } 180 | } else if (msg==2) { 181 | sprintf(dst,"(signal) Output "); 182 | } 183 | } 184 | 185 | void *xsyn_new(t_symbol *s, int argc, t_atom *argv) 186 | { 187 | #if MSP 188 | t_xsyn *x = (t_xsyn *)newobject(xsyn_class); 189 | dsp_setup((t_pxobject *)x,2); 190 | outlet_new((t_pxobject *)x, "signal"); 191 | #endif 192 | #if PD 193 | t_xsyn *x = (t_xsyn *)pd_new(xsyn_class); 194 | inlet_new(&x->x_obj, &x->x_obj.ob_pd,gensym("signal"), gensym("signal")); 195 | outlet_new(&x->x_obj, gensym("signal")); 196 | #endif 197 | x->overlap = atom_getfloatarg(0,argc,argv); 198 | x->winfac = atom_getfloatarg(1,argc,argv); 199 | if(!fftease_power_of_two(x->overlap)) 200 | x->overlap = 4; 201 | if(!fftease_power_of_two(x->winfac)) 202 | x->winfac = 1; 203 | 204 | x->R = sys_getsr(); 205 | x->vs = sys_getblksize(); 206 | 207 | xsyn_init(x,0); 208 | return (x); 209 | } 210 | 211 | void xsyn_init(t_xsyn *x, short initialized) 212 | { 213 | 214 | 215 | x->D = x->vs; 216 | x->N = x->D * x->overlap; 217 | x->Nw = x->N * x->winfac; 218 | limit_fftsize(&x->N,&x->Nw,OBJECT_NAME); 219 | x->N2 = (x->N)>>1; 220 | x->Nw2 = (x->Nw)>>1; 221 | x->inCount = -(x->Nw); 222 | x->mult = 1. / (float) x->N; 223 | 224 | x->c_fundamental = (float) x->R/( (x->N2)<<1 ); 225 | x->c_factor_in = (float) x->R/((float)x->D * TWOPI); 226 | x->c_factor_out = TWOPI * (float) x->D / (float) x->R; 227 | if(!initialized){ 228 | x->mute = 0; 229 | x->Wanal = (float *) getbytes( MAX_Nw * sizeof(float) ); 230 | x->Wsyn = (float *) getbytes( MAX_Nw * sizeof(float) ); 231 | x->Hwin = (float *) getbytes( MAX_Nw * sizeof(float) ); 232 | x->input1 = (float *) getbytes(MAX_Nw * sizeof(float)); 233 | x->buffer1 = (float *) getbytes(MAX_N * sizeof(float)); 234 | x->channel1 = (float *) getbytes((MAX_N+2) * sizeof(float)); 235 | x->input2 = (float *) getbytes(MAX_Nw * sizeof(float)); 236 | x->buffer2 = (float *) getbytes(MAX_N * sizeof(float)); 237 | x->channel2 = (float *) getbytes((MAX_N+2) * sizeof(float)); 238 | x->output = (float *) getbytes(MAX_Nw * sizeof(float)); 239 | x->bitshuffle = (int *) getbytes(MAX_N * 2 * sizeof(int)); 240 | x->trigland = (float *) getbytes(MAX_N * 2 * sizeof(float)); 241 | x->c_lastphase_in1 = (float *) getbytes((MAX_N2+1) * sizeof(float)); 242 | x->c_lastphase_in2 = (float *) getbytes((MAX_N2+1) * sizeof(float)); 243 | x->c_lastphase_out = (float *) getbytes((MAX_N2+1) * sizeof(float)); 244 | } 245 | memset((char *)x->input1,0,x->Nw * sizeof(float)); 246 | memset((char *)x->input2,0,x->Nw * sizeof(float)); 247 | memset((char *)x->output,0,x->Nw * sizeof(float)); 248 | memset((char *)x->c_lastphase_in1,0,(x->N2+1) * sizeof(float)); 249 | memset((char *)x->c_lastphase_in2,0,(x->N2+1) * sizeof(float)); 250 | memset((char *)x->c_lastphase_out,0,(x->N2+1) * sizeof(float)); 251 | 252 | init_rdft( x->N, x->bitshuffle, x->trigland); 253 | makehanning( x->Hwin, x->Wanal, x->Wsyn, x->Nw, x->N, x->D, 0); 254 | } 255 | 256 | t_int *xsyn_perform(t_int *w) 257 | { 258 | t_float *in1,*out, *in2; 259 | 260 | float sample, outsamp ; 261 | 262 | float *input1, *input2, 263 | *output, 264 | *buffer1, *buffer2, 265 | *Wanal, 266 | *Wsyn, 267 | *channel1, *channel2; 268 | 269 | int n, 270 | i,j, 271 | inCount, 272 | R, 273 | N, 274 | N2, 275 | D, 276 | Nw; 277 | float maxamp ; 278 | int *bitshuffle; 279 | float *trigland; 280 | float mult; 281 | float a1, a2, b1, b2; 282 | int even, odd; 283 | 284 | 285 | 286 | t_xsyn *x = (t_xsyn *) (w[1]); 287 | in1 = (t_float *)(w[2]); 288 | in2 = (t_float *)(w[3]); 289 | out = (t_float *)(w[4]); 290 | n = (int)(w[5]); 291 | 292 | /* dereference struncture */ 293 | input1 = x->input1; 294 | input2 = x->input2; 295 | buffer1 = x->buffer1; 296 | buffer2 = x->buffer2; 297 | inCount = x->inCount; 298 | R = x->R; 299 | N = x->N; 300 | N2 = x->N2; 301 | D = x->D; 302 | Nw = x->Nw; 303 | Wanal = x->Wanal; 304 | Wsyn = x->Wsyn; 305 | output = x->output; 306 | buffer1 = x->buffer1; 307 | buffer2 = x->buffer2; 308 | channel1 = x->channel1; 309 | channel2 = x->channel2; 310 | bitshuffle = x->bitshuffle; 311 | trigland = x->trigland; 312 | mult = x->mult; 313 | 314 | if(x->mute){ 315 | while(n--){ 316 | *out++ = 0.0; 317 | } 318 | return (w+6); 319 | } 320 | x->inCount += D; 321 | 322 | for ( j = 0 ; j < Nw - D ; j++ ){ 323 | input1[j] = input1[j+D]; 324 | input2[j] = input2[j+D]; 325 | } 326 | for ( j = Nw - D; j < Nw; j++ ) { 327 | input1[j] = *in1++; 328 | input2[j] = *in2++; 329 | } 330 | 331 | fold( input1, Wanal, Nw, buffer1, N, inCount ); 332 | fold( input2, Wanal, Nw, buffer2, N, inCount ); 333 | rdft( N, 1, buffer1, bitshuffle, trigland ); 334 | rdft( N, 1, buffer2, bitshuffle, trigland ); 335 | leanconvert( buffer1, channel1, N2 ); 336 | leanconvert( buffer2, channel2, N2 ); 337 | maxamp = 0 ; 338 | for( i = 0; i < N; i+= 2 ) { 339 | if( channel2[i] > maxamp ) { 340 | maxamp = channel2[i]; 341 | } 342 | } 343 | if( maxamp == 0.0 ) 344 | maxamp = 1.0 ; 345 | for( i = 0; i < N; i+= 2 ) { 346 | channel1[i] *= (channel2[i] / maxamp ); 347 | } 348 | 349 | leanunconvert( channel1, buffer1, N2 ); 350 | 351 | rdft( N, -1, buffer1, bitshuffle, trigland ); 352 | 353 | overlapadd( buffer1, N, Wsyn, output, Nw, inCount); 354 | 355 | for ( j = 0; j < D; j++ ) 356 | *out++ = output[j] * mult; 357 | 358 | for ( j = 0; j < Nw - D; j++ ) 359 | output[j] = output[j+D]; 360 | 361 | for ( j = Nw - D; j < Nw; j++ ) 362 | output[j] = 0.; 363 | 364 | 365 | 366 | /* restore state variables */ 367 | x->inCount = inCount; 368 | return (w+6); 369 | } 370 | 371 | void xsyn_dsp(t_xsyn *x, t_signal **sp, short *count) 372 | { 373 | if(x->vs != sp[0]->s_n || x->R != sp[0]->s_sr ){ 374 | x->vs = sp[0]->s_n; 375 | x->R = sp[0]->s_sr; 376 | xsyn_init(x,1); 377 | } 378 | 379 | dsp_add(xsyn_perform, 5, x, sp[0]->s_vec, sp[1]->s_vec, sp[2]->s_vec, sp[0]->s_n); 380 | } 381 | 382 | --------------------------------------------------------------------------------