changeset 35:790939017078

V0.5. Now uses new continuous hilbert curve. HOORAY.
author Robert Tubb <rt300@eecs.qmul.ac.uk>
date Mon, 08 Apr 2013 17:23:13 +0100
parents 94df2cd72d7b
children a42903c61558
files AppCore.mm BottomTabViewController.h eventLogger.h eventLogger.mm grid.h grid.mm hilbert.cpp hilbert.h presetManager.h presetManager.mm testApp.mm
diffstat 11 files changed, 157 insertions(+), 361 deletions(-) [+]
line wrap: on
line diff
--- a/AppCore.mm	Mon Apr 08 12:58:21 2013 +0100
+++ b/AppCore.mm	Mon Apr 08 17:23:13 2013 +0100
@@ -51,7 +51,7 @@
 	pd.start();
 
 	// open patch
-	Patch patch = pd.openPatch("mytest.pd");
+	Patch patch = pd.openPatch("synth5param.pd");
 	cout << patch << endl;
 
 
--- a/BottomTabViewController.h	Mon Apr 08 12:58:21 2013 +0100
+++ b/BottomTabViewController.h	Mon Apr 08 17:23:13 2013 +0100
@@ -15,6 +15,7 @@
 
 
 -(IBAction)show:(id)sender;
+-(IBAction)show:(id)sender withSelection:(NSInteger)sel;
 -(void)setAppRef:(id)theOFApp;
 - (IBAction)interfaceSelected:(id)sender;
 
--- a/eventLogger.h	Mon Apr 08 12:58:21 2013 +0100
+++ b/eventLogger.h	Mon Apr 08 17:23:13 2013 +0100
@@ -30,10 +30,10 @@
 
 #define EVENT_THIN_FACTOR 15
 #define EVENT_LOG_FILENAME "log.json"
-#define UPLOAD_CHUNK_SIZE 1000
+#define UPLOAD_CHUNK_SIZE 100
 #define APP_CREATION_TIME 381429000000   // milliseconds to the time i wrote this wee blighter. saves digits
 #define SCROLL_TRAIL_LENGTH 200
-#define PROGRAM_VERSION 0.4 // IMPORTANT TOCHNAGE!
+#define PROGRAM_VERSION 0.5 // NOW USES NEW HILBERT CURVE. ALL OLD PRESETS WILL BE INVALID :(
 
 #define SUPERVISED // this def will save files
 
