NXPCup_Cachan / Mbed 2 deprecated NXPCup

Dependencies:   mbed

Bluetooth/IHM_Bluetooth.cpp

Committer:
EISR
Date:
2020-03-12
Revision:
3:07109a6bb472
Parent:
2:1103f5d61035

File content as of revision 3:07109a6bb472:

#include "IHM_Bluetooth.h"                                                           
#include "NXPCam.h"

extern Serial bt;
extern int xG,xD;

// Constructeur
IHM_Bluetooth::IHM_Bluetooth() : /*blueTxBuffer{STARTBYTE,0,0,0,0,STOPBYTE}, paramRx{1, 0, 0, 0},*/ cb_lm(0), cb_rm(0), cb_err(0), cb_cerr(0), cb_speed(0)
{
    unsigned int tab1[6] = {STARTBYTE,0,0,0,0,STOPBYTE}, tab2[4] = {1, 0, 0, 0};
    
    for(int i=0; i<6; ++i)
        blueRxBuffer[i] = tab1[i];
        
    for(int i=0; i<4; ++i)
        paramRx[i] = tab2[i];
}

/*************************************** Main ******************************************/

void IHM_Bluetooth::run(void)
{
    bt.attach(this, &IHM_Bluetooth::receptionBlu, Serial::RxIrq);              // Creation interruption de reception sur bt
    bt.printf("Hello world");                                                  // Message de test
    timer.attach(this, &IHM_Bluetooth::automate_Tx,0.015);                     // Interruption toutes les 15ms, lance la fonction automate_Tx (timer est 1 Ticker)
}


/******************************* Fonctions de transmission *****************************/

void IHM_Bluetooth::transmitBlu(void)                                          // Permet la transmission d'une trame de octets stockee dans un buffer
{
    static short i = 0;
    if(bt.writable())                                                          // Fonctionne si la liaison est libre
    {
       bt.putc(blueTxBuffer[i]);                                               // Transmission de la trame de 6 octets
       i++;
    }
    if(i>5)                                                                    // Quand la trame est transmise
    {
        i=0;
        bt.attach(NULL, Serial::TxIrq);                                        // Arret de la transmission lorsqu une trame est envoyee. 
//                                                                                fonction detachee de l'interruption de transmission sur bt
    }
}

void IHM_Bluetooth::formatTrameT(short reg, int val)                           // Creation de trames de 6 octets pour des  donnees a valeur decimale
{   
    val=val*10000;                                                             // Transformation de la valeur decimale en un entier
    blueTxBuffer[1]=(char)reg;                                                 // entete de la donnee a transmettre
    blueTxBuffer[2]=(char)((val&0xFF0000)>>16);                                // Conversion de la valeur sur trois octets independants
    blueTxBuffer[3]=(char)((val&0x00FF00)>>8);
    blueTxBuffer[4]=(char)((val&0x0000FF));
                                                                               // La trame a envoyer est realisee
                                                                               
    bt.attach(this, &IHM_Bluetooth::transmitBlu, Serial::TxIrq);               // Ouverture de l'interruption de transmission. 
//                                                                                Fonction transmitBlu attachee a la transmission sur bt
}

void IHM_Bluetooth::TrameCAM( int CAM1, int CAM2)                              // Creation d'une trame de 6 octets permettant d'envoyer la position sur X
//                                                                                des vecteurs gauche et droit vu par la camera 
{
    blueTxBuffer[1]=(char)CAMXBYTE;                                            // entete des donnees de la camera
    blueTxBuffer[2]=(char)1;                                                   // Valeur inutile. Ne peut pas etre 0 car cela ignifie une erreur
    blueTxBuffer[3]=(char)CAM1;                                                // Position de la ligne gauche entre 0 et 200
    blueTxBuffer[4]=(char)CAM2;                                                // Position de la ligne droite entre 0 et 200
                                                                               // La trame a envoyer est realisee
                                                                               
    bt.attach(this, &IHM_Bluetooth::transmitBlu, Serial::TxIrq);               // Ouverture de l'interruption de transmission. 
//                                                                                Fonction transmitBlu attachee a la transmission sur bt
}

