annotate testApp.mm @ 24:a4908ad8c78e

Top and bottom toolbars. Intro page.
author Robert Tubb <rt300@eecs.qmul.ac.uk>
date Fri, 01 Feb 2013 11:16:56 +0000
parents 8c0783739337
children f42a00e3f22d
rev   line source
rt300@0 1 #include "testApp.h"
rt300@2 2
rt300@24 3 #define SLIDER_GUI_WIDTH 256
rt300@0 4 extern Grid theGridView;
rt300@0 5 extern PresetManager presetManager;
rt300@1 6 extern EventLogger eventLogger;
rt300@3 7 extern Frequencer frequencer;
rt300@9 8
rt300@24 9 const vector<string> parameterNames;
rt300@24 10
rt300@24 11 const string sliderParamNames[10] = {"Transpose", "1/4 note","1/6 note","1/7 note","1/8 note","Waveform", "Filter Type","Filter Freq", "Envelope","FM amt"};
rt300@24 12 //const vector<const string> v(ra[0],ra[1]);
rt300@24 13
rt300@24 14
rt300@7 15 //DeviceID3523537000
rt300@0 16 //--------------------------------------------------------------
rt300@0 17 void testApp::setup(){
rt300@16 18 paused = true;
rt300@16 19
rt300@24 20
rt300@16 21 ofBackground( 0, 0, 0 );
rt300@0 22 ofEnableAlphaBlending();
rt300@21 23 //ofEnableSmoothing();
rt300@0 24
rt300@0 25 // open an outgoing connection to HOST:PORT
rt300@0 26 sender.setup( HOST, PORT );
rt300@3 27 ofSetFrameRate(30);
rt300@0 28 // reciever
rt300@6 29 lastMoveTime = ofGetSystemTimeMicros();
rt300@0 30 prevTouchX = 0;
rt300@0 31 prevTouchY = 0;
rt300@0 32
rt300@0 33 xLocked = false;
rt300@0 34 yLocked = false;
rt300@0 35
rt300@0 36 numActiveTouches = 0;
rt300@3 37 touch0.setCoord(17./7., 2./3.);
rt300@0 38 touch1.setCoord(10,20);
rt300@3 39
rt300@0 40 prevTouch0.setCoord(1,2);
rt300@0 41 prevTouch1.setCoord(10,20);
rt300@0 42 prevDist = 10;
rt300@16 43 slowFactor = 0.98;
rt300@16 44
rt300@16 45
rt300@16 46 // the 5 harmonics for the frequencer
rt300@16 47 freqIndexes.push_back(0);
rt300@16 48 freqIndexes.push_back(4);
rt300@16 49 freqIndexes.push_back(6);
rt300@16 50 freqIndexes.push_back(7);
rt300@16 51 freqIndexes.push_back(8);
rt300@16 52
rt300@16 53
rt300@16 54 ofxiPhoneSetOrientation( OFXIPHONE_ORIENTATION_PORTRAIT ); // do this before setting up all the other objects
rt300@0 55
rt300@24 56 // initialise the interfaces
rt300@0 57 theGridView.init();
rt300@0 58
rt300@24 59 setupSliderGui();
rt300@24 60 sliderGUI->setVisible(true);
rt300@0 61
rt300@0 62 // initial slider vals
rt300@0 63 for(int i=0; i<10;i++){
rt300@0 64 sliderVals.push_back(64);
rt300@0 65 }
rt300@8 66
rt300@24 67 // initialise PD
rt300@24 68
rt300@2 69 int ticksPerBuffer = 8; // 8 * 64 = buffer len of 512
rt300@2 70
rt300@2 71 // setup the app core
rt300@2 72 core.setup(2, 1, 44100, ticksPerBuffer);
rt300@2 73
rt300@2 74 // setup OF sound stream
rt300@2 75 ofSoundStreamSetup(2, 1, this, 44100, ofxPd::blockSize()*ticksPerBuffer, 3);
rt300@1 76
rt300@24 77
rt300@24 78
rt300@24 79 // set up iOS gui stuff
rt300@24 80 bottomTabViewController = [[BottomTabViewController alloc] initWithNibName:@"BottomTabViewController" bundle:nil];
rt300@24 81 [ofxiPhoneGetGLParentView() addSubview:bottomTabViewController.view];
rt300@24 82
rt300@24 83 [bottomTabViewController setAppRef:(id)this];
rt300@24 84 [bottomTabViewController show:(id)this];
rt300@24 85
rt300@24 86 bottomTabViewController.view.frame = CGRectMake(0,getHeight()-44,getWidth(),44);
rt300@24 87
rt300@24 88 /////
rt300@24 89
rt300@24 90 topButtonViewController = [[TopButtonViewController alloc] initWithNibName:@"TopButtonViewController" bundle:nil];
rt300@24 91 [ofxiPhoneGetGLParentView() addSubview:topButtonViewController.view];
rt300@24 92
rt300@24 93 [topButtonViewController setAppRef:(id)this];
rt300@24 94 [topButtonViewController show:(id)this];
rt300@24 95
rt300@24 96 topButtonViewController.view.frame = CGRectMake(0,0,getWidth(),44);
rt300@24 97
rt300@24 98 // initialise user logging stuff
rt300@5 99 presetManager.startupLoadAll();
rt300@7 100 eventLogger.init();
rt300@24 101
rt300@24 102
rt300@24 103 // GO
rt300@16 104 paused = false;
rt300@16 105
rt300@24 106 }
rt300@24 107
rt300@24 108
rt300@24 109 //--------------------------------------------------------------
rt300@24 110 void testApp::exit(){
rt300@24 111 if(consentGiven){
rt300@24 112 presetManager.exitAndSaveAll();
rt300@24 113 eventLogger.exitAndSave();
rt300@24 114 }
rt300@5 115
rt300@24 116 // else - don't save anything and app will boot up into consent/intro screen
rt300@24 117 core.exit();
rt300@24 118
rt300@24 119 [introViewController release];
rt300@24 120 [topButtonViewController release];
rt300@24 121 [bottomTabViewController release];
rt300@24 122
rt300@24 123 delete sliderGUI;
rt300@24 124
rt300@24 125 cout << "exit done \n";
rt300@0 126 }
rt300@24 127
rt300@24 128 //--------------------------------------------------------------
rt300@3 129 #pragma mark GUI
rt300@16 130 //--
rt300@16 131 float testApp::getWidth(){
rt300@16 132 // depends on orientation
rt300@16 133 return ofGetWidth();
rt300@16 134
rt300@16 135 }
rt300@16 136 float testApp::getHeight(){
rt300@16 137 // depends on orientation
rt300@16 138 return ofGetHeight();
rt300@16 139
rt300@16 140 }
rt300@24 141 #pragma mark GUI
rt300@24 142
rt300@0 143 //--------------------------------------------------------------
rt300@24 144 /*
rt300@0 145 void testApp::setupZoomGui(){
rt300@16 146 // width = height
rt300@24 147 int buttonHeight = 45;
rt300@24 148 zoomGUI = new ofxUICanvas(getWidth()-200,0,190,buttonHeight*7);
rt300@24 149 zoomGUI->setTheme(OFX_UI_THEME_METALGEAR );
rt300@0 150
rt300@24 151 zoomGUI->addLabelToggle("START/STOP", false);
rt300@24 152 zoomGUI->addLabelButton("SAVE PRESET", false);
rt300@3 153 zoomGUI->addLabelButton("ZOOM MIN", false);
rt300@3 154 zoomGUI->addLabelButton("ZOOM MAX", false);
rt300@16 155 zoomGUI->addLabelButton("QUESTIONS", false);
rt300@3 156
rt300@24 157
rt300@24 158 ofxUILabelToggle * butt = zoomGUI->addLabelToggle("LOCK SEQUENCE (X)", false);
rt300@24 159 butt->setColorFill(ofColor(0,0,255));
rt300@24 160 butt->setColorFillHighlight(ofColor(0,0,255));
rt300@24 161
rt300@24 162 ofxUILabelToggle * butt2 = zoomGUI->addLabelToggle("LOCK SYNTH (Y)", false);
rt300@24 163 butt2->setColorFill(ofColor(255,0,0));
rt300@24 164 butt2->setColorFillHighlight(ofColor(255,0,0));
rt300@24 165
rt300@24 166
rt300@0 167 ofAddListener(zoomGUI->newGUIEvent, this, &testApp::zoomGUIEvent);
rt300@0 168 }
rt300@24 169
rt300@0 170 //--------------------------------------------------------------
rt300@0 171 void testApp::zoomGUIEvent(ofxUIEventArgs &e){
rt300@0 172
rt300@24 173 if(e.widget->getName() == "SAVE PRESET")
rt300@0 174 {
rt300@0 175
rt300@16 176 if(((ofxUIButton *)e.widget)->getValue()==0){ // touchup
rt300@3 177 cout << "SAVE PRESET\n";
rt300@9 178 presetManager.showNameDialog();
rt300@8 179
rt300@3 180 }
rt300@3 181
rt300@3 182 }else if(e.widget->getName() == "ZOOM MIN")
rt300@3 183 {
rt300@16 184 if(((ofxUIButton *)e.widget)->getValue()==0){ // touchup
rt300@3 185 cout << "ZOOM MIN\n";
rt300@5 186 theGridView.setMinZoom();
rt300@5 187 eventLogger.logEvent(SET_MIN_ZOOM);
rt300@3 188 }
rt300@3 189 }else if(e.widget->getName() == "ZOOM MAX")
rt300@3 190 {
rt300@16 191 if(((ofxUIButton *)e.widget)->getValue()==0){ // touchup
rt300@8 192 cout << "ZOOM MAX\n";
rt300@5 193 theGridView.setMaxZoom();
rt300@5 194 eventLogger.logEvent(SET_MAX_ZOOM);
rt300@8 195
rt300@3 196 }
rt300@16 197 }else if(e.widget->getName() == "QUESTIONS")
rt300@16 198 {
rt300@16 199 if(((ofxUIButton *)e.widget)->getValue()==0){ // touchup
rt300@16 200 showQuestionnaire();
rt300@16 201 }
rt300@24 202 }else if(e.widget->getName() == "LOCK SEQUENCE (X)")
rt300@7 203 {
rt300@20 204
rt300@20 205 cout << "LOCK SEQUENCE (X)\n";
rt300@20 206 // lock
rt300@20 207 theGridView.shiftCentreToSnapped();
rt300@20 208 xLocked = !xLocked;
rt300@20 209
rt300@7 210 }else if(e.widget->getName() == "LOCK SYNTH (Y)")
rt300@7 211 {
rt300@7 212
rt300@7 213 cout << "LOCK SYNTH (Y)\n";
rt300@7 214 // lock
rt300@20 215 theGridView.shiftCentreToSnapped();
rt300@7 216 if(((ofxUIButton *)e.widget)->getValue()){
rt300@7 217 yLocked = true;
rt300@7 218 }else{
rt300@7 219 yLocked = false;
rt300@7 220
rt300@7 221 }
rt300@24 222
rt300@24 223 }else if(e.widget->getName() == "START/STOP")
rt300@24 224 {
rt300@24 225
rt300@24 226
rt300@24 227 //pd.startMessage();
rt300@24 228 /// pd.addSymbol("hello");
rt300@24 229 /// pd.addFloat(1.23);
rt300@24 230 /// pd.finishList("test");
rt300@24 231 }else{
rt300@24 232 cout << "GUI error : unknown event recieved\n";
rt300@7 233 }
rt300@7 234
rt300@24 235 }
rt300@24 236 */
rt300@24 237
rt300@24 238
rt300@24 239 ////////////////////////////
rt300@24 240 // These functions called from iOS toolbars
rt300@24 241 //--------------------------------------------------------------
rt300@24 242 void testApp::lockSequencerPressed(bool locked){
rt300@24 243 theGridView.shiftCentreToSnapped();
rt300@24 244 xLocked = locked;
rt300@24 245
rt300@24 246 }
rt300@24 247 //--------------------------------------------------------------
rt300@24 248 void testApp::lockSynthPressed(bool locked){
rt300@24 249 theGridView.shiftCentreToSnapped();
rt300@24 250 yLocked = locked;
rt300@24 251
rt300@24 252 }
rt300@24 253 //--------------------------------------------------------------
rt300@24 254 void testApp::seqStartStop(bool go){
rt300@24 255 if(!go){ //stop
rt300@24 256 core.pd.startMessage();
rt300@24 257 core.pd.addFloat(0);
rt300@24 258 core.pd.finishMessage("fromOF", "seqStartStop");
rt300@24 259 }else { // play
rt300@24 260 //stopSequencer();
rt300@24 261 core.pd.startMessage();
rt300@24 262 core.pd.addFloat(1);
rt300@24 263 core.pd.finishMessage("fromOF", "seqStartStop");
rt300@24 264 }
rt300@24 265 }
rt300@24 266 //--------------------------------------------------------------
rt300@24 267 void testApp::showQuestionnaire(){
rt300@24 268 // stop updating / drawing
rt300@24 269
rt300@24 270 // if(eventLogger.questionnaireCompleted) return;
rt300@24 271
rt300@24 272 paused = true;
rt300@24 273
rt300@24 274 //stopSequencer
rt300@24 275 core.pd.startMessage();
rt300@24 276 core.pd.addFloat(0);
rt300@24 277 core.pd.finishMessage("fromOF", "seqStartStop");
rt300@24 278
rt300@24 279 questionnaireViewController = [[QuestionnaireViewController alloc] initWithNibName:@"QuestionnaireViewController" bundle:nil];
rt300@24 280 [ofxiPhoneGetGLParentView() addSubview:questionnaireViewController.view];
rt300@24 281
rt300@24 282 [questionnaireViewController setAppRef:(id)this];
rt300@24 283 [questionnaireViewController show:(id)this];
rt300@24 284
rt300@24 285 whichInterfaceShowing = QUESTIONNAIRE;
rt300@24 286
rt300@24 287
rt300@24 288 }
rt300@24 289 //--------------------------------------------------------------
rt300@24 290 void testApp::questionnaireHidden(vector<int> answers){
rt300@24 291 // send answers to server as json
rt300@24 292 eventLogger.questionnaireAnswersObtained(answers);
rt300@24 293
rt300@24 294 // set "we've done questionnaire" to true in event logger
rt300@24 295 paused = false;
rt300@24 296
rt300@24 297 //startSequencer (TODO what about the toggle ? ?)
rt300@24 298 core.pd.startMessage();
rt300@24 299 core.pd.addFloat(1);
rt300@24 300 core.pd.finishMessage("fromOF", "seqStartStop");
rt300@24 301 whichInterfaceShowing = BOTH;
rt300@24 302 // tell bottomtabviewcontroller
rt300@24 303
rt300@24 304 }
rt300@24 305 //--------------------------------------------------------------
rt300@24 306 void testApp::showIntro(){
rt300@24 307 paused = true;
rt300@24 308 consentGiven = false;
rt300@24 309 cout << "SHOW INTRO\n";
rt300@24 310
rt300@24 311 introViewController = [[IntroViewController alloc] initWithNibName:@"IntroViewController" bundle:nil];
rt300@24 312 [ofxiPhoneGetGLParentView() addSubview:introViewController.view];
rt300@24 313
rt300@24 314 [introViewController setAppRef:(id)this];
rt300@24 315 [introViewController show:(id)this];
rt300@24 316
rt300@24 317
rt300@24 318 whichInterfaceShowing = INTRO;
rt300@24 319
rt300@24 320 }
rt300@24 321 //--------------------------------------------------------------
rt300@24 322 void testApp::introHidden(bool OK){
rt300@24 323 if(OK){
rt300@24 324 paused = false;
rt300@24 325 consentGiven = true;
rt300@24 326 whichInterfaceShowing = BOTH;
rt300@24 327 }
rt300@24 328 // no unOK
rt300@24 329 }
rt300@24 330 //--------------------------------------------------------------
rt300@24 331 // called from BottomTabViewController iOS segmented thing
rt300@24 332 void testApp::interfaceSelected(int which){
rt300@24 333 switch (which){
rt300@24 334 case 0:
rt300@24 335
rt300@24 336 whichInterfaceShowing = SLIDERS;
rt300@24 337 sliderGUI->setVisible(true);
rt300@24 338 // set the slider values to stuff got from zoomer
rt300@24 339 sliderVals = theGridView.getParams();
rt300@24 340 setAllGUISliders(sliderVals);
rt300@24 341 break;
rt300@24 342 case 1:
rt300@24 343
rt300@24 344 whichInterfaceShowing = BOTH;
rt300@24 345 sliderGUI->setVisible(true);
rt300@24 346 // set the slider values to stuff got from zoomer
rt300@24 347 sliderVals = theGridView.getParams();
rt300@24 348 setAllGUISliders(sliderVals);
rt300@24 349 break;
rt300@24 350 case 2:
rt300@24 351
rt300@24 352 sliderGUI->setVisible(false);
rt300@24 353 whichInterfaceShowing = ZOOMER;
rt300@24 354 break;
rt300@24 355 }
rt300@24 356
rt300@24 357 }
rt300@24 358 //--------------------------------------------------------------
rt300@24 359 //--------------------------------------------------------------
rt300@24 360 void testApp::setupSliderGui(){
rt300@24 361 float xInit = OFX_UI_GLOBAL_WIDGET_SPACING;
rt300@24 362 float length = SLIDER_GUI_WIDTH - (OFX_UI_GLOBAL_WIDGET_SPACING*2);
rt300@24 363
rt300@24 364
rt300@24 365 //float dim = 42;
rt300@24 366
rt300@24 367 // make this iphone size...?
rt300@24 368 int height = 480;
rt300@24 369 int width = 320;
rt300@24 370 float dim = (height-10.0*OFX_UI_GLOBAL_WIDGET_SPACING)/10.0;
rt300@24 371 // LEFT GUI
rt300@24 372 sliderGUI = new ofxUICanvas(0,100,SLIDER_GUI_WIDTH,getHeight());
rt300@24 373
rt300@24 374 // Uh.. loop this
rt300@24 375 for(int i = 1; i<=10;i++){
rt300@24 376
rt300@24 377 ofxUISlider *slider;
rt300@24 378 slider = (ofxUISlider *)sliderGUI->addWidgetDown(new ofxUISlider(width,dim,0.0,127,64,sliderParamNames[i-1]));
rt300@24 379 slider->setDrawPadding(true);
rt300@24 380 if(i <= 5){
rt300@24 381 slider->setColorFill(ofColor(0,0,255));
rt300@24 382 slider->setColorFillHighlight(ofColor(0,0,255));
rt300@24 383 }else{
rt300@24 384 slider->setColorFill(ofColor(255,0,0));
rt300@24 385 slider->setColorFillHighlight(ofColor(255,0,0));
rt300@24 386 }
rt300@24 387
rt300@24 388 sliders.push_back(slider);
rt300@24 389 }
rt300@24 390
rt300@24 391
rt300@24 392
rt300@24 393 ofAddListener(sliderGUI->newGUIEvent, this, &testApp::sliderGUIEvent);
rt300@24 394
rt300@24 395 }
rt300@24 396 //--------------------------------------------------------------
rt300@24 397 void testApp::sliderGUIEvent(ofxUIEventArgs &e){
rt300@24 398 if(whichInterfaceShowing == ZOOMER){
rt300@24 399 cout << "GUI ERROR";
rt300@24 400 return;
rt300@24 401 }
rt300@24 402
rt300@0 403 // "normal" parameter changes
rt300@0 404 for(int i = 1; i<=10;i++){
rt300@0 405
rt300@24 406 if(e.widget->getName() == sliderParamNames[i-1])
rt300@0 407 {
rt300@0 408 //cout << "param change: " << p;
rt300@0 409 ofxUISlider *slider = (ofxUISlider *) e.widget;
rt300@3 410 sliderMoved(i-1,slider->getScaledValue()); // internal array 0 indexed
rt300@0 411 }
rt300@0 412 }
rt300@24 413
rt300@0 414 }
rt300@0 415 //--------------------------------------------------------------
rt300@3 416 void testApp::sliderMoved(int which, float value){
rt300@3 417 // an update caused by slider view being touched
rt300@0 418 sliderVals[which] = (int)value;
rt300@0 419 theGridView.setParams(sliderVals);
rt300@24 420
rt300@3 421 sendParametersToPD();
rt300@5 422
rt300@9 423 eventLogger.logEvent(CHANGE_SLIDER, TwoVector(),0.0,which , value);
rt300@5 424
rt300@0 425 }
rt300@0 426 //--------------------------------------------------------------
rt300@3 427 void testApp::setAllGUISliders(vector<int> vals){
rt300@3 428 // an update caused by zoomer view being moved
rt300@0 429 for(int i = 0; i<10;i++){
rt300@0 430 sliders[i]->setValue(vals[i]);
rt300@1 431 sliderVals[i] = vals[i];
rt300@0 432 }
rt300@3 433
rt300@0 434 }
rt300@0 435 //--------------------------------------------------------------
rt300@3 436 void testApp::sendParametersToPD(){
rt300@3 437 // frequencer stuff to get 16 steps
rt300@3 438 vector<double> vals;
rt300@3 439
rt300@3 440
rt300@3 441 vals.push_back((sliderVals[0]+32)*8.); // DC offset
rt300@3 442 for(int i=1; i<5;i++){
rt300@3 443 vals.push_back((sliderVals[i] - 64)*2.);
rt300@3 444 }
rt300@3 445
rt300@3 446 vector<double> steps = frequencer.freqMagEdit(freqIndexes, vals);
rt300@3 447 // send a list using the List object
rt300@3 448 List seqSteps;
rt300@3 449
rt300@3 450 seqSteps.addSymbol("seqSteps");
rt300@3 451 for(int i=0; i < 16; i++){
rt300@3 452 seqSteps.addFloat(round(steps[i])); // rounding here??
rt300@3 453 }
rt300@3 454
rt300@3 455 core.pd.sendList("fromOF", seqSteps);
rt300@8 456
rt300@3 457 sendOscShape(sliderVals[5]);
rt300@3 458 sendFiltType(sliderVals[6]);
rt300@3 459 sendFiltFreq(sliderVals[7]);
rt300@3 460 sendEnvShape(sliderVals[8]);
rt300@3 461 sendModFreq(sliderVals[9]);
rt300@3 462
rt300@3 463 }
rt300@8 464 //--------------------------------------------------------------
rt300@3 465 #pragma mark STANDARD OF FUNCTIONS
rt300@3 466 //--------------------------------------------------------------
rt300@0 467 void testApp::update(){
rt300@0 468 //we do a heartbeat on iOS as the phone will shut down the network connection to save power
rt300@0 469 //this keeps the network alive as it thinks it is being used.
rt300@16 470 if(paused) return;
rt300@16 471
rt300@0 472 if( ofGetFrameNum() % 120 == 0 ){
rt300@0 473 ofxOscMessage m;
rt300@0 474 m.setAddress( "/misc/heartbeat" );
rt300@0 475 m.addIntArg( ofGetFrameNum() );
rt300@0 476 sender.sendMessage( m );
rt300@0 477 }
rt300@0 478
rt300@5 479 // continiue to move at velocity, unless snapped
rt300@3 480
rt300@3 481 if (numActiveTouches == 0){ // no touches, use momentum
rt300@3 482
rt300@22 483 if(moveVel.norm() > 0.3){
rt300@22 484 if(theGridView.snapped){
rt300@22 485 // stop it, send snap event
rt300@22 486 moveVel.setCoord(0.0,0.0);
rt300@22 487 }else{
rt300@22 488 theGridView.move(moveVel);
rt300@22 489 moveVel = moveVel*slowFactor;
rt300@22 490 }
rt300@3 491 // and get new parameter values
rt300@5 492 setAllGUISliders(theGridView.getParams());
rt300@3 493 sendParametersToPD();
rt300@22 494 }else if(moveVel.norm() > 0.01){ // and less than 0.3
rt300@3 495 // stop it
rt300@3 496 moveVel.setCoord(0.0,0.0);
rt300@5 497 setAllGUISliders(theGridView.getParams());
rt300@3 498 sendParametersToPD();
rt300@5 499 eventLogger.logEvent(SCROLL_STOPPED, theGridView.getCoord() );
rt300@22 500
rt300@3 501 }else{
rt300@3 502 // stopped - do nothing
rt300@3 503 }
rt300@3 504
rt300@0 505 }
rt300@0 506 // continiue to zoom at velocity
rt300@0 507 if (numActiveTouches < 2 && abs(zoomVel)>0.001){
rt300@0 508 theGridView.zoom(zoomVel + 1.0); // +1 because zoomVel factor is + or - , wheras zoom is a multiplier near 1
rt300@0 509 zoomVel = zoomVel*slowFactor;
rt300@0 510 }
rt300@6 511
rt300@0 512 }
rt300@0 513 //--------------------------------------------------------------
rt300@0 514 void testApp::sendOSCParams(){
rt300@0 515
rt300@0 516 vector<int> params = theGridView.getParams(); // FILTER HERE? NEED FLOATS...
rt300@0 517 vector<int>::iterator iter = params.begin();
rt300@0 518
rt300@0 519 ofxOscMessage m;
rt300@0 520 m.setAddress( "p" );
rt300@0 521
rt300@0 522 for(;iter < params.end();iter++){
rt300@0 523
rt300@0 524 m.addFloatArg( *iter );
rt300@0 525
rt300@0 526 }
rt300@0 527 sender.sendMessage( m );
rt300@0 528 }
rt300@0 529 //--------------------------------------------------------------
rt300@0 530 void testApp::draw(){
rt300@16 531 if(paused) return;
rt300@24 532
rt300@24 533 switch (whichInterfaceShowing){
rt300@24 534 case SLIDERS:
rt300@24 535 break;
rt300@24 536 case ZOOMER:
rt300@24 537 theGridView.draw();
rt300@24 538 break;
rt300@24 539 case BOTH:
rt300@24 540
rt300@24 541 theGridView.draw();
rt300@24 542 break;
rt300@24 543 case INTRO:
rt300@24 544 break;
rt300@24 545
rt300@24 546 case QUESTIONNAIRE:
rt300@24 547 break;
rt300@24 548
rt300@0 549 }
rt300@16 550
rt300@4 551
rt300@0 552 }
rt300@0 553
rt300@0 554 //--------------------------------------------------------------
rt300@0 555 void testApp::touchDown(ofTouchEventArgs &touch){
rt300@24 556
rt300@24 557 // TODO check if in gui area!!!
rt300@24 558 if(whichInterfaceShowing == SLIDERS){
rt300@24 559 return;
rt300@24 560 }else if (whichInterfaceShowing == BOTH && touch.x < (SLIDER_GUI_WIDTH+10)){
rt300@24 561 return;
rt300@24 562
rt300@24 563 }// otherwise we're good to let the zoomer handle touch
rt300@0 564
rt300@0 565 numActiveTouches++;
rt300@0 566 // absolute position doesn't matter
rt300@0 567 // which one?
rt300@0 568 if(touch.id == 0){
rt300@0 569 touch0.setCoord(touch.x,touch.y);
rt300@0 570 prevTouch0 = touch0;
rt300@0 571 }else if(touch.id == 1){
rt300@0 572
rt300@0 573 touch1.setCoord(touch.x,touch.y);
rt300@0 574 prevTouch1 = touch1;
rt300@0 575
rt300@0 576 }
rt300@0 577 if(numActiveTouches == 1){
rt300@0 578 moveVel.setCoord(0.0, 0.0);
rt300@0 579 prevMove.setCoord(0.0, 0.0);
rt300@0 580 prevMove2.setCoord(0.0, 0.0);
rt300@0 581 }else if(numActiveTouches == 2){
rt300@0 582 zoomVel = 0.0;
rt300@0 583 prevZoom = 0.0;
rt300@0 584 prevZoom2 = 0.0;
rt300@0 585 double dist = touch1.distanceTo(touch0);
rt300@0 586 prevDist = dist;
rt300@0 587 }
rt300@0 588
rt300@0 589 }
rt300@0 590
rt300@0 591 //--------------------------------------------------------------
rt300@0 592 void testApp::touchMoved(ofTouchEventArgs &touch){
rt300@1 593
rt300@24 594 // TODO check if in gui area!!!
rt300@24 595 if(whichInterfaceShowing == SLIDERS){
rt300@24 596 return;
rt300@24 597 }else if (whichInterfaceShowing == BOTH && touch.x < (SLIDER_GUI_WIDTH+10)){
rt300@24 598 return;
rt300@24 599
rt300@24 600 }// otherwise we're good to let the zoomer handle touch
rt300@24 601
rt300@1 602
rt300@7 603 // check if in other gui area
rt300@16 604 if(touch.x > getWidth()-200 && touch.y < 300){
rt300@7 605 return;
rt300@7 606 }
rt300@0 607
rt300@1 608 // which one? keep track of each touch point
rt300@0 609 if(touch.id == 0){
rt300@0 610 touch0.setCoord(touch.x,touch.y);
rt300@0 611
rt300@0 612 }else if(touch.id == 1){
rt300@0 613
rt300@0 614 touch1.setCoord(touch.x,touch.y);
rt300@0 615 }
rt300@0 616
rt300@1 617 if(numActiveTouches == 1){
rt300@0 618
rt300@1 619 handleScroll();
rt300@0 620 }else if(numActiveTouches == 2){
rt300@1 621 handleZoom();
rt300@0 622
rt300@0 623 }
rt300@0 624 prevTouch0 = touch0;
rt300@0 625
rt300@0 626
rt300@0 627 }
rt300@5 628
rt300@1 629 //--------------------------------------------------------------
rt300@1 630 void testApp::handleScroll(){
rt300@6 631
rt300@1 632 TwoVector move = touch0 - prevTouch0;
rt300@5 633 if(yLocked){
rt300@5 634 move.y = 0.0;
rt300@5 635 }
rt300@5 636 if(xLocked){
rt300@5 637 move.x = 0.0;
rt300@5 638 }
rt300@5 639
rt300@6 640 // check time since last move - if
rt300@6 641 unsigned int moveTime = ofGetSystemTimeMicros();
rt300@6 642 if(moveTime - lastMoveTime > 100000){
rt300@6 643 moveVel = TwoVector(); // zero
rt300@6 644 }else{
rt300@6 645 moveVel = (move*0.3 + prevMove*0.34 + prevMove2*0.38); // use the time
rt300@6 646
rt300@6 647 }
rt300@6 648 lastMoveTime = moveTime;
rt300@6 649
rt300@5 650
rt300@1 651 prevMove2 = prevMove;
rt300@1 652 prevMove = move;
rt300@1 653
rt300@5 654
rt300@3 655 theGridView.move(move);
rt300@3 656
rt300@3 657 // and get new parameter values
rt300@3 658 setAllGUISliders(theGridView.getParams());
rt300@3 659 sendParametersToPD();
rt300@1 660 }
rt300@1 661 //--------------------------------------------------------------
rt300@1 662 void testApp::handleZoom(){
rt300@1 663 // work out change in difference
rt300@1 664 double dist = touch1.distanceTo(touch0);
rt300@1 665 double zoomFactor = prevDist/dist;
rt300@1 666
rt300@1 667 //TODO check for sensible maximums, e.g. spurious touch data
rt300@1 668 if(zoomFactor > 2.0 || zoomFactor < 0.5){
rt300@1 669 cout << "Zoom too much!!!!" << zoomFactor;
rt300@1 670 zoomFactor = 1.0;
rt300@1 671 }
rt300@1 672
rt300@1 673 zoomVel = (zoomFactor-1)*0.3 + prevZoom*0.34 + prevZoom2*0.38;
rt300@1 674 prevZoom2 = prevZoom;
rt300@1 675 prevZoom = (zoomFactor-1);
rt300@1 676
rt300@1 677 theGridView.zoom(zoomFactor);
rt300@1 678
rt300@1 679 prevDist = dist;
rt300@3 680
rt300@1 681 }
rt300@0 682 //--------------------------------------------------------------
rt300@0 683 void testApp::touchUp(ofTouchEventArgs &touch){
rt300@1 684 if(numActiveTouches > 0) numActiveTouches--; // dirty
rt300@1 685
rt300@24 686 // TODO check if in gui area!!!
rt300@24 687 if(whichInterfaceShowing == SLIDERS){
rt300@24 688 return;
rt300@24 689 }else if (whichInterfaceShowing == BOTH && touch.x < 256){
rt300@24 690 return;
rt300@1 691
rt300@24 692 }// otherwise we're good to let the zoomer handle touch
rt300@24 693
rt300@1 694
rt300@0 695 // which one?
rt300@0 696 if(touch.id == 0){
rt300@0 697 // tricky situation - we tried to zoom but may have left non-move finger on
rt300@0 698 prevTouch0.setCoord(touch.x,touch.y);
rt300@0 699
rt300@0 700 }else if(touch.id == 1){
rt300@0 701
rt300@0 702
rt300@0 703 prevTouch1.setCoord(0,0);
rt300@6 704
rt300@6 705 }
rt300@6 706 if(numActiveTouches == 0){
rt300@6 707 // check time since last move
rt300@6 708 // check time since last move - if
rt300@6 709 unsigned int moveTime = ofGetSystemTimeMicros();
rt300@6 710 if(moveTime - lastMoveTime > 100000){
rt300@6 711 moveVel = TwoVector(); // zero
rt300@6 712 }else{
rt300@6 713 moveVel = (move*0.3 + prevMove*0.34 + prevMove2*0.38); // use the time
rt300@6 714
rt300@6 715 }
rt300@6 716 lastMoveTime = moveTime;
rt300@0 717 }
rt300@0 718
rt300@0 719 }
rt300@0 720
rt300@0 721 //--------------------------------------------------------------
rt300@0 722 void testApp::touchDoubleTap(ofTouchEventArgs &touch){
rt300@0 723 // preset?
rt300@0 724
rt300@0 725 }
rt300@0 726
rt300@0 727 //--------------------------------------------------------------
rt300@0 728 void testApp::lostFocus(){
rt300@0 729
rt300@0 730 }
rt300@0 731
rt300@0 732 //--------------------------------------------------------------
rt300@0 733 void testApp::gotFocus(){
rt300@0 734
rt300@0 735 }
rt300@0 736
rt300@0 737 //--------------------------------------------------------------
rt300@0 738 void testApp::gotMemoryWarning(){
rt300@0 739
rt300@0 740 }
rt300@0 741
rt300@0 742 //--------------------------------------------------------------
rt300@0 743 void testApp::deviceOrientationChanged(int newOrientation){
rt300@16 744 /*
rt300@0 745 cout << "orientation: " << newOrientation;
rt300@15 746
rt300@0 747 if(newOrientation == 4){
rt300@16 748 ofxiPhoneSetOrientation( OF_ORIENTATION_DEFAULT );
rt300@16 749
rt300@0 750 }else if(newOrientation == 3){
rt300@0 751 ofxiPhoneSetOrientation( OF_ORIENTATION_90_LEFT );
rt300@16 752 }else if(newOrientation == 3){
rt300@16 753 ofxiPhoneSetOrientation( OF_ORIENTATION_90_LEFT );
rt300@16 754 }
rt300@16 755
rt300@16 756
rt300@16 757 [ofxiPhoneGetGLView() updateDimensions];
rt300@16 758 */
rt300@0 759 }
rt300@0 760
rt300@0 761
rt300@0 762 //--------------------------------------------------------------
rt300@0 763 void testApp::touchCancelled(ofTouchEventArgs& args){
rt300@0 764
rt300@0 765 }
rt300@3 766 //---------------------------------------------------------------
rt300@3 767 // AUDIO STUFF
rt300@3 768 //---------------------------------------------------------------
rt300@3 769
rt300@3 770 #pragma mark AUDIO STREAMS
rt300@3 771 //--------------------------------------------------------------
rt300@3 772 void testApp::audioReceived(float * input, int bufferSize, int nChannels) {
rt300@3 773 core.audioReceived(input, bufferSize, nChannels);
rt300@3 774 }
rt300@3 775
rt300@3 776 void testApp::audioRequested(float * output, int bufferSize, int nChannels) {
rt300@3 777 core.audioRequested(output, bufferSize, nChannels);
rt300@3 778 }
rt300@3 779 //---------------------------------------------------------------
rt300@3 780 #pragma mark UTILITIES
rt300@0 781
rt300@0 782 // 5hz cut off
rt300@0 783 const double fB[3] = {0.049489956268677, 0.098979912537354, 0.049489956268677};
rt300@0 784
rt300@0 785 const double fA[3] = {1.000000000000000, -1.279632424997809, 0.477592250072517};
rt300@0 786
rt300@0 787 // 1hz cut off
rt300@0 788 //const double fB[3] = {0.002550535158536, 0.005101070317073, 0.002550535158536};
rt300@0 789
rt300@0 790 //const double fA[3] = {1.000000000000000, -1.852146485395936, 0.862348626030081};
rt300@0 791
rt300@0 792
rt300@0 793 //a(1)*y(n) = b(1)*x(n) + b(2)*x(n-1) + ... + b(nb+1)*x(n-nb)- a(2)*y(n-1) - ... - a(na+1)*y(n-na)
rt300@0 794 //---------------------------------------------------------------
rt300@0 795 vector<float> testApp::vectorFilter(vector<float> newVec){
rt300@0 796 static vector<float> x0(10,0);
rt300@0 797 static vector<float> x1(10,0);
rt300@0 798 static vector<float> x2(10,0);
rt300@0 799 static vector<float> y0(10,0);
rt300@0 800 static vector<float> y1(10,0);
rt300@0 801 static vector<float> y2(10,0);
rt300@0 802
rt300@0 803 x0 = newVec;
rt300@0 804
rt300@0 805 // this low passes a bunch of params values all at once
rt300@0 806 int sz = newVec.size();
rt300@0 807 for(int i=0; i<sz; i++){
rt300@0 808 y0[i] = fB[0]*x0[i] + fB[1]*x1[i] + fB[2]*x2[i] - fA[1]*y1[i] - fA[2]*y2[i];
rt300@0 809 }
rt300@0 810 // shift
rt300@0 811 x2 = x1;
rt300@0 812 x1 = x0;
rt300@0 813 y2 = y1;
rt300@0 814 y1 = y0;
rt300@0 815
rt300@0 816 return y0;
rt300@2 817 }
rt300@24 818 float ctrlSmoother(float newsamp){
rt300@24 819 static float x1,x2,y1,y2;
rt300@24 820 float x0, y0;
rt300@24 821
rt300@24 822 x0 = newsamp;
rt300@24 823
rt300@24 824 y0 = fB[0]*x0 + fB[1]*x1 + fB[2]*x2 - fA[1]*y1 - fA[2]*y2;
rt300@24 825
rt300@24 826 // shift
rt300@24 827 x2 = x1;
rt300@24 828 x1 = x0;
rt300@24 829 y2 = y1;
rt300@24 830 y1 = y0;
rt300@24 831
rt300@24 832 return y0;
rt300@24 833 }
rt300@8 834 //---------------------------------------------------------------
rt300@3 835 void testApp::sendOscShape(int ctrlin){
rt300@3 836
rt300@3 837 static int numpoints = 5;
rt300@3 838 static int numcontrols = 5;
rt300@3 839 //float values[points][controls] =
rt300@3 840 float ctrlout[numcontrols];
rt300@3 841 string ctrlName[5] = {"pWidth" , "sqVol", "sawVol", "sineVol", "FMAmt"};
rt300@3 842 float values[5][5] =
rt300@3 843 {{0.5, 0., 0., 1., 1.}, // 0
rt300@3 844 {0.5, 0., 0., 1., 0.}, // 32
rt300@3 845 {0.5, 0., 1., 0., 0.}, // 64
rt300@3 846 {0.5, 1., 1., 0., 0.}, // 96
rt300@3 847 {0.01,1., 1., 0., 0.}}; // 127
rt300@3 848
rt300@3 849 float fidx = (numpoints-1)*ctrlin/128.;
rt300@3 850 int idx = floor(fidx);
rt300@3 851 float frac = fidx - idx;
rt300@3 852 for(int i=0; i < numcontrols; i++){
rt300@3 853 ctrlout[i] = (1 - frac)*values[idx][i] + (frac)*values[idx+1][i];
rt300@3 854 // send to PD
rt300@3 855 List toPD;
rt300@3 856
rt300@3 857 toPD.addSymbol(ctrlName[i]);
rt300@3 858 toPD.addFloat(ctrlout[i]); // rounding here??
rt300@3 859
rt300@3 860 core.pd.sendList("fromOF", toPD);
rt300@3 861 //cout << ctrlName[i] << "sending" << ctrlout[i] << "\n";
rt300@3 862 }
rt300@3 863
rt300@2 864 }
rt300@8 865 //---------------------------------------------------------------
rt300@3 866 void testApp::sendFiltType(int ctrlin){
rt300@3 867 static int numpoints = 3;
rt300@3 868 static int numcontrols = 4;
rt300@3 869 //float values[points][controls] =
rt300@3 870 float ctrlout[numcontrols];
rt300@3 871 string ctrlName[4] = {"lpLev" , "bpLev", "hpLev", "reson"};
rt300@3 872 float values[3][4] =
rt300@24 873 {{2., 0., 0., 1.}, // 0
rt300@24 874 {0., 10., 0., 10.}, // 64
rt300@24 875 {0., 0., 1., 1.}}; // 127
rt300@3 876
rt300@3 877 float fidx = (numpoints-1)*ctrlin/128.;
rt300@3 878 int idx = floor(fidx);
rt300@3 879 float frac = fidx - idx;
rt300@3 880 for(int i=0; i < numcontrols; i++){
rt300@3 881 ctrlout[i] = (1 - frac)*values[idx][i] + (frac)*values[idx+1][i];
rt300@3 882 // send to PD
rt300@3 883 List toPD;
rt300@3 884
rt300@3 885 toPD.addSymbol(ctrlName[i]);
rt300@3 886 toPD.addFloat(ctrlout[i]); // rounding here??
rt300@3 887
rt300@3 888 core.pd.sendList("fromOF", toPD);
rt300@3 889 //cout << ctrlName[i] << "sending" << ctrlout[i] << "\n";
rt300@3 890 }
rt300@2 891 }
rt300@8 892 //---------------------------------------------------------------
rt300@3 893 void testApp::sendFiltFreq(int ctrlin){
rt300@24 894 // smooth this
rt300@24 895 float fin = ctrlin;
rt300@24 896 float fout;
rt300@24 897 fout = (int)ctrlSmoother(fin);
rt300@3 898 List toPD;
rt300@3 899
rt300@3 900 toPD.addSymbol("filtFreq");
rt300@24 901 toPD.addFloat(fout);
rt300@3 902
rt300@3 903 core.pd.sendList("fromOF", toPD);
rt300@3 904 }
rt300@8 905 //---------------------------------------------------------------
rt300@3 906 void testApp::sendEnvShape(int ctrlin){
rt300@3 907 static int numpoints = 5;
rt300@3 908 static int numcontrols = 3;
rt300@3 909 //float values[points][controls] =
rt300@3 910 float ctrlout[numcontrols];
rt300@3 911 string ctrlName[3] = {"attack" , "decay", "sustain"};
rt300@3 912 float values[5][3] =
rt300@3 913 {{0., 0., 0.}, // 0
rt300@3 914 {0., 0.5, 0.}, // 32
rt300@3 915 {0.0, 1., 0.8}, // 64
rt300@3 916 {0.99, 0.3, 0.}, // 96
rt300@3 917 {0.3, 0.1, 0.}}; // 127
rt300@3 918
rt300@3 919 float fidx = (numpoints-1)*ctrlin/128.;
rt300@3 920 int idx = floor(fidx);
rt300@3 921 float frac = fidx - idx;
rt300@3 922 for(int i=0; i < numcontrols; i++){
rt300@3 923 ctrlout[i] = (1 - frac)*values[idx][i] + (frac)*values[idx+1][i];
rt300@3 924 // send to PD
rt300@3 925 List toPD;
rt300@3 926
rt300@3 927 toPD.addSymbol(ctrlName[i]);
rt300@3 928 toPD.addFloat(ctrlout[i]); // rounding here??
rt300@3 929
rt300@3 930 core.pd.sendList("fromOF", toPD);
rt300@3 931 //cout << ctrlName[i] << "sending" << ctrlout[i] << "\n";
rt300@3 932 }
rt300@3 933 }
rt300@8 934 //---------------------------------------------------------------
rt300@3 935 void testApp::sendModFreq(int ctrlin){
rt300@3 936 float fm = ctrlin/127.;
rt300@3 937 List toPD;
rt300@3 938
rt300@3 939 toPD.addSymbol("FMFreq");
rt300@3 940 toPD.addFloat(fm); // rounding here??
rt300@3 941
rt300@3 942 core.pd.sendList("fromOF", toPD);
rt300@8 943 }
rt300@8 944 //---------------------------------------------------------------