Control PID para horno de reflujo con seguimiento de consigna
Dependencies: Debounced Pulse1 QEI RTC-DS1307 TextLCD mbed
Fork of Tarea3_procesadores_Ds1307 by
Tarea 4 procesadores 2018-1
Juan Camilo Londoño Julieta Serrano Escalante
PID para horno de reflujo conseguimiento de consigna
main.cpp
- Committer:
- jclondonol
- Date:
- 2018-06-01
- Revision:
- 3:35a40be1047f
- Parent:
- 2:bef1b1c9e387
File content as of revision 3:35a40be1047f:
#include "mbed.h" #include "DebouncedIn.h" #include "TextLCD.h" #include "QEI.h" #include "Rtc_Ds1307.h" #include <Pulse1.h> TextLCD lcd(PTE20, PTB1, PTB2, PTB3, PTC2, PTE21); // rs, e, d4, d5, d6, d7 Rtc_Ds1307 rtc(PTE0, PTE1); QEI wheel (PTD7, PTD6, NC, 30); DebouncedIn button_enco(PTC5); PwmOut U_pwm(PTE29); AnalogOut U_analog(PTE30); AnalogIn Y(A0); DigitalOut pwm_analog(PTC6); int main() { int C1 = 0x0C; int m = 0; int Lugar = 0; // Definen el punto en el cual va el programa int i = 0; int pos = 0; int Kp = 1, Ki = 1, Kd = 1, Sp = 0; float sp_temp = 0; float T1 = 0.1, T2 = 0.1, T3 = 0.1; int flag_pwm = 0; float periodo; float Frecuencia = 2000; float pid = 0,ai = 0,ad = 0,ap = 0,med = 0,err = 0; float err_v; int tiempo = 0, sec = 0, sec_ant = 0; Rtc_Ds1307::Time_rtc tm = {}; lcd.cls(); lcd.writeCommand(C1);//escribimos un comando segun el manual del modulo LCD lcd.locate(0,0); rtc.getTime(tm); periodo=(1/Frecuencia); U_pwm.period(periodo); U_pwm.pulsewidth(0); U_analog = 0.0; pwm_analog = 0; while(1) { switch (Lugar) { case 0: // Seleccionar Configuracion m = wheel.getPulses(); if(m != 0) { wheel.reset(); pos = pos + m; m = 0; lcd.cls(); } if(pos > 3){pos = 0;} if(pos < 0){pos = 3;} switch(pos) { case 0: lcd.locate(0,0); lcd.printf("Kp: %03d", Kp); lcd.locate(8,0); lcd.printf("Ki: %03d", Ki); lcd.locate(0,1); lcd.printf("Kd: %03d", Kd); lcd.locate(8,1); lcd.printf("Sp: %03d", Sp); wait(0.1); break; case 1: lcd.locate(0,0); lcd.printf("T1: %0.1f", T1); lcd.locate(8,0); lcd.printf("T2: %0.1f", T2); lcd.locate(0,1); lcd.printf("T3: %0.1f", T3); lcd.locate(8,1); lcd.printf("(min)"); wait(0.1); break; case 2: lcd.locate(0,0); lcd.printf("Setup Out"); lcd.locate(0,1); if(flag_pwm == 0) { lcd.printf("-> Pwm -- Analog"); } else { lcd.printf("-- Pwm -> Analog"); } break; case 3: lcd.locate(0,0); lcd.printf("Start PID"); break; } if (button_enco.falling()) //si se pulsa boton encoder { if(pos == 0) { Lugar = 1; i = 0; lcd.cls(); lcd.locate(0,0); lcd.printf("Kp: "); } if(pos == 1) { Lugar = 2; i = 0; lcd.cls(); lcd.locate(0,0); lcd.printf("T1: "); } if(pos == 2) { Lugar = 3; } if(pos == 3) { Lugar = 4; lcd.cls(); tm.min = 0; tm.sec = 0; tm.hour = 1; tm.mon = 1; tm.date = 1; tm.year = 2018; rtc.setTime(tm, false, false); rtc.startClock(); lcd.locate(0,1); lcd.printf("Time: "); } } break; case 1: // Configurar Constantes switch(i) { case 0: // Establecer Kp m = wheel.getPulses(); if (m != 0) { Kp = Kp + m; if(Kp > 99) { Kp = 0; } if(Kp < 0) { Kp = 99; } wheel.reset(); m = 0; } lcd.locate(4,0); lcd.printf("%03d",Kp); if (button_enco.falling()) { i++; lcd.cls(); lcd.locate(0,0); lcd.printf("Ki: "); } break; case 1: // Establecer Ki m = wheel.getPulses(); if (m != 0) { Ki = Ki + m; if(Ki > 99) { Ki = 0; } if(Ki < 0) { Ki = 99; } wheel.reset(); m = 0; } lcd.locate(4,0); lcd.printf("%03d",Ki); if (button_enco.falling()) { i++; lcd.cls(); lcd.locate(0,0); lcd.printf("Kd: "); } break; case 2: // Establecer Kd m = wheel.getPulses(); if (m != 0) { Kd = Kd + m; if(Kd > 99) { Kd = 0; } if(Kd < 0) { Kd = 99; } wheel.reset(); m = 0; } lcd.locate(4,0); lcd.printf("%03d",Kd); if (button_enco.falling()) { i++; lcd.cls(); lcd.locate(0,0); lcd.printf("Sp: "); } break; case 3: // Establecer Sp m = wheel.getPulses(); if (m != 0) { Sp = Sp + m*1; if(Sp > 100) { Sp = 0; } if(Sp < 0) { Sp = 100; } wheel.reset(); m = 0; } lcd.locate(4,0); lcd.printf("%03d",Sp); if (button_enco.falling()) { lcd.cls(); lcd.locate(0, 0); lcd.printf("Parameters Set"); wait(1); i = 0; Lugar = 0; lcd.cls(); } break; } break; case 2: // Configurar Tiempos switch(i) { case 0: // Establecer T1 m = wheel.getPulses(); if (m != 0) { T1 = T1 + m*0.1; if(T1 > 5.0) { T1 = 0.1; } if(T1 < 0.1) { T1 = 5.0; } wheel.reset(); m = 0; } lcd.locate(4,0); lcd.printf("%0.1f (min)",T1); if (button_enco.falling()) { i++; lcd.cls(); lcd.locate(0,0); lcd.printf("T2: "); T2 = T1 + 0.1; } break; case 1: // Establecer T2 m = wheel.getPulses(); if (m != 0) { T2 = T2 + m*0.1; if(T2 > 5.0) { T2 = T1 + 0.1; } if(T2 < (T1 + 0.1)) { T2 = 5.0; } wheel.reset(); m = 0; } lcd.locate(4,0); lcd.printf("%0.1f (min)",T2); if (button_enco.falling()) { i++; lcd.cls(); lcd.locate(0,0); lcd.printf("T3: "); T3 = T2 + 0.1; } break; case 2: // Establecer T3 m = wheel.getPulses(); if (m != 0) { T3 = T3 + m*0.1; if(T3 > 5.0) { T3 = T2 + 0.1; } if(T3 < (T2 + 0.1)) { T3 = 5.0; } wheel.reset(); m = 0; } lcd.locate(4,0); lcd.printf("%0.1f (min)",T3); if (button_enco.falling()) { lcd.cls(); lcd.locate(0, 0); lcd.printf("Time Set"); wait(1); i = 0; Lugar = 0; lcd.cls(); } break; } break; case 3: // Configurar salida m = wheel.getPulses(); if(flag_pwm == 0) { if(m != 0) { flag_pwm = 1; wheel.reset(); m = 0; lcd.locate(1,1); lcd.printf("-"); lcd.locate(8,1); lcd.printf(">"); } } if(flag_pwm == 1) { if(m != 0) { flag_pwm = 0; wheel.reset(); m = 0; lcd.locate(1,1); lcd.printf(">"); lcd.locate(8,1); lcd.printf("-"); } } if (button_enco.falling()) { lcd.cls(); lcd.locate(0, 0); lcd.printf("Out Set"); if(flag_pwm == 1){pwm_analog = 1;} else{pwm_analog = 0;} wait(1); Lugar = 0; lcd.cls(); } break; case 4: // CICLO PRINCIPAL CONTROLADOR PID lop1: rtc.getTime(tm); lcd.locate(0,0); lcd.printf("%Y : %0.0f ", med); lcd.locate(6,1); lcd.printf("%02d:",tm.min); lcd.printf("%02d",tm.sec); tiempo = tm.sec + tm.min*60; sec = tm.sec; if(sec != sec_ant) { sec_ant = sec; if(tiempo <= (T1*60)) { sp_temp = sp_temp + Sp/(T1*60); } if( (tiempo > (T2*60)) && (tiempo < (T3*60)) ) { sp_temp = sp_temp + ((10)-Sp)/((T3*60)-(T2*60)); } //if(tiempo > (T3*60)) //{ //sp_temp = 0; //} } med = Y.read()*100.0; err = (sp_temp-med); //se calcula el error ap = Kp*10*err*0.01f; //se calcula la accion proporcinal ai =(Ki*10*err*0.01f)+ai; //calculo de la integral del error ad = Kd*10*(err-err_v)*0.01f; //calculo de la accion derivativa pid = (ap+ai+ad); // se verifica que pid sea positivo ************************************** if(pid<0) { pid = 0; } // se verifica que pid sea menor o igual la valor maximo ***************** if (pid > 100) { pid = 100; } //Normalizacion de la salida // se actualizan las variables ******************************************* err_v = err; U_analog = pid/100; U_pwm.pulsewidth(U_analog*periodo); // se envia el valor pid a puerto analogico de salida (D/A) ************** // se repite el ciclo if (button_enco.falling()) { lcd.cls(); lcd.locate(0, 0); lcd.printf("PID Stop"); wait(1); Lugar = 0; lcd.cls(); U_analog = 0.0; U_pwm.pulsewidth(0); sec = 0; sec_ant = 0; } else { wait_ms(300); goto lop1; } break; } } }