--- a/eventLogger.mm	Mon Apr 08 12:58:21 2013 +0100
+++ b/eventLogger.mm	Mon Apr 08 17:23:13 2013 +0100
@@ -16,7 +16,7 @@
 extern PresetManager presetManager;
 //---------------------------------------------------------------------------
 void lEvent::draw(){
-    // can't draw lines you fool
+
     double size = 2.0;
     TwoVector pos = theGridView.coordToPixel(TwoVector(val1,val2)); // euch -rely on grid view?
     
@@ -268,6 +268,7 @@
 
 bool EventLogger::uploadEventLog(bool async){
     // COMMENT THIS OUTRT   !!!!!!!!
+    theEvents.clear();
     return false;
     // show indicator
     logUploadInProgress = true;
@@ -483,7 +484,7 @@
             break;
         case SNAPPED_TO_PRESET:
             theEvents.push_back(lEvent(evtType,centre.x,centre.y,sliderID));
-            cout << "SCROLL STOPPED EVENT\n";
+            cout << "Snapped EVENT\n";
             break;
         case SWAP_VIEW:
             theEvents.push_back(lEvent(evtType,0.0 , 0.0 , sliderID)); // slider ID is which view
@@ -555,8 +556,8 @@
     root["savedInteractionTime"] = savedInteractionTime;
     root["questionnaireCompleted"] = questionnaireCompleted;
     root["questionnaireUploaded"] = questionnaireUploaded;
-    root["questionnaire"] = questionnaireToJson();
-
+    if(!questionnaireUploaded) root["questionnaire"] = questionnaireToJson();
+    
     
     int i = 0;
     for(eventIter = theEvents.begin(); eventIter < theEvents.end(); eventIter++){
--- a/grid.h	Mon Apr 08 12:58:21 2013 +0100
+++ b/grid.h	Mon Apr 08 17:23:13 2013 +0100
@@ -42,8 +42,10 @@
     void setMinZoom();
     void setMaxZoom();
     
+    // HILBERT now does each coord for this
     vector<int> calculateParamsFromCoord(TwoVector coord) const;
     TwoVector calculateCoordFromParams(vector<int> params) const;
+
     TwoVector coordToPixel(TwoVector coord);
  
     // the inverse stuff
@@ -54,10 +56,13 @@
 
     const double maxValue;    // width of entire space
     const double minValue;    // smallest zoom
-    const int paramsPerDim; // no of parameters per dimension (
+    int paramsPerDim; // no of parameters per dimension (
+    int paramBitDepth; // number of bits for the parameter control data - i.e. always 7 for midi CC
+    /* HILBERT
+    
     int codeLength; // the 1d size of the code, determines max extent of single tile, related to params per dim
-    const int paramBitDepth; // number of bits for the parameter control data - i.e. always 7 for midi CC
     
+    */
 
     
     TwoVector topLeft; // top left corner of view, surface coords GUI
@@ -71,29 +76,31 @@
     Preset * closestPreset; // pointer to the currently selected (snapped to ) preset.. NULL if none.
     
     bool maxZoom, minZoom;
-    int cubeWidth;    // side of hypercube. 2 for binary coding.
 
+    /* HILBERT
     vector< vector<bool> > vcode; //
     vector<int> icode;
     vector<int> transSeq;
+     */
+    
     int midiCC[10]; // the actual params SHOULD BE INITED FROM 2*paramsPerDim
     
 // private functions
     
-    void makeCode();
+    // HILBERT void makeCode();
     void checkLimits();
     void viewWasChanged();
     void checkConsistencies();
     
-    vector<bool> intToGray(int num, int dimToTravel=3) const;
-    vector<int> coordTobase32(double coord) const;
-    vector<int> grayToMidi(vector<vector <bool> > grayCodes) const;
+    // HILBERT vector<bool> intToGray(int num, int dimToTravel=3) const;
+    // HILBERT vector<int> coordTobase32(double coord) const;
+    // HILBERT vector<int> grayToMidi(vector<vector <bool> > grayCodes) const;
     
     // the inverse stuff
-    int grayToInt(vector<bool>) const;
-    double base32toCoord(vector<int>) const;
-    vector<vector <bool> > midiToGray(vector<int>) const;
-    vector<int> codesToBase32(vector<vector<bool> >) const;
+    // HILBERT int grayToInt(vector<bool>) const;
+    // HILBERT double base32toCoord(vector<int>) const;
+    // HILBERT vector<vector <bool> > midiToGray(vector<int>) const;
+    // HILBERT vector<int> codesToBase32(vector<vector<bool> >) const;
     
     vector<int> walkDiff(vector<bool> left, vector<bool> right); // not used... not worth it!
     
--- a/grid.mm	Mon Apr 08 12:58:21 2013 +0100
+++ b/grid.mm	Mon Apr 08 17:23:13 2013 +0100
@@ -15,7 +15,7 @@
 extern EventLogger eventLogger;
 extern Hilbert hilbert;
 //--------------------------------------------------------------
-Grid::Grid(): maxValue(pow(32.0,7.0)-1), minValue(60),     paramsPerDim(5), paramBitDepth(7){
+Grid::Grid(): maxValue(pow(32.0,7.0)-1), minValue(30),     paramsPerDim(5), paramBitDepth(7){
 
 }
 //--------------------------------------------------------------
@@ -28,12 +28,11 @@
     maxZoom = false;
     minZoom = false;
 
-    codeLength = pow(2.0,paramsPerDim);
-    
     pixSize.setCoord(ofGetWidth(), ofGetHeight());
  
-    //set scale and position to mid way
+    //set scale and position to random
     scale = 15500.0;
+    
     snapDist = TwoVector(9,9);
     snapped = false;
     
@@ -42,8 +41,6 @@
     topLeft.setCoord(centre.x - size.x/2, centre.y - size.y/2);
 
     hilbert.init(paramBitDepth, paramsPerDim);
-    
-    makeCode();
 
     // set a starting param value, find coord that does it.
     vector<int> params(paramsPerDim*2);
@@ -51,141 +48,19 @@
         midiCC[i] = 12;
         params[i] = 12;
     }
+    
+    
     TwoVector coord = calculateCoordFromParams(params);
     setCoord(coord);
     
     viewWasChanged();
     
-    cout << "SIZEOF " << sizeof(long long);
-    
-    
 }
 
 template <typename T> int sgn(T val) {
     return (T(0) < val) - (val < T(0));
 }
-//--------------------------------------------------------------
-void Grid::makeCode(){
- 
-    ////////////////////////////////~~~,,,,,,,,.........
-    ////////// gray code generation
-    //////
-    ///
-    // TODO 5bit specific
-    // transition sequence.... what a palaver! only need to do once though.
-    
-    // max MRL
-    int trans[] = {0,1,2,3,0,4,2,1,0,3,2,1,0,4,2,3,0,1,2,3,0,4,2,1,0,3,2,1,0,4,2,3};
-    // balanced
-    int transB[] = {1,2,3,4,5,1,5,2,3,5,2,4,2,3,4,1,4,3,2,3,1,5,3,4,1,5,2,5,3,4,1,3};
-    for(int i = 0; i<codeLength; i++){
-        transB[i] = transB[i] - 1;
-    }
-    
-    int code[codeLength][paramsPerDim]; // start with normal array
-    
-   
-    
-    for(int j=0; j<paramsPerDim; j++){
-        code[0][j] = 0;
-    }
-    
-    for(int i=0; i < codeLength-1; i++){  // don't need last 3
-        transSeq.push_back(trans[i]); // member vector
-        for(int j=0; j<paramsPerDim; j++){
-            
-            if (j == abs(trans[i])){
-                code[i+1][j] = !code[i][j];
-            }else{
-                code[i+1][j] = code[i][j]; 
-            }
-        }
 
-    }
-    
-    for(int i=0; i < codeLength; i++){ // fill vector
-        
-        vcode.push_back(vector<bool>());
-        
-        for(int j=0; j<paramsPerDim; j++){
-            vcode[i].push_back(code[i][j]);
-        }
-    }
-    /*
-    // now try with iterators to print...
-    vector< vector<bool> >::iterator cit;
-    //vector<bool>::iterator bit;
-    vector<bool>::iterator bit;
-    int i = 0;
-    for(cit=vcode.begin(); cit!=vcode.end() ; cit++){ // fill vector
-        i++;
-        cout << i << " = ";
-        bit = (*cit).begin();
-        for(bit=(*cit).begin(); bit!=(*cit).end() ; bit++){
-            
-            cout  << *bit;
-        }
-        cout << "\n";
-
-    }
-    
-    // codeToInt unit test
-    vector<bool> aCode = vcode[12];
-    int result = grayToInt(aCode);
-    cout << "GRAY TO INT : " << result << "\n";
-
-    cout << "-------------------------------\n";
-    
-    // base32toFloat unit test
-
-    vector<int> test32 = coordTobase32(869437.0);
-    double cresult = base32toCoord(test32);
-    cout << "base32toCoord : " << cresult << "\n";
-     
-     cout << "-------------------------------\n";
-    
-    
-    
-    // midiToGray unit test
-
-    vector<vector<bool> > incodes(paramBitDepth, vector<bool>(paramsPerDim));
-    for(int i=0;i<7;i++){
-        incodes[i] = vcode[i+5];
-    }
-
-    vector<int> midiTest;
-    midiTest = grayToMidi(incodes);
-    vector<vector<bool> > outcodes = midiToGray(midiTest);
-    
-    vector< vector<bool> >::iterator cit1;
-    //vector<bool>::iterator bit;
-    vector<bool>::iterator bit1;
-    cout << "midiToGray Unit test\n";
-    for(int i=0;i<paramBitDepth;i++){ // fill vector
-
-        for(int j=0;j<paramsPerDim;j++){
-            
-            cout  << (incodes[i][j] == outcodes[i][j]) << ",";
-        }
-        cout << "\n";
-        
-    }
-     cout << "-------------------------------\n";
-
-    
-    // whole process unit test(?)
-    
-    TwoVector inCoord(888999777,777666555);
-    vector<int> checkParam;
-    checkParam = calculateParamsFromCoord(inCoord);
-    for(int i=0; i<2*paramsPerDim;i++){
-        cout << checkParam[i] << "_";
-    }
-    TwoVector outCoord = calculateCoordFromParams(checkParam);
-    cout << "Unit TEst coord = " << outCoord.x << "," << outCoord.y << "\n";
-*/
-    
-}
 //--------------------------------------------------------------
 void Grid::draw(){  // draw lines
     // TODO too friggin long
@@ -430,7 +305,6 @@
 }
  //--------------------------------------------------------------
 void Grid::update(){  // ?
-    // "update" bit of a crap name - all we do here is calculate the dimension params from the x,y position
 
 
 }
@@ -510,7 +384,7 @@
         }
         snapCentre = closestPreset->coordinates;
         eventLogger.logEvent(SNAPPED_TO_PRESET, getCoord(),closestPreset->creationTime );
-        cout << "SNAPPED CHECK\n";
+        //cout << "SNAPPED CHECK\n";
     }else{
         snapped = false;
         closestPreset = NULL;
@@ -680,114 +554,41 @@
         ccValueX[i] = params[i];
         ccValueY[i] = params[i+paramsPerDim];
     }
