Biorobotics 2018: Project group 16

Dependencies:   HIDScope MODSERIAL QEI biquadFilter mbed

Committer:
ThomBMT
Date:
Thu Nov 01 23:50:06 2018 +0000
Revision:
4:a682fb1f37d2
Parent:
3:766e9f13d84e
Laatste versie;

Who changed what in which revision?

UserRevisionLine numberNew contents of line
ThomBMT 0:94cf6b327972 1 #include "mbed.h"
ThomBMT 1:ba14d8f4d444 2 #include "MODSERIAL.h"
ThomBMT 1:ba14d8f4d444 3 #include "HIDScope.h"
ThomBMT 1:ba14d8f4d444 4 #include "QEI.h"
ThomBMT 1:ba14d8f4d444 5 #include "BiQuad.h"
ThomBMT 0:94cf6b327972 6
ThomBMT 3:766e9f13d84e 7 // Pin defintions:
ThomBMT 3:766e9f13d84e 8 MODSERIAL pc(USBTX, USBRX);
ThomBMT 3:766e9f13d84e 9 DigitalOut DirectionPin1(D4);
ThomBMT 3:766e9f13d84e 10 DigitalOut DirectionPin2(D7);
ThomBMT 3:766e9f13d84e 11 PwmOut PwmPin1(D5);
ThomBMT 3:766e9f13d84e 12 PwmOut PwmPin2(D6);
ThomBMT 3:766e9f13d84e 13 DigitalIn Knop1(D2);
ThomBMT 3:766e9f13d84e 14 DigitalIn Knop2(D3);
ThomBMT 3:766e9f13d84e 15 DigitalIn Knop3(PTA4);
ThomBMT 3:766e9f13d84e 16 DigitalIn Knop4(PTC6);
ThomBMT 3:766e9f13d84e 17 AnalogIn pot1 (A5);
ThomBMT 3:766e9f13d84e 18 AnalogIn pot2 (A4);
ThomBMT 3:766e9f13d84e 19 AnalogIn emg0( A0 );
ThomBMT 3:766e9f13d84e 20 AnalogIn emg1( A1 );
ThomBMT 3:766e9f13d84e 21 AnalogIn emg2( A2 );
ThomBMT 3:766e9f13d84e 22 AnalogIn emg3( A3 );
ThomBMT 3:766e9f13d84e 23 DigitalOut led_G(LED_GREEN);
ThomBMT 3:766e9f13d84e 24 DigitalOut led_R(LED_RED);
ThomBMT 3:766e9f13d84e 25 DigitalOut led_B(LED_BLUE);
ThomBMT 1:ba14d8f4d444 26
ThomBMT 3:766e9f13d84e 27 // Encoder functions.
ThomBMT 1:ba14d8f4d444 28 QEI Encoder1(D12,D13,NC,64,QEI::X4_ENCODING);
ThomBMT 1:ba14d8f4d444 29 QEI Encoder2(D10,D11,NC,64,QEI::X4_ENCODING);
ThomBMT 1:ba14d8f4d444 30
ThomBMT 3:766e9f13d84e 31 // Filter definitions:
ThomBMT 3:766e9f13d84e 32 BiQuadChain bqc1;
ThomBMT 3:766e9f13d84e 33 BiQuadChain bqc2;
ThomBMT 3:766e9f13d84e 34 BiQuadChain bqc3;
ThomBMT 3:766e9f13d84e 35 BiQuadChain bqc4;
ThomBMT 3:766e9f13d84e 36 BiQuadChain bqc5;
ThomBMT 3:766e9f13d84e 37 BiQuadChain bqc6;
ThomBMT 3:766e9f13d84e 38 BiQuadChain bqc7;
ThomBMT 3:766e9f13d84e 39 BiQuadChain bqc8;
ThomBMT 1:ba14d8f4d444 40
ThomBMT 3:766e9f13d84e 41 BiQuad BqNotch1_1( 9.65081e-01, -1.56203e+00, 9.65081e-01,-1.56858e+00, 9.64241e-01 );
ThomBMT 3:766e9f13d84e 42 BiQuad BqNotch2_1( 1.00000e+00, -1.61855e+00, 1.00000e+00 ,-1.61100e+00, 9.65922e-01);
ThomBMT 3:766e9f13d84e 43 BiQuad BqNotch1_2( 9.65081e-01, -1.56203e+00, 9.65081e-01,-1.56858e+00, 9.64241e-01 );
ThomBMT 3:766e9f13d84e 44 BiQuad BqNotch2_2( 1.00000e+00, -1.61855e+00, 1.00000e+00 ,-1.61100e+00, 9.65922e-01);
ThomBMT 3:766e9f13d84e 45 BiQuad BqNotch1_3( 9.65081e-01, -1.56203e+00, 9.65081e-01,-1.56858e+00, 9.64241e-01 );
ThomBMT 3:766e9f13d84e 46 BiQuad BqNotch2_3( 1.00000e+00, -1.61855e+00, 1.00000e+00 ,-1.61100e+00, 9.65922e-01);
ThomBMT 3:766e9f13d84e 47 BiQuad BqNotch1_4( 9.65081e-01, -1.56203e+00, 9.65081e-01,-1.56858e+00, 9.64241e-01 );
ThomBMT 3:766e9f13d84e 48 BiQuad BqNotch2_4( 1.00000e+00, -1.61855e+00, 1.00000e+00 ,-1.61100e+00, 9.65922e-01);
ThomBMT 3:766e9f13d84e 49 BiQuad BqHP1( 9.86760e-01, -1.97352e+00, 9.86760e-01, -1.97334e+00, 9.73695e-01 );
ThomBMT 3:766e9f13d84e 50 BiQuad BqHP2( 9.86760e-01, -1.97352e+00, 9.86760e-01, -1.97334e+00, 9.73695e-01 );
ThomBMT 3:766e9f13d84e 51 BiQuad BqHP3( 9.86760e-01, -1.97352e+00, 9.86760e-01, -1.97334e+00, 9.73695e-01 );
ThomBMT 3:766e9f13d84e 52 BiQuad BqHP4( 9.86760e-01, -1.97352e+00, 9.86760e-01, -1.97334e+00, 9.73695e-01 );
ThomBMT 1:ba14d8f4d444 53
ThomBMT 3:766e9f13d84e 54 BiQuad BqLP1( 3.91302e-05, 7.82604e-05, 3.91302e-05, -1.98223e+00, 9.82385e-01 );
ThomBMT 3:766e9f13d84e 55 BiQuad BqLP2( 3.91302e-05, 7.82604e-05, 3.91302e-05, -1.98223e+00, 9.82385e-01 );
ThomBMT 3:766e9f13d84e 56 BiQuad BqLP3( 3.91302e-05, 7.82604e-05, 3.91302e-05, -1.98223e+00, 9.82385e-01 );
ThomBMT 3:766e9f13d84e 57 BiQuad BqLP4( 3.91302e-05, 7.82604e-05, 3.91302e-05, -1.98223e+00, 9.82385e-01 );
ThomBMT 3:766e9f13d84e 58
ThomBMT 3:766e9f13d84e 59 BiQuad LowPassFilter(0.0640, 0.1279, 0.0640, -1.1683, 0.4241);
ThomBMT 1:ba14d8f4d444 60
ThomBMT 3:766e9f13d84e 61 // Tickers for the main loop:
ThomBMT 3:766e9f13d84e 62 Ticker StateTicker;
ThomBMT 3:766e9f13d84e 63 Ticker printTicker;
ThomBMT 1:ba14d8f4d444 64
ThomBMT 3:766e9f13d84e 65 // Setting the HIDscope:
ThomBMT 3:766e9f13d84e 66 HIDScope scope( 4 );
ThomBMT 1:ba14d8f4d444 67
ThomBMT 3:766e9f13d84e 68 // All variables for EMG-processing:
ThomBMT 1:ba14d8f4d444 69 volatile float Bicep_Right = 0.0;
ThomBMT 1:ba14d8f4d444 70 volatile float Bicep_Left = 0.0;
ThomBMT 1:ba14d8f4d444 71 volatile float Tricep_Right = 0.0;
ThomBMT 1:ba14d8f4d444 72 volatile float Tricep_Left = 0.0;
ThomBMT 1:ba14d8f4d444 73 volatile float FilterHP_Bi_R;
ThomBMT 1:ba14d8f4d444 74 volatile float Filterabs_Bi_R;
ThomBMT 1:ba14d8f4d444 75 volatile float Filtered_Bi_R;
ThomBMT 1:ba14d8f4d444 76 volatile float FilterHP_Bi_L;
ThomBMT 1:ba14d8f4d444 77 volatile float Filterabs_Bi_L;
ThomBMT 1:ba14d8f4d444 78 volatile float Filtered_Bi_L;
ThomBMT 1:ba14d8f4d444 79 volatile float FilterHP_Tri_R;
ThomBMT 1:ba14d8f4d444 80 volatile float Filterabs_Tri_R;
ThomBMT 1:ba14d8f4d444 81 volatile float Filtered_Tri_R;
ThomBMT 1:ba14d8f4d444 82 volatile float FilterHP_Tri_L;
ThomBMT 1:ba14d8f4d444 83 volatile float Filterabs_Tri_L;
ThomBMT 1:ba14d8f4d444 84 volatile float Filtered_Tri_L;
ThomBMT 1:ba14d8f4d444 85
ThomBMT 3:766e9f13d84e 86 // Variables for the PID-Controller:
ThomBMT 3:766e9f13d84e 87 volatile float error_1_integral = 0;
ThomBMT 3:766e9f13d84e 88 volatile float error_2_integral = 0;
ThomBMT 3:766e9f13d84e 89 volatile float error_1_prev; // initialization with this value only done once!
ThomBMT 3:766e9f13d84e 90 volatile float error_2_prev;
ThomBMT 4:a682fb1f37d2 91 volatile const float Kp = 3.2;
ThomBMT 4:a682fb1f37d2 92 volatile const float Ki = 0.000;
ThomBMT 4:a682fb1f37d2 93 volatile const float Kd = 0.0;
ThomBMT 4:a682fb1f37d2 94 volatile const float Ts = 0.002f; // Sample time in seconds
ThomBMT 3:766e9f13d84e 95 volatile float error_1;
ThomBMT 3:766e9f13d84e 96 volatile float error_2;
ThomBMT 4:a682fb1f37d2 97 volatile float u_k_1;
ThomBMT 4:a682fb1f37d2 98 volatile float u_k_2;
ThomBMT 4:a682fb1f37d2 99 volatile float u_i_1;
ThomBMT 4:a682fb1f37d2 100 volatile float u_i_2;
ThomBMT 4:a682fb1f37d2 101 volatile float u_d_1;
ThomBMT 4:a682fb1f37d2 102 volatile float u_d_2;
ThomBMT 3:766e9f13d84e 103 volatile float U_1;
ThomBMT 3:766e9f13d84e 104 volatile float U_2;
ThomBMT 1:ba14d8f4d444 105
ThomBMT 3:766e9f13d84e 106 // Constant values used in computations and such:
ThomBMT 1:ba14d8f4d444 107 volatile const float pi = 3.1415926;
ThomBMT 1:ba14d8f4d444 108 volatile const float rad_count = 0.0007479; // 2pi/8400;
ThomBMT 1:ba14d8f4d444 109 volatile const float maxVelocity = 2.0f * pi; // in rad/s
ThomBMT 1:ba14d8f4d444 110 volatile const float r_3 = 0.035;
ThomBMT 1:ba14d8f4d444 111
ThomBMT 3:766e9f13d84e 112 // Some counting variables:
ThomBMT 1:ba14d8f4d444 113 volatile int i = 0; // Led blink status
ThomBMT 1:ba14d8f4d444 114 volatile int ii = 0; // Calibratie timer
ThomBMT 1:ba14d8f4d444 115 volatile int iii = 0; // Start up timer
ThomBMT 1:ba14d8f4d444 116
ThomBMT 3:766e9f13d84e 117 // Variables for computations of joint angle and velocities:
ThomBMT 4:a682fb1f37d2 118 volatile float q_ref1_o = 7.0f*pi/4.0f;
ThomBMT 4:a682fb1f37d2 119 volatile float q_ref1_n;
ThomBMT 4:a682fb1f37d2 120 volatile float q_ref2_o = 1.0f*pi/3.0f;
ThomBMT 4:a682fb1f37d2 121 volatile float q_ref2_n;
ThomBMT 3:766e9f13d84e 122 volatile float r_1;
ThomBMT 3:766e9f13d84e 123 volatile float r_2;
ThomBMT 3:766e9f13d84e 124 volatile float w_1;
ThomBMT 3:766e9f13d84e 125 volatile float w_2;
ThomBMT 3:766e9f13d84e 126 volatile float vx;
ThomBMT 3:766e9f13d84e 127 volatile float vy;
ThomBMT 3:766e9f13d84e 128 volatile float rad_m1;
ThomBMT 3:766e9f13d84e 129 volatile float rad_m2;
ThomBMT 3:766e9f13d84e 130 volatile int counts1;
ThomBMT 3:766e9f13d84e 131 volatile int counts2;
ThomBMT 1:ba14d8f4d444 132
ThomBMT 3:766e9f13d84e 133 // Threshold values and variables:
ThomBMT 3:766e9f13d84e 134 volatile float Flex_Bi_R;
ThomBMT 3:766e9f13d84e 135 volatile float Flex_Bi_L;
ThomBMT 3:766e9f13d84e 136 volatile float Flex_Tri_R;
ThomBMT 3:766e9f13d84e 137 volatile float Flex_Tri_L;
ThomBMT 3:766e9f13d84e 138 volatile float Threshold_Value;
ThomBMT 3:766e9f13d84e 139 volatile float Threshold_Bi_R;
ThomBMT 3:766e9f13d84e 140 volatile float Threshold_Bi_L;
ThomBMT 3:766e9f13d84e 141 volatile float Threshold_Tri_R;
ThomBMT 3:766e9f13d84e 142 volatile float Threshold_Tri_L;
ThomBMT 3:766e9f13d84e 143 volatile bool Checking_Bi_R = false;
ThomBMT 3:766e9f13d84e 144 volatile bool Checking_Bi_L = false;
ThomBMT 3:766e9f13d84e 145 volatile bool Checking_Tri_R = false;
ThomBMT 3:766e9f13d84e 146 volatile bool Checking_Tri_L = false;
ThomBMT 1:ba14d8f4d444 147
ThomBMT 3:766e9f13d84e 148 // States for the switch-statemachine:
ThomBMT 1:ba14d8f4d444 149 enum states{Starting, Calibration, Homing_M1, Homing_M2, Post_Homing, Function, Safe};
ThomBMT 3:766e9f13d84e 150
ThomBMT 3:766e9f13d84e 151 // The very first state:
ThomBMT 1:ba14d8f4d444 152 volatile states Active_State = Starting;
ThomBMT 1:ba14d8f4d444 153
ThomBMT 3:766e9f13d84e 154
ThomBMT 1:ba14d8f4d444 155 void Encoding()
ThomBMT 1:ba14d8f4d444 156 {
ThomBMT 3:766e9f13d84e 157 // Encoding is necessary for the computations of the joint angles and
ThomBMT 3:766e9f13d84e 158 // velocities of the arm given certain linear velocities.
ThomBMT 1:ba14d8f4d444 159
ThomBMT 1:ba14d8f4d444 160 counts1 = Encoder1.getPulses();
ThomBMT 1:ba14d8f4d444 161 counts2 = Encoder2.getPulses();
ThomBMT 1:ba14d8f4d444 162
ThomBMT 4:a682fb1f37d2 163 rad_m1 = (rad_count * (float)counts1) + (1.0f*pi/3.0f);
ThomBMT 4:a682fb1f37d2 164 rad_m2 = (rad_count * (float)counts2) + (7.0f*pi/4.0f);
ThomBMT 1:ba14d8f4d444 165 }
ThomBMT 1:ba14d8f4d444 166
ThomBMT 1:ba14d8f4d444 167 void Filter()
ThomBMT 1:ba14d8f4d444 168 {
ThomBMT 3:766e9f13d84e 169 // Our Filter function will take the raw (incomming) EMG-signal and process
ThomBMT 3:766e9f13d84e 170 // it in such a way that we can use it to opperate our system.
ThomBMT 3:766e9f13d84e 171
ThomBMT 1:ba14d8f4d444 172 FilterHP_Bi_R = bqc1.step( emg0.read() );
ThomBMT 1:ba14d8f4d444 173 Filterabs_Bi_R = fabs(FilterHP_Bi_R);
ThomBMT 1:ba14d8f4d444 174 Filtered_Bi_R = bqc2.step( Filterabs_Bi_R );
ThomBMT 1:ba14d8f4d444 175
ThomBMT 1:ba14d8f4d444 176 FilterHP_Bi_L = bqc3.step( emg1.read() );
ThomBMT 1:ba14d8f4d444 177 Filterabs_Bi_L = fabs(FilterHP_Bi_L);
ThomBMT 1:ba14d8f4d444 178 Filtered_Bi_L = bqc4.step( Filterabs_Bi_L );
ThomBMT 1:ba14d8f4d444 179
ThomBMT 1:ba14d8f4d444 180 FilterHP_Tri_R = bqc5.step( emg2.read() );
ThomBMT 1:ba14d8f4d444 181 Filterabs_Tri_R = fabs(FilterHP_Tri_R);
ThomBMT 1:ba14d8f4d444 182 Filtered_Tri_R = bqc6.step( Filterabs_Tri_R );
ThomBMT 1:ba14d8f4d444 183
ThomBMT 1:ba14d8f4d444 184 FilterHP_Tri_L = bqc7.step( emg3.read() );
ThomBMT 1:ba14d8f4d444 185 Filterabs_Tri_L = fabs(FilterHP_Tri_L);
ThomBMT 1:ba14d8f4d444 186 Filtered_Tri_L = bqc8.step( Filterabs_Tri_L );
ThomBMT 1:ba14d8f4d444 187 }
ThomBMT 1:ba14d8f4d444 188
ThomBMT 1:ba14d8f4d444 189 void BlinkLed()
ThomBMT 1:ba14d8f4d444 190 {
ThomBMT 3:766e9f13d84e 191 // This is a function used purely for feedback that will give insight in
ThomBMT 3:766e9f13d84e 192 // what the system is doing without having to fully opperate it.
ThomBMT 3:766e9f13d84e 193
ThomBMT 1:ba14d8f4d444 194 if(i==1)
ThomBMT 1:ba14d8f4d444 195 {
ThomBMT 1:ba14d8f4d444 196 led_G=led_B=1;
ThomBMT 1:ba14d8f4d444 197 static int rr = 0;
ThomBMT 1:ba14d8f4d444 198 rr++;
ThomBMT 1:ba14d8f4d444 199 if (rr == 1)
ThomBMT 1:ba14d8f4d444 200 {
ThomBMT 1:ba14d8f4d444 201 led_R = !led_R;
ThomBMT 1:ba14d8f4d444 202 }
ThomBMT 1:ba14d8f4d444 203 else if (rr == 50)
ThomBMT 1:ba14d8f4d444 204 {
ThomBMT 1:ba14d8f4d444 205 rr = 0;
ThomBMT 1:ba14d8f4d444 206 }
ThomBMT 1:ba14d8f4d444 207 }
ThomBMT 1:ba14d8f4d444 208 else if(i==2)
ThomBMT 1:ba14d8f4d444 209 {
ThomBMT 1:ba14d8f4d444 210 led_R=led_B=1;
ThomBMT 1:ba14d8f4d444 211
ThomBMT 1:ba14d8f4d444 212 static int gg = 0;
ThomBMT 1:ba14d8f4d444 213 gg++;
ThomBMT 1:ba14d8f4d444 214 if (gg == 1)
ThomBMT 1:ba14d8f4d444 215 {
ThomBMT 1:ba14d8f4d444 216 led_G = !led_G;
ThomBMT 1:ba14d8f4d444 217 }
ThomBMT 1:ba14d8f4d444 218 else if (gg == 250)
ThomBMT 1:ba14d8f4d444 219 {
ThomBMT 1:ba14d8f4d444 220 gg = 0;
ThomBMT 1:ba14d8f4d444 221 }
ThomBMT 1:ba14d8f4d444 222 }
ThomBMT 1:ba14d8f4d444 223 else if (i==3)
ThomBMT 1:ba14d8f4d444 224 {
ThomBMT 1:ba14d8f4d444 225 led_R=1;
ThomBMT 1:ba14d8f4d444 226 static int bb = 0;
ThomBMT 1:ba14d8f4d444 227 bb++;
ThomBMT 1:ba14d8f4d444 228 if (bb == 1)
ThomBMT 1:ba14d8f4d444 229 {
ThomBMT 1:ba14d8f4d444 230 led_B = !led_B;
ThomBMT 1:ba14d8f4d444 231 }
ThomBMT 1:ba14d8f4d444 232 else if (bb == 500)
ThomBMT 1:ba14d8f4d444 233 {
ThomBMT 1:ba14d8f4d444 234 bb = 0;
ThomBMT 1:ba14d8f4d444 235 }
ThomBMT 1:ba14d8f4d444 236 }
ThomBMT 1:ba14d8f4d444 237 else if (i==4)
ThomBMT 1:ba14d8f4d444 238 {
ThomBMT 1:ba14d8f4d444 239 led_G=1;
ThomBMT 1:ba14d8f4d444 240 static int rr = 0;
ThomBMT 1:ba14d8f4d444 241 rr++;
ThomBMT 1:ba14d8f4d444 242 if (rr == 1)
ThomBMT 1:ba14d8f4d444 243 {
ThomBMT 1:ba14d8f4d444 244 led_R = !led_R;
ThomBMT 1:ba14d8f4d444 245 led_B = !led_B;
ThomBMT 1:ba14d8f4d444 246 }
ThomBMT 1:ba14d8f4d444 247 else if (rr == 250)
ThomBMT 1:ba14d8f4d444 248 {
ThomBMT 1:ba14d8f4d444 249 rr = 0;
ThomBMT 1:ba14d8f4d444 250 }
ThomBMT 1:ba14d8f4d444 251 }
ThomBMT 1:ba14d8f4d444 252 else
ThomBMT 1:ba14d8f4d444 253 {
ThomBMT 1:ba14d8f4d444 254 led_R=led_G=led_B=1;
ThomBMT 1:ba14d8f4d444 255 }
ThomBMT 1:ba14d8f4d444 256 }
ThomBMT 1:ba14d8f4d444 257
ThomBMT 1:ba14d8f4d444 258 void EMG_Read()
ThomBMT 1:ba14d8f4d444 259 {
ThomBMT 3:766e9f13d84e 260 // This is only to define our first (raw) EMG-signals and give each a
ThomBMT 3:766e9f13d84e 261 // suitable name.
ThomBMT 3:766e9f13d84e 262
ThomBMT 1:ba14d8f4d444 263 Bicep_Right = emg0.read();
ThomBMT 1:ba14d8f4d444 264 Bicep_Left = emg1.read();
ThomBMT 1:ba14d8f4d444 265 Tricep_Right = emg2.read();
ThomBMT 1:ba14d8f4d444 266 Tricep_Left = emg3.read();
ThomBMT 1:ba14d8f4d444 267 }
ThomBMT 1:ba14d8f4d444 268
ThomBMT 1:ba14d8f4d444 269 void sample()
ThomBMT 1:ba14d8f4d444 270 {
ThomBMT 3:766e9f13d84e 271 // HIDscope allows us to check our filtered EMG-signal and gives insight
ThomBMT 3:766e9f13d84e 272 // into thresholdvalues and how well the calibration was done.
ThomBMT 1:ba14d8f4d444 273
ThomBMT 1:ba14d8f4d444 274 scope.set(0, Filtered_Bi_R*10.0f );
ThomBMT 1:ba14d8f4d444 275 scope.set(1, Filtered_Bi_L*10.0f );
ThomBMT 1:ba14d8f4d444 276 scope.set(2, Filtered_Tri_R*10.0f );
ThomBMT 1:ba14d8f4d444 277 scope.set(3, Filtered_Tri_L*10.0f );
ThomBMT 1:ba14d8f4d444 278
ThomBMT 1:ba14d8f4d444 279 scope.send();
ThomBMT 1:ba14d8f4d444 280 }
ThomBMT 1:ba14d8f4d444 281
ThomBMT 1:ba14d8f4d444 282 void Calibrating()
ThomBMT 1:ba14d8f4d444 283 {
ThomBMT 3:766e9f13d84e 284 // Calibration is done to ensure that threshold values not predetermined and
ThomBMT 3:766e9f13d84e 285 // can vary each user. This makes the system more universal.
ThomBMT 3:766e9f13d84e 286
ThomBMT 1:ba14d8f4d444 287 static float n = 0.0;
ThomBMT 1:ba14d8f4d444 288 static float m = 0.0;
ThomBMT 1:ba14d8f4d444 289 static float l = 0.0;
ThomBMT 1:ba14d8f4d444 290 static float k = 0.0;
ThomBMT 1:ba14d8f4d444 291
ThomBMT 1:ba14d8f4d444 292 ii++;
ThomBMT 1:ba14d8f4d444 293
ThomBMT 1:ba14d8f4d444 294 if (ii<=2500)
ThomBMT 1:ba14d8f4d444 295 {
ThomBMT 1:ba14d8f4d444 296 if (ii == 1)
ThomBMT 1:ba14d8f4d444 297 {
ThomBMT 1:ba14d8f4d444 298 pc.printf("Relax your muscles please. \r\n");
ThomBMT 1:ba14d8f4d444 299 i = 2;
ThomBMT 1:ba14d8f4d444 300 }
ThomBMT 1:ba14d8f4d444 301 else if (ii == 1750)
ThomBMT 1:ba14d8f4d444 302 {
ThomBMT 1:ba14d8f4d444 303 pc.printf("Flex your right bicep now please.\r\n");
ThomBMT 1:ba14d8f4d444 304 i = 3;
ThomBMT 1:ba14d8f4d444 305 }
ThomBMT 1:ba14d8f4d444 306 //chillen
ThomBMT 1:ba14d8f4d444 307 }
ThomBMT 1:ba14d8f4d444 308 else if (ii>2500 && ii<5000) //
ThomBMT 1:ba14d8f4d444 309 {
ThomBMT 1:ba14d8f4d444 310 n = n + Filtered_Bi_R; // dit wordt de variable naam na het filter
ThomBMT 1:ba14d8f4d444 311 i = 1;
ThomBMT 1:ba14d8f4d444 312 }
ThomBMT 1:ba14d8f4d444 313 else if (ii == 5000)
ThomBMT 1:ba14d8f4d444 314 {
ThomBMT 1:ba14d8f4d444 315 Flex_Bi_R = n / 2500.0f;
ThomBMT 1:ba14d8f4d444 316 pc.printf("You can relax your right bicep, thank you. \r\nYour mean flexing value was %f\r\n\r\n", Flex_Bi_R);
ThomBMT 1:ba14d8f4d444 317 i = 2;
ThomBMT 1:ba14d8f4d444 318 }
ThomBMT 1:ba14d8f4d444 319 else if (ii>5000 && ii<=6000)
ThomBMT 1:ba14d8f4d444 320 {
ThomBMT 1:ba14d8f4d444 321 if (ii == 5500)
ThomBMT 1:ba14d8f4d444 322 {
ThomBMT 1:ba14d8f4d444 323 pc.printf("Flex your left bicep now please. \r\n");
ThomBMT 1:ba14d8f4d444 324 i = 3;
ThomBMT 1:ba14d8f4d444 325 }
ThomBMT 1:ba14d8f4d444 326 //chillen
ThomBMT 1:ba14d8f4d444 327 }
ThomBMT 1:ba14d8f4d444 328 else if(ii>6000 && ii<8500)
ThomBMT 1:ba14d8f4d444 329 {
ThomBMT 1:ba14d8f4d444 330 m = m + Filtered_Bi_L;
ThomBMT 1:ba14d8f4d444 331 i = 1;
ThomBMT 1:ba14d8f4d444 332 }
ThomBMT 1:ba14d8f4d444 333 else if (ii == 8500)
ThomBMT 1:ba14d8f4d444 334 {
ThomBMT 1:ba14d8f4d444 335 Flex_Bi_L = m / 2500.0f;
ThomBMT 1:ba14d8f4d444 336 pc.printf("You can relax your left bicep, thank you. \r\nYour mean flexing value was %f\r\n\r\n", Flex_Bi_L);
ThomBMT 1:ba14d8f4d444 337 i = 2;
ThomBMT 1:ba14d8f4d444 338 }
ThomBMT 1:ba14d8f4d444 339 else if (ii>8500 && ii<=9500)
ThomBMT 1:ba14d8f4d444 340 {
ThomBMT 1:ba14d8f4d444 341 if (ii == 9000)
ThomBMT 1:ba14d8f4d444 342 {
ThomBMT 1:ba14d8f4d444 343 pc.printf("Flex your right tricep now please. \r\n");
ThomBMT 1:ba14d8f4d444 344 i = 3;
ThomBMT 1:ba14d8f4d444 345 }
ThomBMT 1:ba14d8f4d444 346 //chillen
ThomBMT 1:ba14d8f4d444 347 }
ThomBMT 1:ba14d8f4d444 348 else if (ii>9500 && ii<12000)
ThomBMT 1:ba14d8f4d444 349 {
ThomBMT 1:ba14d8f4d444 350 l = l + Filtered_Tri_R;
ThomBMT 1:ba14d8f4d444 351 i = 1;
ThomBMT 1:ba14d8f4d444 352 }
ThomBMT 1:ba14d8f4d444 353 else if (ii == 12000)
ThomBMT 1:ba14d8f4d444 354 {
ThomBMT 1:ba14d8f4d444 355 Flex_Tri_R = l / 2500.0f;
ThomBMT 1:ba14d8f4d444 356 pc.printf("You can relax your right tricep, thank you. \r\nYour mean flexing value was %f\r\n\r\n", Flex_Tri_R);
ThomBMT 1:ba14d8f4d444 357 i = 2;
ThomBMT 1:ba14d8f4d444 358 }
ThomBMT 1:ba14d8f4d444 359 else if (ii>12000 && ii <=13000)
ThomBMT 1:ba14d8f4d444 360 {
ThomBMT 1:ba14d8f4d444 361 if (ii == 12500)
ThomBMT 1:ba14d8f4d444 362 {
ThomBMT 1:ba14d8f4d444 363 pc.printf("Flex your left tricep now please. \r\n");
ThomBMT 1:ba14d8f4d444 364 i = 3;
ThomBMT 1:ba14d8f4d444 365 }
ThomBMT 1:ba14d8f4d444 366 //chillen
ThomBMT 1:ba14d8f4d444 367 }
ThomBMT 1:ba14d8f4d444 368 else if (ii>13000 && ii<15500)
ThomBMT 1:ba14d8f4d444 369 {
ThomBMT 1:ba14d8f4d444 370 k = k + Filtered_Tri_L;
ThomBMT 1:ba14d8f4d444 371 i = 1;
ThomBMT 1:ba14d8f4d444 372 }
ThomBMT 1:ba14d8f4d444 373 else if (ii == 15500)
ThomBMT 1:ba14d8f4d444 374 {
ThomBMT 1:ba14d8f4d444 375 Flex_Tri_L = k / 2500.0f;
ThomBMT 1:ba14d8f4d444 376 pc.printf("You can relax your left tricep, thank you. \r\nYour mean flexing value was %f\r\n\r\nThe calibration has been completed, the system is now operatable. \r\n",Flex_Tri_L);
ThomBMT 1:ba14d8f4d444 377 i = 2;
ThomBMT 1:ba14d8f4d444 378 }
ThomBMT 3:766e9f13d84e 379
ThomBMT 3:766e9f13d84e 380 // Setting the Threshold:
ThomBMT 4:a682fb1f37d2 381 Threshold_Value = 0.85f;
ThomBMT 1:ba14d8f4d444 382
ThomBMT 1:ba14d8f4d444 383 Threshold_Bi_R = Threshold_Value * Flex_Bi_R;
ThomBMT 1:ba14d8f4d444 384 Threshold_Bi_L = Threshold_Value * Flex_Bi_L;
ThomBMT 1:ba14d8f4d444 385 Threshold_Tri_R = Threshold_Value * Flex_Tri_R;
ThomBMT 1:ba14d8f4d444 386 Threshold_Tri_L = Threshold_Value * Flex_Tri_L;
ThomBMT 1:ba14d8f4d444 387
ThomBMT 1:ba14d8f4d444 388 if (ii == 16500)
ThomBMT 1:ba14d8f4d444 389 {
ThomBMT 1:ba14d8f4d444 390 pc.printf("\r\nThreshold value right bicep = %f\r\nThreshold value left bicep = %f\r\nThreshold value right tricep = %f\r\nThreshold value left tricep = %f\r\n\r\n",Threshold_Bi_R,Threshold_Bi_L,Threshold_Tri_R,Threshold_Tri_L);
ThomBMT 1:ba14d8f4d444 391 }
ThomBMT 1:ba14d8f4d444 392 else if (ii == 20000)
ThomBMT 1:ba14d8f4d444 393 {
ThomBMT 3:766e9f13d84e 394 pc.printf("\r\nAutomatic switch to Homing State for Motor 1\r\n");
ThomBMT 4:a682fb1f37d2 395 Active_State = Function;
ThomBMT 1:ba14d8f4d444 396 i = 0;
ThomBMT 1:ba14d8f4d444 397 }
ThomBMT 1:ba14d8f4d444 398 }
ThomBMT 1:ba14d8f4d444 399
ThomBMT 1:ba14d8f4d444 400
ThomBMT 1:ba14d8f4d444 401
ThomBMT 1:ba14d8f4d444 402 void Start_Up()
ThomBMT 1:ba14d8f4d444 403 {
ThomBMT 3:766e9f13d84e 404 // This function is active only when the system is started up or when the
ThomBMT 3:766e9f13d84e 405 // system has entered Sleep_Mode (iii > 40 000).
ThomBMT 3:766e9f13d84e 406 // It is not possible to get out of this function without some opperation on
ThomBMT 3:766e9f13d84e 407 // the Mbed.
ThomBMT 3:766e9f13d84e 408
ThomBMT 1:ba14d8f4d444 409 i++;
ThomBMT 1:ba14d8f4d444 410 iii++;
ThomBMT 1:ba14d8f4d444 411 if (iii == 1)
ThomBMT 1:ba14d8f4d444 412 {
ThomBMT 1:ba14d8f4d444 413 pc.printf("\r\n\r\nSystem is starting...\r\nWaiting for further input...\r\n");
ThomBMT 1:ba14d8f4d444 414 }
ThomBMT 1:ba14d8f4d444 415
ThomBMT 1:ba14d8f4d444 416 else if (iii == 30000)
ThomBMT 1:ba14d8f4d444 417 {
ThomBMT 1:ba14d8f4d444 418 pc.printf("1 minute without input..\r\nReseting start-up...\r\n");
ThomBMT 1:ba14d8f4d444 419 iii = 0;
ThomBMT 1:ba14d8f4d444 420 }
ThomBMT 1:ba14d8f4d444 421 else if (iii == 40001) // sleeping state is only added for designing purposes and will most likely never be used
ThomBMT 1:ba14d8f4d444 422 { // when working with patients. Furthermore it cannot be reached automaticly
ThomBMT 1:ba14d8f4d444 423 pc.printf("Sleeping... Press button 4 to wake me up!\r\n\r\n");
ThomBMT 1:ba14d8f4d444 424 iii++;
ThomBMT 1:ba14d8f4d444 425 }
ThomBMT 1:ba14d8f4d444 426 else if (iii == 45000)
ThomBMT 1:ba14d8f4d444 427 {
ThomBMT 1:ba14d8f4d444 428 iii = 40000;
ThomBMT 1:ba14d8f4d444 429 }
ThomBMT 1:ba14d8f4d444 430 }
ThomBMT 1:ba14d8f4d444 431
ThomBMT 1:ba14d8f4d444 432 void OFF_m1()
ThomBMT 1:ba14d8f4d444 433 {
ThomBMT 3:766e9f13d84e 434 // This function ensures that Motor 1 is turned off.
ThomBMT 3:766e9f13d84e 435
ThomBMT 1:ba14d8f4d444 436 PwmPin1 = 0;
ThomBMT 1:ba14d8f4d444 437 }
ThomBMT 1:ba14d8f4d444 438 void OFF_m2()
ThomBMT 1:ba14d8f4d444 439 {
ThomBMT 3:766e9f13d84e 440 // This function ensures that Motor 2 is turned off.
ThomBMT 3:766e9f13d84e 441
ThomBMT 1:ba14d8f4d444 442 PwmPin2 = 0;
ThomBMT 1:ba14d8f4d444 443 }
ThomBMT 1:ba14d8f4d444 444
ThomBMT 1:ba14d8f4d444 445 void Going_Home_Motor1()
ThomBMT 1:ba14d8f4d444 446 {
ThomBMT 3:766e9f13d84e 447 // This is the Homing function for Motor 1.
ThomBMT 3:766e9f13d84e 448
ThomBMT 1:ba14d8f4d444 449 if (counts1 == 0)
ThomBMT 1:ba14d8f4d444 450 {
ThomBMT 3:766e9f13d84e 451 pc.printf("Switching to Homing State for Motor 2\r\n");
ThomBMT 4:a682fb1f37d2 452 Active_State = Function; // Statement here instead of statemachine because of checking speed
ThomBMT 1:ba14d8f4d444 453 }
ThomBMT 1:ba14d8f4d444 454 else if (counts1 > 0)
ThomBMT 1:ba14d8f4d444 455 {
ThomBMT 4:a682fb1f37d2 456 PwmPin1 = 0.5f;
ThomBMT 1:ba14d8f4d444 457 DirectionPin1 = false;
ThomBMT 1:ba14d8f4d444 458 }
ThomBMT 1:ba14d8f4d444 459 else
ThomBMT 1:ba14d8f4d444 460 {
ThomBMT 4:a682fb1f37d2 461 PwmPin1 = 0.5f;
ThomBMT 1:ba14d8f4d444 462 DirectionPin1 = true;
ThomBMT 1:ba14d8f4d444 463 }
ThomBMT 1:ba14d8f4d444 464 }
ThomBMT 1:ba14d8f4d444 465
ThomBMT 1:ba14d8f4d444 466 void Going_Home_Motor2()
ThomBMT 1:ba14d8f4d444 467 {
ThomBMT 3:766e9f13d84e 468 // This is the Homing function for Motor 2.
ThomBMT 3:766e9f13d84e 469
ThomBMT 1:ba14d8f4d444 470 if (counts2 == 0)
ThomBMT 1:ba14d8f4d444 471 {
ThomBMT 1:ba14d8f4d444 472 // als het goed is hoeft hier niets te staan // Statement in statemachine because of the double check
ThomBMT 1:ba14d8f4d444 473 }
ThomBMT 1:ba14d8f4d444 474 else if (counts2 > 0)
ThomBMT 1:ba14d8f4d444 475 {
ThomBMT 4:a682fb1f37d2 476 PwmPin2 = 0.5f;
ThomBMT 1:ba14d8f4d444 477 DirectionPin2 = true;
ThomBMT 1:ba14d8f4d444 478 }
ThomBMT 1:ba14d8f4d444 479 else
ThomBMT 1:ba14d8f4d444 480 {
ThomBMT 4:a682fb1f37d2 481 PwmPin2 = 0.5f;
ThomBMT 1:ba14d8f4d444 482 DirectionPin2 = false;
ThomBMT 1:ba14d8f4d444 483 }
ThomBMT 1:ba14d8f4d444 484 }
ThomBMT 1:ba14d8f4d444 485
ThomBMT 1:ba14d8f4d444 486 void Checking_EMG()
ThomBMT 1:ba14d8f4d444 487 {
ThomBMT 3:766e9f13d84e 488 // This function will make the the setting of signal to movement easier.
ThomBMT 1:ba14d8f4d444 489
ThomBMT 1:ba14d8f4d444 490 if (Filtered_Bi_R >= Threshold_Bi_R)
ThomBMT 1:ba14d8f4d444 491 {
ThomBMT 1:ba14d8f4d444 492 Checking_Bi_R = true;
ThomBMT 1:ba14d8f4d444 493 }
ThomBMT 1:ba14d8f4d444 494 if (Filtered_Bi_L >= Threshold_Bi_L)
ThomBMT 1:ba14d8f4d444 495 {
ThomBMT 1:ba14d8f4d444 496 Checking_Bi_L = true;
ThomBMT 1:ba14d8f4d444 497 }
ThomBMT 1:ba14d8f4d444 498 if (Filtered_Tri_R >= Threshold_Tri_R)
ThomBMT 1:ba14d8f4d444 499 {
ThomBMT 1:ba14d8f4d444 500 Checking_Tri_R = true;
ThomBMT 1:ba14d8f4d444 501 }
ThomBMT 1:ba14d8f4d444 502 if (Filtered_Tri_L >= Threshold_Tri_L)
ThomBMT 1:ba14d8f4d444 503 {
ThomBMT 1:ba14d8f4d444 504 Checking_Tri_L = true;
ThomBMT 1:ba14d8f4d444 505 }
ThomBMT 1:ba14d8f4d444 506 }
ThomBMT 1:ba14d8f4d444 507
ThomBMT 1:ba14d8f4d444 508 void Setting_Movement()
ThomBMT 1:ba14d8f4d444 509 {
ThomBMT 3:766e9f13d84e 510 // Here we will set the emg values to the movement of the arm.
ThomBMT 1:ba14d8f4d444 511
ThomBMT 1:ba14d8f4d444 512 if (Checking_Bi_R && Checking_Bi_L) // sloping y = x, y > 0
ThomBMT 1:ba14d8f4d444 513 {
ThomBMT 4:a682fb1f37d2 514 vx = 0.01f;
ThomBMT 4:a682fb1f37d2 515 vy = 0.01f;
ThomBMT 1:ba14d8f4d444 516 }
ThomBMT 1:ba14d8f4d444 517 else if (Checking_Bi_R && Checking_Tri_L) // sloping y = -x, y > 0
ThomBMT 1:ba14d8f4d444 518 {
ThomBMT 4:a682fb1f37d2 519 vx = -0.01f;
ThomBMT 4:a682fb1f37d2 520 vy = 0.01f;
ThomBMT 1:ba14d8f4d444 521 }
ThomBMT 1:ba14d8f4d444 522 else if (Checking_Bi_L && Checking_Tri_R) // sloping y = -x, y < 0
ThomBMT 1:ba14d8f4d444 523 {
ThomBMT 4:a682fb1f37d2 524 vx = 0.01f;
ThomBMT 4:a682fb1f37d2 525 vy = -0.01f;
ThomBMT 1:ba14d8f4d444 526 }
ThomBMT 1:ba14d8f4d444 527 else if (Checking_Tri_R && Checking_Tri_L) // sloping y = x, y < 0
ThomBMT 1:ba14d8f4d444 528 {
ThomBMT 4:a682fb1f37d2 529 vx = -0.01f;
ThomBMT 4:a682fb1f37d2 530 vy = -0.01f;
ThomBMT 1:ba14d8f4d444 531 }
ThomBMT 4:a682fb1f37d2 532 if (Checking_Bi_R) // y > 0
ThomBMT 1:ba14d8f4d444 533 {
ThomBMT 1:ba14d8f4d444 534 vx = 0.0f;
ThomBMT 4:a682fb1f37d2 535 vy = 0.01f;
ThomBMT 1:ba14d8f4d444 536 }
ThomBMT 1:ba14d8f4d444 537 else if (Checking_Bi_L) // x > 0
ThomBMT 1:ba14d8f4d444 538 {
ThomBMT 4:a682fb1f37d2 539 vx = 0.01f;
ThomBMT 1:ba14d8f4d444 540 vy = 0.0f;
ThomBMT 1:ba14d8f4d444 541 }
ThomBMT 4:a682fb1f37d2 542 else if (Checking_Tri_R) // x < 0
ThomBMT 1:ba14d8f4d444 543 {
ThomBMT 1:ba14d8f4d444 544 vx = 0.0f;
ThomBMT 4:a682fb1f37d2 545 vy = -0.01f;
ThomBMT 1:ba14d8f4d444 546 }
ThomBMT 1:ba14d8f4d444 547 else if (Checking_Tri_L) // y < 0
ThomBMT 1:ba14d8f4d444 548 {
ThomBMT 4:a682fb1f37d2 549 vx = -0.01f;
ThomBMT 1:ba14d8f4d444 550 vy = 0.0f;
ThomBMT 1:ba14d8f4d444 551 }
ThomBMT 1:ba14d8f4d444 552 }
ThomBMT 1:ba14d8f4d444 553
ThomBMT 4:a682fb1f37d2 554
ThomBMT 4:a682fb1f37d2 555 void Inverse()
ThomBMT 4:a682fb1f37d2 556 {
ThomBMT 4:a682fb1f37d2 557 // Here we calculate the movement of each joint (Motor 1 and Motor 2) given
ThomBMT 4:a682fb1f37d2 558 // a certain linear velocity-input.
ThomBMT 4:a682fb1f37d2 559 q_ref1_n = q_ref1_o+w_1*Ts;
ThomBMT 4:a682fb1f37d2 560 q_ref2_n = q_ref2_o+w_2*Ts;
ThomBMT 4:a682fb1f37d2 561 r_1= -0.2f;
ThomBMT 4:a682fb1f37d2 562 r_2= -0.2f;
ThomBMT 4:a682fb1f37d2 563
ThomBMT 4:a682fb1f37d2 564 float u = -r_2*sin(q_ref1_n)*cos(q_ref2_n)-(r_2)*cos(q_ref1_n)*sin(q_ref2_n);
ThomBMT 4:a682fb1f37d2 565 float z = 2.0f*(r_2*cos(q_ref1_n)*cos(q_ref2_n))-r_3;
ThomBMT 4:a682fb1f37d2 566 float y = r_2*cos(q_ref1_n)*cos(q_ref2_n)-r_2*sin(q_ref1_n)*sin(q_ref2_n)+2.0f*(r_1*cos(q_ref1_n))-r_3;
ThomBMT 4:a682fb1f37d2 567 float x = (-2.0f)*r_2*sin(q_ref1_n)*cos(q_ref2_n);
ThomBMT 4:a682fb1f37d2 568 float D = 1.0f/(u*z-x*y); // Determinant
ThomBMT 4:a682fb1f37d2 569 //printf("Determinant is %f\r\n", D);
ThomBMT 4:a682fb1f37d2 570
ThomBMT 4:a682fb1f37d2 571 float a = D*z; // Inverse jacobian a,b,c,d vormen 2 bij 2 matrix
ThomBMT 4:a682fb1f37d2 572 float b = -D*x; // Inverse jacobian
ThomBMT 4:a682fb1f37d2 573 float c = -D*y; // Inverse jacobian
ThomBMT 4:a682fb1f37d2 574 float d = D*u; // Inverse jacobian
ThomBMT 4:a682fb1f37d2 575
ThomBMT 4:a682fb1f37d2 576 float referenceVelocity1;
ThomBMT 4:a682fb1f37d2 577 if (pot1.read()>0.8f)
ThomBMT 4:a682fb1f37d2 578 {
ThomBMT 4:a682fb1f37d2 579 // Clockwise rotation
ThomBMT 4:a682fb1f37d2 580 referenceVelocity1 = 0.005f;
ThomBMT 4:a682fb1f37d2 581 }
ThomBMT 4:a682fb1f37d2 582
ThomBMT 4:a682fb1f37d2 583
ThomBMT 4:a682fb1f37d2 584
ThomBMT 4:a682fb1f37d2 585 else if (pot1.read() < 0.2f)
ThomBMT 4:a682fb1f37d2 586 {
ThomBMT 4:a682fb1f37d2 587 // Counterclockwise rotation
ThomBMT 4:a682fb1f37d2 588 referenceVelocity1 = -0.005f ;
ThomBMT 4:a682fb1f37d2 589 }
ThomBMT 4:a682fb1f37d2 590
ThomBMT 4:a682fb1f37d2 591 else
ThomBMT 4:a682fb1f37d2 592 {
ThomBMT 4:a682fb1f37d2 593 referenceVelocity1 = pot1.read() * 0.0f;
ThomBMT 4:a682fb1f37d2 594 }
ThomBMT 4:a682fb1f37d2 595 float referenceVelocity2;
ThomBMT 4:a682fb1f37d2 596
ThomBMT 4:a682fb1f37d2 597 // This is where Motor 2 is opperated.
ThomBMT 4:a682fb1f37d2 598
ThomBMT 4:a682fb1f37d2 599 if (pot2.read()>0.8f)
ThomBMT 4:a682fb1f37d2 600 {
ThomBMT 4:a682fb1f37d2 601 // Clockwise rotation
ThomBMT 4:a682fb1f37d2 602 referenceVelocity2 = 0.005f;
ThomBMT 4:a682fb1f37d2 603 }
ThomBMT 4:a682fb1f37d2 604
ThomBMT 4:a682fb1f37d2 605 else if (pot2.read() < 0.2f)
ThomBMT 4:a682fb1f37d2 606 {
ThomBMT 4:a682fb1f37d2 607 // Counterclockwise rotation
ThomBMT 4:a682fb1f37d2 608 referenceVelocity2 = -0.005f ;
ThomBMT 4:a682fb1f37d2 609 }
ThomBMT 4:a682fb1f37d2 610
ThomBMT 4:a682fb1f37d2 611 else
ThomBMT 4:a682fb1f37d2 612 {
ThomBMT 4:a682fb1f37d2 613 referenceVelocity2 = pot2.read() * 0.0f;
ThomBMT 4:a682fb1f37d2 614 }
ThomBMT 4:a682fb1f37d2 615
ThomBMT 4:a682fb1f37d2 616 //vx = 0.0;//referenceVelocity1; // uit emg data
ThomBMT 4:a682fb1f37d2 617 //vy = 0.01;referenceVelocity2; // uit emg data
ThomBMT 4:a682fb1f37d2 618
ThomBMT 4:a682fb1f37d2 619 w_1 = vx*a+vy*b;
ThomBMT 4:a682fb1f37d2 620 w_2 = vx*c+vy*d;
ThomBMT 4:a682fb1f37d2 621
ThomBMT 4:a682fb1f37d2 622
ThomBMT 4:a682fb1f37d2 623 q_ref1_o = q_ref1_n;
ThomBMT 4:a682fb1f37d2 624 q_ref2_o = q_ref2_n;
ThomBMT 4:a682fb1f37d2 625 }
ThomBMT 4:a682fb1f37d2 626
ThomBMT 4:a682fb1f37d2 627
ThomBMT 4:a682fb1f37d2 628 void PID_controller()
ThomBMT 2:bc6043623fb7 629 {
ThomBMT 3:766e9f13d84e 630 // The PID-controller reduces the error between the reference signal
ThomBMT 3:766e9f13d84e 631 // and the actual value.
ThomBMT 3:766e9f13d84e 632
ThomBMT 4:a682fb1f37d2 633 error_1 = q_ref1_o - rad_m2 + (w_1*Ts);
ThomBMT 4:a682fb1f37d2 634 error_2 = q_ref2_o - rad_m1 + (w_2*Ts);
ThomBMT 2:bc6043623fb7 635
ThomBMT 2:bc6043623fb7 636 error_1_prev = error_1;
ThomBMT 2:bc6043623fb7 637 error_2_prev = error_2;
ThomBMT 2:bc6043623fb7 638
ThomBMT 2:bc6043623fb7 639 // Proportional part:
ThomBMT 4:a682fb1f37d2 640 u_k_1 = Kp * error_1;
ThomBMT 4:a682fb1f37d2 641 u_k_2 = Kp * error_2;
ThomBMT 2:bc6043623fb7 642
ThomBMT 2:bc6043623fb7 643 // Integral part
ThomBMT 2:bc6043623fb7 644 error_1_integral = error_1_integral + error_1 * Ts;
ThomBMT 2:bc6043623fb7 645 error_2_integral = error_2_integral + error_2 * Ts;
ThomBMT 4:a682fb1f37d2 646 u_i_1 = Ki * error_1_integral;
ThomBMT 4:a682fb1f37d2 647 u_i_2 = Ki * error_2_integral;
ThomBMT 2:bc6043623fb7 648
ThomBMT 2:bc6043623fb7 649 // Derivative part
ThomBMT 2:bc6043623fb7 650 float error_1_derivative = (error_1 - error_1_prev)/Ts;
ThomBMT 2:bc6043623fb7 651 float error_2_derivative = (error_2 - error_2_prev)/Ts;
ThomBMT 4:a682fb1f37d2 652 //float filtered_error_1_derivative = LowPassFilter.step(error_1_derivative);
ThomBMT 4:a682fb1f37d2 653 //float filtered_error_2_derivative = LowPassFilter.step(error_2_derivative);
ThomBMT 4:a682fb1f37d2 654
ThomBMT 4:a682fb1f37d2 655 u_d_1 = Kd * error_1_derivative;
ThomBMT 4:a682fb1f37d2 656 u_d_2 = Kd * error_2_derivative;
ThomBMT 4:a682fb1f37d2 657
ThomBMT 2:bc6043623fb7 658 error_1_prev = error_1;
ThomBMT 2:bc6043623fb7 659 error_2_prev = error_2;
ThomBMT 2:bc6043623fb7 660
ThomBMT 2:bc6043623fb7 661 // Sum all parts and return it
ThomBMT 4:a682fb1f37d2 662 U_1 = u_k_1; //+ u_i_1 + u_d_1;
ThomBMT 4:a682fb1f37d2 663 U_2 = u_k_2;//+ u_i_2 + u_d_2;
ThomBMT 4:a682fb1f37d2 664
ThomBMT 2:bc6043623fb7 665 }
ThomBMT 2:bc6043623fb7 666
ThomBMT 2:bc6043623fb7 667 void motor1()
ThomBMT 4:a682fb1f37d2 668 {
ThomBMT 4:a682fb1f37d2 669 // This is where Motor 1 is operated.
ThomBMT 3:766e9f13d84e 670
ThomBMT 4:a682fb1f37d2 671 float u = 0.4f + 0.6f* fabs(U_1);
ThomBMT 2:bc6043623fb7 672 PwmPin1 = fabs(u);
ThomBMT 4:a682fb1f37d2 673 if (U_1 >= 0)
ThomBMT 4:a682fb1f37d2 674 {
ThomBMT 4:a682fb1f37d2 675 DirectionPin1 = false;
ThomBMT 4:a682fb1f37d2 676 }
ThomBMT 4:a682fb1f37d2 677 else if (U_1 < 0)
ThomBMT 4:a682fb1f37d2 678 {
ThomBMT 4:a682fb1f37d2 679 DirectionPin1 = true;
ThomBMT 4:a682fb1f37d2 680 }
ThomBMT 4:a682fb1f37d2 681
ThomBMT 2:bc6043623fb7 682 }
ThomBMT 2:bc6043623fb7 683
ThomBMT 2:bc6043623fb7 684 void motor2()
ThomBMT 4:a682fb1f37d2 685 {
ThomBMT 4:a682fb1f37d2 686 float u = 0.4f+ 0.6f* fabs(U_2);
ThomBMT 2:bc6043623fb7 687 PwmPin2 = fabs(u);
ThomBMT 4:a682fb1f37d2 688 if (U_2 <= 0)
ThomBMT 4:a682fb1f37d2 689 {
ThomBMT 4:a682fb1f37d2 690 DirectionPin2 = false;
ThomBMT 4:a682fb1f37d2 691 }
ThomBMT 4:a682fb1f37d2 692 else if (U_2 > 0)
ThomBMT 4:a682fb1f37d2 693 {
ThomBMT 4:a682fb1f37d2 694 DirectionPin2 = true;
ThomBMT 4:a682fb1f37d2 695 }
ThomBMT 4:a682fb1f37d2 696 //DirectionPin2 = u > 0.0f;
ThomBMT 4:a682fb1f37d2 697
ThomBMT 2:bc6043623fb7 698 }
ThomBMT 2:bc6043623fb7 699
ThomBMT 1:ba14d8f4d444 700 void Printing()
ThomBMT 1:ba14d8f4d444 701 {
ThomBMT 3:766e9f13d84e 702 // This function is merely for printing feedback from the system to our
ThomBMT 3:766e9f13d84e 703 // screen when we wish to see or check something.
ThomBMT 4:a682fb1f37d2 704
ThomBMT 3:766e9f13d84e 705 if (Active_State == Function )//|| Active_State == Homing_M1)
ThomBMT 1:ba14d8f4d444 706 {
ThomBMT 4:a682fb1f37d2 707 pc.printf("U_K1 is %f \r\nU_K2 is %f \r\n\r\n rad_m1 is %f \r\n rad_m2 is %f \r\n\r\n Bi_R is %f \r\n Bi_L is %f \r\n\r\n counts1 is %i \r\n counts2 is %i\r\n\r\n", u_k_1, u_k_2, rad_m1, rad_m2, Filtered_Bi_R, Filtered_Bi_L, counts1, counts2);
ThomBMT 4:a682fb1f37d2 708 //u_k_1 + u_i_1 + u_d_1;
ThomBMT 4:a682fb1f37d2 709 //u_k_2 + u_i_2 + u_d_2;
ThomBMT 4:a682fb1f37d2 710 //pc.printf("q1 = %f [rad] \r\nq2 = %f [rad] \r\ncount1= %i\r\ncount2= %i\r\nq1dot = %f [rad/s] \r\nq2dot = %f [rad/s] \r\n\r\n", rad_m1, rad_m2,counts1, counts2, w_1, w_2);
ThomBMT 4:a682fb1f37d2 711 // pc.printf("U_1 = %f [error] \r\nU_2 = %f [error]\n\r\n",U_1,U_2);
ThomBMT 4:a682fb1f37d2 712 //pc.printf("u_k_1 = %f\r\nu_k_2 = %f\r\nu_i_1 = %f \r\nu_i_2 = %f \r\nu_d_1 = %f \r\nu_d_2 = %f\r\n\r\n",u_k_1,u_k_2,u_i_1,u_i_2,u_d_1,u_d_2);
ThomBMT 1:ba14d8f4d444 713 }
ThomBMT 1:ba14d8f4d444 714 }
ThomBMT 1:ba14d8f4d444 715
ThomBMT 2:bc6043623fb7 716 void EMG_test() // even nalopen of dit ook kan met i++!
ThomBMT 1:ba14d8f4d444 717 {
ThomBMT 3:766e9f13d84e 718 // Here we can check the opperation of the system for checking purposes.
ThomBMT 3:766e9f13d84e 719
ThomBMT 1:ba14d8f4d444 720 led_G=led_R=led_B=1;
ThomBMT 1:ba14d8f4d444 721
ThomBMT 1:ba14d8f4d444 722 if (Filtered_Bi_R >= Threshold_Bi_R)
ThomBMT 1:ba14d8f4d444 723 {
ThomBMT 1:ba14d8f4d444 724 i = 1;
ThomBMT 1:ba14d8f4d444 725 //led_R = 0; // rood
ThomBMT 1:ba14d8f4d444 726 }
ThomBMT 1:ba14d8f4d444 727 if (Filtered_Bi_L >= Threshold_Bi_L)
ThomBMT 1:ba14d8f4d444 728 {
ThomBMT 1:ba14d8f4d444 729 i = 3;
ThomBMT 1:ba14d8f4d444 730 //led_B = 0; // blauw
ThomBMT 1:ba14d8f4d444 731 }
ThomBMT 1:ba14d8f4d444 732 if (Filtered_Tri_R >= Threshold_Tri_R)
ThomBMT 1:ba14d8f4d444 733 {
ThomBMT 1:ba14d8f4d444 734 i = 2;
ThomBMT 1:ba14d8f4d444 735 //led_G = 0; // groen
ThomBMT 1:ba14d8f4d444 736 }
ThomBMT 1:ba14d8f4d444 737 if (Filtered_Tri_L >= Threshold_Tri_L)
ThomBMT 1:ba14d8f4d444 738 {
ThomBMT 1:ba14d8f4d444 739 i = 4;
ThomBMT 1:ba14d8f4d444 740 //led_B = 0;
ThomBMT 1:ba14d8f4d444 741 //led_R = 0; // paars
ThomBMT 1:ba14d8f4d444 742 }
ThomBMT 1:ba14d8f4d444 743
ThomBMT 1:ba14d8f4d444 744 }
ThomBMT 1:ba14d8f4d444 745
ThomBMT 1:ba14d8f4d444 746 void StateMachine()
ThomBMT 1:ba14d8f4d444 747 {
ThomBMT 3:766e9f13d84e 748 // In the Statemachine every function is integrated into the system
ThomBMT 3:766e9f13d84e 749 // depending on the state that the system is in. This is makes the
ThomBMT 3:766e9f13d84e 750 // integration and the opperation of the system a lot simpeler.
ThomBMT 3:766e9f13d84e 751
ThomBMT 3:766e9f13d84e 752 // We have 5 main states:
ThomBMT 4:a682fb1f37d2 753 //
ThomBMT 3:766e9f13d84e 754 // - Starting
ThomBMT 3:766e9f13d84e 755 // - Start_Up
ThomBMT 3:766e9f13d84e 756 // - Sleep_Mode
ThomBMT 3:766e9f13d84e 757 // - Calibration
ThomBMT 3:766e9f13d84e 758 // - Homing
ThomBMT 3:766e9f13d84e 759 // - Homing_M1
ThomBMT 3:766e9f13d84e 760 // - Homing_M2
ThomBMT 3:766e9f13d84e 761 // - Post_Homing
ThomBMT 3:766e9f13d84e 762 // - Function
ThomBMT 3:766e9f13d84e 763 // - Safe
ThomBMT 3:766e9f13d84e 764
ThomBMT 3:766e9f13d84e 765 // As seen above some states have substates that make the system run better
ThomBMT 3:766e9f13d84e 766 // or give the state some unique features. These are explained within the
ThomBMT 3:766e9f13d84e 767 // functions that are called in that state.
ThomBMT 3:766e9f13d84e 768
ThomBMT 1:ba14d8f4d444 769 switch (Active_State)
ThomBMT 1:ba14d8f4d444 770 {
ThomBMT 1:ba14d8f4d444 771 case Starting:
ThomBMT 1:ba14d8f4d444 772 Start_Up();
ThomBMT 1:ba14d8f4d444 773 OFF_m1();
ThomBMT 1:ba14d8f4d444 774 OFF_m2();
ThomBMT 1:ba14d8f4d444 775
ThomBMT 1:ba14d8f4d444 776 if (!Knop4 == true)
ThomBMT 1:ba14d8f4d444 777 {
ThomBMT 1:ba14d8f4d444 778 Active_State = Calibration;
ThomBMT 1:ba14d8f4d444 779 pc.printf("Entering Calibration State \r\n");
ThomBMT 1:ba14d8f4d444 780 }
ThomBMT 1:ba14d8f4d444 781 else if (!Knop3 == true)
ThomBMT 1:ba14d8f4d444 782 {
ThomBMT 1:ba14d8f4d444 783 Active_State = Homing_M1;
ThomBMT 1:ba14d8f4d444 784 pc.printf("Entering Homing State \r\n");
ThomBMT 1:ba14d8f4d444 785 }
ThomBMT 1:ba14d8f4d444 786
ThomBMT 1:ba14d8f4d444 787
ThomBMT 1:ba14d8f4d444 788 break;
ThomBMT 1:ba14d8f4d444 789
ThomBMT 1:ba14d8f4d444 790 case Calibration:
ThomBMT 1:ba14d8f4d444 791
ThomBMT 1:ba14d8f4d444 792 Filter();
ThomBMT 1:ba14d8f4d444 793 Calibrating();
ThomBMT 1:ba14d8f4d444 794 OFF_m1();
ThomBMT 1:ba14d8f4d444 795 OFF_m2();
ThomBMT 1:ba14d8f4d444 796 BlinkLed();
ThomBMT 1:ba14d8f4d444 797
ThomBMT 1:ba14d8f4d444 798 if (!Knop1 && !Knop2)
ThomBMT 1:ba14d8f4d444 799 {
ThomBMT 1:ba14d8f4d444 800 pc.printf("Switched to Sleeping State\r\n");
ThomBMT 1:ba14d8f4d444 801 Active_State = Starting;
ThomBMT 1:ba14d8f4d444 802 iii = 40001;
ThomBMT 1:ba14d8f4d444 803 }
ThomBMT 1:ba14d8f4d444 804 else if (Knop1==false)
ThomBMT 1:ba14d8f4d444 805 {
ThomBMT 1:ba14d8f4d444 806 pc.printf("Manual switch to Homing state \r\n");
ThomBMT 4:a682fb1f37d2 807 Active_State = Function;
ThomBMT 1:ba14d8f4d444 808 }
ThomBMT 1:ba14d8f4d444 809
ThomBMT 1:ba14d8f4d444 810
ThomBMT 1:ba14d8f4d444 811 sample();
ThomBMT 2:bc6043623fb7 812 EMG_Read();
ThomBMT 1:ba14d8f4d444 813 break;
ThomBMT 1:ba14d8f4d444 814
ThomBMT 1:ba14d8f4d444 815 case Homing_M1:
ThomBMT 1:ba14d8f4d444 816
ThomBMT 1:ba14d8f4d444 817 Going_Home_Motor1();
ThomBMT 1:ba14d8f4d444 818 OFF_m2();
ThomBMT 2:bc6043623fb7 819 Encoding();
ThomBMT 1:ba14d8f4d444 820
ThomBMT 4:a682fb1f37d2 821 if (fabs(rad_m1)>(2.0f*pi/6.0f) || fabs(rad_m2)>(pi/6.0f)) // pi/4 is a safe value, can/will be editted
ThomBMT 1:ba14d8f4d444 822 {
ThomBMT 1:ba14d8f4d444 823 pc.printf("SAFE MODUS ACTIVE!\r\n RESET MANDATORY!\r\n");
ThomBMT 1:ba14d8f4d444 824 Active_State = Safe;
ThomBMT 1:ba14d8f4d444 825 }
ThomBMT 1:ba14d8f4d444 826 else if (!Knop1 && !Knop2)
ThomBMT 1:ba14d8f4d444 827 {
ThomBMT 1:ba14d8f4d444 828 pc.printf("Switched to Sleeping State\r\n");
ThomBMT 1:ba14d8f4d444 829 Active_State = Starting;
ThomBMT 1:ba14d8f4d444 830 iii = 40000;
ThomBMT 1:ba14d8f4d444 831 }
ThomBMT 1:ba14d8f4d444 832 else if (Knop2==false)
ThomBMT 1:ba14d8f4d444 833 {
ThomBMT 1:ba14d8f4d444 834 pc.printf("Manual switch to Funtioning State \r\n");
ThomBMT 1:ba14d8f4d444 835 Active_State = Function;
ThomBMT 1:ba14d8f4d444 836 }
ThomBMT 1:ba14d8f4d444 837 else if (Knop4==false)
ThomBMT 1:ba14d8f4d444 838 {
ThomBMT 1:ba14d8f4d444 839 Active_State = Calibration;
ThomBMT 1:ba14d8f4d444 840 pc.printf("Re-entering Calibration State \r\n");
ThomBMT 1:ba14d8f4d444 841 }
ThomBMT 2:bc6043623fb7 842
ThomBMT 1:ba14d8f4d444 843 break;
ThomBMT 1:ba14d8f4d444 844
ThomBMT 1:ba14d8f4d444 845 case Homing_M2:
ThomBMT 1:ba14d8f4d444 846
ThomBMT 1:ba14d8f4d444 847 Going_Home_Motor2();
ThomBMT 1:ba14d8f4d444 848 OFF_m1();
ThomBMT 2:bc6043623fb7 849 Encoding();
ThomBMT 1:ba14d8f4d444 850
ThomBMT 1:ba14d8f4d444 851 if (fabs(rad_m1)>(pi/6.0f) || fabs(rad_m2)>(pi/6.0f)) // pi/4 is a safe value, can/will be editted
ThomBMT 1:ba14d8f4d444 852 {
ThomBMT 1:ba14d8f4d444 853 pc.printf("SAFE MODUS ACTIVE!\r\n RESET MANDATORY!\r\n");
ThomBMT 1:ba14d8f4d444 854 Active_State = Safe;
ThomBMT 1:ba14d8f4d444 855 }
ThomBMT 1:ba14d8f4d444 856 else if (counts2 == 0 && counts1 == 0)
ThomBMT 1:ba14d8f4d444 857 {
ThomBMT 1:ba14d8f4d444 858 Active_State = Post_Homing;
ThomBMT 1:ba14d8f4d444 859 }
ThomBMT 1:ba14d8f4d444 860
ThomBMT 1:ba14d8f4d444 861 break;
ThomBMT 1:ba14d8f4d444 862
ThomBMT 1:ba14d8f4d444 863 case Post_Homing:
ThomBMT 1:ba14d8f4d444 864
ThomBMT 1:ba14d8f4d444 865 static int mm = 0;
ThomBMT 1:ba14d8f4d444 866 mm++;
ThomBMT 1:ba14d8f4d444 867 if (mm == 1000);
ThomBMT 1:ba14d8f4d444 868 {
ThomBMT 1:ba14d8f4d444 869 Active_State = Function;
ThomBMT 1:ba14d8f4d444 870 pc.printf("Homing was succesfull\r\n\r\nAutomatic switch to Funtioning state\r\n\r\n");
ThomBMT 1:ba14d8f4d444 871 mm=0; // reseting the state
ThomBMT 1:ba14d8f4d444 872 }
ThomBMT 1:ba14d8f4d444 873
ThomBMT 1:ba14d8f4d444 874 OFF_m1();
ThomBMT 1:ba14d8f4d444 875 OFF_m2();
ThomBMT 1:ba14d8f4d444 876 break;
ThomBMT 1:ba14d8f4d444 877
ThomBMT 1:ba14d8f4d444 878 case Function:
ThomBMT 2:bc6043623fb7 879
ThomBMT 2:bc6043623fb7 880 EMG_test();
ThomBMT 2:bc6043623fb7 881 Filter();
ThomBMT 2:bc6043623fb7 882 Inverse();
ThomBMT 2:bc6043623fb7 883 sample();
ThomBMT 2:bc6043623fb7 884 EMG_Read();
ThomBMT 2:bc6043623fb7 885 Encoding();
ThomBMT 2:bc6043623fb7 886 Checking_EMG();
ThomBMT 2:bc6043623fb7 887 Setting_Movement();
ThomBMT 2:bc6043623fb7 888 PID_controller();
ThomBMT 2:bc6043623fb7 889 motor1();
ThomBMT 2:bc6043623fb7 890 motor2();
ThomBMT 1:ba14d8f4d444 891
ThomBMT 4:a682fb1f37d2 892 if (fabs(rad_m1)>(2.0f*pi/3.0f) || fabs(rad_m2)>(25.0f*pi/12.0f)) // pi/4 is a safe value, can/will be editted
ThomBMT 1:ba14d8f4d444 893 {
ThomBMT 1:ba14d8f4d444 894 pc.printf("SAFE MODUS ACTIVE!\r\n RESET MANDATORY!\r\n");
ThomBMT 1:ba14d8f4d444 895 Active_State = Safe;
ThomBMT 1:ba14d8f4d444 896 }
ThomBMT 1:ba14d8f4d444 897 else if (Knop4==false)
ThomBMT 1:ba14d8f4d444 898 {
ThomBMT 1:ba14d8f4d444 899 pc.printf("Re-entering Calibration State \r\n");
ThomBMT 1:ba14d8f4d444 900 Active_State = Calibration;
ThomBMT 1:ba14d8f4d444 901 ii=0;
ThomBMT 1:ba14d8f4d444 902 }
ThomBMT 1:ba14d8f4d444 903 else if (Knop3==false)
ThomBMT 1:ba14d8f4d444 904 {
ThomBMT 1:ba14d8f4d444 905 pc.printf("Re-entering Homing State \r\n");
ThomBMT 1:ba14d8f4d444 906 Active_State = Homing_M1;
ThomBMT 1:ba14d8f4d444 907 }
ThomBMT 1:ba14d8f4d444 908 else if (!Knop1 && !Knop2)
ThomBMT 1:ba14d8f4d444 909 {
ThomBMT 1:ba14d8f4d444 910 pc.printf("Switched to Sleeping State\r\n");
ThomBMT 1:ba14d8f4d444 911 Active_State = Starting;
ThomBMT 1:ba14d8f4d444 912 iii = 40000;
ThomBMT 1:ba14d8f4d444 913 }
ThomBMT 2:bc6043623fb7 914
ThomBMT 1:ba14d8f4d444 915 break;
ThomBMT 1:ba14d8f4d444 916
ThomBMT 1:ba14d8f4d444 917 case Safe:
ThomBMT 1:ba14d8f4d444 918
ThomBMT 1:ba14d8f4d444 919 OFF_m1();
ThomBMT 1:ba14d8f4d444 920 OFF_m2();
ThomBMT 1:ba14d8f4d444 921
ThomBMT 1:ba14d8f4d444 922 break;
ThomBMT 1:ba14d8f4d444 923
ThomBMT 1:ba14d8f4d444 924 default:
ThomBMT 1:ba14d8f4d444 925 pc.printf("UNKNOWN COMMAND");
ThomBMT 1:ba14d8f4d444 926 }
ThomBMT 1:ba14d8f4d444 927 }
ThomBMT 1:ba14d8f4d444 928
ThomBMT 1:ba14d8f4d444 929 int main()
ThomBMT 1:ba14d8f4d444 930 {
ThomBMT 3:766e9f13d84e 931 // Our main loop is as empty as possible and contains only statements that
ThomBMT 3:766e9f13d84e 932 // cannot be put elsewhere due to functioning reasons.
ThomBMT 3:766e9f13d84e 933 // Also the "while-loop" is completely empty, which improves the running
ThomBMT 3:766e9f13d84e 934 // speed of the system.
ThomBMT 3:766e9f13d84e 935
ThomBMT 1:ba14d8f4d444 936 pc.baud(115200);
ThomBMT 1:ba14d8f4d444 937 PwmPin1.period_us(30); //60 microseconds pwm period, 16.7 kHz
ThomBMT 1:ba14d8f4d444 938
ThomBMT 1:ba14d8f4d444 939 bqc1.add( &BqNotch1_1 ).add( &BqNotch2_1 ).add( &BqHP1 ); //Oh wat lelijk...
ThomBMT 1:ba14d8f4d444 940 bqc2.add(&BqLP1);
ThomBMT 1:ba14d8f4d444 941 bqc3.add( &BqNotch1_2 ).add( &BqNotch2_2 ).add( &BqHP2 );
ThomBMT 1:ba14d8f4d444 942 bqc4.add(&BqLP2);
ThomBMT 1:ba14d8f4d444 943 bqc5.add( &BqNotch1_3 ).add( &BqNotch2_3 ).add( &BqHP3 );
ThomBMT 1:ba14d8f4d444 944 bqc6.add(&BqLP3);
ThomBMT 1:ba14d8f4d444 945 bqc7.add( &BqNotch1_4 ).add( &BqNotch2_4 ).add( &BqHP4 );
ThomBMT 1:ba14d8f4d444 946 bqc8.add(&BqLP4);
ThomBMT 1:ba14d8f4d444 947
ThomBMT 1:ba14d8f4d444 948 StateTicker.attach(&StateMachine, 0.002);
ThomBMT 1:ba14d8f4d444 949
ThomBMT 4:a682fb1f37d2 950 printTicker.attach(&Printing, 0.5);
ThomBMT 1:ba14d8f4d444 951
ThomBMT 1:ba14d8f4d444 952 while(true)
ThomBMT 1:ba14d8f4d444 953 {
ThomBMT 1:ba14d8f4d444 954 }
ThomBMT 1:ba14d8f4d444 955 }