Measures EMG signal, filters them and puts on a led
Dependencies: HIDScope MODSERIAL Math MovingAverage biquadFilter mbed
Fork of EMG by
main.cpp@21:30a33a4aa868, 2018-10-26 (annotated)
- Committer:
- Roooos
- Date:
- Fri Oct 26 11:03:48 2018 +0000
- Revision:
- 21:30a33a4aa868
- Parent:
- 20:97059009a491
EMG Realtime Filter Measures EMG from Left and Right Bicep, Filters them and puts a led on.
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
vsluiter | 0:32bb76391d89 | 1 | #include "mbed.h" |
vsluiter | 11:ce72ec658a95 | 2 | #include "HIDScope.h" |
Roooos | 21:30a33a4aa868 | 3 | #include "BiQuad.h" |
Roooos | 21:30a33a4aa868 | 4 | #include "MovingAverage.h" |
Roooos | 21:30a33a4aa868 | 5 | #include "MODSERIAL.h" |
Roooos | 21:30a33a4aa868 | 6 | #include "math.h" |
Roooos | 21:30a33a4aa868 | 7 | #define NSAMPLE 200 |
Roooos | 21:30a33a4aa868 | 8 | |
vsluiter | 0:32bb76391d89 | 9 | |
vsluiter | 4:8b298dfada81 | 10 | //Define objects |
Roooos | 21:30a33a4aa868 | 11 | AnalogIn emg0( A0 ); //Biceps Left |
Roooos | 21:30a33a4aa868 | 12 | AnalogIn emg1( A1 ); //Biceps Right |
Roooos | 21:30a33a4aa868 | 13 | InterruptIn button(PTC6); |
Roooos | 21:30a33a4aa868 | 14 | InterruptIn button2(PTA4); |
tomlankhorst | 14:f83354387756 | 15 | Ticker sample_timer; |
Roooos | 21:30a33a4aa868 | 16 | |
Roooos | 21:30a33a4aa868 | 17 | //Ticker driving_timer; |
Roooos | 21:30a33a4aa868 | 18 | HIDScope scope( 4 ); //Number of Channels |
Roooos | 21:30a33a4aa868 | 19 | DigitalOut led1(LED_GREEN); |
Roooos | 21:30a33a4aa868 | 20 | DigitalOut led2(LED_BLUE); |
Roooos | 21:30a33a4aa868 | 21 | DigitalOut led3(LED_RED); |
Roooos | 21:30a33a4aa868 | 22 | MovingAverage <double>Movag_LB(NSAMPLE,0.0); //Make Moving Average, Define NSAMPLE above |
Roooos | 21:30a33a4aa868 | 23 | MovingAverage <double>Movag_RB(NSAMPLE,0.0); |
Roooos | 21:30a33a4aa868 | 24 | |
Roooos | 21:30a33a4aa868 | 25 | MODSERIAL pc(USBTX, USBRX); |
Roooos | 21:30a33a4aa868 | 26 | |
Roooos | 21:30a33a4aa868 | 27 | volatile bool BicepLeft = false; |
Roooos | 21:30a33a4aa868 | 28 | volatile bool BicepRight = false; |
vsluiter | 2:e314bb3b2d99 | 29 | |
Roooos | 21:30a33a4aa868 | 30 | |
Roooos | 21:30a33a4aa868 | 31 | //Make Biquad filters Left(a0, a1, a2, b1, b2) |
Roooos | 21:30a33a4aa868 | 32 | BiQuadChain bqc1; //chain voor High Pass en Notch |
Roooos | 21:30a33a4aa868 | 33 | BiQuad bq1(0.39131200825291007, -0.7826240165058201, 0.39131200825291007, -0.36950493743858204, 0.1957430955730582); //High Pass Filter |
Roooos | 21:30a33a4aa868 | 34 | BiQuad bq2(9.91104e-01, -1.60364e+00, 9.91104e-01, -1.60364e+00, 9.82207e-01); //Notch Filter |
Roooos | 21:30a33a4aa868 | 35 | BiQuad bq3(0.00044924972004654657, 0.0008984994400930931, 0.00044924972004654657, -1.6169385656964415, 0.6187355645766276); //Low Pass Filter |
Roooos | 21:30a33a4aa868 | 36 | |
Roooos | 21:30a33a4aa868 | 37 | //Make Biquad filters Right |
Roooos | 21:30a33a4aa868 | 38 | BiQuadChain bqc2; //chain voor High Pass en Notch |
Roooos | 21:30a33a4aa868 | 39 | BiQuad bq4(0.39131200825291007, -0.7826240165058201, 0.39131200825291007, -0.36950493743858204, 0.1957430955730582); //High Pass Filter |
Roooos | 21:30a33a4aa868 | 40 | BiQuad bq5(9.91104e-01, -1.60364e+00, 9.91104e-01, -1.60364e+00, 9.82207e-01); //Notch Filter |
Roooos | 21:30a33a4aa868 | 41 | |
Roooos | 21:30a33a4aa868 | 42 | //Function to read samples and filter and send to HIDScope |
tomlankhorst | 14:f83354387756 | 43 | void sample() |
vsluiter | 2:e314bb3b2d99 | 44 | { |
Roooos | 21:30a33a4aa868 | 45 | //Filter Left Bicep |
Roooos | 21:30a33a4aa868 | 46 | double LB_Filter_1 = bqc1.step(emg0.read()); //High Pass + Notch |
Roooos | 21:30a33a4aa868 | 47 | double LB_Rectify = fabs(LB_Filter_1); //Rectify Signal |
Roooos | 21:30a33a4aa868 | 48 | //double Filtered_emg_1 = bq3.step(LB_Rectify); //Low Pass |
Roooos | 21:30a33a4aa868 | 49 | Movag_LB.Insert(LB_Rectify); |
Roooos | 21:30a33a4aa868 | 50 | double LB_Out = Movag_LB.GetAverage(); |
Roooos | 21:30a33a4aa868 | 51 | |
Roooos | 21:30a33a4aa868 | 52 | //Filter Right Bicep |
Roooos | 21:30a33a4aa868 | 53 | double RB_Filter_1 = bqc2.step(emg1.read()); //High Pass + Notch |
Roooos | 21:30a33a4aa868 | 54 | double RB_Rectify = fabs(RB_Filter_1); //Rectify Signal |
Roooos | 21:30a33a4aa868 | 55 | //double Filtered_emg_1 = bq3.step(RB_Rectify); //Low Pass |
Roooos | 21:30a33a4aa868 | 56 | Movag_RB.Insert(RB_Rectify); |
Roooos | 21:30a33a4aa868 | 57 | double RB_Out = Movag_RB.GetAverage(); |
Roooos | 21:30a33a4aa868 | 58 | |
Roooos | 21:30a33a4aa868 | 59 | scope.set(0, emg0.read() ); //Raw EMG signal left bicep |
Roooos | 21:30a33a4aa868 | 60 | scope.set(1, LB_Out); // Filtered EMG signal left bicep |
Roooos | 21:30a33a4aa868 | 61 | scope.set(2, emg1.read()); //Raw EMG signal right bicep |
Roooos | 21:30a33a4aa868 | 62 | scope.set(3, RB_Out); //Filtered EMG signal right bicep |
Roooos | 21:30a33a4aa868 | 63 | |
vsluiter | 11:ce72ec658a95 | 64 | scope.send(); |
Roooos | 21:30a33a4aa868 | 65 | |
Roooos | 21:30a33a4aa868 | 66 | if (LB_Out > ThresholdLeft) { |
Roooos | 21:30a33a4aa868 | 67 | led1 = 0; |
Roooos | 21:30a33a4aa868 | 68 | BicepLeft = true; |
Roooos | 21:30a33a4aa868 | 69 | } |
Roooos | 21:30a33a4aa868 | 70 | else { |
Roooos | 21:30a33a4aa868 | 71 | led1 = 1; |
Roooos | 21:30a33a4aa868 | 72 | BicepLeft = false; |
Roooos | 21:30a33a4aa868 | 73 | } |
Roooos | 21:30a33a4aa868 | 74 | if (RB_Out > ThresholdRight) { |
Roooos | 21:30a33a4aa868 | 75 | led2 = 0; |
Roooos | 21:30a33a4aa868 | 76 | BicepRight = true; |
Roooos | 21:30a33a4aa868 | 77 | } |
Roooos | 21:30a33a4aa868 | 78 | else { |
Roooos | 21:30a33a4aa868 | 79 | led2 = 1; |
Roooos | 21:30a33a4aa868 | 80 | BicepRight = false; |
Roooos | 21:30a33a4aa868 | 81 | } |
vsluiter | 2:e314bb3b2d99 | 82 | } |
vsluiter | 0:32bb76391d89 | 83 | |
Roooos | 21:30a33a4aa868 | 84 | |
vsluiter | 0:32bb76391d89 | 85 | int main() |
tomlankhorst | 19:2bf824669684 | 86 | { |
Roooos | 21:30a33a4aa868 | 87 | bqc1.add( &bq1 ).add( &bq2 ); //make BiQuadChain |
Roooos | 21:30a33a4aa868 | 88 | bqc2.add( &bq4 ).add( &bq5 ); //make BiQuadChain |
Roooos | 21:30a33a4aa868 | 89 | sample_timer.attach(&sample, 0.002); //read samples at 500 Hz |
tomlankhorst | 15:0da764eea774 | 90 | while(1) {} |
Roooos | 21:30a33a4aa868 | 91 | } |