Main Page | Namespaces | Classes | Compounds | Files | Compound Members | Related sndutils.cpp00001 // 00002 // SYNTOPIA. See http://Syntopia.sourceforge.net for details and documentation. 00003 // 00004 // Author of this file: Mikael Hvidtfeldt Christensen (mikaelc@users.sourceforge.net) 00005 // 00006 00007 #include <iostream> 00008 #include "sndutils.h" 00009 #include <math.h> 00010 #include <complex> 00011 #include "Utils.h" 00012 #include "fft.h" 00013 00014 namespace SynthCore { 00015 00016 #define IS_DENORMAL(f) (((*(unsigned int *)&(f))&0x7f800000) == 0) 00017 00018 DelayLine::DelayLine(int Length) { 00019 bufferLength = Length; 00020 00021 bufferStart = new float[bufferLength]; 00022 bufferEnd = bufferStart + bufferLength; 00023 for(int i=0; i<bufferLength; i++) { bufferStart[i] = 0.0f; } 00024 readPtr = bufferStart; 00025 } 00026 00027 DelayLine::~DelayLine() { 00028 delete[] bufferStart; 00029 } 00030 00031 float DelayLine::read(float input) { 00032 00033 // catch denormal numbers. 00034 if (IS_DENORMAL(input)) {input = 0;} 00035 00036 output1 = *readPtr; 00037 *readPtr = input; 00038 00039 if (((*readPtr) < 0.0001) && ((*readPtr) > -0.0001)) {*readPtr = 0.0f;} 00040 00041 if(++readPtr >= bufferEnd) readPtr = bufferStart; 00042 00043 return output1; 00044 } 00045 00046 float DelayLine::readNBack(int N) { 00047 00048 temp = readPtr; 00049 temp -= N; // step back N steps; 00050 00051 if(temp < bufferStart) temp += bufferLength; 00052 00053 return *temp; 00054 } 00055 00056 00057 float DelayLine::readNForward(int N) { 00058 00059 temp = readPtr; 00060 temp += N; // step forward N steps; 00061 00062 if(temp >= bufferEnd) temp -= bufferLength; 00063 00064 return *temp; 00065 } 00066 00067 00068 // The BiFilter class coefficient formulas are based on the following reference: 00069 // 00070 // ------------------------------------------------------------------------------------------------------------- 00071 // Cookbook formulae for audio EQ biquad filter coefficients 00072 // by Robert Bristow-Johnson <robert@wavemechanics.com> 00073 // ------------------------------------------------------------------------------------------------------------- 00074 // http://www.harmony-central.com/Computer/Programming/Audio-EQ-Cookbook.txt 00075 // 00076 // 00077 00078 BiFilter::BiFilter() { 00079 // init vars 00080 a1 = 0.0f; a2 = 0.0f; a0 = 1.0f; 00081 b1 = 0.0f; b2 = 0.0f; b0 = 0.0f; 00082 x1 = 0.0f; x2 = 0.0f; x0 = 0.0f; 00083 y1 = 0.0f; y2 = 0.0f; y0 = 0.0f; 00084 lowpassFreqAndQ(1222.0f, 0.15f); 00085 } 00086 00087 00088 00089 00090 float BiFilter::read(float input) { 00091 x2 = x1; x1 = x0; 00092 00093 00094 y2 = y1; y1 = y0; 00095 00096 x0 = input; 00097 y0 = (b0)*x0 + (b1)*x1 + (b2)*x2 - (a1)*y1 - (a2)*y2; 00098 if (IS_DENORMAL(y0)) {y0=0.0f;} 00099 return y0; 00100 } 00101 00102 void BiFilter::getPolesAndZeroes(float &p1r,float &p1i,float &p2r,float &p2i,float &z1r,float &z1i,float &z2r,float &z2i) 00103 { 00104 // 2. degrees pol. -b+-sqrt(D) / 2a 00105 // D=b*b-4a*c 00106 00107 float a,b,c,D; 00108 00109 // First find roots of pole polynomium. 00110 // 00111 00112 a = 1.0f; // we have normalized, so that a0 is 1.0 00113 b = a1; 00114 c = a2; 00115 00116 D=b*b-4*a*c; 00117 if (D < 0) { 00118 p1r=-b/(2*a); 00119 p1i=sqrt(-D)/(2*a); 00120 p2r=p1r; 00121 p2i=-p1i; 00122 } else { 00123 p1r=(-b+sqrt(D))/(2*a); 00124 p2r=(-b-sqrt(D))/(2*a); 00125 p1i=0; 00126 p2i=0; 00127 } 00128 00129 a = b0; // we have normalized, so that a0 is 1.0 00130 b = b1; 00131 c = b2; 00132 00133 if (a==0) { a= 1.0f; } 00134 00135 // find roots of zeroes polynomium 00136 00137 D=b*b-4*a*c; 00138 if (D < 0) { 00139 z1r=-b/(2*a); 00140 z1i=sqrt(-D)/(2*a); 00141 z2r=z1r; 00142 z2i=-z1i; 00143 } else { 00144 z1r=(-b+sqrt(D))/(2*a); 00145 z2r=(-b-sqrt(D))/(2*a); 00146 z1i=0; 00147 z2i=0; 00148 } 00149 00150 } 00151 00152 float BiFilter::getFreqResponse(float wT) { 00153 // should be changed to FFT method. 00154 std::complex<float> temp; 00155 std::complex<float> temp2; 00156 00157 00158 temp = b0 * std::complex<float>(1.0,0); 00159 temp += b1 * std::complex<float>(cos(-wT),sin(-wT)); 00160 temp += b2 * std::complex<float>(cos(-2*wT),sin(-2*wT)); 00161 00162 temp2 = std::complex<float>(1.0,0)+(a1) * std::complex<float>(cos(-wT),sin(-wT)); 00163 temp2 += a2 * std::complex<float>(cos(-2*wT),sin(-2*wT)); 00164 00165 temp2 = temp/temp2; 00166 00167 return std::abs(temp2); 00168 } 00169 00170 float BiFilter::getPhaseResponse(float wT) { 00171 // should be changed to FFT method. 00172 std::complex<float> temp; 00173 std::complex<float> temp2; 00174 00175 00176 temp = b0 * std::complex<float>(1.0,0); 00177 temp += b1 * std::complex<float>(cos(-wT),sin(-wT)); 00178 temp += b2 * std::complex<float>(cos(-2*wT),sin(-2*wT)); 00179 00180 temp2 = std::complex<float>(1.0,0)+(a1) * std::complex<float>(cos(-wT),sin(-wT)); 00181 temp2 += a2 * std::complex<float>(cos(-2*wT),sin(-2*wT)); 00182 00183 temp2 = temp/temp2; 00184 00185 return std::arg(temp2); 00186 } 00187 00188 float BiFilter::getFreqResponse2(float wT) { 00189 // should be changed to FFT method. 00190 float c=0.0f; 00191 float temp; 00192 float max; 00193 for (int t = 0; t<120; t++) 00194 { 00195 c++; 00196 read(cos(wT*c)); 00197 } 00198 temp = 0; max = 0; 00199 for (int y = 0; y<2020; y++) 00200 { 00201 c++; 00202 temp = read(cos(wT*c)); 00203 if (temp>max) {max=temp;} 00204 if (-temp>max) {max=-temp;} 00205 } 00206 return max; 00207 } 00208 00209 Sample * BiFilter::getFreqResponseSample(int resolution) 00210 { 00211 Sample * mySample = new Sample(resolution); 00212 float f; 00213 for (int i = 0; i< resolution; i++) 00214 { 00215 f = (getFreqResponse(3.1415927*(float)i/(float) resolution)); 00216 if (f<0.0f) {f = 0.0000001f;} 00217 mySample->samples[i] = 20.0f*log(f); 00218 } 00219 return mySample; 00220 } 00221 00222 Sample * BiFilter::getPhaseResponseSample(int resolution) 00223 { 00224 Sample * mySample = new Sample(resolution); 00225 for (int i = 0; i< resolution; i++) 00226 { 00227 mySample->samples[i] = (getPhaseResponse(3.1415927*(float)i/(float) resolution)); 00228 } 00229 return mySample; 00230 } 00231 00232 00233 void BiFilter::lowpassFreqAndQ(float freq, float Q) 00234 { 00235 /* 00236 // ------------------------------------------------------------------------------------- 00237 A = sqrt[ 10^(dBgain/20) ] 00238 = 10^(dBgain/40) (for peaking and shelving EQ filters only) 00239 00240 omega = 2*pi*frequency/sampleRate 00241 00242 sin = sin(omega) 00243 cos = cos(omega) 00244 00245 00246 alpha = sin/(2*Q) (if Q is specified) 00247 = sin*sinh[ ln(2)/2 * bandwidth * omega/sin ] (if bandwidth is specified) 00248 00249 The relationship between bandwidth and Q is 00250 1/Q = 2*sinh[ln(2)/2*bandwidth*omega/sin] (digital filter using BLT) 00251 or 1/Q = 2*sinh[ln(2)/2*bandwidth]) (analog filter prototype) 00252 00253 00254 beta = sqrt(A)/Q (for shelving EQ filters only) 00255 = sqrt(A)*sqrt[ (A + 1/A)*(1/S - 1) + 2 ] (if shelf slope is specified) 00256 = sqrt[ (A^2 + 1)/S - (A-1)^2 ] 00257 00258 The relationship between shelf slope and Q is 00259 1/Q = sqrt[(A + 1/A)*(1/S - 1) + 2] 00260 // ----------------------------------------------------------------------------------- 00261 */ 00262 00263 00264 omega = (float) 2.0f*3.1415f*freq/48000.0f; 00265 cs = (float) cos(omega); 00266 alpha = (float) (sin(omega)/(2*(Q*5.0f))); 00267 00268 a0 = (1.0f + alpha); 00269 00270 b0 = (1.0f - cs)/(2.0f*a0); 00271 b1 = (1.0f - cs)/a0; 00272 b2= b0; 00273 00274 a1 = (-2.0f*cs)/a0; 00275 a2 = (1.0f - alpha)/a0; 00276 } 00277 00278 00279 void BiFilter::bypassFreqAndQ(float freq, float Q) 00280 { 00281 // Bypass filter. 00282 b0 = 1.0f; 00283 a0 = b1 = b2 = a1 = a2 = 0.0f; 00284 } 00285 00286 00287 void BiFilter::allpassFreqAndQ(float freq, float Q) 00288 { 00289 /* 00290 APF: H(s) = (s^2 - s/Q + 1) / (s^2 + s/Q + 1) 00291 00292 b0 = 1 - alpha 00293 b1 = -2*cos 00294 b2 = 1 + alpha 00295 a0 = 1 + alpha 00296 a1 = -2*cos 00297 a2 = 1 - alpha 00298 */ 00299 00300 omega = (float) 2.0f*3.1415f*freq/48000.0f; 00301 cs = (float) cos(omega); 00302 alpha = (float) (sin(omega)/(2*(Q*5.0f))); 00303 00304 a0 = (1.0f + alpha); 00305 a0INV = 1.0f/a0; 00306 00307 b0 = (1.0f - alpha)*a0INV; 00308 b1 = (- 2.0f*cs)*a0INV; 00309 b2= 1; 00310 a1 = b1; 00311 a2 = b0; 00312 } 00313 00314 void BiFilter::clone(BiFilter * from) 00315 { 00316 a0 = from->a0; 00317 a1 = from->a1; 00318 a2 = from->a2; 00319 b0 = from->b0; 00320 b1 = from->b1; 00321 b2 = from->b2; 00322 } 00323 00324 00325 00326 void BiFilter::highpassFreqAndQ(float freq, float Q) 00327 { 00328 /* 00329 HPF: H(s) = s^2 / (s^2 + s/Q + 1) 00330 00331 b0 = (1 + cos)/2 00332 b1 = -(1 + cos) 00333 b2 = (1 + cos)/2 00334 a0 = 1 + alpha 00335 a1 = -2*cos 00336 a2 = 1 - alpha 00337 */ 00338 00339 00340 omega = (float) 2.0f*3.1415f*freq/48000.0f; 00341 cs = (float) cos(omega); 00342 alpha = (float) (sin(omega)/(2*(Q*5.0f))); 00343 00344 a0 = (1.0f + alpha); 00345 a0INV = 1.0f/a0; 00346 00347 b0 = (1.0f + cs)*a0INV*0.5f; 00348 b1 = -b0*2.0f; 00349 b2= b0; 00350 a1 = (-2.0f*cs)*a0INV; 00351 a2 = (1.0f-alpha)*a0INV; 00352 } 00353 00354 void BiFilter::bandpass1FreqAndQ(float freq, float Q) 00355 { /* 00356 BPF: H(s) = s / (s^2 + s/Q + 1) (constant skirt gain, peak gain = Q) 00357 00358 b0 = sin/2 = Q*alpha 00359 b1 = 0 00360 b2 = -sin/2 = -Q*alpha 00361 a0 = 1 + alpha 00362 a1 = -2*cos 00363 a2 = 1 - alpha 00364 */ 00365 00366 omega = (float) 2.0f*3.1415f*freq/48000.0f; 00367 cs = (float) cos(omega); 00368 sn = (float) sin(omega); 00369 alpha = (float) (sin(omega)/(2*(Q*5.0f))); 00370 00371 a0 = (1.0f + alpha); 00372 a0INV = 1.0f/a0; 00373 00374 b0 = sn*a0INV*0.5f; 00375 b1 = 0.0f; 00376 b2= -b0; 00377 a1 = (-2.0f*cs)*a0INV; 00378 a2 = (1.0f-alpha)*a0INV; 00379 } 00380 00381 void BiFilter::bandpass2FreqAndQ(float freq, float Q) 00382 { /* 00383 BPF2: H(s) = (s/Q) / (s^2 + s/Q + 1) (constant 0 dB peak gain) 00384 00385 b0 = alpha 00386 b1 = 0 00387 b2 = -alpha 00388 a0 = 1 + alpha 00389 a1 = -2*cos 00390 a2 = 1 - alpha 00391 */ 00392 00393 omega = (float) 2.0f*3.1415f*freq/48000.0f; 00394 cs = (float) cos(omega); 00395 sn = (float) sin(omega); 00396 alpha = (float) (sin(omega)/(2*(Q*5.0f))); 00397 00398 a0 = (1.0f + alpha); 00399 a0INV = 1.0f/a0; 00400 00401 b0 = alpha*a0INV; 00402 b1 = 0.0f; 00403 b2= -b0; 00404 a1 = (-2.0f*cs)*a0INV; 00405 a2 = (1.0f-alpha)*a0INV; 00406 } 00407 00408 void BiFilter::notchFreqAndQ(float freq, float Q) 00409 { /* 00410 H(s) = (s^2 + 1) / (s^2 + s/Q + 1) 00411 00412 b0 = 1 00413 b1 = -2*cos 00414 b2 = 1 00415 a0 = 1 + alpha 00416 a1 = -2*cos 00417 a2 = 1 - alpha 00418 00419 */ 00420 00421 omega = (float) 2.0f*3.1415f*freq/48000.0f; 00422 cs = (float) cos(omega); 00423 sn = (float) sin(omega); 00424 alpha = (float) (sin(omega)/(2*(Q*5.0f))); 00425 00426 a0 = (1.0f + alpha); 00427 a0INV = 1.0f/a0; 00428 00429 b0 = 1.0f*a0INV; 00430 b1 = (-2.0f*cs)*a0INV; 00431 b2= b0; 00432 a1 = (-2.0f*cs)*a0INV; 00433 a2 = (1.0f-alpha)*a0INV; 00434 } 00435 00436 00437 void BiFilter::peakingEQFreqAndQAndA(float freq, float Q, float A) 00438 { 00439 /* 00440 peakingEQ: H(s) = (s^2 + s*(A/Q) + 1) / (s^2 + s/(A*Q) + 1) 00441 00442 b0 = 1 + alpha*A 00443 b1 = -2*cos 00444 b2 = 1 - alpha*A 00445 a0 = 1 + alpha/A 00446 a1 = -2*cos 00447 a2 = 1 - alpha/A*/ 00448 00449 omega = (float) 2.0f*3.1415f*freq/48000.0f; 00450 cs = (float) cos(omega); 00451 sn = (float) sin(omega); 00452 alpha = (float) (sin(omega)/(2*(Q*5.0f))); 00453 beta = sqrt(A)/Q ; 00454 00455 a0 = (1.0f + alpha/A); 00456 a0INV = 1.0f/a0; 00457 00458 b0 = (1.0f+alpha*A)*a0INV; 00459 b1 = (-2.0f*cs)*a0INV; 00460 b2= (1.0f-alpha*A)*a0INV; 00461 a1 = (-2.0f*cs)*a0INV; 00462 a2 = (1.0f - alpha/A)*a0INV; 00463 } 00464 00465 00466 void BiFilter::lowShelfFreqAndQAndA(float freq, float Q, float A) 00467 { 00468 /* 00469 lowShelf: H(s) = A * (s^2 + (sqrt(A)/Q)*s + A) / (A*s^2 + (sqrt(A)/Q)*s + 1) 00470 00471 b0 = A*[ (A+1) - (A-1)*cos + beta*sin ] 00472 b1 = 2*A*[ (A-1) - (A+1)*cos ] 00473 b2 = A*[ (A+1) - (A-1)*cos - beta*sin ] 00474 a0 = (A+1) + (A-1)*cos + beta*sin 00475 a1 = -2*[ (A-1) + (A+1)*cos ] 00476 a2 = (A+1) + (A-1)*cos - beta*sin 00477 */ 00478 00479 omega = (float) 2.0f*3.1415f*freq/48000.0f; 00480 cs = (float) cos(omega); 00481 sn = (float) sin(omega); 00482 alpha = (float) (sin(omega)/(2*(Q*5.0f))); 00483 beta = sqrt(A)/Q ; 00484 00485 00486 a0 = (A+1) + (A-1)*cs + beta*sn; 00487 a0INV = 1.0f/a0; 00488 00489 b0 = A*( (A+1) - (A-1)*cs + beta* sn)*a0INV; 00490 b1 = 2.0f*A*( (A-1) - (A+1)*cs)*a0INV; 00491 b2= A*( (A+1) - (A-1)*cs - beta* sn)*a0INV; 00492 a1 = -2*( (A-1) + (A+1)*cs )*a0INV; 00493 a2 = ((A+1) + (A-1)*cs - beta*sn)*a0INV; 00494 } 00495 00496 void BiFilter::highShelfFreqAndQAndA(float freq, float Q, float A) 00497 { 00498 /* 00499 b0 = A*[ (A+1) + (A-1)*cos + beta*sin ] 00500 b1 = -2*A*[ (A-1) + (A+1)*cos ] 00501 b2 = A*[ (A+1) + (A-1)*cos - beta*sin ] 00502 a0 = (A+1) - (A-1)*cos + beta*sin 00503 a1 = 2*[ (A-1) - (A+1)*cos ] 00504 a2 = (A+1) - (A-1)*cos - beta*sin 00505 */ 00506 00507 omega = (float) 2.0f*3.1415f*freq/48000.0f; 00508 cs = (float) cos(omega); 00509 sn = (float) sin(omega); 00510 alpha = (float) (sin(omega)/(2*(Q*5.0f))); 00511 beta = sqrt(A)/Q ; 00512 00513 00514 a0 = (A+1) - (A-1)*cs + beta*sn; 00515 a0INV = 1.0f/a0; 00516 00517 b0 = A*( (A+1) + (A-1)*cs + beta* sn)*a0INV; 00518 b1 = -2.0f*A*( (A-1) + (A+1)*cs)*a0INV; 00519 b2= A*( (A+1) + (A-1)*cs - beta* sn)*a0INV; 00520 a1 = 2*( (A-1) - (A+1)*cs )*a0INV; 00521 a2 = ((A+1) + (A-1)*cs - beta*sn)*a0INV; 00522 } 00523 00524 00525 00526 00527 void Fourier::transform(float data[], unsigned long nn, int isign) { 00528 float * fr = new float[nn]; 00529 float * fi = new float[nn]; 00530 00531 00532 00533 for (int i = 0; i< nn; i++) 00534 { 00535 fr[i] = data[i*2]; 00536 fi[i] = data[i*2+1]; 00537 } 00538 00539 int ldn = (int) Utils::Log2(nn); 00540 00541 fft_f(fr,fi,ldn, isign); 00542 00543 00544 { 00545 for (int i = 0; i< nn; i++) 00546 { 00547 data[i*2] = fr[i]; 00548 data[i*2+1] = fi[i]; 00549 }} 00550 00551 delete[] fr; 00552 delete[] fi; 00553 00554 } 00555 00556 00557 00558 Sample * Fourier::sawtooth(int sampleLength, int partials, int wrapAround) 00559 { 00560 float * array= new float[sampleLength*2]; 00561 00562 if (partials > (sampleLength / 4)) {partials = sampleLength / 4; } 00563 00564 // reset array 00565 for (int j=0; j<sampleLength * 2; j++) { 00566 array[j] = 0.0; 00567 } 00568 00569 // setup Fourier components. 00570 for (int n=1; n<partials; n++) { 00571 // Set imaginary part of Fourier spectrum. 00572 array[(n*2)+1]=1.0/(float)(n); 00573 array[sampleLength*2-(n*2)+1]=-1.0/(float)(n); 00574 } 00575 00576 // do transformation 00577 Fourier::transform(array, sampleLength, -1); 00578 00579 // create a new sample 00580 Sample * mySample= new Sample(sampleLength,wrapAround); 00581 00582 for (int i=0; i<sampleLength; i++) { 00583 // Copy real part of Fourier transform to mySample. 00584 mySample->samples[i] = array[i*2]; 00585 } 00586 00587 mySample->makeWrap(); 00588 mySample->wavenormalize(); 00589 delete [] array; 00590 return mySample; 00591 } 00592 00593 Sample * Fourier::square(int sampleLength, int partials, int wrapAround) 00594 { 00595 float * array= new float[sampleLength*2]; 00596 00597 if (partials > (sampleLength / 4)) {partials = sampleLength / 4; } 00598 00599 // reset array 00600 for (int j=0; j<sampleLength * 2; j++) { 00601 array[j] = 0.0; 00602 } 00603 00604 // setup Fourier components. 00605 for (int n=1; n<partials; n=n+2) { 00606 // Set imaginary part of Fourier spectrum. 00607 array[(n*2)+1]=1.0/(float)(n); 00608 array[sampleLength*2-(n*2)+1]=-1.0/(float)(n); 00609 } 00610 00611 // do transformation 00612 Fourier::transform(array, sampleLength, -1); 00613 00614 // create a new sample 00615 Sample * mySample= new Sample(sampleLength,wrapAround); 00616 00617 for (int i=0; i<sampleLength; i++) { 00618 // Copy real part of Fourier transform to mySample. 00619 mySample->samples[i] = array[i*2]; 00620 } 00621 00622 mySample->makeWrap(); 00623 mySample->wavenormalize(); 00624 delete [] array; 00625 return mySample; 00626 } 00627 00628 Sample * Fourier::triangle(int sampleLength, int partials, int wrapAround) 00629 { 00630 float * array= new float[sampleLength*2]; 00631 00632 if (partials > (sampleLength / 2)) {partials = sampleLength / 2; } 00633 00634 // reset array 00635 for (int j=0; j<sampleLength * 2; j++) { 00636 array[j] = 0.0; 00637 } 00638 00639 // setup Fourier components. 00640 for (int n=1; n<partials; n++) { 00641 if ((n % 2)==1) 00642 { // Set real part of Fourier spectrum. 00643 array[(n*2)]=1.0/(float)(n*n); 00644 array[sampleLength*2-(n*2)]=1.0/(float)(n*n); 00645 } 00646 } 00647 00648 // do transformation 00649 Fourier::transform(array, sampleLength, -1); 00650 00651 // create a new sample 00652 Sample * mySample= new Sample(sampleLength,wrapAround); 00653 00654 for (int i=0; i<sampleLength; i++) { 00655 // Copy real part of Fourier transform to mySample. 00656 mySample->samples[i] = array[i*2]; 00657 } 00658 00659 mySample->makeWrap(); 00660 mySample->wavenormalize(); 00661 delete [] array; 00662 return mySample; 00663 } 00664 00665 00666 Sample * Fourier::sine(int sampleLength, int partials, int wrapAround) 00667 { 00668 float * array= new float[sampleLength*2]; 00669 00670 if (partials > (sampleLength / 2)) {partials = sampleLength / 2; } 00671 00672 // reset array 00673 for (int j=0; j<sampleLength * 2; j++) { 00674 array[j] = 0.0; 00675 } 00676 00677 00678 { // Set real part of Fourier spectrum. 00679 array[2]=1.0f; 00680 array[sampleLength*2-2]=1.0f; 00681 } 00682 00683 // do transformation 00684 Fourier::transform(array, sampleLength, -1); 00685 00686 // create a new sample 00687 Sample * mySample= new Sample(sampleLength,wrapAround); 00688 00689 for (int i=0; i<sampleLength; i++) { 00690 // Copy real part of Fourier transform to mySample. 00691 mySample->samples[i] = array[i*2]; 00692 } 00693 00694 mySample->makeWrap(); 00695 mySample->wavenormalize(); 00696 delete [] array; 00697 return mySample; 00698 } 00699 00700 Sample * Fourier::wave1(int sampleLength, int partials, int wrapAround) 00701 { 00702 float * array= new float[sampleLength*2]; 00703 00704 if (partials > (sampleLength / 2)) {partials = sampleLength / 2; } 00705 00706 // reset array 00707 for (int j=0; j<sampleLength * 2; j++) { 00708 array[j] = 0.0; 00709 } 00710 00711 00712 { // Set real part of Fourier spectrum. 00713 00714 array[2]=1.0f; 00715 array[sampleLength*2-2]=1.0f; 00716 00717 array[8]=1.0f; 00718 array[sampleLength*2-8]=0.25f; 00719 00720 array[4]=1.0f; 00721 array[sampleLength*2-4]=0.5f; 00722 00723 array[16]=1.0f; 00724 array[sampleLength*2-16]=0.125f; 00725 } 00726 00727 // do transformation 00728 Fourier::transform(array, sampleLength, -1); 00729 00730 // create a new sample 00731 Sample * mySample= new Sample(sampleLength,wrapAround); 00732 00733 for (int i=0; i<sampleLength; i++) { 00734 // Copy real part of Fourier transform to mySample. 00735 mySample->samples[i] = array[i*2]; 00736 } 00737 00738 mySample->makeWrap(); 00739 mySample->wavenormalize(); 00740 delete [] array; 00741 return mySample; 00742 } 00743 00744 Sample * Fourier::wave2(int sampleLength, int partials, int wrapAround) 00745 { 00746 float * array= new float[sampleLength*2]; 00747 00748 if (partials > (sampleLength / 2)) {partials = sampleLength / 2; } 00749 00750 // reset array 00751 for (int j=0; j<sampleLength * 2; j++) { 00752 array[j] = 0.0; 00753 } 00754 00755 00756 for (int n=1; n<partials; n++) { 00757 if ((n % 3)==1) 00758 { // Set real part of Fourier spectrum. 00759 array[(n*2)]=1.0/(float)(n); 00760 array[sampleLength*2-(n*2)]=1.0/(float)(n); 00761 } 00762 } 00763 00764 // do transformation 00765 Fourier::transform(array, sampleLength, -1); 00766 00767 // create a new sample 00768 Sample * mySample= new Sample(sampleLength,wrapAround); 00769 00770 for (int i=0; i<sampleLength; i++) { 00771 // Copy real part of Fourier transform to mySample. 00772 mySample->samples[i] = array[i*2]; 00773 } 00774 00775 mySample->makeWrap(); 00776 mySample->wavenormalize(); 00777 delete [] array; 00778 return mySample; 00779 } 00780 00781 00782 Sample * Fourier::wave3(int sampleLength, int partials, int wrapAround) 00783 { 00784 float * array= new float[sampleLength*2]; 00785 00786 if (partials > (sampleLength / 2)) {partials = sampleLength / 2; } 00787 00788 // reset array 00789 for (int j=0; j<sampleLength * 2; j++) { 00790 array[j] = 0.0; 00791 } 00792 00793 00794 for (int n=1; n<partials; n++) { 00795 if ((n % 2)==1) 00796 { // Set real part of Fourier spectrum. 00797 array[(n*2)]=1.0/(float)(sqrt(n)); 00798 array[sampleLength*2-(n*2)]=1.0/(float)(sqrt(n)); 00799 } 00800 } 00801 00802 // do transformation 00803 Fourier::transform(array, sampleLength, -1); 00804 00805 // create a new sample 00806 Sample * mySample= new Sample(sampleLength,wrapAround); 00807 00808 for (int i=0; i<sampleLength; i++) { 00809 // Copy real part of Fourier transform to mySample. 00810 mySample->samples[i] = array[i*2]; 00811 } 00812 00813 mySample->makeWrap(); 00814 mySample->wavenormalize(); 00815 delete [] array; 00816 return mySample; 00817 } 00818 00819 00820 Sample * Fourier::wave4(int sampleLength, int partials, int wrapAround) 00821 { 00822 float * array= new float[sampleLength*2]; 00823 00824 if (partials > (sampleLength / 2)) {partials = sampleLength / 2; } 00825 00826 // reset array 00827 for (int j=0; j<sampleLength * 2; j++) { 00828 array[j] = 0.0; 00829 } 00830 00831 00832 for (int n=1; n<partials; n++) { 00833 if ((n % 2)==1) 00834 { // Set real part of Fourier spectrum. 00835 array[(n*2)]=1.0; 00836 array[sampleLength*2-(n*2)]=1.0; 00837 } 00838 } 00839 00840 // do transformation 00841 Fourier::transform(array, sampleLength, -1); 00842 00843 // create a new sample 00844 Sample * mySample= new Sample(sampleLength,wrapAround); 00845 00846 for (int i=0; i<sampleLength; i++) { 00847 // Copy real part of Fourier transform to mySample. 00848 mySample->samples[i] = array[i*2]; 00849 } 00850 00851 mySample->makeWrap(); 00852 mySample->wavenormalize(); 00853 delete [] array; 00854 return mySample; 00855 } 00856 00857 }; // end of namespace: SynthCore 00858 00859 Docs made by Doxygen. Email: Mikael Christensen |