1

I have 3 nodes in my system. One centralNode and two sensor nodes (right and left).
Sensor nodes transmit data to the centralNode and receive from it. centralNode may transmit to both nodes and receive from them.

I'm using an Arduino nano for central node and Uno and Mega for sensor nodes. I'm using nRF24's base module (with regulators and caps and all) but one node does not have base module (Although I've given it a descent 3.3 V and bypass caps).

Here is my problem:
1- It seems the centralNode can't detect which nodes data it is receiving. I can sometimes get it to work using different delays for sensorNodes but again, on reset it messes up the data. How can I detect which data's reading the centralNode is receiving?

2- How can I use radio.available(??) I've put 0, 1 , 2 and pipe addresses in ?? but it does not work (prints garbage data) radio.available's API

Here are the codes: centralNode:

/*
   Testing multi-node functionality of nRF24l01+
   This is centralNode code

   BOM
   1 Arduino Nano centralNode
   1 Ardiuno Uno rightSensorNode
   1 Arduino Mega leftSensorNode
   3 nRF24l01+
*/

#include <SPI.h>
#include "RF24.h"
#include <printf.h>

#define CEpin 6
#define CSpin 7

RF24 radio(CEpin, CSpin);
byte addresses [][6] = {"1Node", "2Node", "3Node"};

int rightNodeCount = 0;
int leftNodeCount = 0;
void setup() {
  Serial.begin(115200);
  Serial.println(F("This is the central node"));
  printf_begin();
  radio.begin();
  radio.setPALevel(RF24_PA_MAX);

  radio.openWritingPipe(addresses[0]);
  radio.openReadingPipe(1, addresses[1]);
  radio.openReadingPipe(2, addresses[2]);
  radio.startListening();
  radio.printDetails();
}

void loop() {
  if (radio.available()) {
    radio.read(&rightNodeCount, sizeof(rightNodeCount));
    radio.read(&leftNodeCount, sizeof(leftNodeCount));
  }
  //  if (radio.available(1)) {
  //    radio.read(&leftNodeCount, sizeof(leftNodeCount));
  //  }
  Serial.println("centralNode is reporting:");
  Serial.print("centralNode address : ");
  Serial.println((char *)addresses[0]);

  Serial.print("rightNode address : ");
  Serial.println((char *)addresses[1]);
  Serial.print("rightNodeCount = ");
  Serial.println(rightNodeCount);

  Serial.print("leftNode address : ");
  Serial.println((char *)addresses[2]);
  Serial.print("leftNodeCount = ");
  Serial.println(leftNodeCount);

  Serial.println("---END OF REPORT---\n\n\n\n");
  delay(500);
}

rightSensorNode:

/*
   Testing multi-node functionality of nRF24l01+
   This is rightSensorNode code

   BOM
   1 Arduino Nano centralNode
   1 Ardiuno Uno rightSensorNode
   1 Arduino Mega leftSensorNode
   3 nRF24l01+
*/

#include <SPI.h>
#include "RF24.h"
#include <printf.h>

#define CEpin 7
#define CSpin 8

RF24 radio(CEpin, CSpin);
byte addresses [][6] = {"1Node", "2Node", "3Node"};

int rightNodeCount = 0;
void setup() {
  Serial.begin(115200);
  Serial.println(F("This is the right node"));
  printf_begin();


  radio.begin();
  radio.setPALevel(RF24_PA_MAX);

  radio.openWritingPipe(addresses[1])

  radio.printDetails();

}

void loop() {
  rightNodeCount++;
  Serial.println("Sending data to centralNode");
  Serial.print("rightNode address : ");
  Serial.println((char *)addresses[1]);
  Serial.print("rightNodeCount = ");
  Serial.println(rightNodeCount);
  radio.write(&rightNodeCount, sizeof(rightNodeCount));

  Serial.println("---END OF REPORT---\n\n\n\n");
  delay(1000);
}

leftSensorNode:

/*
   Testing multi-node functionality of nRF24l01+
   This is leftSensorNode code

   BOM
   1 Arduino Nano centralNode
   1 Ardiuno Uno rightSensorNode
   1 Arduino Mega leftSensorNode
   3 nRF24l01+
*/

#include <SPI.h>
#include "RF24.h"
#include <printf.h>

