Comunicazione tra 2 Arduino UNO

Sera,

esiste qualche documentazione/schema elettrico/libreria che permetta di trasferire delle informazioni da un Arduino UNO ad un altro?

Potrebbe andare bene una lettura dello stato HIGH/LOW su diversi PIN, ma sarebbe anche meglio se si riuscisse con un unico PIN a dare diverse indicazioni (è possibile, ad esempio, passare un valore analog con 255 possibili stati, o digital con 1024?).

Grazie.

Salve SmallG, dipende da che tipo di dato devi trasmettere, esistono molti protocolli di trasmissione che possono fare al caso tuo e altrettante maniere per realizzare una trasmissione.
Esistono dei moduli wireless che permettono la trasmissione tra due Arduino, per esempio i moduli nRF24L01 o MX-05V, MX-FS-03V o xBee.
Altrimenti c'è una trasmissione con fili molto semplice ma funzionale, devi implementare la libreria Wire.h ma ti posso aiutare!

Questo non è altro che il semplice cablaggio che devi effettuare:

Il funzionamento è semplice, il Master richiede un byte allo Slave, quando lo slave riceve la richiesta legge lo stato del pulsante e se è premuto invia "a" altrimenti invia "s". Il master leggerà il byte ricevuto, in caso esso fosse "a" un diodo LED viene acceso, in caso contrario se "s" è il byte ricevuto non verrà accesso il diodo LED.

Il diodo led è collegato a un Arduino e il pulsante all'altro. A4 e A5 dei due Arduino sono interconnessi in modo da avere la comunicazione tramite il protocollo/bus I2C, sono necessarie due resistenze di pull-up del valore di 4.7k ohm per evitare che il segnale resti fluttuante alterando quindi i dati.

Dovrai poi caricare questo nell'Arduino che deciderai di usare come Master

    #include <Wire.h>      /* Questa libreria è già presente in Arduino IDE (il software di programmazione) non dovrai scaricarla */
    void setup()
    {
      Wire.begin();        // Con questo comando inizializziamo il bus i2c
      pinMode (2,OUTPUT);
    }
    void loop()
    {
      Wire.requestFrom(2, 1); // Richiediamo un byte al dispositivo presente all'indirizzo 2.
      String b = "";
      char c = Wire.read(); // Leggiamo il byte ricevuto
      b = b + c;
      delay (100);
      if (b == "a")
      {
        digitalWrite(2, HIGH);
      }
      else
      {
        digitalWrite(2, LOW);
      }
      delay(10);
    }

Fatto ciò manca soltanto la programmazione dello Slave, che è la seguente:

     #include <Wire.h>
    void setup()
    {
      pinMode(2, INPUT);
      pinMode(13,OUTPUT);
      Wire.begin(2);                // Inizializza il bus I2C all'indirizzo 2
      Wire.onRequest(requestEvent); // Esegue la funzione sottoscritta quando ha una richiesta
    }
    void loop()
    {
      delay(100);
    }
    void requestEvent()
    {
      if (digitalRead(2) == HIGH){
        Wire.write("a");       // Se il pulsante è premuto invia il carattere "a"  
        digitalWrite(13,HIGH);  
      }
      else
      {
        Wire.write("s");      // Altrimenti invia il carattere "s"
        digitalWrite(13,LOW);
      }
    }

Se hai qualche problema scrivi pure qui, spero di aver centrato la tua domanda, cordiali saluti.

Ciao e grazie,