-    vector<vector <bool> > codesX = midiToGray(ccValueX);
-    vector<vector <bool> > codesY = midiToGray(ccValueY);
-
-    vector<int> base32X = codesToBase32(codesX);
-    vector<int> base32Y = codesToBase32(codesY);
     
     TwoVector result;
-    result.x = base32toCoord(base32X);
-    result.y = base32toCoord(base32Y);
+    result.x = hilbert.calculateIndexFromParams(ccValueX);
+    result.y = hilbert.calculateIndexFromParams(ccValueY);
     return result;
 }
 
 //--------------------------------------------------------------
 vector<int> Grid::calculateParamsFromCoord(TwoVector coord) const{
-    // some arrays in reverse order of power from normal numbers!   1,2,4,
-    
-    // centre to base 32
+
     if (coord.x > maxValue || coord.y > maxValue){
         cout << "calculateParams Error: centre double value is too large" << "\n";
         vector<int> empty;
         return empty;
     }
-
-    //--------------------------
-    // X
-    vector<int> base32x = coordTobase32(coord.x); // 7 numbers from 0 to 31
-    vector<vector <bool> > grayCodesX;
-    
-    int size = base32x.size();
-    for(int i=0;i<size;i++){
-        grayCodesX.push_back(intToGray(base32x[i]));
-    }
-    
-    vector<int> result;
-    result = grayToMidi(grayCodesX);
-    //--------------------------
-    // AND FOR Y
-    vector<int> base32y = coordTobase32(coord.y);
-    vector<vector <bool> > grayCodesY;
-    
-    size = base32y.size();
-    for(int i=0;i<size;i++){
-        grayCodesY.push_back(intToGray(base32y[i]));
+    if (coord.x < 0 || coord.y < 0){
+        cout << "calculateParams Error: centre double value is negative" << "\n";
+        vector<int> empty;
+        return empty;
     }
 
+    // X
+    vector<int> resultX;
+    resultX = hilbert.calculateParamsFromIndex(coord.x);
+    // Y
     vector<int> resultY;
-    resultY = grayToMidi(grayCodesY);
+    resultY = hilbert.calculateParamsFromIndex(coord.y);
     
     // concatenate
+    vector<int> result = resultX;
+    
     result.insert( result.end(), resultY.begin(), resultY.end() );
     return result;
 }
-//-------------------------------------------------------------------
 
-// for 1 dimension!!! i.e. call this twice
-vector<int> Grid::grayToMidi(vector<vector <bool> > grayCodes) const{
-
-    // gray to midi CC values
-    // loop thru the scales to build up a CC number per dimension
-    int midiCCresult[paramsPerDim]; // TODO dims specific
-    for(int i=0;i<paramsPerDim;i++){
-        midiCCresult[i] = 0;
-    }
-    
-    int bin = 1;
-    bin = bin << grayCodes.size()-1;
-    
-    int midP = 0;
-    
-    vector<vector <bool> >::iterator piter = grayCodes.begin();
-    for(;piter < grayCodes.end();piter++){ // each lesser power of 2
-        midP = 0; // reset
-        vector<bool>::iterator diter = (*piter).begin();
-        for(; diter <= (*piter).end();diter++){ // each one is different dimension
-            int ig = int(*diter); // convert binary to int
-            //cout << "ig: " << ig;
-            midiCCresult[midP] += ig*bin; // mult by power of two
-            midP++;
-        }
-        bin = bin >> 1; // next power of 2 down
-        
-    }
-    
-    // put in vector
-    vector<int> result;
-    for(int i=0;i<paramsPerDim;i++){
-        result.push_back(midiCCresult[i]);
-    }
-    
-    return result;
-    
-    
-}
-
-
-//--------------------------------------------------------------
-
-vector<bool> Grid::intToGray(int num, int dimToTravel) const{
-
-    // dimToTravel - this is the dimension that we want the walk to traverse, i.e. the last non zero digit of the code
-    // so swap it for 3 to produce correct orientation
-
-    // just use look up table... until it gets huuuge.
-    vector<bool> grayCode = vcode[num];
-    grayCode[3] = vcode[num][dimToTravel];
-    grayCode[dimToTravel] = vcode[num][3];
-    return grayCode;
-}
 //--------------------------------------------------------------
 vector<int> Grid::walkDiff(vector<bool> left, vector<bool> right){
     // horrible
@@ -810,106 +611,6 @@
     
     return result;
 }
-
-//--------------------------------------------------------------
-/*
-breaks down float into a base 32 number (2^D)
-each of these is converted to gray code
-this is then converted to 10 parameters, where each 32-digit becomes separate power of 2
- so "zoom" grid 32-patches are converted to 2-scales. 1,2,4,8,16,32,64,(128?) biggest number is 32^7
-*/
-vector<int> Grid::coordTobase32(double value) const{
-    //double base = 32.0;
-    if(value < 0.0){
-        cout << "coordTobase32 error: input value is negative\n";
-        value = 0.0;
-    }else if(value > maxValue){
-        cout << "coordTobase32 error: input value too big!\n";
-    }
-    double rem, divdr = 0.0;
-    int digit32;
-
-    // what power of 32 to start at?
-    int maxpow = 7; // midi cc specific
-    vector<int> result; 
-
-    rem = value;
-    for(;maxpow >=0;maxpow--){
-        // repeatedly get digit and remainder. This is exactly what we're doing in draw !?... could put all this in one place?
-        divdr = pow((double)codeLength,(double)maxpow);
-        digit32 = floor(rem/divdr);
-        rem = rem - digit32*divdr; 
-        result.push_back(digit32);  // array, biggest index is smallest power
-    }
-    // at this point rem should be fractional... use for interp?
-
-    return result;
-}
-//--------------------------------------------------------------
-
-vector<int> Grid::codesToBase32(vector<vector<bool> > inCodes) const{
-    vector<int> result;
-    for(int i=0;i<paramBitDepth;i++){
-        result.push_back(grayToInt(inCodes[i]));
-    }
-    return result;
-}
-//--------------------------------------------------------------
-
-int Grid::grayToInt(vector<bool> incode) const{
-    // look for match in table
-    
-    int s = vcode.size();
-    
-    for(int i=0; i<s;i++){ // fill vector
-        if(vcode[i] == incode){
-            return i;
-        }
-        
-    }
-    cout << "grayToInt error: no matching code found!";
-    return -1;
-}
-//--------------------------------------------------------------
-double Grid::base32toCoord(vector<int> base32Digs) const{
-    // build up the big float from a base 32 number
-    double result = 0.0;
-   
-    // what power of 32 to start at?
-    int mpow = base32Digs.size() - 1; // should be 7...
-    
-    for(int p=0;p<=mpow;p++){ // biggest index is smallest power
-        result += ((double)base32Digs[p]) * pow(32.0, (double)mpow-p);
-  
-    }
-    return result;
-    
-}
-//--------------------------------------------------------------
-// for 1 dimension - takes in 5 cc params and outputs  7 codes 
-vector<vector <bool> > Grid::midiToGray(vector<int> ccValue) const{
-    int pow2 = 1 << (paramBitDepth-1);
-
-    vector<int> aCode(paramsPerDim);
-    vector<vector<int> > theXCodes(paramBitDepth,aCode);
-    
-    // build up binary gray code representations from the bits of the midi ccs
-
-    vector<vector<bool> > theCodes(paramBitDepth, vector<bool>(paramsPerDim));
-
-    // x
-    for(int p=0;p<paramBitDepth;p++){
-
-        for(int i=0;i<paramsPerDim;i++){
-            
-            bool bit = (pow2 == (ccValue[i] & pow2));
-            theCodes[p][i] = bit;
-        }
-        pow2 = pow2 >> 1;
-        
-    }
-    return theCodes;
-}
 //--------------------------------------------------------------
 //--------------------------------------------------------------
 //--------------------------------------------------------------
\ No newline at end of file
--- a/hilbert.cpp	Mon Apr 08 12:58:21 2013 +0100
+++ b/hilbert.cpp	Mon Apr 08 17:23:13 2013 +0100
@@ -58,10 +58,11 @@
         bin[i] = (number/(1 << pwr)) % 2;
         bin.push_back(0);
     }
