Sending and Receiving Data with nrf24l01

Have a nice day. I made a display that I can print numbers with bluetooth by getting help from the forum before. Again, I wrote the kg information from the weight indicator to the serial port with modbus by getting help from the forum. I wanted to send the data we received from modbus to the display with bluetooth but it was not successful. Since there was only one rx tx in Arduino nano and uno, I could not use bluetooth. I tried to send the data from the Arduino receiving data from modbus to the Arduino connected to the display with nrf24l01 RF modules but it was not successful. I could not make the necessary arrangements in the receiver and transmitter programs. I would be very happy if you could help me send and receive modbus data with nrf24I01 modules in this way.

nrf24l01 Transmitter program

/*******************************************************

  Modbus Client Example D 485halfduplex

  This Modbus Client
  - reads registers from Modbus Servers periodically

  based on an idea or the (incorrect):
  RS485_HalfDuplex.pde - example using ModbusMaster library to communicate
  reading M02  using a half-duplex RS485 transceiver.

  hardware
  - a MAX485-TTL adapter

  by noiasca
  2024-10-27  https://forum.arduino.cc/t/arduino-modbus-master-help-please/1315703
  2022-07-31  OK - tested with Arduino MEGA

 *******************************************************/


/* *******************************************************
   Serial Interface
 * **************************************************** */
// if you don't have enough HW Serial (i.e. on an UNO)
// you are forced to use SoftwareSerial or AltSoftSerial
#include <SoftwareSerial.h>
constexpr uint8_t rxPin = 2;                   // for Softserial
constexpr uint8_t txPin = 3;
SoftwareSerial mySerial(rxPin, txPin);

// On a Mega you can simply use
// a Reference to an existing HW Serial:
//HardwareSerial &mySerial = Serial3;

/* **************************************************** *
   Modbus
 * **************************************************** */
#include <ModbusMaster.h>                        // Modbus Master 2.0.0 by Doc Walker - install with Library Manager
constexpr uint8_t modbusEnablePin = 5;           // The GPIO used to control the MAX485 TX pin. Set to 255 if you are not using RS485 or a selfsensing adapter
constexpr uint32_t modbusBaud = 9600;            // use slow speeds with SoftSerial
constexpr uint16_t modbusRestTx = 15000;         // rest time between transmissions - microseconds
uint32_t modbusPreviousTx = 0;                   // timestamp of last transmission - microseconds
ModbusMaster serverA;                            // instantiate ModbusMaster object - slave - node

// this function will be called before the client transmits data
void preTransmission()
{
  while (micros() - modbusPreviousTx < modbusRestTx)   // check last transmission end and wait if the call was to early
  {
    yield();                                           // wait some time and allow background tasks
  }
  digitalWrite(modbusEnablePin, HIGH);
}

// this function will be called after the transmission
void postTransmission()
{
  digitalWrite(modbusEnablePin, LOW);
  modbusPreviousTx = micros();         // remember last timestamp
}

// do all the settings for the Modbus
void modbusInit()
{
  mySerial.begin(modbusBaud);                     // initialize Modbus communication baud rate
  serverA.begin(1, mySerial);                     // communicate with Modbus server ID over the given Serial interface
  pinMode(modbusEnablePin, OUTPUT);               // Init enable pins for modbus master library
  digitalWrite(modbusEnablePin, LOW);
  serverA.preTransmission(preTransmission);       // Callbacks allow us to configure the RS485 transceiver correctly
  serverA.postTransmission(postTransmission);
}

// getdata from Modubs Server(Slave) and print to Serial
void requestData()
{
  constexpr uint16_t interval = 150;             // interval of modbus requests
  static uint32_t previousMillis = -interval;     // timestamp of last request
  uint32_t currentMillis = millis();

  if (currentMillis - previousMillis > interval)  // set the interval in ms
  {
    previousMillis = currentMillis;
    uint16_t reg = 0x0;
    int result;
    result = serverA.readHoldingRegisters(reg, 2);  // request from startregster, n Registers
    if (result == serverA.ku8MBSuccess)           // do something if read is successfull
    {
      int low = serverA.getResponseBuffer(0x00);
if (low > 10000){
low = 0;
}
int high = serverA.getResponseBuffer(0x01);
if (high > 10000){
high = 0;
}
Serial.print(F("LOW :     ")); Serial.println(low);
Serial.print(F("High:     ")); Serial.println(high);
     }
    else
    {
      Serial.print(F(" ServerA no success register ")); Serial.print(reg, HEX); Serial.print(F(" result=")); Serial.println(result, HEX);
    }
  }
}

/* **************************************************** *
   setup and loop
 * **************************************************** */

void setup()
{
  Serial.begin(115200);
  Serial.println(F("Modbus Client Example D 485 halfduplex"));

  modbusInit();
}

void loop()
{
  requestData();
}

nrf24l01 Receiver Program

#include <SoftwareSerial.h>
SoftwareSerial mySerial(7, 8); // RX, TX
//#define mySerial Serial
#define dataPin  4
#define latchPin 5
#define clockPin 6
unsigned long sa = 88888UL;

const uint8_t digit[] =
{
  //  uGFEDCBA  Segments      7-segment map:
  0b00111111, // 0   "0"          AAA
  0b00000110, // 1   "1"         F   B
  0b01011011, // 2   "2"         F   B
  0b01001111, // 3   "3"          GGG
  0b01100110, // 4   "4"         E   C
  0b01101101, // 5   "5"         E   C
  0b01111101, // 6   "6"          DDD
  0b00000111, // 7   "7"
  0b01111111, // 8   "8"
  0b01101111,  // 9   "9"
  0b00000000
};
void setup() {
  mySerial.begin(9600);
  pinMode(latchPin, OUTPUT);
  pinMode(dataPin, OUTPUT);
  pinMode(clockPin, OUTPUT);
  Display(sa);
  delay(1000);
  Display(0);
  mySerial.println();
}