il mio problema è sorto perché ho un modulo wi fi esp8266 e 3 moduli rfid rdm6300. Ho notato che i codici dei singoli sensori vanno bene in sketch separati, ma quando li unisco danno problemi. Il problema inizia dove inizializzo i Serial, quindi credo che lì fanno interferenza (ho provato a cambiare l'ordine, in alcuni casi va solo il wi-fi, in altri il serial non mostra più nulla e quindi non è utilizzabile).

Per questo volevo usare il wi-fi su un altro arduino restituendo solo il risultato che mi serve (che sono 1 variabile 0 o 1 e un altra 0, 1 o 2, che potrei gestire anche con un solo valore creando delle combinazioni)

00
01
02
10
11
12

Altra questione, riesco alimentando solo il master a far alimentare anche l'altro arduino o gli serve un alimentazione a parte?
Il master è alimentato tramite l'usb-b /usb-a su trasformatore 5v 1A.
Ho anche 4 batterie per un totale di 6v che alimentano solo un motore dal master (e non continuamente).

Questo sistema mi permette di fare tutto ciò?

Grazie!

Il problema inizia dove inizializzo i Serial,

Non fai prima a postare lo sketch ?

Questo, essendo troppo lungo mi dice che supero i 9000 caratteri del forum, quindi l'ho caricato qui:

http://pastebin.com/BmrqffQy

Come pensavo.....
hai istanziato piu' SoftwareSerial, ma il problema è che ne puoi usare solo una alla volta

quindi devi usare la Listen per scegliere la porta che voi usare

Ho provato così, ma continua a non trovarmi i lettori RFID:

// Includo librerie
#include "SoftwareSerial.h"    // Libreria per l'emulazione com. seriale
#include "WiFiEsp.h"           // Libreria per il modulo WiFi ESP8266-01
#include "Servo.h"             // Libreria per il servo motore
#include "Adafruit_NeoPixel.h" // Libreria per gestire i led

// Variabili pin componenti
const int Pin_Distanza1_Echo = 2;
const int Pin_Distanza1_Trigger = 3;
const int Pin_WiFi1_RX = 5;
const int Pin_WiFi1_TX = 6;
const int Pin_RFID1_RX = 8;
const int Pin_RFID1_TX = 9;
const int Pin_RFID2_RX = 10;
const int Pin_RFID2_TX = 11;
const int Pin_RFID3_RX = 12;
const int Pin_RFID3_TX = 13;
const int Pin_Led1 = 14;     // Analogico A0 usato come digitale
const int Pin_Led2 = 15;     // Analogico A1 usato come digitale
const int Pin_Led3 = 16;     // Analogico A2 usato come digitale
const int Pin_Servo1 = 17;   // Analogico A4 usato come digitale

// Comunicazioni seriali tramite libreria SoftwareSerial.h
SoftwareSerial WIFI1(Pin_WiFi1_RX, Pin_WiFi1_TX); // Modulo WiFi
SoftwareSerial RFID1(Pin_RFID1_RX, Pin_RFID1_TX); // Modulo RFID 1
SoftwareSerial RFID2(Pin_RFID1_RX, Pin_RFID1_TX); // Modulo RFID 2

// Dati di connessione alla rete WiFi e estrazione dati meteo
char rete[] = "";                  // Nome della rete (SSID) di connessione internet
char pass[] = "";                  // Password di rete
int status = WL_IDLE_STATUS;                // Stato trasmettitore WiFi
char server[] = "appendiabiti.altervista.org"; // Server di richiesta dati
boolean dato_scrivi = 0;          // Variabile per iniziare e concludere la lettura del dato meteo
int dato_attuale = 1;             // Variabile per passare a registrare il dato meteo successivo
String dati_ok =  String("");     // Stringa di verifica ottenimento corretto dei dati
String temp_max =  String("");    // Temperatura massima dal meteo
String temp_min =  String("");    // Temperatura minima dal meteo
String pioggia_tot =  String(""); // Millimetri di pioggia dal meteo

const unsigned int Intervallo_WiFi = 10000;
unsigned long Ultima_WiFi = millis() - (Intervallo_WiFi + 1);

// Variabili moduli RFID
int i; // Conta ciclo for
String t = String(""); // Lettura valore tag
String tag1 = String("25166484854496665705449543");
String tag2 = String("25165484857695466535357653");
String tag3 = String("25153484853526551707051683");
int Tag_Su_Lettore1 = 0; // 0 = nessun tag corrispondente
int Tag_Su_Lettore2 = 0; // 0 = nessun tag corrispondente
int Tag_Su_Lettore3 = 0; // 0 = nessun tag corrispondente
int Tag_Corrispondenti = 0; // Verifica disponibilità tag
int Lettore1_Tag;
int Lettore2_Tag;
int Lettore3_Tag;

// Variabili condizioni meteo
int Meteo_Consiglia;

// Inizializzazione oggetti
WiFiEspClient client; // Nome client WiFi
Servo servomotore;    // Nome servo motore

void setup() {
  Serial.begin(9600); // Arduino
  
  RFID1.begin(9600);  // Lettore RFID1
  RFID2.begin(9600);  // Lettore RFID2
  WIFI1.begin(9600);
  WiFi.init(&WIFI1);
  
  if (WiFi.status() == WL_NO_SHIELD) {
    Serial.println("[WiFiEsp] Shield WiFi non presente.");
    delay(1000);
  }
  
  while ( status != WL_CONNECTED) {
    Serial.print("[WiFiEsp] Tentativo di connessione alla rete: ");
    Serial.println(rete);
    status = WiFi.begin(rete, pass);
  }
  Serial.println("[WiFiEsp] Connessione eseguita.");
  delay(1000);
}

void loop() {
  WIFI1.listen();
  if (WIFI1.isListening() && millis() - Ultima_WiFi > Intervallo_WiFi) {
    Serial.println("WIFI1: Listening!");
    client.stop();
    if (client.connect(server, 80)) {
      Serial.println("Connecting...");
      client.println(F("GET /meteo/dato.php HTTP/1.1"));
      client.println(F("Host: appendiabiti.altervista.org"));
      client.println("Connection: close");
      client.println();
      Ultima_WiFi = millis();
      Serial.println("[WiFiEsp] Connessione riuscita.");
    }
    else {
      Serial.println("[WiFiEsp] Connessione non riuscita.");
    }
    while (client.available()) {
      char c = client.read();
      if (c == 123) { // 123 = "{" in ASCII
          dato_scrivi = 1;
          if( dato_attuale == 1) {
            dati_ok = "";
          }
          else if( dato_attuale == 2) {
            temp_min = "";
          }
          else if( dato_attuale == 3) {
            temp_max = "";
          }
          else if( dato_attuale == 4) {
            pioggia_tot = "";
          }
      }
      else if (c == 125) { // 125 = "}" in ASCII
          dato_scrivi = 0;
          dato_attuale = dato_attuale + 1;
          if( dato_attuale == 5) {
            dato_attuale = 1;
          }
      }
      else if ( dato_scrivi == 1 && dato_attuale == 1 ) {
         dati_ok = String(dati_ok + c);
      }
      else if ( dato_scrivi == 1 && dato_attuale == 2 ) {
          temp_min = String(temp_min + c);
      }
      else if ( dato_scrivi == 1 && dato_attuale == 3 ) {
          temp_max = String(temp_max + c);
      }
      else if ( dato_scrivi == 1 && dato_attuale == 4 ) {
          pioggia_tot = String(pioggia_tot + c);
      }
    }
    if(dati_ok == "OK") {
      Serial.println("[WiFiEsp] Dati meteo prelevati correttamente.");
      Serial.print("Minima: ");
      Serial.println(temp_min.toFloat());
      Serial.print("Max: ");
      Serial.println(temp_max.toFloat());
      Serial.print("Pioggia: ");
      Serial.println(pioggia_tot.toFloat());
      Ultima_WiFi = millis();
    }
    else {
      Serial.println("[WiFiEsp] Errore ricezione dati. Ritento al prossimo loop.");
      Ultima_WiFi = millis() - (Intervallo_WiFi + 1);
      delay(5000);
    }
    delay(1000);
  }

    // 04.C) Leggo tag accanto ai lettori RFID se presenti e quali
    RFID1.listen();
    if (RFID1.isListening() && RFID1.available() > 0) {
      Serial.println("RFID1: Listening!");
      t = String("");
      for(i = 0; i < 14; i++) {
        t = String(t + RFID1.read());
      }
      Serial.println(t);
      delay(1000);
      if(t == tag1) {
        Serial.println("Tag su lettore 1: 1");
        Tag_Su_Lettore1 = 1;
      }
      else if(t == tag2) {
        Serial.println("Tag su lettore 1: 2");
        Tag_Su_Lettore1 = 2;
      }
      else if(t == tag3) {
        Serial.println("Tag su lettore 1: 3");
        Tag_Su_Lettore1 = 3;
      }
      else {
        Serial.println("Tag su lettore 1: Nessuno o sconosciuto");
        Tag_Su_Lettore1 = 0;
      }
    }
    else {
      Serial.println("Lettore RFID1 non riconosciuto o non disponibile.");
    }
    t = String("");
    delay(1000);

    RFID2.listen();
    if (RFID2.isListening() && RFID2.available() > 0) {
      Serial.println("RFID2: Listening!");
      t = String("");
      for(i = 0; i < 14; i++) {
        t = String(t + RFID1.read());
      }
      Serial.println(t);
      delay(1000);
      if(t == tag1) {
        Serial.println("Tag su lettore 1: 1");
        Tag_Su_Lettore1 = 1;
      }
      else if(t == tag2) {
        Serial.println("Tag su lettore 1: 2");
        Tag_Su_Lettore1 = 2;
      }
      else if(t == tag3) {
        Serial.println("Tag su lettore 1: 3");
        Tag_Su_Lettore1 = 3;
      }
      else {
        Serial.println("Tag su lettore 1: Nessuno o sconosciuto");
        Tag_Su_Lettore1 = 0;
      }
    }
    else {
      Serial.println("Lettore RFID2 non riconosciuto o non disponibile.");
    }
    t = String("");
    delay(1000);
}

Risultato:

uhmm il problema è che funziona una sola SoftwareSerial alla volta, quindi solo quella che è in listen().
Tutte le altre NON ricevono i dati mentre un'altra lavora.

Quindi se tu passi una card mentre sta' colloquiando con l'ESP , dato che ci mette un tempo lunghissimo, è come se non la vedesse

Mi sa' che devi passare a una scheda con multiseriale, come ad esempio la Mega2560, che ne ha 4

Strano però perché dopo che leggo i dati in teoria assegno il listen() al modulo RFID, quando la connessione è già terminata..

Si, ma a meno che tu non sia mandrake e riuscire a passare la card nel tempo che fa' l' IF......

prova a togliere quel delay in fondo allo sketch

E comunque dovresti rimanere sull'RFID che ha risposto fino a che non passano tutti i dati, altrimenti prendi un carattere e ti perdi quello dopo

Ho rivisto tutto lo sketch provando prima solo con 2 RFID e poi aggiungendo il WiFi. Con qualche millis credo di aver risolto:

Il wi fi lo userò una volta ogni 30/60 minuti, ma anche nelle prove in cui aggiorno ogni 10 secondi ora va abbastanza decentemente.

Un breve delay l'ho messo non prima di listen() ma subito dopo (e prima del codice che utilizza quel seriale), credo che così ha un po' di tempo per utilizzare al meglio la porta voluta.
I lettori RFID non ci prendono sempre, a volte mi danno letture vuote.. Ho risolto considerando per X secondi l'ultimo valore letto, in modo che non lo considero più sol se effettivamente il tag è stato rimosso per almeno X secondi (in genere sbaglia al massimo 2-3 letture consecutive e così evito che mi si spenga/accenda il led relativo ogni mezzo secondo).

Il MEGA è sicuramente un opzione che permette maggiore stabilità e meno compromessi, lo tengo a mente se mi serve fare qualcosa di più serio. Per ora così ho risolto. Grazie per l'indicazione sul listen(), non l'avrei mai trovato da solo.