-    
+    return bin;
     
     
 }
+//--------------------------------------------------------------------
 void printBool(vector <bool> vcode){
     vector<bool>::iterator bit;
 
@@ -83,7 +84,7 @@
     
     // whole process unit test(?)
     
-    unsigned long long inCoord = 888999777;
+    unsigned long long inCoord = 982635920;
     vector<int> checkParam;
     checkParam = calculateParamsFromIndex(inCoord);
     cout << "PARAMS: ";
@@ -92,7 +93,7 @@
     }
     cout << '\n';
     unsigned long long outCoord = calculateIndexFromParams(checkParam);
-    cout << "Unit TEst coord = " << outCoord << "\n";
+    cout << "UNIT TEST COORD = " << outCoord << "\n";
     
     
 }
@@ -196,11 +197,11 @@
         subindex = index >> blev*P;
         subindex = mask & subindex;
         
-        cout << "subindex: " << subindex << "\n";
+        //cout << "subindex: " << subindex << "\n";
         // which vertex corresponds to this index?
         if(subindex < theGrayCode.size()) vertex = theGrayCodeD[subindex];
 
-        cout << "rotated: " << vertex << "\n";
+        //cout << "rotated: " << vertex << "\n";
  
         
         //% inverse rotate this T_e,d
@@ -208,7 +209,7 @@
         directionInv = (P - direction - 2);
         vertex = rotate(vertex,entryPointInv,directionInv);
 
