Código para el uso del Módulo RTC DS3231 (Pantalla LCD - ENCODER - IRDA) para establecer un sistema de Alarmas en tiempo real.
Dependencies: mbed QEI ds3231 TextLCD Pulse1
Diff: main.cpp
- Revision:
- 0:dc639ee44cab
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/main.cpp Tue Aug 13 03:24:11 2019 +0000 @@ -0,0 +1,635 @@ +/*Práctica 4 - Procesadores 2019-1 + Giovani Cardona Sánchez + Mateo Valencia Diaz + Verónica Ríos Vargas + Juan Esteban Rodriguez Oquendo + Juan Camilo Pérez Estrada +*/ + +#include "ds3231.h" +#include "TextLCD.h" +#include <Pulse1.h> +#include "QEI.h" + +//--------------------------Puertos---------------------------------// +TextLCD lcd(PTB10, PTB11, PTE2, PTE3, PTE4, PTE5, TextLCD::LCD20x4); // rs, e, d4-d7 +Ds3231 rtc(PTE0, PTE1); //rtc object Ds3231::Ds3231(PinName sda, PinName scl) : I2C(sda, scl) +PulseInOut irda(PTD5);// en este puerto se pone el sensor infrarrojo +QEI wheel (PTD7, PTD6, NC, 624); +Serial pc(USBTX, USBRX); + +DigitalOut ledR(LED_RED); // led rojo +DigitalOut ledG(LED_GREEN); // led verde +DigitalOut ledB(LED_BLUE); // led azul + +DigitalOut Buzzer(PTD4); +InterruptIn button(PTA17); + +//--------------------------Variables---------------------------------// + +int day = 0, date = 0, month = 0, year = 0, hours = 0, minutes = 0, seconds = 0; +int modo = 0, pulsos = 0, x = 0, pos = 0, count = 0, n = 0, x_i = -1, f = 0; +int Alarmas[16][6]; + +//--------IRDA--------// +int header =0; //tiempo de cabecera pulso abajo +const int head_H = 11000; //+20% medida con osciloscopio en microsegundos +const int head_L = 4444 ;//-20% medida con osciloscopio +int i=0; +const int T_alto=1670;//ponga su tiempo de la prueba +const int T_bajo=847;//ponga su tiempo de la prueba +const int num_bits = 32;//ponga su numero de bits +int num[num_bits];//cadena para almacenar todos los tiempos que conforman los bits de datos +int sec[num_bits];//cadena para almacenar la cadena codificada en binario +int boton1[]= {0,0,1,0,0,0,0,0,1,1,0,1,1,1,1,1,1,0,0,0,1,0,0,0,0,1,1,1,0,1,1,0}; +int boton2[]= {0,0,1,0,0,0,0,0,1,1,0,1,1,1,1,1,0,1,0,0,1,0,0,0,1,0,1,1,0,1,1,0}; +int boton3[]= {0,0,1,0,0,0,0,0,1,1,0,1,1,1,1,1,1,1,0,0,1,0,0,0,0,0,1,1,0,1,1,0}; +int boton4[]= {0,0,1,0,0,0,0,0,1,1,0,1,1,1,1,1,0,0,1,0,1,0,0,0,1,1,0,1,0,1,1,0}; +int boton5[]= {0,0,1,0,0,0,0,0,1,1,0,1,1,1,1,1,1,0,1,0,1,0,0,0,0,1,0,1,0,1,1,0}; +int boton6[]= {0,0,1,0,0,0,0,0,1,1,0,1,1,1,1,1,0,1,1,0,1,0,0,0,1,0,0,1,0,1,1,0}; +int boton7[]= {0,0,1,0,0,0,0,0,1,1,0,1,1,1,1,1,1,1,1,0,1,0,0,0,0,0,0,1,0,1,1,0}; +int boton8[]= {0,0,1,0,0,0,0,0,1,1,0,1,1,1,1,1,0,0,0,1,1,0,0,0,1,1,1,0,0,1,1,0}; +int boton9[]= {0,0,1,0,0,0,0,0,1,1,0,1,1,1,1,1,1,0,0,1,1,0,0,0,0,1,1,0,0,1,1,0}; +int boton0[]= {0,0,1,0,0,0,0,0,1,1,0,1,1,1,1,1,0,0,0,0,1,0,0,0,1,1,1,1,0,1,1,0}; +int OK[] = {0,0,1,0,0,0,0,0,1,1,0,1,1,1,1,1,0,0,0,0,0,0,0,0,1,1,1,1,1,1,1,0}; + +int flag1,flag2,flag3,flag_OK; //Banderas de boton presionado +int dato; // tiempo de cada dato que se lee + + +//----------------------Funciones--------------------------------// +void get_user_input(char* message, uint8_t min, uint8_t max, uint32_t* member); +void get_user_input(char* message, uint8_t min, uint8_t max, bool* member); +void set_RTC(void); +void set_Alarm_encoder(void); +int set_Alarm_IRDA(void); +void print_Alarm(void); +int detect_number(void); +int sel_number(void); + + +//----------------------Interrupciones---------------------------// +void Button(void) { + wait(0.1); + if(button == 1){ + if(n == 0){ + ledG = !ledG; //Se va a ingresar una alarma por IRDA + modo = 2; + f = 0; + count = 0; + } + if(modo == 0){ + pos = x; + //ledR = !ledR; + printf("\nInterrupcion- Alarma = %d",pos); + modo = 1; //Cambio de alarma por encoder + count = 0; + x = 0; + } + else if(modo == 1){ + Alarmas[pos-1][count] = x; + ledR = !ledR; + wait(0.05); + ledR = !ledR; + count++; + x = 0; + } + } +} + + +//----------------------Ciclo principal---------------------------// +int main(void) +{ + //DS3231 rtc variables - default, use bit masks in ds3231.h for desired operation + ds3231_cntl_stat_t rtc_control_status = {0,0}; + rtc.set_cntl_stat_reg(rtc_control_status); + + //******************************// + ds3231_time_t time = {12, 0, 0, 0, 1}; + ds3231_calendar_t calendar = {1, 1, 1, 0}; + ledR = 1; ledB = 1; ledG = 1;//LEDs OFF + + //set_RTC(); //Configuración del RTC + + //******************************// + + while(1) + { + rtc.get_time(&time); // NO se va a usar el modo (1 for 12hr 0 for 24hr) o (0 for AM 1 for PM) + lcd.locate(0, 0); + lcd.printf("Time %02d:%02d:%02d - RTC", time.hours, time.minutes, time.seconds); + + rtc.get_calendar(&calendar); + lcd.locate(0, 1); + lcd.printf("Calendar %02d/%02d/%02d",calendar.date, calendar.month, calendar.year); + + //-------Verificación Alarma encendido------// + for (int i= 0; i<=7;i++){ + if((time.hours == Alarmas[i][0])&& (time.minutes == Alarmas[i][1]) && (time.seconds == Alarmas[i][2]) && (calendar.date == Alarmas[i][3]) && (calendar.month == Alarmas[i][4]) && (calendar.year == Alarmas[i][5])){ + ledB = 0; + Buzzer = 1; + lcd.locate(0, 3); + lcd.printf(" Alarm %d activated", i+1); + wait(0.5); + Buzzer = 0; + lcd.locate(0, 3); + lcd.printf(" "); + } + } + //-------------------------// + + //-------Verificación Alarma apagado------// + for (int i= 8; i<=15;i++){ + if((time.hours == Alarmas[i][0])&& (time.minutes == Alarmas[i][1]) && (time.seconds == Alarmas[i][2]) && (calendar.date == Alarmas[i][3]) && (calendar.month == Alarmas[i][4]) && (calendar.year == Alarmas[i][5])){ + ledB = 1; + Buzzer = 1; + lcd.locate(0, 3); + lcd.printf("Alarm %d deactivated", i+1); + wait(0.5); + Buzzer = 0; + lcd.locate(0, 3); + lcd.printf(" "); + } + } + //-------------------------// + + switch (modo) + { + case 0: //Selección de Alarma + + //Cambio de estado del Encoder + x = x - wheel.getPulses(); + wheel.reset(); + button.rise(&Button); + + //printf("\nx: %d ",x); + if ((x != 0) && (modo == 0)) + { + if (x < 1){x = 1;} + if (x > 16){x = 16;} + + lcd.locate(0, 2); + lcd.printf(" Alarm %02d", x); + button.rise(&Button); + n = 1; + } + break; + + case 1: //Modo 1 - Encoder + set_Alarm_encoder(); + if (count == 6){ + lcd.locate(0, 2); + lcd.printf(" Alarm saved! "); + wait(0.8); + lcd.locate(0, 2); + lcd.printf(" "); + lcd.locate(0, 3); + lcd.printf(" "); + count = 0; + modo = 0; + print_Alarm(); + n = 0; + } + break; + + case 2: + //Cambio de estado con IRDA + lcd.locate(0, 0); + lcd.printf(" "); + lcd.locate(0, 1); + lcd.printf(" "); + lcd.locate(0, 0); + lcd.printf(" Alarm IRDA"); + lcd.locate(0, 1); + lcd.printf(" Select Alarm: "); + + + int x1 = 0, x2 = 0, x3 = 0, c = 0; + while(1){ + if (detect_number() == 1){ + c++; + if(c == 1){ + x1 = sel_number(); + pc.printf("\nx1: %d c: %d\n",x1,c); + x_i = x1; + } + + if(c == 2){ + x2 = sel_number(); + pc.printf("\nx2: %d c: %d\n",x2,c); + if( x2 == -1){ + x_i = x1; + break; + } + else{ + x_i = x1*10 + x2; + } + } + if (c == 3){ + x3 = sel_number(); + pc.printf("\nx3: %d c: %d\n",x3,c); + if( x3 == -1){ + x_i= x1*10 + x2; + break; + } + } + } + } + x1 = 0; x2 = 0; x3 = 0; c = 0; + // -------------------- // + lcd.locate(0, 1); + lcd.printf(" Select Alarm: %d", x_i); + while(f == 0){ + f = set_Alarm_IRDA(); + count++; + print_Alarm(); + } + + break; + } + + + //wait(0.2); + }//loop +} + +//-----------------------Funciones---------------------------------// +void set_Alarm_encoder(void){ + + lcd.locate(0, 3); + lcd.printf(" %02d:%02d:%02d %02d/%02d/%02d", Alarmas[pos-1][0],Alarmas[pos-1][1],Alarmas[pos-1][2],Alarmas[pos-1][3],Alarmas[pos-1][4],Alarmas[pos-1][5]); + + x = x - wheel.getPulses(); + wheel.reset(); + + switch (count) //count representa la posición de la columna en la matriz Alarmas - en este orden HH:MM:SS DD/MM/YY + { + case 0: //Hora + if (x < 0){x = 0;} + if (x > 23){x = 23;} + Alarmas[pos-1][count] = x; + break; + + case 1: //Minutos + if (x < 0){x = 0;} + if (x > 59){x = 59;} + Alarmas[pos-1][count] = x; + break; + + case 2: //Segundos + if (x < 0){x = 0;} + if (x > 59){x = 59;} + Alarmas[pos-1][count] = x; + break; + + case 3: // Día + if (x < 0){x = 0;} + if (x > 31){x = 31;} + Alarmas[pos-1][count] = x; + break; + + case 4: // Mes + if (x < 0){x = 0;} + if (x > 12){x = 12;} + Alarmas[pos-1][count] = x; + break; + + case 5: // Año + if (x < 0){x = 0;} + if (x > 99){x = 99;} + Alarmas[pos-1][count] = x; + break; + } +} + +// ---- IRDA ----// +int detect_number(void){ + int y = 0; + header=0; + header = irda.read_low_us(); //funcion para leer un pulso de caida o bajo + + if (header > head_L && header < head_H){ + wait_us(2000); + for(int i=0; i<(num_bits-1); ++i) // POR OSCILOSCOPIO se determina que llegan (num_bits),datos + { + dato = irda.read_high_us(); //leer un bit de datos que es pulso arriba en este control + num[i]=dato; + wait_us(332); + } + for(int i=0; i<num_bits; ++i) + { + if(num[i] > ((T_alto+T_bajo)/2)) + { + pc.printf("1"); + sec[i]=1; // guardo la secuancia en binario + } + else + { + sec[i]=0; //guardo la secuencia en binario + pc.printf("0"); + } + pc.printf(","); + } + pc.printf("\n"); + y = 1; + } + return y; +} + +int sel_number(void){ + int flag1=1,flag2=1,flag3=1,flag4=1,flag5=1,flag6=1,flag7=1,flag8=1,flag9=1,flag0=1,flag_OK=1; + int x_irda; + + for(i=0; i<32; ++i) + { + if(sec[i]!=boton1[i]) //en caso de que un bit no coincida se descarta el boton 1 + { + flag1=0; + } + if(sec[i]!=boton2[i]) //en caso de que un bit no coincida se descarta el boton 2 + { + flag2=0; + } + if(sec[i]!=boton3[i]) //en caso de que un bit no coincida se descarta el boton 3 + { + flag3=0; + } + if(sec[i]!=boton4[i]) //en caso de que un bit no coincida se descarta el boton 1 + { + flag4=0; + } + if(sec[i]!=boton5[i]) //en caso de que un bit no coincida se descarta el boton 2 + { + flag5=0; + } + if(sec[i]!=boton6[i]) //en caso de que un bit no coincida se descarta el boton 3 + { + flag6=0; + } + if(sec[i]!=boton7[i]) //en caso de que un bit no coincida se descarta el boton 1 + { + flag7=0; + } + if(sec[i]!=boton8[i]) //en caso de que un bit no coincida se descarta el boton 2 + { + flag8=0; + } + if(sec[i]!=boton9[i]) //en caso de que un bit no coincida se descarta el boton 3 + { + flag9=0; + } + if(sec[i]!=boton0[i]) //en caso de que un bit no coincida se descarta el boton 3 + { + flag0=0; + } + if(sec[i]!=OK[i]) //en caso de que un bit no coincida se descarta el boton 3 + { + flag_OK=0; + } + } + + if(flag1 == 1) {x_irda =1;} + if(flag2 == 1) {x_irda =2;} + if(flag3 == 1) {x_irda =3;} + if(flag4 == 1) {x_irda =4;} + if(flag5 == 1) {x_irda =5;} + if(flag6 == 1) {x_irda =6;} + if(flag7 == 1) {x_irda =7;} + if(flag8 == 1) {x_irda =8;} + if(flag9 == 1) {x_irda =9;} + if(flag0 == 1) {x_irda =0;} + if(flag_OK == 1) {x_irda =-1;} + + return x_irda; +} + +int set_Alarm_IRDA(void){ + lcd.locate(0, 3); + int x1 = 0, x2 = 0, x3 = 0, c = 0; + pos = x_i; + f = 0; + lcd.printf(" %02d:%02d:%02d %02d/%02d/%02d", Alarmas[pos-1][0],Alarmas[pos-1][1],Alarmas[pos-1][2],Alarmas[pos-1][3],Alarmas[pos-1][4],Alarmas[pos-1][5]); + + while(1){ + if (detect_number() == 1){ + c++; + if(c == 1){ + x1 = sel_number(); + pc.printf("\nx1: %d c: %d\n",x1,c); + x = x1; + } + + if(c == 2){ + x2 = sel_number(); + pc.printf("\nx2: %d c: %d\n",x2,c); + if( x2 == -1){ + x = x1; + break; + } + else{ + x = x1*10 + x2; + } + } + if (c == 3){ + x3 = sel_number(); + pc.printf("\nx3: %d c: %d\n",x3,c); + if( x3 == -1){ + x = x1*10 + x2; + break; + } + } + } + } + + switch (count) //count representa la posición de la columna en la matriz Alarmas - en este orden HH:MM:SS DD/MM/YY + { + case 0: //Hora + if (x < 0){x = 0;} + if (x > 23){x = 23;} + Alarmas[pos-1][count] = x; + break; + + case 1: //Minutos + if (x < 0){x = 0;} + if (x > 59){x = 59;} + Alarmas[pos-1][count] = x; + break; + + case 2: //Segundos + if (x < 0){x = 0;} + if (x > 59){x = 59;} + Alarmas[pos-1][count] = x; + break; + + case 3: // Día + if (x < 0){x = 0;} + if (x > 31){x = 31;} + Alarmas[pos-1][count] = x; + break; + + case 4: // Mes + if (x < 0){x = 0;} + if (x > 12){x = 12;} + Alarmas[pos-1][count] = x; + break; + + case 5: // Año + if (x < 0){x = 0;} + if (x > 99){x = 99;} + Alarmas[pos-1][count] = x; + break; + } + + if (count == 5){ + modo = 0; + count = 0; + f = 1; + lcd.locate(0, 2); + lcd.printf(" Alarm saved! "); + lcd.locate(0, 3); + lcd.printf(" %02d:%02d:%02d %02d/%02d/%02d", Alarmas[pos-1][0],Alarmas[pos-1][1],Alarmas[pos-1][2],Alarmas[pos-1][3],Alarmas[pos-1][4],Alarmas[pos-1][5]); + wait(0.8); + lcd.locate(0, 2); + lcd.printf(" "); + lcd.locate(0, 3); + lcd.printf(" "); + x = 0; + } + return f; +} + +void print_Alarm(void){ + printf("\n"); + for (int i=0; i<=15;i++){ + for (int j= 0; j<=5;j++){ + printf("%d ",Alarmas[i][j]); + } + printf("\n"); + } +} + +/********************************************************************** +* Function: get_user_input() +* Parameters: message - user prompt +* min - minimum value of input +* max - maximum value of input +* member - pointer to struct member +* Returns: none +* +* Description: get time/date input from user +* +**********************************************************************/ +void get_user_input(char* message, uint8_t min, uint8_t max, uint32_t* member) +{ + uint32_t temp; + + do + { + printf("\n%s", message); + + //for some reason mbed doesn't like a pointer to a member in scanf + //term.scanf("%d", member); works with gcc on RPi + scanf("%d", &temp); + + *member = temp; + + if((*(member)< min) || (*(member) > max)) + { + printf("\nERROR-RTI"); + } + } + while((*(member) < min) || (*(member) > max)); +} + + +void get_user_input(char* message, uint8_t min, uint8_t max, bool* member) +{ + uint32_t temp; + + do + { + printf("\n%s", message); + + //for some reason mbed doesn't like a pointer to a member in scanf + //term.scanf("%d", member); works with gcc on RPi + scanf("%d", &temp); + + *member = temp; + + if((*(member)< min) || (*(member) > max)) + { + printf("\nERROR-RTI"); + } + } + while((*(member) < min) || (*(member) > max)); +} + +void set_RTC(void){ + +//Cambio de la configuración del RTC DS3231 + ds3231_time_t rtc_time; + ds3231_calendar_t rtc_calendar; + + //get day from user + get_user_input("\nPlease enter day of week, 1 for Sunday (1-7): ", 1, + 7, &rtc_calendar.day); + + //get day of month from user + get_user_input("\nPlease enter day of month (1-31): ", 1, 31, + &rtc_calendar.date); + + //get month from user + get_user_input("\nPlease enter the month, 1 for January (1-12): ", 1, + 12, &rtc_calendar.month); + + //get year from user + get_user_input("\nPlease enter the year (0-99): ",0, 99, + &rtc_calendar.year); + + //Get time mode + get_user_input("\nWhat time mode? 1 for 12hr 0 for 24hr: ", 0, 1, + &rtc_time.mode); + + if(rtc_time.mode) + { + //Get AM/PM status + get_user_input("\nIs it AM or PM? 0 for AM 1 for PM: ", 0, 1, + &rtc_time.am_pm); + //Get hour from user + get_user_input("\nPlease enter the hour (1-12): ", 1, 12, + &rtc_time.hours); + } + else + { + //Get hour from user + get_user_input("\nPlease enter the hour (0-23): ", 0, 23, + &rtc_time.hours); + } + + //Get minutes from user + get_user_input("\nPlease enter the minute (0-59): ", 0, 59, + &rtc_time.minutes); + + + //Get seconds from user + get_user_input("\nPlease enter the second (0-59): ", 0, 59, + &rtc_time.seconds); + + + + //Set the time, uses inverted logic for return value + if(rtc.set_time(rtc_time)) + { + printf("\nrtc.set_time failed!!\n"); + exit(0); + } + + //Set the calendar, uses inverted logic for return value + if(rtc.set_calendar(rtc_calendar)) + { + printf("\nrtc.set_calendar failed!!\n"); + exit(0); + } + +}