void IHM_Bluetooth::TramePos(int left, int barc, int right)                    // Creation d'une trame de 6 octets permettant d'envoyer la position du robot
//                                                                                sur la piste (cote gauche, barycentre, cote droit)
{
    blueTxBuffer[1]=(char)POSBYTE;                                             // entete des donnees de position du robot sur la piste 
    blueTxBuffer[2]=(char)left;                                                // Point gauche ??? 
    blueTxBuffer[3]=(char)barc;                                                // Barycentre   ???
    blueTxBuffer[4]=(char)right;                                               // Point droit  ???
                                                                               // La trame a envoyer est realisee
    bt.attach(this, &IHM_Bluetooth::transmitBlu, Serial::TxIrq);               // Ouverture de l'interruption de transmission. 
//                                                                                Fonction transmitBlu attachee a la transmission sur bt
}


void IHM_Bluetooth::automate_Tx(void)                                          // Automate pour la transmission. Permet de choisir la trame a creer
{    
    static int etat_futur=POSBYTE, val=50;
                                                                               // Transmission des donnees à l'application 
    switch(etat_futur){                                                              
        case POSBYTE : // Position du robot sur la piste                                                        
            TramePos(xG+100, ((xD+xG)/2)+100, xD+100);                               // Envoie de 3 octets de position par rapport aux lignes, respectivement : Gauche, barycentre et droit
//                                                                                Ces valeurs sont comprises entre -100 et 100 or on veut des nombres positifs
            if (cb_lm == 1)etat_futur = LMBYTE;                                
            else if(cb_rm == 1)etat_futur=RMBYTE;                              // Lecture de l'etat des checkboxes sur l'application
            else if(cb_err == 1)etat_futur=ERRORBYTE;                          // Si la checkbox est activee, l'etat futur sera celui associé
            else if(cb_cerr == 1)etat_futur=CERRBYTE;
            else if(cb_speed == 1)etat_futur=SGRABYTE;
            else etat_futur=CAMXBYTE;                                          // Si aucune checkbox n'est active, l'etat futur sera la lecture de la camera
            break;
        
        case LMBYTE : // Vitesse du moteur gauche
            formatTrameT(LMBYTE, xD );                                        // Utilisation de la fonction FormatTrameT
            if(cb_rm == 1)etat_futur=RMBYTE;
            else if(cb_err == 1)etat_futur=ERRORBYTE;                          // Meme fonctionnement des checkboxes que precedemment 
            else if(cb_cerr == 1)etat_futur=CERRBYTE;
            else if(cb_speed == 1)etat_futur=SGRABYTE;
            else etat_futur=CAMXBYTE;
            break;
        
        case RMBYTE : // Vitesse du moteur droit
            formatTrameT(RMBYTE, xG );
            if(cb_err == 1)etat_futur=ERRORBYTE;
            else if(cb_cerr == 1)etat_futur=CERRBYTE;
            else if(cb_speed == 1)etat_futur=SGRABYTE;
            else etat_futur=CAMXBYTE;
            break;
            
        case ERRORBYTE : // Erreur de position
            formatTrameT(ERRORBYTE, xD );
            if(cb_cerr == 1)etat_futur=CERRBYTE;
            else if(cb_speed == 1)etat_futur=SGRABYTE;
            else etat_futur=CAMXBYTE;
            break;
            
        case CERRBYTE : // Correction de l'erreur de position
            formatTrameT(CERRBYTE, xG );
            if(cb_speed == 1)etat_futur=SGRABYTE;
            else etat_futur=CAMXBYTE;
            break;
            
        case SGRABYTE : // Vitesse du véhicule
            formatTrameT(SGRABYTE, xG );
            etat_futur=CAMXBYTE;
            break;
        
        case CAMXBYTE : // Position sur X des vecteurs gauche et droit
            TrameCAM(xG+100, xD+100);                                        // Retour de la camera, respectivement vecteur Gauche et Droit
            etat_futur=POSBYTE;
            break;            
        }
}

/****************************** Fonctions de reception ******************************/