-        cout << "vertex: " << vertex << "\n";
+        //cout << "vertex: " << vertex << "\n";
         
         //% build up bits of params
      
@@ -224,7 +225,7 @@
         int lse2 = rotr(newe, P-direction-1,P);
         entryPoint = entryPoint ^ lse2;
         direction = (direction + newd + 1) % P;
-        cout << "------------\n";
+        //cout << "------------\n";
     }
 
     return params;
@@ -239,16 +240,16 @@
 
 
 //--------------------------------------------------------------------
-long long Hilbert::calculateIndexFromParams(vector<int> params){
+unsigned long long Hilbert::calculateIndexFromParams(vector<int> params){
     // set  %set start and direction of biggest cube
 
-    long long h = 0;
+    unsigned long long h = 0;
     
     unsigned int i;
     unsigned int entryPoint = 0;
     int direction = P - 1;
-    unsigned int vertex=0, subindex=0, newe=0, newd=0;
-    
+    unsigned int vertex=0,  newe=0, newd=0;
+    unsigned long long subindex; // needs to be long cos we lewt shift by alot
     vector<int> subindices;
 
     
@@ -262,14 +263,14 @@
             vertexb.push_back((params[i]/(1 << blev)) % 2);
             
         }
-        printBool(vertexb);
+        //printBool(vertexb);
         vertex = bin2dec(vertexb);
-        cout << "INV vertex: " << vertex << "\n";
+        //cout << "INV vertex: " << vertex << "\n";
         // rotate it
         vertex = rotate(vertex,entryPoint,direction);
         
         //    % get new index of thisun
-        cout << "INV rotated: " << vertex << "\n";
+        //cout << "INV rotated: " << vertex << "\n";
         
         
         for(i=0;i<codeLength;i++){
@@ -277,7 +278,7 @@
                 subindex = i;
             }
         }
