4 directional EMG control of the XY table. Made during my bachelor end assignment.

Dependencies:   C12832_lcd HIDScope mbed-dsp mbed

Files at this revision

API Documentation at this revision

Comitter:
jessekaiser
Date:
Wed Jun 10 17:17:37 2015 +0000
Parent:
53:f783b3192dbb
Child:
55:fa6d5ee5c854
Commit message:
Test setup for max speed motors with potmeter

Changed in this revision

HIDScope.lib Show diff for this revision Revisions of this file
main.cpp Show annotated file Show diff for this revision Revisions of this file
mbed-dsp.lib Show diff for this revision Revisions of this file
--- a/HIDScope.lib	Wed Jun 10 08:33:52 2015 +0000
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,1 +0,0 @@
-http://mbed.org/users/tomlankhorst/code/HIDScope/#e44574634162
--- a/main.cpp	Wed Jun 10 08:33:52 2015 +0000
+++ b/main.cpp	Wed Jun 10 17:17:37 2015 +0000
@@ -1,276 +1,44 @@
-/*Code by Jesse Kaiser, s1355783 for control of the 2DOF Planar Table
-Some variables are also numbered at the end. The numbers stands for the muscle that controls it.
-Biceps =            1
-Triceps =           2
-Pectoralis Major =  3
-Deltoid =           4
-The "x" and "y" at the end of variables stand for the X-Spindle or Y-Spindle respectivly.
-*/
-
 #include "mbed.h"
 #include "C12832_lcd.h"
-#include "arm_math.h"
-#include "HIDScope.h"
 
-#define K_Gain      14      //Gain of the filtered EMG signal
-#define Damp        5       //Deceleration of the motor
-#define Mass        1       // Mass value
-#define dt          0.002   //Sample frequency
-#define MAX_bi      0.04    //Can be used for normalisation of the EMG signal of the biceps
-#define MAX_tri     0.04
-#define MAX_pect    0.04
-#define MAX_delt    0.04
-#define MIN_freq    500     //The motor turns off below this frequency
-#define EMG_tresh   0.01
+#define P_GAIN 0.995
 
-//Motor control
-DigitalOut Dirx(p21);
-PwmOut Stepx(p22);
-DigitalOut Diry(p23);
-PwmOut Stepy(p24);
-
-//Signal to and from computer
-Serial pc(USBTX, USBRX);
-
-DigitalOut Enablex(p26); //Connected to green led
-DigitalOut Enabley(p25); //Connected to blue led
-
-//Microstepping
+DigitalOut Dir(p23);
+PwmOut Step(p24);
+AnalogIn Pos1(p17); 
+AnalogIn Pos2(p18); 
+DigitalOut Enable(p16);
 DigitalOut MS1(p27);
 DigitalOut MS2(p28);
 DigitalOut MS3(p29);
-
-//Potmeter and EMG
 AnalogIn Pot1(p19);
 AnalogIn Pot2(p20);
-
-AnalogIn emg1(p15); //EMG bordje bovenop, biceps
-AnalogIn emg2(p16); //triceps
-AnalogIn emg3(p17);
-AnalogIn emg4(p18);
-
-HIDScope scope(4);
-Ticker   scopeTimer;
-
-//lcd
 C12832_LCD lcd;
 
