Good afternoon,
After searching a lot I can't find the solution to my problem. I expose: I am doing an application in which I need to transfer the weight of some scales to an external controller updating with the "minimum sample rate". I explain all the architecture to see if you can help me. On the one hand I have a Mega 2560 rev3 + ethernet shield 2 + 8 scales (I use the ADC HX711+loadcells), this works correctly and I am able to manage the values and display on the LCD screen. I also have a temperature/humidity sensor DHT11 that I also can manage with and see its values through the serial terminal. On the other hand I have a Raspberry Pi 4 with Codesys runtime. I want to communicate with the raspberry via Ethernet and be able to send the weight variables of each scale. My idea is through Modbus TCP, I try to configure the Arduino as a Server and the raspberry as a Client to make the queries. I copy the code that I have, to begin with I want to try to read / write fixed values and when I see them in the raspberry correctly modify it by the weight variables. Any help will be a great help. To begin with, in the "Holdresult = modbusTCPServer.configureHoldingRegisters(0x01, nreg); " I get the result of "1" which I see indicates a failure and I don't understand why.
#include <HX711.h>
#include <Wire.h>
#include <LiquidCrystal_I2C.h>
#include <DHT.h>
#include <SPI.h>
#include <Ethernet.h>
#include <ArduinoRS485.h> // ArduinoModbus depends on the ArduinoRS485 library
#include <ArduinoModbus.h>
//**********MODBUSTCP**********
byte mac[] = {
0xA8, 0x61, 0x0A, 0xAE, 0xA8, 0x23
};
IPAddress ip(192, 168, 178, 10);
EthernetServer ethServer(502);
ModbusTCPServer modbusTCPServer;
uint16_t regis[] = {10, 8, 1, 2, 4, 5, 98, 74, 87, 12};
int Holdresult;
int nreg = 10;
int hold;
//***********DHT11*************
int DHTPIN = 13;
int DHTTYPE = DHT11;
int Temp;
int Hum;
DHT dht(DHTPIN, DHT11);
//**********Loadcells**********
HX711 bascula1; //Decl objeto bascula 1
HX711 bascula2; //Decl objeto bascula 2
HX711 bascula3; //Decl objeto bascula 3
HX711 bascula4; //Decl objeto bascula 4
HX711 bascula5; //Decl objeto bascula 5
HX711 bascula6; //Decl objeto bascula 6
HX711 bascula7; //Decl objeto bascula 7
HX711 bascula8; //Decl objeto bascula 8
//*****************************
LiquidCrystal_I2C lcd(0x27,20,4); //Crear el objeto lcd dirección 0x27 y 20 columnas x 4 filas
const int DOUT_1=A0; //Declaracion pines bascula 1
const int CLK_1=A1; //Declaracion pin CLK bascula 1
const int DOUT_2=A2; //Declaracion pines bascula 2
const int CLK_2=A3; //Declaracion pin CLK bascula 2
const int DOUT_3=A4; //Declaracion pines bascula 3
const int CLK_3=A5; //Declaracion pin CLK bascula 3
const int DOUT_4=22; //Declaracion pines bascula 4
const int CLK_4=23; //Declaracion pin CLK bascula 4
const int DOUT_5=A8; //Declaracion pines bascula 5
const int CLK_5=A9; //Declaracion pin CLK bascula 5
const int DOUT_6=A10; //Declaracion pines bascula 6
const int CLK_6=A11; //Declaracion pin CLK bascula 6
const int DOUT_7=A12; //Declaracion pines bascula 7
const int CLK_7=A13; //Declaracion pin CLK bascula 7
const int DOUT_8=A14; //Declaracion pines bascula 8
const int CLK_8=A15; //Declaracion pin CLK bascula 8
int sw1_pin =2; //Declaración n pin interruptor 1
int sw2_pin =3; //Declaración n pin interruptor 2
int sw3_pin =4; //Declaración n pin interruptor 3
int sw4_pin =5; //Declaración n pin interruptor 4
int sw5_pin =6; //Declaración n pin interruptor 5
int sw6_pin =7; //Declaración n pin interruptor 6
int sw7_pin =8; //Declaración n pin interruptor 7
int sw8_pin =9; //Declaración n pin interruptor 8
int rst_pin =12; //Declaración n pin 8 reset min/max
int w1; //Declaracion variable peso1
int w2; //Declaracion variable peso2
int w3; //Declaracion variable peso3
int w4; //Declaracion variable peso4
int w5; //Declaracion variable peso5
int w6; //Declaracion variable peso6
int w7; //Declaracion variable peso7
int w8; //Declaracion variable peso8
char w1_fixed[4]; //Declaración para mostrar peso con longitud fija
char w2_fixed[4]; //Declaración para mostrar peso con longitud fija
char w3_fixed[4]; //Declaración para mostrar peso con longitud fija
char w4_fixed[4]; //Declaración para mostrar peso con longitud fija
char w5_fixed[4]; //Declaración para mostrar peso con longitud fija
char w6_fixed[4]; //Declaración para mostrar peso con longitud fija
char w7_fixed[4]; //Declaración para mostrar peso con longitud fija
char w8_fixed[4]; //Declaración para mostrar peso con longitud fija
const float scale[9] = {0, 300.3, 297.3, -328.6, -325.6, 333.2, -333.9, -329.9, -333.58};
//========================================================
void setup() {
pinMode(sw1_pin, INPUT_PULLUP); //Declaración pin interruptor y tipo
pinMode(sw2_pin, INPUT_PULLUP); //Declaración pin interruptor y tipo
pinMode(sw3_pin, INPUT_PULLUP); //Declaración pin interruptor y tipo
pinMode(sw4_pin, INPUT_PULLUP); //Declaración pin interruptor y tipo
pinMode(sw5_pin, INPUT_PULLUP); //Declaración pin interruptor y tipo
pinMode(sw6_pin, INPUT_PULLUP); //Declaración pin interruptor y tipo
pinMode(sw7_pin, INPUT_PULLUP); //Declaración pin interruptor y tipo
pinMode(sw8_pin, INPUT_PULLUP); //Declaración pin interruptor y tipo
pinMode(rst_pin, INPUT_PULLUP); //Declaración pin y tipo
lcd.init(); //Inicializar el LCD
lcd.clear(); //Borra pantall y situa cursor (0.0)
lcd.backlight(); //Encender luz LCD
dht.begin(); //inicializacion de sensor DHT11
bascula1.begin(DOUT_1, CLK_1); //Iniciar sensor 1
bascula2.begin(DOUT_2, CLK_2); //Iniciar sensor 2
bascula3.begin(DOUT_3, CLK_3); //Iniciar sensor 3
bascula4.begin(DOUT_4, CLK_4); //Iniciar sensor 4
bascula5.begin(DOUT_5, CLK_5); //Iniciar sensor 5
bascula6.begin(DOUT_6, CLK_6); //Iniciar sensor 6
bascula7.begin(DOUT_7, CLK_7); //Iniciar sensor 7
bascula8.begin(DOUT_8, CLK_8); //Iniciar sensor 8
lcd.setCursor(0,0);
lcd.print("**Inicializando...**");
bascula1.set_scale(scale[1]); //Escala sensor 1
bascula2.set_scale(scale[2]); //Escala sensor 2
bascula3.set_scale(scale[3]); //Escala sensor 3
bascula4.set_scale(scale[4]); //Escala sensor 4
bascula5.set_scale(scale[5]); //Escala sensor 5
bascula6.set_scale(scale[6]); //Escala sensor 6
bascula7.set_scale(scale[7]); //Escala sensor 7
bascula8.set_scale(scale[8]); //Escala sensor 8
bascula1.tare(); //Tara sensor 1
bascula2.tare(); //Tara sensor 2
bascula3.tare(); //Tara sensor 3
bascula4.tare(); //Tara sensor 4
bascula5.tare(); //Tara sensor 5
bascula6.tare(); //Tara sensor 6
bascula7.tare(); //Tara sensor 7
bascula8.tare(); //Tara sensor 8
delay(1000);
lcd.setCursor(0,1);
lcd.print("Listo para pesar");
delay(1000);
lcd.clear();
//*************MODBUS************//
Serial.begin(9600);
while (!Serial) {
; // wait for serial port to connect. Needed for native USB port only
}
Serial.println("Ethernet Modbus TCP Example");
// start the Ethernet connection and the server:
Ethernet.begin(mac, ip);
// Check for Ethernet hardware present
if (Ethernet.hardwareStatus() == EthernetNoHardware) {
Serial.println("Ethernet shield was not found. Sorry, can't run without hardware. :(");
while (true) {
delay(1); // do nothing, no point running without Ethernet hardware
}
}
if (Ethernet.linkStatus() == LinkOFF) {
Serial.println("Ethernet cable is not connected.");
delay(100);
}
// start the server
ethServer.begin();
// start the Modbus TCP server
if (!modbusTCPServer.begin()) {
Serial.println("Failed to start Modbus TCP Server!");
while (1);
}
// configure input registers at address 0x00 // int configureInputRegisters(int startAddress, int nb);
Holdresult = modbusTCPServer.configureHoldingRegisters(0x01, nreg);
Serial.print("Holding register initialization Result= ");
Serial.print(Holdresult);
Serial.print("\n");
Serial.print("Modbus server address:");
Serial.println(Ethernet.localIP());
// Filling input registers
for(uint16_t i = 0; i < nreg; i++)
{
hold = modbusTCPServer.holdingRegisterWrite((0x00 + i),(i + 1));
Serial.println(hold, DEC);
}
Serial.println("End of Setup");
}
void LecturaPes() {
lcd.setCursor(0,0);
lcd.print("P1: ");
lcd.setCursor(11,0);
lcd.print("P2: ");
lcd.setCursor(0,1);
lcd.print("P3: ");
lcd.setCursor(11,1);
lcd.print("P4: ");
lcd.setCursor(0,2);
lcd.print("P5: ");
lcd.setCursor(11,2);
lcd.print("P6: ");
lcd.setCursor(0,3);
lcd.print("P7: ");
lcd.setCursor(11,3);
lcd.print("P8: ");
lcd.setCursor(4,0);
w1=bascula1.get_units(16); //Vact - Tara / Escala. "n" es promedio lecturas. Si se incluye ",n2"-> n2 num decimales si no es entero
sprintf (w1_fixed, "%4d",w1); // Da formato al dato, en este caso longitud 4 digitos sin signo.
lcd.print(w1_fixed);
lcd.setCursor(15,0);
w2=bascula2.get_units(16); //Vact - Tara / Escala. "n" es promedio lecturas. Si se incluye ",n2"-> n2 num decimales si no es entero
sprintf (w2_fixed, "%4d",w2); // Da formato al dato, en este caso longitud 4 digitos sin signo.
lcd.print(w2_fixed);
lcd.setCursor(4,1);
w3=bascula3.get_units(16); //Vact - Tara / Escala. "n" es promedio lecturas. Si se incluye ",n2"-> n2 num decimales si no es entero
sprintf (w3_fixed, "%4d",w3); // Da formato al dato, en este caso longitud 4 digitos sin signo.
lcd.print(w3_fixed);
lcd.setCursor(15,1);
w4=bascula4.get_units(16); //Vact - Tara / Escala. "n" es promedio lecturas. Si se incluye ",n2"-> n2 num decimales si no es entero
sprintf (w4_fixed, "%4d",w4); // Da formato al dato, en este caso longitud 4 digitos sin signo.
lcd.print(w4_fixed);
lcd.setCursor(4,2);
w5=bascula5.get_units(16); //Vact - Tara / Escala. "n" es promedio lecturas. Si se incluye ",n2"-> n2 num decimales si no es entero
sprintf (w5_fixed, "%4d",w5); // Da formato al dato, en este caso longitud 4 digitos sin signo.
lcd.print(w5_fixed);
lcd.setCursor(15,2);
w6=bascula6.get_units(16); //Vact - Tara / Escala. "n" es promedio lecturas. Si se incluye ",n2"-> n2 num decimales si no es entero
sprintf (w6_fixed, "%4d",w6); // Da formato al dato, en este caso longitud 4 digitos sin signo.
lcd.print(w6_fixed);
lcd.setCursor(4,3);
w7=bascula7.get_units(16); //Vact - Tara / Escala. "n" es promedio lecturas. Si se incluye ",n2"-> n2 num decimales si no es entero
sprintf (w7_fixed, "%4d",w7); // Da formato al dato, en este caso longitud 4 digitos sin signo.
lcd.print(w7_fixed);
lcd.setCursor(15,3);
w8=bascula8.get_units(16); //Vact - Tara / Escala. "n" es promedio lecturas. Si se incluye ",n2"-> n2 num decimales si no es entero
sprintf (w8_fixed, "%4d",w8); // Da formato al dato, en este caso longitud 4 digitos sin signo.
lcd.print(w8_fixed);
}
void loop() {
LecturaPes();
Temp = dht.readTemperature(); // lectura valor temp
Hum = dht.readHumidity(); // lectura valor humitat
// Serial.print("Temperatura: ");
// Serial.print(Temp);
// Serial.print(" Humitat: ");
// Serial.println(Hum);
// delay(500);
// listen for incoming clients
EthernetClient client = ethServer.available();
if (client) {
LecturaPes();
// a new client connected
Serial.println("new client");
// let the Modbus TCP accept the connection
modbusTCPServer.accept(client);
while (client.connected()) {
// poll for Modbus TCP requests, while client connected
modbusTCPServer.poll();
// LecturaPes();
}
Serial.println("client disconnected");
}
}
Thank you very much for your help!