Serveur/client Avec ESP32 et Processing

Bonjour,
Je suis actuellement en BTS, et mon projet de fin d'année est de crée une serre automatique.

Je doit donc créer un IHM avec Processing et un serveur qui va regrouper toute les données des capteurs.

Mon IHM sur processing est mon client, qui va afficher les données de la serre mais qui va aussi permettre à l'utilisateur de modifier les paramètres de la serre.

Le client doit donc recevoir des données du serveur mais aussi lui en envoyer.

Le serveur est un ESP32 WROOM. J'ai déjà réussi à faire un programme où Processing est le client et envoie des données au serveur ESP32. Mais je n'arrive pas à faire l'inverse (le serveur ESP32 envoie des données au client Processing). J'ai fait beaucoup de recherches et je n'arrive pas à trouver.

Je viens donc vous demander de l'aide pour m'aider à avancer sur ce petit blocage.

Merci par avance pour vos conseille.

Les programme suivant sont ceux qui marche et que j'ai réussis a faire, mais impossible de trouver pour que le client reçoit des données du serveur.
CODE PROCESSING CLIEN


import processing.net.*;

Client c;
String input;
int data[];

void setup() 
{
  size(450, 255);
  background(204);
  stroke(0);
  frameRate(5); // Slow it down a little
  // Connect to the server's IP address and port
  c = new Client(this, "adress IP du server", 80); // Replace with your server's IP and port
}

void draw() 
{
  if (mousePressed == true) {
    // Draw our line
    stroke(255);
    line(pmouseX, pmouseY, mouseX, mouseY);
    // Send mouse coords to other person
    c.write(pmouseX + " " + pmouseY + " " + mouseX + " " + mouseY + "\n");
    println(pmouseX + " " + pmouseY + " " + mouseX + " " + mouseY + "\n");
  }
  // Receive data from server
  if (c.available() > 0) {
    input = c.readString();
    input = input.substring(0, input.indexOf("\n")); // Only up to the newline
    data = int(split(input, ' ')); // Split values into an array
    // Draw line using received coords
    stroke(0);
    line(data[0], data[1], data[2], data[3]);
     println("reading message from client at " + c.ip() + " <- input=", input, "; data=", data);

  }
}

CODE SERVEUR ESP32

#include <WiFi.h>

const char* ssid     = "";
const char* password = "";

int counter;
WiFiServer server(80);



void setup()
{
    Serial.begin(115200);
    delay(10);

    // We start by connecting to a WiFi network

    Serial.println();
    Serial.println();
    Serial.print("Connecting to ");
    Serial.println(ssid);
    WiFi.begin(ssid, password);

    while (WiFi.status() != WL_CONNECTED) {
        delay(500);
        Serial.print(".");
    }

    Serial.println("");
    Serial.println("WiFi connected.");
    Serial.println("IP address: ");
    Serial.println(WiFi.localIP());
    
    server.begin();


}

void loop(){
 WiFiClient client = server.available(); 

  if (client) {                             // if you get a client,
    Serial.println("New Client.");           // print a message out the serial port
    String currentLine = "";                // make a String to hold incoming data from the client
    while (client.connected()) { 
      server.write(200);// loop while the client's connected
      if (client.available()) {             // if there's bytes to read from the client,
        char c = client.read();// read a byte, then
        Serial.write(c);
                               // print it out the serial monitor
    }
    }
    // close the connection:
    client.stop();
    Serial.println("Client Disconnected.");
  }
}

Peut tu décrire plus en détails ce que tu veux faire ?

Car dans le code de ton ESP32, tu ne renvois pas de données au client et tu n'essayes pas non plus de contacter le "client" Processing.

Les deux programme sont des programmes de test pour reussir à trouver une solution viable où les deux puissent communiquer entre eux.

J'ai reussi pour le moment à faire une communication uniquement dans un sens ( du client au serveur) et je cherche de l'aide pour m'aider a faire dans l'autre sens car tout ce que j'ai essayé ne marchait pas

Oui, c'est ce que j'ai vu dans ton code.

Oui, j'avais bien compris dans ton premier message, c'est pour ça que je te demandais de détailler.
Car suivant ce que tu veux faire il y a en gros deux façon de faire.

