Alarma de pico y placa usando módulo RTC.

Dependencies:   QEI TextLCD mbed

Fork of grafica_PID_android by Nicolás Villegas Echavarría

main.cpp

Committer:
NicolasV
Date:
2017-06-03
Revision:
5:82ac4b34c3d9
Parent:
3:2e823b16a4a1

File content as of revision 5:82ac4b34c3d9:

/*
 * Código por: Laura Álvila
 *             Daniela López
 *             Nicolás Villegas            
 */
 
#include "mbed.h"
#include "QEI.h"
#include "TextLCD.h"

Serial GSM(PTE0,PTE1);  // Módulo Bluetooh
TextLCD lcd(PTB10, PTB11, PTE2, PTE3, PTE4, PTE5); // rs, e, d4-d7
QEI encoder (PTA13, PTD5, NC, 10);
Timer t;

AnalogIn y(PTC2);   // Entrada análoga: Salida del sistema
AnalogOut u(PTE30); // Salida análoga: Señal de control

DigitalOut led1(LED1);
DigitalOut led2(LED2);
DigitalOut led3(LED3);

DigitalIn button3(PTC16); // Botón del encoder
DigitalIn button4(PTC17); // Pulsador

int C1=0x0F;
int C2=0x18;
int C3=0x1A;
int C4=0x0C;

int cambio = 0, diferencia = 0;
float pid, o, ai, ad, ap, med, err, setpoint;
float err_v;
int spnum = 0, kinum = 0, kpnum = 0 ,kdnum = 0, pos = 1;
int j,k; 
long t_pid = 0, t_btn = 0;