void IHM_Bluetooth::receptionBlu(void)
{
    static short j = 0;
    
    if(bt.readable())                                                          // Si la liaison est libre
    {
        blueRxBuffer[j]=(unsigned int)bt.getc();                               // Reception des octets dans un tableau
        j++;
        if(j==6)                                                               // Si 6 octets ont ete recus                                                  
        {
            if((blueRxBuffer[0]==STARTBYTE) && (blueRxBuffer[5]==STOPBYTE))    // Si la trame commence et termine par Start et Stop
            {
                switch(blueRxBuffer[1]){                                       // Automate en fonction de la valeur de l'entete
                    case KPBYTE : // Coefficient de proportionnalité pour correcteur PID de la position
                        paramRx[0] = ((blueRxBuffer[2]<<16)+(blueRxBuffer[3]<<8)+blueRxBuffer[4])/10000; 
                                                                               // Recomposition de la donnee et division par 10000 pour obtenir un decimal
                        break;
                    
                    case KIBYTE : // Coefficient integral pour correcteur PID de la position
                        paramRx[1] = ((blueRxBuffer[2]<<16)+(blueRxBuffer[3]<<8)+blueRxBuffer[4])/10000;   
                        break;
                    
                    case KDBYTE : // Coefficient derive pour correcteur PID de la position
                        paramRx[2] = ((blueRxBuffer[2]<<16)+(blueRxBuffer[3]<<8)+blueRxBuffer[4])/10000;   
                        break;
                        
                    case SPCMDBYTE : // Commande de vitesse pour le robot
                        paramRx[3] = ((blueRxBuffer[2]<<16)+(blueRxBuffer[3]<<8)+blueRxBuffer[4])/10000;
                        break;
                        
                    case ERRORBYTE : // Etat de la checkbox du graphe de d'erreur de position
                        if(((blueRxBuffer[2]<<16)+(blueRxBuffer[3]<<8)+blueRxBuffer[4]) == 1)
                        {                                                      // Si le 
                            if(cb_err == 0)cb_err=1;            
                            else if(cb_err == 1)cb_err=0;
                        } 
                        break;
                    
                    case CERRBYTE : // Etat de la checkbox du graphe de la correction d'erreur de position
                        if(((blueRxBuffer[2]<<16)+(blueRxBuffer[3]<<8)+blueRxBuffer[4]) == 1)
                        {
                            if(cb_cerr == 0)cb_cerr=1;
                            else if(cb_cerr == 1)cb_cerr=0;
                        }
                        break;
                    
                    case LMBYTE : // Etat de la checkbox du graphe de vitesse du moteur gauche
                        if(((blueRxBuffer[2]<<16)+(blueRxBuffer[3]<<8)+blueRxBuffer[4]) == 1)
                        {
                            if(cb_lm == 0)cb_lm=1;
                            else if(cb_lm == 1)cb_lm=0;
                        }
                        break;
                                                                               // Faire automate pour la transmission
                    case RMBYTE : // Etat de la checkbox du graphe de vitesse du moteur droit
                        if(((blueRxBuffer[2]<<16)+(blueRxBuffer[3]<<8)+blueRxBuffer[4]) == 1)
                        {
                            if(cb_rm == 0)cb_rm=1;
                            else if(cb_rm == 1)cb_rm=0;
                        }
                        break;
                        
                    case SGRABYTE : // Etat de la checkbox du graphe de vitesse du robot
                        if(((blueRxBuffer[2]<<16)+(blueRxBuffer[3]<<8)+blueRxBuffer[4]) == 1)
                        {
                            if(cb_speed == 0)cb_speed=1;
                            else if(cb_speed == 1)cb_speed=0;
                        }
                        break;
                }
                j=0;
            }else{                                                             //Si le message ne commence pas par start ou ne finit pas par stop
                for(int i = 0;i<5;i++){
                    blueRxBuffer[i]=blueRxBuffer[i+1];                         // On decale le msg reçu dans le buffer                         
                }
                j=5;                                                           // le compteur est mis a 5 pour recevoir un autre octet
//                                                                                avant de refaire le test sur la trame
            }
        }
    }
}
                    
int IHM_Bluetooth::get_val_pc(short reg)                                       // reg = entete choisi par l'utilisateur pour connaitre
//                                                                                      la valeur reçue associee a celui-ci
{
    short indice;
    
    if(reg == KPBYTE)indice = 0;                                               // On associe un indice en fonction de l'entete pour pouvoir
    else if(reg == KIBYTE)indice = 1;                                          // parcourir le tableau contenant les valeurs recues
    else if(reg == KDBYTE)indice = 2;
    else if(reg == SPCMDBYTE)indice = 3;
    
    return paramRx[indice];                                                    // Renvoie de la valeur souhaitee
}