Main Page | Namespaces | Classes | Compounds | Files | Compound Members | Related FilterDialog.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 "FilterDialog.h" 00008 #include "Filters.h" 00009 00010 namespace SynthGUI { 00011 00012 void FilterDialog::setFreqAndRez(float freq,float rez) { 00013 for (int j = 0; j< myMod->mv.size(); j++) 00014 { // whee: another unsafe typecast. 00015 ((BiQuad *)(myMod->mv[j]))->setFreqAndRez(freq,rez); 00016 } 00017 00018 } 00019 00020 00021 00022 00023 void FilterDialog::filterType(int fltType) { 00024 00025 for (int j = 0; j< myMod->mv.size(); j++) 00026 { // whee: another unsafe typecast. 00027 ((BiQuad *)(myMod->mv[j]))->filterType = fltType; 00028 } 00029 00030 } 00031 00032 00033 00034 00035 FilterDialog::FilterDialog(mod * moduleptr) : myMod(moduleptr) { 00036 myFilter = ((BiQuad *)(myMod->mv[0]))->myFilter; 00037 00038 00039 freq = 4000.0f; q = 0.4f; 00040 00041 00042 //myFilter->notchFreqAndQ(freq, q); 00043 setFreqAndRez(freq,q); 00044 00045 t =0; 00046 myWindow = new WinForm(640,650, WinForm::standard, "Syntopia - Filter setup"); 00047 //hwdn = my_hInstance; //? 00048 myText = new TextBox(); 00049 myText2 = new TextBox(); 00050 myButton3 = new Button("DX JAM"); 00051 00052 //myScroll = new ScrollBar(); 00053 00054 00055 00056 int lx1 = 50; 00057 int lx2 = 280; 00058 int ly1 = 50; 00059 int lx3 = 510; 00060 00061 // setup Labels 00062 00063 typeLabel = new Label("Type:"); 00064 filterLabel = new Label("Filter Setup:"); 00065 seriesLabel = new Label("Connect in series:");; 00066 zPlaneLabel = new Label("Z-Plane plot:"); 00067 responseLabel = new Label("Frequency Response:");; 00068 00069 00070 typeLabel->PutInWinForm(myWindow, lx1, ly1, 200, 30); 00071 filterLabel->PutInWinForm(myWindow, 10, 10, 200, 30); 00072 seriesLabel->PutInWinForm(myWindow, lx2, ly1, 200, 30); 00073 zPlaneLabel->PutInWinForm(myWindow, lx1, ly1+65, 200, 30); 00074 responseLabel->PutInWinForm(myWindow, lx2, ly1+65, 200, 30); 00075 00076 // setup ComboBoxes 00077 00078 filterDropDown = new ComboBox(); 00079 filterDropDown->PutInWinForm(myWindow, lx1, ly1+30, 200, 140); 00080 filterDropDown->add(FDD1 = new ComboBoxItem("Low Pass")); 00081 filterDropDown->add(FDD2 = new ComboBoxItem("High Pass")); 00082 filterDropDown->add(FDD3 = new ComboBoxItem("Band pass")); 00083 filterDropDown->add(FDD4 = new ComboBoxItem("Band pass 2")); 00084 filterDropDown->add(FDD5 = new ComboBoxItem("Notch")); 00085 filterDropDown->add(FDD6 = new ComboBoxItem("All Pass")); 00086 filterDropDown->add(FDD7 = new ComboBoxItem("Peaking EQ (+6dB)")); 00087 filterDropDown->add(FDD8 = new ComboBoxItem("High Shelf (+6dB)")); 00088 filterDropDown->add(FDD9 = new ComboBoxItem("Low Shelf (+6dB)")); 00089 filterDropDown->add(FDD10 = new ComboBoxItem("Bypass (no filter)")); 00090 filterDropDown->setSelected(FDD1); 00091 00092 seriesDropDown = new ComboBox(); 00093 seriesDropDown->PutInWinForm(myWindow, lx2, ly1+30, 200, 140); 00094 SDD1 = new ComboBoxItem("1 : 12 db per octave"); 00095 SDD2 = new ComboBoxItem("2 : 24 db per octave"); 00096 SDD3 = new ComboBoxItem("3 : 36 db per octave"); 00097 SDD4 = new ComboBoxItem("3 : 48 db per octave"); 00098 seriesDropDown->add(SDD1); 00099 seriesDropDown->add(SDD2); 00100 seriesDropDown->add(SDD3); 00101 seriesDropDown->add(SDD4); 00102 seriesDropDown->setSelected(SDD1); 00103 00104 // Setup Canvases. 00105 00106 poleCanvas = new MCanvas(); 00107 responseCanvas = new MCanvas(); 00108 poleCanvas->PutInWinForm(myWindow, lx1,ly1+90,200,200); 00109 responseCanvas->PutInWinForm(myWindow, lx2,ly1+90,200,200); 00110 00111 // Setup Inputs 00112 00113 freqInput = new AInput("Freq", 100.0f, 22000.0f, 1000, false); 00114 00115 QInput = new AInput("Q", 0.0001f, 1.5f, 1000, false); 00116 00117 freqInput->PutInWinForm(myWindow, lx1,ly1+300,200,200); 00118 freqInput->setValue(freq); 00119 QInput->PutInWinForm(myWindow, lx1,ly1+340,200,200); 00120 QInput->setValue(q); 00121 00122 00123 // Setup buttons 00124 00125 OKButton = new Button("OK"); 00126 CancelButton = new Button("Cancel"); 00127 00128 OKButton->PutInWinForm(myWindow,lx3,ly1,100,28); 00129 CancelButton->PutInWinForm(myWindow,lx3,ly1+40,100,28); 00130 00131 // Setup Dividers 00132 00133 div1 = new divider(); 00134 div2 = new divider(); 00135 00136 div1->PutInWinForm(myWindow, lx3-15, 5, 5, 600); 00137 div2->PutInWinForm(myWindow, 5, 29, lx3-35, 5); 00138 00139 00140 00141 // Debug: 00142 00143 myText2->PutInWinForm(myWindow,lx1,450,lx2+200-lx1,100); 00144 00145 00146 00147 00148 GUIControl::GUIInstance->ErrorTextBox = myText2; 00149 00150 00151 myText->setEventHandler(this); 00152 myText2->setEventHandler(this); 00153 OKButton->setEventHandler(this); 00154 CancelButton->setEventHandler(this); 00155 filterDropDown->setEventHandler(this); 00156 freqInput->setEventHandler(this); 00157 QInput->setEventHandler(this); 00158 00159 myWindow->show(); 00160 drawResponse(); 00161 } 00162 00163 void FilterDialog::MessageLoop() { 00164 // Enter Loop until Exit. 00165 GUIControl::GUIInstance->MessageLoop(); 00166 } 00167 00168 FilterDialog::~FilterDialog() { 00169 // Clean Up. 00170 delete(myWindow); 00171 } 00172 00173 void FilterDialog::drawResponse() 00174 { 00175 if (filterDropDown->getSelected() == FDD1) { 00176 //myFilter->lowpassFreqAndQ(freq,q); 00177 filterType(BiQuad::lowpass); 00178 } 00179 if (filterDropDown->getSelected() == FDD2) { 00180 //myFilter->highpassFreqAndQ(freq,q); 00181 filterType(BiQuad::highpass); 00182 } 00183 if (filterDropDown->getSelected() == FDD3) { 00184 //myFilter->bandpass1FreqAndQ(freq,q); 00185 filterType(BiQuad::bandpass1); 00186 } 00187 if (filterDropDown->getSelected() == FDD4) { 00188 //myFilter->bandpass2FreqAndQ(freq,q); 00189 filterType(BiQuad::bandpass2); 00190 } 00191 if (filterDropDown->getSelected() == FDD5) { 00192 //myFilter->notchFreqAndQ(freq,q); 00193 filterType(BiQuad::notch); 00194 } 00195 if (filterDropDown->getSelected() == FDD6) { 00196 //myFilter->allpassFreqAndQ(freq,q); 00197 filterType(BiQuad::allpass); 00198 } 00199 if (filterDropDown->getSelected() == FDD7) { 00200 //myFilter->peakingEQFreqAndQAndA(freq,q,1.41f); 00201 filterType(BiQuad::peakingEQ); 00202 } 00203 if (filterDropDown->getSelected() == FDD8) { 00204 //myFilter->lowShelfFreqAndQAndA(freq,q,1.41f); 00205 filterType(BiQuad::lowShelf); 00206 } 00207 if (filterDropDown->getSelected() == FDD9) { 00208 //myFilter->highShelfFreqAndQAndA(freq,q,1.41f); 00209 filterType(BiQuad::highShelf); 00210 } 00211 if (filterDropDown->getSelected() == FDD10) { 00212 filterType(BiQuad::bypass); 00213 } 00214 00215 setFreqAndRez(freq,q); 00216 00217 int w=responseCanvas->getWidth()-5; 00218 int h=responseCanvas->getHeight()-15; 00219 //float array[2048]; 00220 00221 //myFilter->notchFreqAndQ(12211, 1.2224); 00222 Sample * mySample = myFilter->getFreqResponseSample(512); 00223 Sample * mySample2 = myFilter->getPhaseResponseSample(512); 00224 mySample2->normalize(); 00225 float MAX = mySample->getMax(); 00226 00227 float MIN = mySample->getMin(); 00228 if (MAX<0.0f) {MAX = 0.05f;} 00229 {MIN = -96.0f;} 00230 00231 00232 std::cout << "CALLED:MAX" << std::endl; 00233 std::cout << MIN << std::endl; 00234 responseCanvas->clear(); 00235 { //responseCanvas->setColor(140,150,250); 00236 for (int i=0; i<mySample->length; i++) { 00237 responseCanvas->setColor(210,210,210); 00238 responseCanvas->line((int)( (float)(i * w)/mySample->length) ,h-5-((h-10)*(0.0-MIN)/(MAX-MIN)), 00239 (int)( (float)(i * w)/mySample->length) ,h+15); 00240 responseCanvas->setColor(140,150,250); 00241 responseCanvas->line((int)( (float)(i * w)/mySample->length) ,h-5-((h-10)*(mySample->samples[i]-MIN)/(MAX-MIN)), 00242 (int)( (float)(i * w)/mySample->length) ,h+15 ); 00243 00244 responseCanvas->putPixel((int)( (float)(i * w)/mySample->length) ,h-5-((h-10)*(mySample->samples[i]-MIN)/(MAX-MIN)),2,2,2); 00245 00246 responseCanvas->putPixel((int)( (float)(i * w)/mySample2->length) ,h-5-((h-10)*(mySample2->samples[i])),255,0,2); 00247 } 00248 } 00249 00250 responseCanvas->doDraw(); 00251 drawPolesAndZeroes(); 00252 00253 } 00254 00255 00256 void FilterDialog::drawPZ(float x1, float x2, float max, int type) 00257 { 00258 int w=poleCanvas->getWidth(); 00259 int h=poleCanvas->getHeight(); 00260 max = max * 1.2; 00261 int x = ((float)w * (x1 + max)/(2*max)); 00262 int y = ((float)h * (x2 + max)/(2*max)); 00263 if (type == 1) { 00264 poleCanvas->setColor(1,1,1); 00265 00266 poleCanvas->line(x-5,y-5,x+5,y+5); 00267 poleCanvas->line(x-5,y+5,x+5,y-5); 00268 } else 00269 if (type == 2) 00270 { poleCanvas->setColor(255,1,1); 00271 00272 poleCanvas->circle(x,y,5); 00273 } else 00274 { poleCanvas->setColor(200,200,250); 00275 int x2 = ((float)w * (1.0 + max)/(2*max)); 00276 poleCanvas->circle(x,y,(int) (x2-x) ); 00277 poleCanvas->line(0,h /2,w,h/2); 00278 poleCanvas->line(w/2,0,w/2,h); 00279 00280 } 00281 00282 } 00283 00284 void FilterDialog::drawPolesAndZeroes() 00285 { 00286 float p1r,p1i,p2r,p2i,z1r,z1i,z2r,z2i; 00287 myFilter->getPolesAndZeroes(p1r,p1i,p2r,p2i,z1r,z1i,z2r,z2i); 00288 00289 // get length 00290 float p1,p2,z1,z2,max; 00291 p1 = p1r*p1r + p1i*p1i; 00292 p2 = p2r*p2r + p2i*p2i; 00293 z1 = z1r*z1r + z1i*z1i; 00294 z2 = z2r*z2r + z2i*z2i; 00295 max = p1; 00296 if (p2 > max) max = p2; 00297 if (z1 > max) max = z1; 00298 if (z2 > max) max = z2; 00299 max = sqrt(max); 00300 poleCanvas->clear(); 00301 drawPZ(0,0,max,3); // Draw unit circle 00302 00303 drawPZ(p1r,p1i,max,1); // Draw poles 00304 drawPZ(p2r,p2i,max,1); 00305 00306 drawPZ(z1r,z1i,max,2); // Draw Zeroes 00307 drawPZ(z2r,z2i,max,2); 00308 poleCanvas->doDraw(); 00309 } 00310 00311 void FilterDialog::HandleEvents(event ev) { 00312 if ((ev.EventSource==filterDropDown) && (HIWORD(ev.wParam)==CBN_SELCHANGE)) 00313 { std::cout << "filterDropDown" << std::endl; 00314 00315 drawResponse(); 00316 } 00317 00318 if ((ev.EventSource==OKButton)) 00319 { 00320 drawResponse(); 00321 std::cout << "OK BUTTON" << std::endl; 00322 } 00323 00324 if ((ev.EventSource==freqInput)) 00325 { 00326 freq = freqInput->getValue(); 00327 drawResponse(); 00328 } 00329 00330 if ((ev.EventSource==QInput)) 00331 { 00332 q = QInput->getValue(); 00333 drawResponse(); 00334 } 00335 } 00336 00337 }; // end of namespace: SynthGUI Docs made by Doxygen. Email: Mikael Christensen |