valeria toffoli
/
COG4050_analogSensor
fft+analohADXL100x
Fork of COG4050_blink by
main.cpp
- Committer:
- vtoffoli
- Date:
- 2018-11-05
- Revision:
- 2:dbe2cc9e3b23
- Parent:
- 1:f56db8105a6a
File content as of revision 2:dbe2cc9e3b23:
#include <stdio.h> #include <complex> #include <math.h> #include "mbed.h" #include "ADXL100x.h" #include "FFT.h" FFT fft; ADXL100x accl(D6, D7, D8, ADC_VIN0, 5, 3); Serial pc(USBTX, USBRX); // tx, rx // Interrupt and timer Timer t; Ticker tck; // Const const float sample_time = 0.03; const int sample_num = 128; #define M_PI 3.14159265358979323846 // Pi constant with double precision uint16_t result; // Pin DigitalOut led1(LED1); DigitalOut led2(LED2); DigitalIn btn1(PB0); DigitalIn btn2(PB1); // Variable double data_array[sample_num]; double time_array[sample_num]; double dt_array[sample_num+1]; complex<double> fft_array[sample_num]; int index = 0; bool alarm = false; /* -------------------------------------------------------------------------- */ /* FFT ---------------------------------------------------------------------- */ /* -------------------------------------------------------------------------- */ /* int log2(int N) //funzione per calcolare il logaritmo in base 2 di un intero { int k = N, i = 0; while(k) { k >>= 1; i++; } return i - 1; } int check(int n) //usato per controllare se il numero di componenti del vettore di input è una potenza di 2 { return n > 0 && (n & (n - 1)) == 0; } int reverse(int N, int n) //calcola il reverse number di ogni intero n rispetto al numero massimo N { int j, p = 0; for(j = 1; j <= log2(N); j++) { if(n & (1 << (log2(N) - j))) p |= 1 << (j - 1); } return p; } void ordina(complex<double>* f1, int N) //dispone gli elementi del vettore ordinandoli per reverse order { complex<double> f2[sample_num]; for(int i = 0; i < N; i++) f2[i] = f1[reverse(N, i)]; for(int j = 0; j < N; j++) f1[j] = f2[j]; } void transform(complex<double>* f, int N) //calcola il vettore trasformato { ordina(f, N); //dapprima lo ordina col reverse order complex<double> W[N / 2]; //vettore degli zeri dell'unità. //Prima N/2-1 ma genera errore con ciclo for successivo //in quanto prova a copiare in una zona non allocata "W[N/2-1]" W[1] = polar(1., -2. * M_PI / N); W[0] = 1; for(int i = 2; i < N / 2; i++) W[i] = pow(W[1], i); int n = 1; int a = N / 2; for(int j = 0; j < log2(N); j++) { for(int i = 0; i < N; i++) { if(!(i & n)) { //ad ogni step di raddoppiamento di n, vengono utilizzati gli indici //'i' presi alternativamente a gruppetti di n, una volta si e una no. complex<double> temp = f[i]; complex<double> Temp = W[(i * a) % (n * a)] * f[i + n]; f[i] = temp + Temp; f[i + n] = temp - Temp; } } n *= 2; a = a / 2; } } void FFT(complex<double>* f, int N, double d) { transform(f, N); for(int i = 0; i < N; i++) f[i] *= d; //moltiplica il vettore per il passo in modo da avere il vettore trasformato effettivo } */ /* -------------------------------------------------------------------------- */ void check_accel(){ uint16_t result = accl.scanx(); pc.printf("%12d \t %6f \t \r\n", result, accl.accelScale(result, 12)); result = accl.standard_dev(12); pc.printf("standard dev: %6f \t \r\n", result); } void check_fft(){ /*if (!btn1) { // collect data t.start(); for(int j = 0; j < 128; j++){ data_array[j]= ain0.read_u16(); t.stop(); time_array[j]= t.read(); t.start();} // plot x[t] data double time=time_array[0]; double dt=0; pc.printf("data \t \r\n"); for(int j = 1; j < 128; j++){ dt = (dt + (time_array[j]-time ))/2; time = time_array[j]; pc.printf("%6f \t %f \t %6f \t \r\n", data_array[j].real(), data_array[j].imag(), time_array[j]);} // compute FFT pc.printf("fft \t \r\n"); FFT(data_array, 128, dt); for(int j = 0; j < 128; j++){ pc.printf("X[f] value: 0x%04X \r\n", data_array[j]);} }*/ } void fill_array(){ if (index >= 128){} else {index = index +1;} } void clear_array(double* f, int N){ for (int i=0; i<N; i++){f[i] = 0;} } /* -------------------------------------------------------------------------- */ int main() { pc.baud(9600); pc.printf("Analog AD sensor Demo: START\n"); while(true){ t.start(); if(!btn1){ // COLLECT DATA pc.printf("Data collecting, please wait 3 minute \t\r\n"); index=0; clear_array(data_array, sample_num); tck.attach(&fill_array, sample_time); // the address of the function to be attached (array_fill) and the interval (1 seconds) while(index <= 127){ result = accl.scanx(); data_array[index] = accl.accelScale(result, 12); time_array[index] = t.read(); //pc.printf("Data index %d \t \r\n", index); } tck.attach(NULL, 10); // stop to call the function (array_fill) for(int j = 0; j < 128; j++){ dt_array[j+1] = time_array[j+1]-time_array[j];} pc.printf("data \t \r\n"); for(int j = 0; j < 128; j++){ pc.printf("%6f \t %6f \t %6f \t \r\n", data_array[j], time_array[j], dt_array[j+1]);} } t.stop(); if(!btn2){ // PERFORM FFT led2 = !led2 ; pc.printf("x[n] data fft \t \r\n"); for(int j = 0; j < 128; j++){ fft_array[j] = data_array[j]; pc.printf("real part \t %6f \t imaginary part \t %6f \t \r\n", fft_array[j].real(), fft_array[j].imag());} fft.fourier(fft_array, 128, sample_time); pc.printf("X[f] data fft \t \r\n"); for(int j = 0; j < 128; j++){ pc.printf("real part \t %6f \t imaginary part \t %6f \t \r\n", fft_array[j].real(), fft_array[j].imag());} } } pc.printf("Analog AD sensor Demo: STOP\n"); }