void loop() {
  if (mySerial.available() > 0) // Do we have any data?
  {
    delay(10);
    sa = mySerial.parseInt();
    while (mySerial.available() > 0)mySerial.read();
    mySerial.println(sa);
    Display(sa);
    delay(1000);
  }
}

void Display(uint32_t num) {
  byte seq[5];
  num %= 100000UL; // number bigger as 99999 show only last 5 digits
  for (byte i = 0 ; i < 5 ; i++)  { // reverse digit order
    seq[i] = num % 10;
    num /= 10;
  }
  if (!seq[4]) {
    seq[4] = 10;
    if (!seq[3]) {
      seq[3] = 10;
      if (!seq[2]) {
        seq[2] = 10;
        if (!seq[1])seq[1] = 10;
      }
    }
  }
  // Display the data in our array now.
  for (byte i = 0 ; i < 5 ; i++)
    shiftOut(dataPin, clockPin, MSBFIRST, digit[seq[i]] << 1);
  digitalWrite(latchPin, 0);
  digitalWrite(latchPin, 1);
}

Your transmitter code doesn't transmit anything, receiver code I don't know what it supposed to do.
Start with some tutorial to make wireless communication.

1 Like

Yes, there are no sections related to nrf24l01 in the codes I wrote for this receiver and transmitter. I am trying to take the modbus data in the code I wrote for the transmitter and write it to the display in the code I wrote for the receiver. I tried and added the codes related to nrf24l01, but I failed. I will also try the code in the link you posted. Thank you for your help.

#include <SoftwareSerial.h>
SoftwareSerial mySerial(2,3);//rxPin, txPin

#include <ModbusMaster.h>                        // Modbus Master 2.0.0 by Doc Walker - install with Library Manager
constexpr uint8_t modbusEnablePin = 5;           // The GPIO used to control the MAX485 TX pin. Set to 255 if you are not using RS485 or a selfsensing adapter
constexpr uint32_t modbusBaud = 9600;            // use slow speeds with SoftSerial
constexpr uint16_t modbusRestTx = 15000;         // rest time between transmissions - microseconds
uint32_t modbusPreviousTx = 0;                   // timestamp of last transmission - microseconds
ModbusMaster serverA;                            // instantiate ModbusMaster object - slave - node

// this function will be called before the client transmits data
void preTransmission()
{
  while (micros() - modbusPreviousTx < modbusRestTx)   // check last transmission end and wait if the call was to early
  {
    yield();                                           // wait some time and allow background tasks
  }
  digitalWrite(modbusEnablePin, HIGH);
}

// this function will be called after the transmission
void postTransmission()
{
  digitalWrite(modbusEnablePin, LOW);
  modbusPreviousTx = micros();         // remember last timestamp
}

// do all the settings for the Modbus
void modbusInit()
{
  mySerial.begin(modbusBaud);                     // initialize Modbus communication baud rate
  serverA.begin(1, mySerial);                     // communicate with Modbus server ID over the given Serial interface
  pinMode(modbusEnablePin, OUTPUT);               // Init enable pins for modbus master library
  digitalWrite(modbusEnablePin, LOW);
  serverA.preTransmission(preTransmission);       // Callbacks allow us to configure the RS485 transceiver correctly
  serverA.postTransmission(postTransmission);
}

// getdata from Modubs Server(Slave) and print to Serial
void requestData()
{
  constexpr uint16_t interval = 150;             // interval of modbus requests
  static uint32_t previousMillis = -interval;     // timestamp of last request
  uint32_t currentMillis = millis();

  if (currentMillis - previousMillis > interval)  // set the interval in ms
  {
    previousMillis = currentMillis;
    uint16_t reg = 0x0;
    int result;
    result = serverA.readHoldingRegisters(reg, 2);  // request from startregster, n Registers
    if (result == serverA.ku8MBSuccess)           // do something if read is successfull
    {
      int low = serverA.getResponseBuffer(0x00);
      if (low > 10000) {
        low = 0;
      }
      int high = serverA.getResponseBuffer(0x01);
      if (high > 10000) {
        high = 0;
      }
      Serial.print(F("LOW :     ")); Serial.println(low);
      Serial.print(F("High:     ")); Serial.println(high);
      struct packet={
        int Low;
        int High;
      } Pack;
      Pack.Low=low;
      Pack.High=high;
      radio.write( &Pack, sizeof(Pack));
    }
    else
    {
      Serial.print(F(" ServerA no success register ")); Serial.print(reg, HEX); Serial.print(F(" result=")); Serial.println(result, HEX);
    }
  }
}

#include <SPI.h>
#include "nRF24L01.h"
#include "RF24.h"
RF24 radio(9,10);

/* **************************************************** *
   setup and loop
 * **************************************************** */

void setup()
{
  Serial.begin(115200);
  Serial.println(F("Modbus Client Example D 485 halfduplex"));
  radio.begin();
  radio.setAutoAck(false);
  radio.setChannel(100);
  radio.startListening();
  radio.stopListening();
  modbusInit();
}

void loop()
{
  requestData();

}
1 Like

This topic was automatically closed 180 days after the last reply. New replies are no longer allowed.