-//Variables for motor control
-float setpoint = 1000; //Frequentie setpint
-float step_freq1 = 1;
-float step_freq2 = 1;
-float step_freq3 = 1;
-float step_freq4 = 1;
-
-//EMG filter
-arm_biquad_casd_df1_inst_f32 lowpass_biceps;
-arm_biquad_casd_df1_inst_f32 lowpass_triceps;
-arm_biquad_casd_df1_inst_f32 lowpass_pect;
-arm_biquad_casd_df1_inst_f32 lowpass_deltoid;
-//lowpass filter settings: Fc = 2 Hz, Fs = 500 Hz, Gain = -3 dB
-float lowpass_const[] = {0.00015514839749793376, 0.00031029679499586753, 0.00015514839749793376, 1.9644602512795832, -0.9650808448695751};
-arm_biquad_casd_df1_inst_f32 highnotch_biceps;
-arm_biquad_casd_df1_inst_f32 highnotch_triceps;
-arm_biquad_casd_df1_inst_f32 highnotch_pect;
-arm_biquad_casd_df1_inst_f32 highnotch_deltoid;
-//highpass filter settings: Fc = 20 Hz, Fs = 500 Hz, notch Fc = 50, Fs = 500 Hz
-float highnotch_const[] = {0.8370879899975344, -1.6741759799950688, 0.8370879899975344, 1.6474576182593796, -0.7008943417307579, 0.7063988100714527, -1.1429772843080923, 0.7063988100714527, 1.1429772843080923, -0.41279762014290533};
-
-//state values
-float lowpass_biceps_states[4];
-float highnotch_biceps_states[8];
-float lowpass_triceps_states[4];
-float highnotch_triceps_states[8];
-float lowpass_pect_states[4];
-float highnotch_pect_states[8];
-float lowpass_deltoid_states[4];
-float highnotch_deltoid_states[8];
-
-//global variabels
-float filtered_biceps, filtered_triceps, filtered_pect, filtered_deltoid;
-float speed_old1, speed_old2, speed_old3, speed_old4;
-float acc1, acc2, acc3, acc4;
-float force1, force2, force3, force4;
-float speed1, speed2, speed3, speed4;
-float damping1, damping2, damping3, damping4;
-
-void looper_emg()
-{
-    float emg_value1_f32, emg_value2_f32, emg_value3_f32, emg_value4_f32;
-    emg_value1_f32 = emg1.read();
-    emg_value2_f32 = emg2.read();
-    emg_value3_f32 = emg3.read();
-    emg_value4_f32 = emg4.read();
-
-    //process emg biceps
-    arm_biquad_cascade_df1_f32(&highnotch_biceps, &emg_value1_f32, &filtered_biceps, 1 );   //High pass and notch filter
-    filtered_biceps = fabs(filtered_biceps);                                                //Rectifier
-    arm_biquad_cascade_df1_f32(&lowpass_biceps, &filtered_biceps, &filtered_biceps, 1 );    //low pass filter
-
-    //process emg triceps
-    arm_biquad_cascade_df1_f32(&highnotch_triceps, &emg_value2_f32, &filtered_triceps, 1 );
-    filtered_triceps = fabs(filtered_triceps);
-    arm_biquad_cascade_df1_f32(&lowpass_triceps, &filtered_triceps, &filtered_triceps, 1 );
-
-    //process emg pectoralis major
-    arm_biquad_cascade_df1_f32(&highnotch_pect, &emg_value3_f32, &filtered_pect, 1 );
-    filtered_pect = fabs(filtered_pect);
-    arm_biquad_cascade_df1_f32(&lowpass_pect, &filtered_pect, &filtered_pect, 1 );
-
-    //process emg deltoid
-    arm_biquad_cascade_df1_f32(&highnotch_deltoid, &emg_value4_f32, &filtered_deltoid, 1 );
-    filtered_deltoid = fabs(filtered_deltoid);
-    arm_biquad_cascade_df1_f32(&lowpass_deltoid, &filtered_deltoid, &filtered_deltoid, 1 );
-
-    /*send value to PC. */
-    scope.set(0,filtered_biceps); //Filtered EMG signal
-    scope.set(1,filtered_triceps);
-    scope.set(2,filtered_pect);
-    scope.set(3,filtered_deltoid);
-}
-
-void looper_motory()
-{
-    //Forward
-    force1 = K_Gain*(filtered_biceps/MAX_bi);
-    force1 = force1 - damping1;
-    acc1 = force1/Mass;
-    speed1 = speed_old1 + (acc1 * dt);
-    damping1 = speed1 * Damp;
-    step_freq1 = (setpoint*speed1);
-    speed_old1 = speed1;
+Serial pc(USBTX, USBRX);
 
-    //Achteruit triceps
-    force2 = K_Gain*(filtered_triceps/MAX_tri);
-    force2 = force2 - damping2;
-    acc2 = force2/Mass;
-    speed2 = speed_old2 + (acc2 * dt);
-    damping2 = speed2 * Damp;
-    step_freq2 = (setpoint*speed2);
-    speed_old2 = speed2;
-    if (filtered_biceps > filtered_triceps) {
-        Diry = 1;
-        speed2 = 0.01;
-        speed_old2 = 0.01;
-        Stepy.period(1.0/step_freq1);
-    }
-    if (filtered_triceps > filtered_biceps) {
-        Diry = 0;
-        speed1 = 0.01;
-        speed_old1 = 0.01;
-        Stepy.period(1.0/step_freq2);
-    }
-    //Speed limit
-    if (speed1 > 1) {
-        speed1 = 1;
-        step_freq1 = setpoint;
-    }
-    if (speed2 > 1) {
-        speed2 = 1;
-        step_freq2 = setpoint;
-    }
-    //EMG treshold
-    if (filtered_biceps < EMG_tresh && filtered_triceps < EMG_tresh) {
-        Enabley = 1; //Enable = 1 turns the motor off.
-        speed1 = 0.01;
-        speed_old1 = 0.01;
-        speed2 = 0.01;
-        speed_old2 = 0.01;
-    } else {
-        Enabley = 0;
-    }
-
-}
-
-void looper_motorx()
-{
-    //To the left
-    force3 = K_Gain*(filtered_pect/MAX_pect);
-    force3 = force3 - damping3;
-    acc3 = force3/Mass;
-    speed3 = speed_old3 + (acc3 * dt);
-    damping3 = speed3 * Damp;
-    step_freq3 = (setpoint*speed3);
-    speed_old3 = speed3;
-
-    //To the right
-    force4 = K_Gain*(filtered_deltoid/MAX_delt);
-    force4 = force4 - damping4;
-    acc4 = force4/Mass;
-    speed4 = speed_old4 + (acc4 * dt);
-    damping4 = speed4 * Damp;
-    step_freq4 = (setpoint*speed4);
-    speed_old4 = speed4;
-    
-    if (filtered_pect > filtered_deltoid) {
-        Dirx = 0;
-        speed4 = 0.01;
-        speed_old4 = 0.01;
-        Stepx.period(1.0/step_freq3);
-    }
-    if (filtered_deltoid > filtered_pect) {
-        Dirx = 1;
-        speed3 = 0.01;
-        speed_old3 = 0.01;
-        Stepx.period(1.0/step_freq4);
-    }
-    //Speed limit
-    if (speed3 > 1) {
-        speed3 = 1;
-        step_freq3 = setpoint;
-    }
-    if (speed4 > 1) {
-        speed4 = 1;
-        step_freq4 = setpoint;
-    }
-    //EMG treshold
-    if (filtered_pect < EMG_tresh && filtered_deltoid < EMG_tresh) {
-        Enablex = 1; //Enable = 1 turns the motor off.
-        speed3 = 0.01;
-        speed_old3 = 0.01;
-        speed4 = 0.01;
-        speed_old4 = 0.01;
-    } else {
-        Enablex = 0;
-    }
-
-}
 int main()
 {
-    // Attach the HIDScope::send method from the scope object to the timer at 500Hz. Hier wordt de sample freq aangegeven.
-    scopeTimer.attach_us(&scope, &HIDScope::send, 2e3);
-
-    Ticker emgtimer;    //biceps
-    arm_biquad_cascade_df1_init_f32(&lowpass_biceps, 1 , lowpass_const, lowpass_biceps_states);
-    arm_biquad_cascade_df1_init_f32(&highnotch_biceps, 2 , highnotch_const, highnotch_biceps_states);
-    //triceps
-    arm_biquad_cascade_df1_init_f32(&lowpass_triceps, 1 , lowpass_const, lowpass_triceps_states);
-    arm_biquad_cascade_df1_init_f32(&highnotch_triceps, 2 , highnotch_const, highnotch_triceps_states);
-    //pectoralis major
-    arm_biquad_cascade_df1_init_f32(&lowpass_pect, 1 , lowpass_const, lowpass_pect_states);
-    arm_biquad_cascade_df1_init_f32(&highnotch_pect, 2 , highnotch_const, highnotch_pect_states);
-    //deltoid
-    arm_biquad_cascade_df1_init_f32(&lowpass_deltoid, 1 , lowpass_const, lowpass_deltoid_states);
-    arm_biquad_cascade_df1_init_f32(&highnotch_deltoid, 2 , highnotch_const, highnotch_deltoid_states);
-    emgtimer.attach(looper_emg, 0.01);
-
-    Ticker looptimer1;
-    looptimer1.attach(looper_motorx, 0.01); //X-Spindle motor, why this freq?
-
-    Ticker looptimer2;
-    looptimer2.attach(looper_motory, 0.01); //Y-Spindle motor
-
-    //Microstepping control, now configured as half stepping (MS1=1,MS2=0,MS3=0)
+    Enable = 0;
+    float setpoint = 7000; //Frequentie 
+    float step_freq = 1;
     MS1 = 1;
     MS2 = 0;
     MS3 = 0;
-    Stepx.write(0.5); // Duty cycle of 50%
-    Stepy.write(0.5);
-
+    
+    Step.period(1./step_freq); // 1 kHz, vanaf 2,5 kHz doet de motor het niet meer.
+    Step.write(0.5); // Duty cycle van 50%
+   
+    Enable = 1;
     while (1) {
+        Dir = 0;
+        float new_step_freq;
+        new_step_freq = ((1-P_GAIN)*setpoint) + (P_GAIN*step_freq);
+        step_freq = new_step_freq;
+        Step.period(1.0/step_freq);
+        
+        pc.printf("%.2f %.0f \n", Pos1.read(), step_freq);
+        wait(0.01); //Hier nog ticker inbouwen
 
-        //lcd.printf("Bi %.2f ,Tri %.2f \n", filtered_biceps, filtered_triceps); Filtered EMG values
-        //lcd.printf("1 %.0f, 2 %.0f, 3 %.0f, 4 %.0f \n", step_freq1, step_freq2, step_freq3, step_freq4); //step_freq value of every EMG sensor
-        //wait(0.01);
     }
-}
+}
\ No newline at end of file
--- a/mbed-dsp.lib	Wed Jun 10 08:33:52 2015 +0000
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,1 +0,0 @@
-http://mbed.org/teams/mbed-official/code/mbed-dsp/#7a284390b0ce