Machine Vachette : Différence entre versions

De troyesGEII
Aller à : navigation, rechercher
(Réseau (MQTT et Node-red))
(Réseau (MQTT et Node-red))
Ligne 64 : Ligne 64 :
 
<br>
 
<br>
 
En haut on a la partie des actionneurs et en dessous la partie des capteurs. Chaque topic (les cubes violets) passe par une fonction qui désigne le GPIO vers laquelle le message est adressé, et donc quelle actionneurs nous souhaitons activer. Il ne faut pas oublié de sélectionner la bonne adresse pour le MCP23008.<br>
 
En haut on a la partie des actionneurs et en dessous la partie des capteurs. Chaque topic (les cubes violets) passe par une fonction qui désigne le GPIO vers laquelle le message est adressé, et donc quelle actionneurs nous souhaitons activer. Il ne faut pas oublié de sélectionner la bonne adresse pour le MCP23008.<br>
Pour les capteurs c'est un peu différents, on les récupère sur des GPIOs des MCP23008 déclarés en ENTREES (important sinon ça ne fonctionne pas)
+
Pour les capteurs c'est un peu différents, on les récupère sur des GPIOs des MCP23008 déclarés en ENTREES (important sinon ça ne fonctionne pas). Ensuite il passe par un bloc qui permet de changer la channel de destination (donc le GPIO) puis ensuite le publish sur le topic, qui est finalement reçu par la raspberryPI.<br>
  
 
=Programmation sous QT Creator=
 
=Programmation sous QT Creator=

Version du 18 juin 2021 à 14:27

Présentation

Objectif : Restauration d’une ancienne machine de transfert “Vachette”

VachetteMachine.jpg

L’objectif de notre projet est de remettre en état une ancienne machine de chaîne d'automatisme de la marque "Vachette", en y ajoutant une touche de "modernité". Cette machine était supposément prévu pour de la serrurerie, avec un poste centrale automatique et trois postes manuels. Cependant, la machine a été modifié afin de convenir à une utilisation plus scolaire. Seul les postes restent, avec les différents capteurs et actionneurs intactes, toute la machinerie a été retiré.

Le but étant de faire marcher la machine à nouveau, plusieurs installations ont été réalisés au fil des années. En passant d'un automate pour aujourd'hui arriver à ce que nous avons réalisé :

Un système de carte électroniques alimentés par des cartes nanoPI et tout le système géré à distance, en réseau grâce à "MQTT" et Node-red, par une raspberryPI avec interface graphique. Sur cette page nous allons expliquer comment nous avons réalisés les cartes et comment nous avons mis en place le réseau capable de faire fonctionner la machine.

Réalisation des cartes

Recherche et développement

Avant de remettre en marche la machine de transfert nous avons dû tester quels capteurs influent sur quels actionneurs en se basant sur les projets réalisés les années précédentes, ainsi que les plans qui ont été réalisés et récupérés par l’IUT. Nous avons donc constater que une adaptions de la tension devais être réaliser dans les 2 sens. En effet la machine vachette étant alimenter et piloté par des signaux 24 volts, notre carte NanoPi et ses GPIO Expanders n'on pas la même tension de travail, ici donc 3.3 volts pour nos cartes et composants de commande.

Pour arriver à nos fins, plusieurs étapes clés se sont poser à nous :

1 - Récupérer les signaux analogiques 24v -> 3.3v
2 - Conversion des signaux numérique/analog 3.3v en 24v
3 - Mise en réseaux des capteurs et actionneurs (Nano pi + Node-red)
4 - Création d’une interface principale sur une RaspberryPI (codage en QT)

Réalisation technique

Afin de convertir les signaux, nous avons dû réaliser des cartes électroniques. Cependant, afin d’optimiser et de simplifier l'utilisation ainsi que la complexité de cette dite carte, nous avons réalisé 3 modèles différents :

Un adaptateur pour faire fonctionner le protocole I2C. Une carte dédiée à la captation de signaux analogiques: 24v -> 3.3v Une carte dédiée à l’activation d'actionneurs (relais par exemples) : 3.3v -> 24V

Réalisation des cartes : Cartes capteurs : Opto Coupleurs 24v -> 3.3v Cartes actionneurs : Opto Coupleurs 3.3v -> 24v

Réseau (MQTT et Node-red)

Nous avons remarqué que le nombre d'entrées et sorties disponibles sur les cartes nanoPI n'était pas suffisant (que 5 disponibles). En effet nous devions donc rajouter des GPIOs, sinon nous ne pourrions pas connecter assez de capteurs et d'actionneurs.

C'est ici que rentre en jeu le MCP23008. Ce composant permet d'ajouter 8 GPIOs, que nous pourrons piloter à distance depuis la raspberryPI principal, il suffit juste de lui donner une adresse I2C valide, après l'avoir évidemment connecter en physique (toujours en I2C).

Pour connecter nos cartes entre elles grâce au MCP23008 nous avons du utiliser un service qui permettait de les relier.
Nous avons utiliser MQTT qui est un service qui permet de relier un client et un serveur à travers un broker.