-        cout << "INV subindex: " << subindex << "\n";
+        //cout << "INV subindex: " << subindex << "\n";
         // work out next rotations
         newe = entryVertices5[subindex];
         newd = rotations5[subindex];
@@ -289,7 +290,7 @@
         
         // now build up h from subindices
         h += subindex << (blev*P);
-        cout << "------------\n";
+        //cout << "------------\n";
     }
 
     return h;
--- a/hilbert.h	Mon Apr 08 12:58:21 2013 +0100
+++ b/hilbert.h	Mon Apr 08 17:23:13 2013 +0100
@@ -32,7 +32,7 @@
     void init(int N, int P);
     void makeCode();
     vector<int> calculateParamsFromIndex(unsigned long long coord);
-    long long calculateIndexFromParams(vector<int> params);
+    unsigned long long calculateIndexFromParams(vector<int> params);
     void makeRotationRules();
     int rotate(int vertex, int entryPoint, int direction);
     int rotateInverse(int vertex, int entryPoint, int direction) ;
--- a/presetManager.h	Mon Apr 08 12:58:21 2013 +0100
+++ b/presetManager.h	Mon Apr 08 17:23:13 2013 +0100
@@ -14,6 +14,7 @@
 #define __oscSenderExample__presetManager__
 
 #define PRESET_FILENAME "presets.json"
