For flywheel rig. Interfaces with matlab flywheel interface. 2.007 MIT Biomimetics Robotics Lab. Sangbae Kim. Ben Katz.

Dependencies:   mbed

Files at this revision

API Documentation at this revision

Comitter:
abraham1
Date:
Fri Apr 14 18:06:13 2017 +0000
Parent:
11:ad41446b0edb
Commit message:
Commented code;

Changed in this revision

main.cpp Show annotated file Show diff for this revision Revisions of this file
diff -r ad41446b0edb -r f9f08c7551f4 main.cpp
--- a/main.cpp	Fri Apr 14 17:35:05 2017 +0000
+++ b/main.cpp	Fri Apr 14 18:06:13 2017 +0000
@@ -1,5 +1,7 @@
 ///setup code for encoder on pins PA0 and PA1 (A0 and A1)///
 
+// TODO: explain basic flow of run and data collection
+
 #include "mbed.h"
 #include "time.h"
 #include "stdio.h"
@@ -7,20 +9,31 @@
 
 #define PI 3.14159265358979323846
 
+//Just for basic debugging
+//User button controls motor speed
+//Green LED should turn on while listening to pc for input before starting run
 InterruptIn button(USER_BUTTON);
-PwmOut pwm(D5);//do not use D3
-DigitalOut a(D2);
-DigitalOut b(D4);
-
-AnalogIn currentSense(A5); //hook up to Vout on current sensor
-Serial pc(USBTX, USBRX, 115200);
 DigitalOut green(LED2);
 
-const int CPR = 900*4;  // Encoder counts per revolution.  Change to match your encoder. x4 for quadrature!
-const double VREF = 3; //Microcontroller reference voltage
-const float currentSensorOutputRatio = 0.185; // Volts/Amp. Divide Voltage by cSenseOutput to get current
-const float PSupply_Voltage = 12.0;
-const float Output_Voltage = 2.0;
+// Pololu VNH5019 Motor Driver Carrier. https://www.pololu.com/product/1451
+PwmOut pwm(D5);     //pwm input on motor controller. do not use D3
+DigitalOut a(D2);   //IN_A input on motor controller
+DigitalOut b(D4);   //IN_B input on motor controller
+
+//Hook up to Vout on current sensor
+//SparkFun Hall-Effect Current Sensor Breakout - ACS712
+//https://www.sparkfun.com/products/8882
+AnalogIn currentSense(A5);
+
+//For communication with pc through matlab
+//Make sure baud rates are equal
+Serial pc(USBTX, USBRX, 115200);
+
+const int CPR = 900*4;  // Encoder counts per revolution (900).  Change to match your encoder. x4 for quadrature
+const double VREF = 3;  // Microcontroller reference voltage
+const float currentSensorOutputRatio = 0.185;   // Volts/Amp specified by current sensor. Divide Voltage by cSenseOutput to get current
+const float PSupply_Voltage = 12.0;             // Voltage input from power supply
+const float Output_Voltage = 2.0;               // Desired output voltage to motor
 const float pwm_flywheel = Output_Voltage/PSupply_Voltage;
 
 void EncoderInitialise(void) {
@@ -77,32 +90,41 @@
 
 int main() {
     
-    int endcount, startcount;
-    double time_between_readings;
+    int endcount, startcount; //encoder counts
+    double time_between_readings; //between encoder readings
     double velocity;
     double currentSensed = 0;
     clock_t start, end, absoluteStart;
     int ticks;
     a=1; b=0; pwm.write(0);
-    button.fall(&pressed);
-    double updatePeriod = 0.01; /* must select carefully */
-    double publishFrequency = 0.05; /* seconds. rate to publish to matlab */
-    double samplesPerPublish = (int)(publishFrequency/updatePeriod); /*this improves time response of filter and maintains smoothness*/
+    button.fall(&pressed);  //adds pressed callback upon button push
+    
+    /*  we don't send all the information to matlab all the time. some collection and smoothing is done
+        here in order to not overload matlab with input making it slow. And to take a lot of data so we
+        can do smoothing quickly on this side */
+    double updatePeriod = 0.01; /* must select carefully. too fast and you don't get enough encoder ticks*/
+    double publishFrequency = 0.05; /* seconds. rate to publish to matlab. no need to overload matlab with input*/
+    double samplesPerPublish = (int)(publishFrequency/updatePeriod); /*this improves time response of current filter and maintains smoothness*/
     int publishCounter = 1;
+    
+    /* the filter ratio on the speed data from encoder and on current input */
     double filterRatio = 0.1;
     double currentFilterRatio = 0.035;
+    
+    /* the current sensor has some resting value. record and subtract that out */
     float currentSensorOffset = 0; int i; 
     for(i=1;i<301;i++){ currentSensorOffset += currentSense.read(); }
     currentSensorOffset = currentSensorOffset*VREF/300;
+    
     EncoderInitialise();
-    fflush(pc);
+    fflush(pc); //clear any previous output
     
         
     while(1) {
     
 
-        while(1) {
-            
+        
+        while(1) {                              //Listen for PC input to start run
             green = true;
             if(pc.readable()) {
                 char charIn = pc.getc();
@@ -119,12 +141,11 @@
                     break; 
                 }
             }
-        
             wait(0.05);
-            
         }  
     
     
+        
         while(1) {
             
             green = false;
@@ -137,20 +158,22 @@
             ticks = endcount-startcount;
             if(abs(ticks)>CPR/2) /***** for rollover case: *****/
             { ticks = ((ticks<0)-(ticks>0))*(CPR-abs(ticks)); }
+            
             velocity = filterRatio*((double)ticks)/CPR*2*PI/time_between_readings + (1-filterRatio)*velocity; /* with filtering*/
             currentSensed = currentFilterRatio*((double)currentSense.read()*VREF-currentSensorOffset) + (1-currentFilterRatio)*currentSensed;
-            if(pc.readable())
-            {
+            
+            if(pc.readable()) {             //PC will send 'r' when run is finished
                 char charIn = pc.getc();
                 if(charIn == 'r'){
                     fflush(pc);
-                    pwm.write(0.0);
-                    break;
+                    pwm.write(0.0);         //kill the motor
+                    break;                  //return to listening loop
                 }
             }        
-            if(publishCounter == samplesPerPublish) {
+            
+            if(publishCounter == samplesPerPublish) {           //only publish once every samplesPerPublish
                 printf("%+9.5f,%+8.4f,%+9.4f,%+8.2f\n", currentSensed/currentSensorOutputRatio, pwm.read(), -velocity, ((double)(end-absoluteStart)/CLOCKS_PER_SEC));
-                publishCounter = 1;  // good for 1000 seconds. and room to grow one power of 10 on all other inputs.  //just changed velocity to 4 precision to give it extra room for no load? bug maybe?
+                publishCounter = 1;  //output formatting very important. running a simple string length checksum on matlab side to discard bad data
             }
             publishCounter++;