PubSub.jpg

Ce système est dit un système de "topic subscribe/publish".
En effet, le fonctionnement est relativement simple. Le client se connecte au topic en "subscribe". Il recevra ainsi en écoute tout les messages qui seront envoyés sur le topic.

Le serveur quand à lui doit se connecter au topic en "publish". Cela lui permettra d'envoyer des messages aux clients "abonnés" au topic.

Ce service cependant marche, comme l'on voit sur l'image, grâce à un broker :
Pour nous, le broker était une raspberry Pi qui était constamment allumé dans la salle des serveurs avec pour adresse IP 10.98.9.20

Afin de mettre le MQTT en oeuvre, il fallu passer par une interface graphique, car sinon tout cela était inutilisable.
Nous avons donc utilisé node-red, qui est un autre service qui permet d'utiliser le MQTT en plus d'avoir une interface graphique sur navigateur.

MainNodeRed.png

Node-red fonctionne avec des blocs de commande simple d'utilisation qui permet donc d'utiliser les services MQTT comme l'on voit sur l'image ci-dessus.
On peut ajouter des modules sur node-red afin de rajouter des composants que l'on n'a pas de disponibles dans les fonctions de base, comme ici nous avons rajouté un module pour ajouter les MCP23008.

En haut on a la partie des actionneurs et en dessous la partie des capteurs. Chaque topic (les cubes violets) passe par une fonction qui désigne le GPIO vers laquelle le message est adressé, et donc quelle actionneurs nous souhaitons activer. Il ne faut pas oublié de sélectionner la bonne adresse pour le MCP23008.
Pour les capteurs c'est un peu différents, on les récupère sur des GPIOs des MCP23008 déclarés en ENTREES (important sinon ça ne fonctionne pas). Ensuite il passe par un bloc qui permet de changer la channel de destination (donc le GPIO) puis ensuite le publish sur le topic, qui est finalement reçu par la raspberryPI.

Programmation sous QT Creator

Réalisation de l'interface graphique via RaspBerry Pi

Pour simplifier l'utilisation de la machine, on a crée une interface graphique qui permet d'interagir avec la machine.

configuration raspberry

