0

I'm adapting a sketch I found to send sensor data over a wifi chip (Nrf2401), and although I get the message through, the value I send contains decimals (e.g. 24.59), but the received message will only be 24.

I'm sure there's something wrong on the transmitter part of the code, but I can't see what.

Here's my code:

#include <RF24.h>
#include <RF24_config.h>
#include <SPI.h>
#include <OneWire.h>
#include <DallasTemperature.h>

OneWire oneWire(4);

DallasTemperature sensors(&oneWire);

// ce,csn pins
RF24 radio(8,7);

// init data buffer to hold a sensor type byte and one uint16_t sensor data
unsigned char data[3] = {
  0};
unsigned long count=0;
void setup(void)
{
  sensors.begin();  
  Serial.begin(57600);
  Serial.println("**************V1 Send Sensor Data***********");
  radio.begin();
  radio.setPALevel(RF24_PA_LOW);
  radio.setChannel(0x4c);

  // open pipe for writing
  radio.openWritingPipe(0xF0F0F0F0E1LL);

  radio.enableDynamicPayloads();
  radio.setAutoAck(true);
  radio.powerUp();
  Serial.println("...Sending");
}

void loop(void)
{

  sensors.requestTemperatures();
  float currentTemp;
  currentTemp = sensors.getTempCByIndex(0);


  //assign 'T' to represent a Temperature reading
  data[0] = 'T';

  data[1] = currentTemp;

  count++;

  sprintf(data, "T %5.2f\n", currentTemp);  // build command in data[]
  radio.txMode(strlen(data));               // set # bytes to xmit
  radio.write(data);                        // send bytes

  // print and increment the counter
  Serial.print("Temperature sent:  ");
  Serial.println(currentTemp);
  // pause a second
  delay(500);
}

In this example, when I print currentTemp, it will display the decimals, but if I print data[1], it won't.

What am I missing?

EDIT:

I've modified the code to include the answer from JRobert (updated code above), but it comes back the following error:

nrf24SendSensorDataV1_ino.cpp: In function 'void loop()':
nrf24SendSensorDataV1_ino:56: error: invalid conversion from 'unsigned char*' to 'char*'
nrf24SendSensorDataV1_ino:56: error: initializing argument 1 of 'int sprintf(char*, const char*, ...)'
nrf24SendSensorDataV1_ino:57: error: 'class RF24' has no member named 'txMode'
nrf24SendSensorDataV1_ino:57: error: invalid conversion from 'unsigned char*' to 'const char*'
nrf24SendSensorDataV1_ino:57: error: initializing argument 1 of 'size_t strlen(const char*)'
nrf24SendSensorDataV1_ino:58: error: no matching function for call to 'RF24::write(unsigned char [3])'
C:\Users\Zuh\Downloads\arduino-1.0.1\libraries\RF24L01/RF24.h:281: note: candidates are: bool RF24::write(const void*, uint8_t)

Any thoughts?

EDIT 2

I've made a dirty fix that will solve the issue.

In the transmitter code I've added:

uint16_t sensorValue = currentTemp*100;
//do the bit shift to put uint16 into uint8 array
data[1] = sensorValue >> 8;
data[2] = sensorValue;
// print and increment the counter
radio.write(data, sizeof(uint16_t)+1);

This will send the (temperature value)*100

On the receiver end, I just convert the uint16_t to a float element and divide it by 100.

uint16_t sensorValue = data[2] | data[1] << 8;
float temp = (float) sensorValue/100;
Serial.print("T: "); 
Serial.println(temp); 

Dirty, but effective!

Many thanks guys for the help, it really pointed me and my lousy programming skills to the right direction.

  • You put the currentTemp float value in the data unsigned char vector. How do you expect the 'data' vector to hold a float number? – m.Alin May 23 '14 at 16:22
0

From the Arduino playground documentation for the Nrf2401 library, the .write method accepts either: a byte to transmit, a pointer to your unsigned char buffer; or a void argument meaning use the library's internal buffer. You must have called the .txmode() method first.

Since you're trying to use your own buffer, you'll need to make it long enough to contain the message you want to transmit (plus one byte for the terminating NUL). You'll need a character representation of the value you want to send, not the binary number itself. At a quick read of the library doc I didn't see the message format the library wants, but assuming it's something like: T<space>12.34<newline>, you'll need something like this (untested, it may need tweaking)

sprintf(data, "T %5.2f\n", currentTemp);  // build command in data[]
radio.txMode(strlen(data));               // set # bytes to xmit
radio.write(data);                        // send bytes
  • Ill test it tonite! Looks really good, thanks JRobert!! – Eric Mitjans May 24 '14 at 16:19
  • I've tested it and I get the following error: nrf24SendSensorDataV1_ino:54: error: stray '\' in program nrf24SendSensorDataV1_ino.cpp: In function 'void loop()': nrf24SendSensorDataV1_ino:54: error: 'f5' was not declared in this scope nrf24SendSensorDataV1_ino:55: error: 'class RF24' has no member named 'txMode' nrf24SendSensorDataV1_ino:55: error: invalid conversion from 'unsigned char*' to 'const char*' – Eric Mitjans May 25 '14 at 0:40
  • nrf24SendSensorDataV1_ino:55: error: initializing argument 1 of 'size_t strlen(const char*)' nrf24SendSensorDataV1_ino:56: error: no matching function for call to 'RF24::write(unsigned char [3])' C:\Users\Zuh\Downloads\arduino-1.0.1\libraries\RF24L01/RF24.h:281: note: candidates are: bool RF24::write(const void*, uint8_t) – Eric Mitjans May 25 '14 at 0:41
  • I fixed a couple typos in the sprintf() format string that should clean up some of the errors; you'll have to make sure your data types match what the library's requirements, especially with regard to const qualifiers. Sorry, I don't have the part to be able to debug this. – JRobert May 25 '14 at 12:14
  • Updated question with your code. I'm using the RF24 library, maybe this interferes with it? Because the error mentions that 'class RF24' has no member named 'txMode' – Eric Mitjans May 25 '14 at 12:31
0

data[] is an array of three chars. You assign the letter "T" to data[0] (the first char of the array), then data[1] = currentTemp attempts to assign a float to the second char in the data array - floats won't fit in chars.

  • Hi Peter. I see! Is there any other way to send currentTemp using radio.write then? Thanks!! – Eric Mitjans May 23 '14 at 16:28
  • I'm not familiar with the radio.* functions you are using. In C, I'd use printf("%5.2f\n", currentTemp); The %5.2f" tells the print function that the variable is a float, and it should be formatted with two digits after the decimal. – Peter Bennett May 23 '14 at 18:21
0

Since I can't comment yet I will place this as answer.

But have you tried to use radio.print(data[1], DEC); ?

DEC stands for Decimal for if you want to force something to print it in Decimals. When you want something to be printed in Hexadecimals you can use HEX for example. Hope this will help you.

  • This post is simply not true. Decimal and decimals are two entirely different things. He's missing the . decimal when sending the data. DEC just specifies that the info given is presented in the decimal (base ten) system. This isn't related. – Anonymous Penguin May 23 '14 at 22:24
  • The info given huh? Now I don't get it that I can simply make a calculator using arduino and print everything in DEC and HEX without writing a new calculation. All I do is printing it as DEC and or HEX. I would love to hear a more specific explanation about it cuz this is what I learned on my college. – Handoko May 23 '14 at 22:38

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.