Dans le code mis si dessous j'arrive a envoyer une donnée a processing de l'esp32 ( processing est toujours le client et l'esp32 est le serveur). Mais une fois la donnée reçus Processing m'affiche "Client got end-of-stream." et je ne sais pas comment régler ce problème.

CODE PROCESSING

import processing.net.*;

Client c;
String input;


void setup() 
{
  size(450, 255);
  background(204);
  stroke(0);
  frameRate(5); // Slow it down a little
  // Connect to the server's IP address and port
  c = new Client(this, "ip", 80); // Replace with your server's IP and port
}
void draw() 
{
  
  if (c.available() > 0) {
    input = c.readString();
    print(input);
  }
}

CODE ESP32

#include <WiFi.h>

const char* ssid     = "";
const char* password = "";


WiFiServer server(80);



void setup()
{
    Serial.begin(115200);
    delay(10);

    // We start by connecting to a WiFi network

    Serial.println();
    Serial.println();
    Serial.print("Connecting to ");
    Serial.println(ssid);
    WiFi.begin(ssid, password);

    while (WiFi.status() != WL_CONNECTED) {
        delay(500);
        Serial.print(".");
    }

    Serial.println("");
    Serial.println("WiFi connected.");
    Serial.println("IP address: ");
    Serial.println(WiFi.localIP());
    
    server.begin();


}

void loop(){
 WiFiClient client = server.available(); 
 int v = random(50);
 String payload = String(v);

client.print(payload);
Serial.println(payload);
delay(1000);
}

Pour etre plus precis mon serveur (ESP32) va recevoir les donnée des capteurs. Il va les metre en forme puis les envoyer a mon Clien( Processing). Mon clien va afficher ces donnée dans un environement graphique. L'utilisateur lui va utiliser l'environnement graphique pour definir des seuils de declanchement ( par exemple une temperature a ne pas depasser sinon on active les chauffage) . Une fois la configuration realiser le clien (Processing) devra envoyer la configuration au serveur (ESP32)

Ok, ton code à changé du coup!

Ton code devrait effectivement envoyer une valeur entre 0 et 49 aléatoirement toutes les secondes.
Qu'a tu sur le moniteur série de l'ESP32?

Je ne connais pas Processing, a priori la fonction draw est appelé en boucle?
La première fois elle reçoit bien quelque chose de l'ESP32?

Ok, merci pour les détailles.
Comme ça, je serais plutôt partie sur inverser les roles pour l'établissement de la connection.
c'est à dire Poocessing en serveur et ESP32 en client, avec fermeture de la connection, si l'envois de donné ne ce fait pas en continue(par ex toutes les minutes).
Mais cela ne change pas le fond de te problème, donc pour l'instant on peut laisser pour plus tard :slight_smile:

Oui le draw est comme le LOOP. Je doit rester dans cette configuration car nimporte quelle pc avec processing et le code pourra bénéficier des données envoyées.

En fete le probleme que je rencontre maintenant avec ce deuxieme programme est que le clien recois une donnée du serveur et lorsque la deuxieme donnée arrive ca me marque " Client got end-of-stream." Et impossible de trouver ce qui créé cette erreur.

Pourquoi vous embêter avec Processing alors que vous pourriez simplement construire une interface Web sur l'ESP32 ce qui permettrait à n'importe quel ordinateur ou smartphone de se connecter pour paramétrer l'ESP32 ?

Son but est de faire une IHM de pilotage de sa serre, pas uniquement de paramétrer l'ESP32.
Ce qui bien évidement peut aussi être fait via une application WEB.

Après à savoir si Processing est plus embêtant que faire du javascript/HTML pour faire une IHM, ne connaissant pas Processing, je ne serais pas trop me positionner.

Processing c’est Java - on peut faire des trucs sympa mais ça reste une dépendance à installer sur le PC/Mac

Ba oui, mais visiblement il a un Processing d'installé sur sa machine et je ne suis pas sûre que l'embetabilité du déploiement de son application fasse partie de son sujet.
De plus à voir si cela ne fait pas partie de son projet de fin d'année.

Oui
Je posais juste la question de savoir si ça avait été envisagé.

Oui oui, ma réflexion était plus sur l'utilisation du javascript/HTML, qui est quand même encore "pénible" par rapport au développement d'application dite lourde.

Processing "de base" n'a pas non plus un kit intégré pour l'IHM (bouton, graphiques, ....). Il y a des trucs comme controlP5 ou G4P mais c'est pas génial...

Oui de ce que j'ai vu rapidement lorsque @bellatore692 en a parlé, c'est plus pour "l'artistique".
Je n'ai pas vu de contrôle tout fait.

J'utilise processing car je n'ai auccun connaissance en HTML alors que peocessing je l'ai deja bien pris en main lors d'un autre projet. De plus le temps pour realiser le projet est un peu cour donc je suis partie sur la solution que je metrise le plus. Apres j'etait pret a me lancer dans une page sur l'ESP32 mais j'etait pas trop confiant.

Si vous maîtrisez Processing / Java ça se comprend

les deux bibliothèques fréquentes sont controlP5 et G4P

Je vais essayer alors

pour que l'ESP puisse parler à votre PC il faut ouvrir un port de communication TCP-IP

un truc du genre

import processing.net.*;

int port = 12345;
Server server;
Client client;

void setup() {
  size(400, 400);
  server = new Server(this, port);
  println("IP du serveur: " + server.ip());
}

void draw() {
  client = server.available();
  if (client != null) {
    while (client.available() > 0) {
      byte[] data = new byte[xxx]; // xxx est la taille de la structure reçue
      client.readBytes(data);
      ... ICI VOTRE CODE
    }
    client.stop();
  }
 }

côté ESP32 il faut un client

const char *serverIP = "Adresse_IP_du_serveur"; // Remplacez par l'adresse IP de votre serveur
const uint16_t port = 12345;

WiFiClient client;

et quand vous voulez envoyer les data vous faites un

if (client.connect(serverIP, port)) {
  client.write((uint8_t *) &laStructure, tailleDeLaStructure );
}