Branchez le câble ethernet sur la raspberry avant de l'allumer.Ensuite sur qt creator,en créant votre application avec widget, ajouter dans le management des kits la raspberry.Il faut la configurer avec son adresse IP apparaissant sur l'écran lié à la raspberry (c'est pour cela qu'il faut brancher le câble ethernet avant d'allumer la raspberry). Une fois l'adresse IP repéré, la rentrer de cette manière:

configuration Raspberry

Puis appuyez sur test. Si tout est correct, vous aurez un message en bleu vous disant que le Raspberry est bien connecté.

création du code

pour référence, voici le dossier contenant le code effectué dont vous pouvez vous en inspirer : Fichier:Comm nanopi to rpi.zip

Les parties importantes qu'il faut à tout prix dans le code était tout d'abord d'installer la librairie mqtt. Ce qui nous permettra depuis le code de souscrire ou de publier sur un topic particulier.
Lorsque vous créerez votre fichier qt, il faudra rajouter dans le fichier .pro la ligne 8:

ligne dans le fichier .pro

Ensuite dans le fichier mainwindow.h ajoutez les classes suivantes:

les classes à rajouter

Etant donné que le code est assez conséquent et que vous avez le dossier à disposition, on va juste regarder les fonctions importantes:

ligne de connexion au broker

 
#include "mainwindow.h"
#include "ui_mainwindow.h"
#include <QDebug>
#include <QMessageBox>

MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
{
    ui->setupUi(this);

    //liaison MQTT
    client.setHostname("10.98.9.20");
    client.setPort(1883);
    client.connectToHost();

Les lignes essentiels dans ce code sont les lignes concernant l'objet client de la classe mqtt (on peut retrouver la déclaration de cette objet dans le fichier mainwindow.h), elles permettent au raspberry de se connecter au broker mosquitto, tout comme les nanopi précedemment.

fonction connecte

 
//description pour liaison MQTT
void MainWindow::connecte()
{
    qDebug() <<"i'm connected";
    qDebug() <<"current state flick= "<<flick;

    //topic auquel vous êtes souscrit
    subscription = client.subscribe(QLatin1String("cptE15"));
    if(!subscription)
    {
        QMessageBox::critical(this,"error","failed to connect to broker");
        return;
    }
    ui->tabWidget->setCurrentIndex(0);
}

Pour cette fonction, la ligne interessante est la ligne de subscription=..., c'est le "cptE15" où l'on peut mettre le topic auquel on veut que la raspberry s'abonne.Ici c'est cptE15 car on faisait des tests de reception des infos d'un capteur sur la machine, et cela a fonctionné : on recevait bien les infos de la machine. On le savait grâce à ce bout de code:

fonction messageRecu

 
void MainWindow::messageRecu(const QByteArray &message, const QMqttTopicName &topic)
{
    qDebug() << QDateTime::currentDateTime().toString() << topic.name() << message;

    trmt=!trmt;
    qDebug() << trmt;
    emit valueChanged(trmt);
    monTimer.setInterval(1000);
    monTimer.start();
    connect(&monTimer,SIGNAL(timeout()),this,SLOT(relaisOFF()));
    //monTimer.stop();
}

Ici c'est lorsqu'on a le message affichant l'heure actuelle à laquelle par exemple sur le topic cptE15, un message a été publié, que l'on sait que la raspberry a bien reçu les données envoyées sur le topic. Passons au prochain code:

exemple d'une fonction actionneur : le moteur du convoyeur principal

 
void MainWindow::convoyeurOFF()
{
    qDebug() <<"arrêt convoyeur";
    QByteArray message = "1";
    quint8 qos = 1;               
    client.publish(QLatin1String("relais"),message,qos);
    flick=false;
    qDebug() << "flick = "<< flick;

    if(flick == false){
    ui->enArret->setStyleSheet("background-color:red");
    ui->enMarche->setStyleSheet("background-color:");
    ui->posteAuto->setStyleSheet("background-color:");

    }
}

void MainWindow::convoyeurON()
{

    qDebug() <<"demarrage convoyeur";
    QByteArray message = "0";
    quint8 qos = 1;
    client.publish(QLatin1String("relais"),message,qos);
    flick=true;
    qDebug() << "flick = " << flick;

    if(flick == true){
    ui->enMarche->setStyleSheet("background-color:green");
    ui->enArret->setStyleSheet("background-color:");
     ui->posteAuto->setStyleSheet("background-color:orange");
    }
}

Le Raspberry agira cette fois-ci comme celui qui publie, et ce sont les actionneurs de la carte actionneurs qui seront souscrit au topic de votre choix. Ici j'ai pris comme exemple la fonction permettant de piloter le moteur depuis l'interface par le biais des cartes électroniques reliées aux actionneurs dont on a besoin sur la machine. Bien sûr que la plupart des fonctions du code pilotant les actionneurs ont le même algorithme, seul le nom des topics est différent.
il suffit de changer le nom du topic dans la ligne client.publish(QLatin1String("relais"),message,qos) le nom du topic ici est relais. Pour plus de renseignement sur le qos, se renseigner sur le lien dans la partie mqtt.

création de l'interface graphique

Vous pourrez accéder et voir par vous même l'interface graphique ainsi que les différents panels proposés:
- une 1ère page qui pourra servir de dépannage pour les différents capteurs et actionneurs
Il y a une fonction dépannage existant qui servira à cela. Il suffira de changer que le topic où l'on veut vérifier.Voici les deux fonctions concernant le dépannage des actionneurs par exemple:

exemple d'une fonction actionneur : fonction dépannage actionneurs

 
//DEPANNAGE
void MainWindow::DepActON()
{
    qDebug() <<"publication topic relais à l'état 1";
    QByteArray message = "0";
    quint8 qos = 1;
    client.publish(QLatin1String("relaisDep"),message,qos);
    flick=true;
    qDebug() << "flick = " << flick;

    if(flick == true){
    ui->enMarche->setStyleSheet("background-color:green");
    ui->enArret->setStyleSheet("background-color:");
    }
}

void MainWindow::DepActOFF()
{
    qDebug() <<"publication topic relais à l'état 0";
    QByteArray message = "1";
    quint8 qos = 1;
    client.publish(QLatin1String("relaisDep"),message,qos);
    flick=false;
    qDebug() << "flick = "<< flick;

    if(flick == false){
    ui->enArret->setStyleSheet("background-color:red");
    ui->enMarche->setStyleSheet("background-color:");
    }
}

Pour le dépannage des capteurs, le plus simple est de modifier le topic dans la fonction capteur, puis de vérifier si le voyant info capteur reçu s'allume en orange. Voici à quoi ressemble la 1ère page:
Capture d’écran 2021-04-11 à 08.03.57.png

- une 2ème page montre des icones représentant la machine.Lorsqu'il y a un moteur d'un des postes manuels et/ou le convoyeur automatique:

représentation sur interface machine transfert

Les icônes s'allumeront en orange lorsqu'un moteur était actif.

- la 3ème page était celle qui permet de démarrer le convoyeur:

interface démarrage moteur

Chaque boutons moteur convoyeur ON et moteur convoyeur OFF sont reliés à des fonctions avec des publications sur des topic dès qu'on appuie sur le bouton.

- Les 3 dernières sont consacrées aux différents postes. Pour ce semestre, on s'est concentré sur le poste 3, c'est pour cela qu'il y a certains actionneurs qui peuvent être pilotés manuellement. Le principe est le même que les boutons pour le convoyeur (une fonction qui comporte une publication de topic avec un bouton. En allant à la page poste 3, vous verrez différents actionneurs qui peuvent être actionnés depuis l'interface.