+#define PILOT_PRESET_FILENAME "pilot_presets.json"
 
 #include <iostream>
 #include <string>
--- a/presetManager.mm	Mon Apr 08 12:58:21 2013 +0100
+++ b/presetManager.mm	Mon Apr 08 17:23:13 2013 +0100
@@ -8,6 +8,8 @@
 
 #include "presetManager.h"
 
+
+
 //---------------------------------------------------------------------------
 extern Grid theGridView;
 PresetManager presetManager;
@@ -123,7 +125,7 @@
     stringstream fileText;
     string line;
     if(!theFile){
-        cout<<"can't find preset file \n";
+        cout<<"can't find preset file: " << jsonFile.c_str() << "\n";
         return;
     }else{
         
@@ -247,8 +249,13 @@
     // load file
 
     string fname = ofxiPhoneGetDocumentsDirectory() + PRESET_FILENAME;
+    readJsonToPresets(fname);
     
-    readJsonToPresets(fname);
+    string fullpath = ofFilePath::getAbsolutePath(ofToDataPath(PILOT_PRESET_FILENAME));
+	string file = ofFilePath::getFileName(fullpath);
+	string folder = ofFilePath::getEnclosingDirectory(fullpath);
+
+    readJsonToPresets(fullpath);
     
     timesOpened++;
 }
@@ -275,6 +282,7 @@
     presetFile << root;
     
 }
+
 //---------------------------------------------------------------------------
 void PresetManager::clearAll(){
     thePresets.clear();
--- a/testApp.mm	Mon Apr 08 12:58:21 2013 +0100
+++ b/testApp.mm	Mon Apr 08 17:23:13 2013 +0100
@@ -6,6 +6,7 @@
 extern PresetManager presetManager;
 extern EventLogger eventLogger;
 extern Frequencer frequencer;
+extern Hilbert hilbert;
 
 const vector<string> parameterNames;
 
@@ -13,6 +14,7 @@
 //const vector<const string> v(ra[0],ra[1]);
 
 
+
 //DeviceID3523537000
 //--------------------------------------------------------------
 void testApp::setup(){
@@ -132,7 +134,6 @@
     
     ofxiPhoneExternalDisplay::mirrorOn();
 
-    
 }
 
 
@@ -463,6 +464,12 @@
             theGridView.zoom(zoomVel + 1.0); // +1 because zoomVel factor is + or - , wheras zoom is a multiplier near 1
             zoomVel = zoomVel*slowFactor;
             moveVel.setCoord(0.0,0.0);; // don't move if zooming! Too many events!
+            
+            // need to do this if zoom goes to snap
+            if(theGridView.snapped){
+                setAllGUISliders(theGridView.getParams());
+                sendParametersToPD();
+            }
         }
         
         if(moveVel.norm() > 0.3){
@@ -486,12 +493,9 @@
         }else{
             // stopped - do nothing
         }