#define CEpin 7
#define CSpin 8

RF24 radio(CEpin, CSpin);

byte addresses [][6] = {"1Node", "2Node", "3Node"};

int leftNodeCount = 0;
void setup() {
  Serial.begin(115200);
  Serial.println(F("This is the left node"));
  printf_begin();

  radio.begin();
  radio.setPALevel(RF24_PA_MAX);

  radio.openWritingPipe(addresses[2]);


  radio.printDetails();

}

void loop() {
  leftNodeCount++;
  Serial.println("Sending data to centralNode");
  Serial.print("leftNode address : ");
  Serial.println((char *)addresses[2]);
  Serial.print("leftNodeCount = ");
  Serial.println(leftNodeCount);
  radio.write(&leftNodeCount, sizeof(leftNodeCount));

  Serial.println("---END OF REPORT---\n\n\n\n");
  delay(1000);
}

migrated from electronics.stackexchange.com Jun 16 '17 at 1:28

This question came from our site for electronics and electrical engineering professionals, students, and enthusiasts.

  • 1
    Have thought about embedding an ID into the transmission and appending each transmission with a checksum? – Andy aka Jun 11 '17 at 10:57
  • @Andyaka 1- Good idea but I have already 32 byte limitation in packet transmission. 2- I think nRF24 does have default CRC checksum. – Zeta.Investigator Jun 11 '17 at 11:05
  • Without an ID, you cannot reliably detect the transmission source or do you have a cunning plan that you haven't mentioned? – Andy aka Jun 11 '17 at 11:07
  • @Andyaka I guess TMRH's RF24 library's available() method does take this issue into account. I don't know how to use it. tmrh20.github.io/RF24/… – Zeta.Investigator Jun 11 '17 at 11:33
  • You could use the pipe addresses as the ID for a small number of nodes by using a different one for each. – Chris Stratton Jun 11 '17 at 11:51
2

Each sensor point should send its address to the central point and this is how the central point knows the source of the message. Then after the central point receives a message, after if (radio.available()) command receive the data just once (not twice) and then use another if statement to determine which sensor has sent a message (by reading the sent address) and then print.

pseudo code:

if (radio.available())
{
    radio.read(&RXbuffer, sizeof(RXbuffer));
    if(RXbuffer.address == sensor1_address)
    {
        print "this is sensor 1"
        print RXbuffer.address;
        print RXbuffer.data;
    }
    else if(RXbuffer.address == sensor2_address)
    {
        print "this is sensor 2"
        print RXbuffer.address;
        print RXbuffer.data;
    }
}

In your code (inside if (radio.available())) you are trying to receive rightNodeCount and lefteNodeCount eventhough at that time just one of them was received.

EDIT:

It seems that RF24 uses dedicated pipes to know the source of the information. The following code should work:

pseudo code:

unsigned char pipe_num;

if (radio.available(&pipe_num))
{
    radio.read(&data, sizeof(data));

    if(pipe_num == 1)
    {
        print "this is sensor 1";
        print data;
    }
    else if (pipe_num == 2)
    {
        print "this is sensor 2";
        print data;
    }
}
  • Thanks but in this method, you are sending an struct I guess? As I said, nRF has 32 Byte limitation in each packet so it would be wasteful use of bandwidth. I'm suspecting that this issue can be solved using radio.available(&pipeNum) method but I don't know how...tmrh20.github.io/RF24/… – Zeta.Investigator Jun 11 '17 at 11:35
  • Here I have used a structure as an example (pseudo code). You can create a union data type to be able to use a structure and an array interchangeably. Or you can use just a simple array. It depends totally on your application. – Macit Jun 11 '17 at 14:01
  • I have edited my answer to use pipes. It should work. If not feel free to share and inform us of your progress. – Macit Jun 11 '17 at 14:33
  • It seems finally I got it. Actually it seems the client should not pass the desired pipeNum to the available(&pipeNum) method. You first declare a uint8_t pipeNum; then the available method fills the pipe number it is listening to into the pipeNum variable. Do you also confirm this? – Zeta.Investigator Jun 12 '17 at 8:22
  • @Zeta.Investigator Oops it seems that pipeNum is filled automatically. It is loaded by the number of the pipe that has received the message. So you are right. Look at the code above. – Macit Jun 12 '17 at 10:52

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.