int main() {
    
    // Se asigna baudrate y se configura el puerto serie de la USART
    
    GSM.baud(9600);   
    GSM.format(8,Serial::None,1);
    t.start();
    
    
    // Animación de bienvenida:
    
    for (int i = 3; i < 15; ++i) {
        lcd.cls();
        lcd.locate(0,0);
        lcd.printf("**Control PID**");
        wait_ms(1000/i);
        
        ++i;
        lcd.cls();
        lcd.locate(1,0);
        lcd.printf("**Control PID**");
        wait_ms(1000/i);
        
        ++i;
        lcd.cls();
        lcd.locate(1,1);
        lcd.printf("**Control PID**");
        wait_ms(1000/i);
        
        ++i;
        lcd.cls();
        lcd.locate(0,1);
        lcd.printf("**Control PID**");
        wait_ms(1000/i);
    }

init:
    
    lcd.cls();
    lcd.writeCommand(C1);
      
    lcd.locate(8,0);
    lcd.printf("Ki=%d", kinum);
    
    lcd.locate(0,1);
    lcd.printf("Kd=%d", kdnum);
    
    lcd.locate(8,1);
    lcd.printf("**PID**");
    
    lcd.locate(0,0);
    lcd.printf("Kp=%d", kpnum);
    
    bool state = 1; // Esta variable determina si se están modificando las constantes del controlador o el Set-Point.
    
    while(true) {

        diferencia=(encoder.getPulses() - cambio)*3;
        cambio=encoder.getPulses();
        
        if (diferencia != 0 && state) {
            switch (pos) {
                case 1:
                    kpnum += diferencia;
                    
                    if (kpnum >= 999)
                        kpnum = 999;
                    else if (kpnum < 0)
                        kpnum = 0;
                        
                    lcd.locate(3,0);
                    lcd.printf("    ");
                    lcd.locate(3,0);
                    lcd.printf("%d", kpnum);
                    break;
                case 2:
                    kinum += diferencia;
                    
                    if (kinum >= 999)
                        kinum = 999;
                    else if (kinum < 0)
                        kinum = 0;

                    lcd.locate(11,0);
                    lcd.printf("    ");
                    lcd.locate(11,0);
                    lcd.printf("%d", kinum);
                    break;
                case 3:
                    kdnum += diferencia;
                    
                    if (kdnum >= 999)
                        kdnum = 999;
                    else if (kdnum < 0)
                        kdnum = 0;

                    lcd.locate(3,1);
                    lcd.printf("    ");
                    lcd.locate(3,1);
                    lcd.printf("%d", kdnum);
                    break;
            }
        }
        
        if (diferencia != 0 && !state) {
            
            spnum += diferencia;
              
            if (spnum >= 999) spnum = 999;
            else if (spnum < 0) spnum = 0;
                
            lcd.locate(10,0);
            lcd.printf("   ");
            lcd.locate(10,0);
            lcd.printf("%d", spnum);
        }
            

        if (!button3) { // Cambia la posición de ingreso de parámetros
            led2 = !led2;
            switch(pos++) {
                case 3:
                    pos = 1;
                    lcd.locate(3,0);
                    lcd.printf("%d", kpnum);
                    break;
                case 1:
                    lcd.locate(11,0);
                    lcd.printf("%d", kinum);
                    break;
                case 2:
                    lcd.locate(3,1);
                    lcd.printf("%d", kdnum);
                    break;
            }
            wait(0.2);
        }

        if (!button4 && state) {
            lcd.cls();
            lcd.locate(8,1);
            lcd.printf("**PID**");
            lcd.locate(0,0);
            lcd.printf("Set-Point=");
            lcd.locate(10,0);
            lcd.printf("%d", spnum);
            wait(0.2);
            state = 0;
        }
        else if (!button4 && !state) {
            wait(0.2);
            break;
        }
        wait(0.1);        
    }
    

 // Transición
    lcd.writeCommand(C4); // Escribimos un comando segun el manual del módulo LCD para quitar cursor bajo
    lcd.cls();
    lcd.locate(0,0); lcd.printf("y=");
    lcd.locate(8,0); lcd.printf("e=");
    lcd.locate(0,1); lcd.printf("r=");
    lcd.locate(8,1); lcd.printf("u=");

loop:   

    if (t.read_ms() - t_pid > 10) {
        
        med = y.read()*999;
        err = spnum - med;              // Se calcula el error
        ap = kpnum*err*0.01f;           // Se calcula la acción proporcional    
        ai += kinum*err*0.01f;          // Cálculo de la integral del error
        ad = kdnum*(err - err_v)*0.01f; // Cálculo de la acción derivativa
        pid = ap + ai + ad;
           
        if (pid <= 0) pid = 0;
        if (pid > 999) pid = 999;
        
        setpoint = spnum;
        GSM.printf("#%3.0f%3.0f&", med, setpoint);   // Se envía una cadena de caracteres por el puerto serial. Se agregan identificadores #...& que denotan el comienzo y la terminación de la misma.
                                                     // Esto se hace con el fin de evitar errores en la transmisión. Estos identificadores se usan en la aplicación de AppInventor. 
        lcd.locate(3,0);  lcd.printf("%3.0f ", med);
        lcd.locate(3,1);  lcd.printf("%3d ", spnum);
        lcd.locate(11,0); lcd.printf("%3.0f ", err);
        lcd.locate(11,1); lcd.printf("%3.0f ", pid);

        err_v = err;
        o = pid/999;
        u.write(o);
        
        t_pid = t.read_ms();
    }
    else {
        
        diferencia=(encoder.getPulses() - cambio)*6;  // Es posible cambiar el Set-Point cuando el controlador ya está funcionando. 
        cambio=encoder.getPulses();
        
        if (diferencia != 0) {
            spnum += diferencia;
            if (spnum >= 999) spnum = 999;
            else if (spnum < 0) spnum = 0;
        }
            
    }
    
    if (!button4) { // Si se presiona el pulsador se vuelve al menú inicial para configurar de nuevo el controlador.
        u.write(0);
        med = 0;
        err = 0;
        pid = 0;
        
        goto init;
    }
    else
        goto loop;
        
}