-        
-
 
     }
 
-
 }
 //--------------------------------------------------------------
 void testApp::sendOSCParams(){
@@ -660,6 +664,12 @@
     theGridView.zoom(zoomFactor);
     
     prevDist = dist;
+    
+    // need to do this if zoom goes to snap
+    if(theGridView.snapped){
+        setAllGUISliders(theGridView.getParams());
+        sendParametersToPD();
+    }
 
 }
 //--------------------------------------------------------------
@@ -812,6 +822,7 @@
     
     return y0;
 }
+//---------------------------------------------------------------
 float ctrlSmoother(float newsamp){
     static float x1,x2,y1,y2;
     float x0, y0;
@@ -830,6 +841,10 @@
 }
 //---------------------------------------------------------------
 void testApp::sendOscShape(int ctrlin){
+    if(ctrlin < 0 || ctrlin > 127){
+        cout << "ERROR: bad slider value!";
+        return;
+    }
     
     static int numpoints = 5;
     static int numcontrols = 5;
@@ -861,6 +876,10 @@
 }
 //---------------------------------------------------------------
 void testApp::sendFiltType(int ctrlin){
+    if(ctrlin < 0 || ctrlin > 127){
+        cout << "ERROR: bad slider value!";
+        return;
+    }
     static int numpoints = 3;
     static int numcontrols = 4;
     //float values[points][controls] =
@@ -888,6 +907,10 @@
 }
 //---------------------------------------------------------------
 void testApp::sendFiltFreq(int ctrlin){
+    if(ctrlin < 0 || ctrlin > 127){
+        cout << "ERROR: bad slider value!";
+        return;
+    }
     // smooth this
     float fin = ctrlin;
     float fout;
@@ -901,6 +924,10 @@
 }
 //---------------------------------------------------------------
 void testApp::sendEnvShape(int ctrlin){
+    if(ctrlin < 0 || ctrlin > 127){
+        cout << "ERROR: bad slider value!";
+        return;
+    }
     static int numpoints = 5;
     static int numcontrols = 3;
     //float values[points][controls] =
@@ -930,6 +957,10 @@
 }
 //---------------------------------------------------------------
 void testApp::sendModFreq(int ctrlin){
+    if(ctrlin < 0 || ctrlin > 127){
+        cout << "ERROR: bad slider value!";
+        return;
+    }
     float fm = ctrlin/127.;
     List toPD;
     
@@ -938,4 +969,49 @@
     
     core.pd.sendList("fromOF", toPD);
 }
-//---------------------------------------------------------------
\ No newline at end of file
+//---------------------------------------------------------------
+
+
+
+//---------------------------------------------------------------------------
+void saveSequences(){
+    ofFile sequenceFile(ofxiPhoneGetDocumentsDirectory() + "pilot_sequences.json" ,ofFile::WriteOnly);
+    
+    // the 5 harmonics for the frequencer
+    vector<int> freqIndexes;
+    freqIndexes.push_back(0);
+    freqIndexes.push_back(4);
+    freqIndexes.push_back(6);
+    freqIndexes.push_back(7);
+    freqIndexes.push_back(8);
+    
+    // loop thru all presets
+    int N = presetManager.thePresets.size();
+    
+    vector<int> sliderVals;
+    
+    Json::Value root;
+    
+    vector<double> vals;
+    
+    for(int i = 0; i< N ; i++){
+        sliderVals = theGridView.calculateParamsFromCoord(presetManager.thePresets[i]->coordinates);
+        
+        vals.push_back((sliderVals[0]+32)*8.); // DC offset
+        for(int i=1; i<5;i++){
+            vals.push_back((sliderVals[i] - 64)*2.);
+        }
+        
+        
+        vector<double> steps = frequencer.freqMagEdit(freqIndexes, vals);
+        
+        for(int j = 0; j<16;j++){
+            root["sequences"][i][j] = int(steps[j]);
+        }
+        vals.clear();
+    }
+    
+    //cout << root;
+    sequenceFile << root;
+}
+//=--------------------------------------------------------------------