RS485 Simple Integer transfer

Could some kind soul please help me modify the attached sketch so as to enable me to transfer

integers (-32,768 to 32,767) between 2 Arduino Uno ( and also Mega).

I am using the attached sketch of Ralph Bacon because it was the only simple one I could find that actually works, but I cannot modify it to transmit integers.

My knowledge of coding is very very very basic so little words would help .

Thanks in advance

TRANSMIT


#include "Arduino.h"

// Library to allow a Serial port on arbitrary pins
#include <SoftwareSerial.h>

// These are the pins we'll be talking to the RS485 device on
#define RS485rx		6 // RS485 Receive pin
#define RS485Tx		7 // RS485 Transmit pin
#define RS485inout	5 // RS485 Transmit or Receive status

#define RS485Transmit	HIGH
#define RS485Receive	LOW
#define ledPin			13
#define baudRate		9600

// Define the RS485 object
SoftwareSerial RS485(RS485rx, RS485Tx);

// The data bytes we're sending or receiving
byte rxValue;
byte txValue;

// -----------------------------------------------------------------
// SETUP         SETUP         SETUP         SETUP         SETUP
// -----------------------------------------------------------------
void setup() /****** SETUP: RUNS ONCE ******/
{
	// Debugging window
	Serial.begin(9600);

	// Set modes for pins
	pinMode(ledPin, OUTPUT);
	pinMode(RS485inout, OUTPUT);

	// Ensure the on-board LED is off
	digitalWrite(ledPin, HIGH);

	// Set RS485 device to read initially
	digitalWrite(RS485inout, RS485Receive);

	// Set the baud rate. The longer the wire the slower you should
	// set the transmission rate. Anything here:
	// 300, 600, 1200, 2400, 4800, 9600, 14400, 19200, 28800, 31250,
	// 38400, 57600, and 115200
	// MUST BE THE SAME AS THE SENDER UNIT!
	RS485.begin(baudRate);
}

// -----------------------------------------------------------------
// LOOP     LOOP     LOOP     LOOP     LOOP     LOOP     LOOP
// -----------------------------------------------------------------
void loop()
{
	static String teststring = "12345"; // Serial Communication is easy!";

	// Continually send the test string with a pause at the end
	for (unsigned int cnt = 0; cnt < teststring.length(); cnt++) {

		// Get the next character to send
		txValue = teststring[cnt];
		Serial.print("Sending:");Serial.println(char(txValue));

		// Set the RS485 to transmit mode and send the value
		digitalWrite(RS485inout, RS485Transmit);
		RS485.write(txValue);

		// small delay to allow transmission to complete
		delay(1);

		// Switch RS485 to receive mode
		digitalWrite(RS485inout, RS485Receive);
delay(100);
		// After each character is sent look for a received answer
		if (RS485.available())
		{
			// LED flicker
			digitalWrite(ledPin, HIGH);

			// Read the incoming byte
			rxValue = RS485.read();

			// Display it on the Serial Monitor as a char (not an integer value)
			Serial.print("                 Got back:");	Serial.println(char(rxValue));

			// Turn off LED
			digitalWrite(ledPin, LOW);  // Show activity
		}

		// Debugging delay so we can follow activity
		delay(100);
	}

	// Entire string sent, longer delay between loops
	//while (!Serial.available());
	//while (Serial.available()){Serial.read();}
	delay(2500);



RECEIVE

[code]
#include "Arduino.h"

// Library to allow a Serial port on arbitrary pins
#include <SoftwareSerial.h>

// These are the pins we'll be talking to the RS485 device on
#define RS485rx		6 // RS485 Receive pin
#define RS485Tx		7 // RS485 Transmit pin
#define RS485inout	5 // RS485 Transmit or Receive status

#define RS485Transmit	HIGH
#define RS485Receive	LOW
#define ledPin			13
#define baudRate		9600

// Define the RS485 object
SoftwareSerial RS485(RS485rx, RS485Tx);

// The data bytes we're sending or receiving
byte rxValue;
byte txValue;

// -----------------------------------------------------------------
// SETUP         SETUP         SETUP         SETUP         SETUP
// -----------------------------------------------------------------
void setup()
{
  // Debugging window
  Serial.begin(9600);

  // Set modes for pins
  pinMode(ledPin, OUTPUT);
  pinMode(RS485inout, OUTPUT);

  // Set RS485 device to read initially
  digitalWrite(RS485inout, RS485Receive);

  // Set the baud rate. The longer the wire the slower you should
  // set the transmission rate. Anything here:
  // 300, 600, 1200, 2400, 4800, 9600, 14400, 19200, 28800, 31250,
  // 38400, 57600, and 115200
  // MUST BE THE SAME AS THE SENDER UNIT!
  RS485.begin(baudRate);
}

// -----------------------------------------------------------------
// LOOP     LOOP     LOOP     LOOP     LOOP     LOOP     LOOP
// -----------------------------------------------------------------
void loop()
{
  // Is there something on the serial pin?
  if (RS485.available())
  {
    txValue = RS485.read();
    Serial.print("Received:");Serial.println(char(txValue));

    // Turn on the on-board LED pin to show activity
    digitalWrite(ledPin, HIGH);

    // Set the direction pin to xmit (HIGH)
    digitalWrite(RS485inout, RS485Transmit);

    // This delay is REQUIRED for things to settle before transmission
    delay(10);

    // Send back a modified value
    RS485.write(txValue);

    // Wait for the transmission to complete.
    // This delay is dependent on the baud rate. To calculate:
    // delay = (baud rate / 10) * 2
    int bufferDelay = (baudRate / 10) * 2 + 100;
    delayMicroseconds(bufferDelay);

    // Set the RS485 back to receive
    digitalWrite(RS485inout, RS485Receive);

    // Turn off built in LED pin
    digitalWrite(ledPin, LOW);
  }
}

}

[/code]

Int variables are 2 bytes on the Uno and Mega so in place of the for() loop iterating over all the elements in a String, you need to send the high byte and then the low byte

int myVal = -100;
txValue = myVal >> 8;  // high byte
// send it out
txValue = myVal & 0xFF; // low byte
// send it out

Thanks for your reply.

How do I convert it back to an integer on the Receiver side?

Farticus:
Thanks for your reply.

How do I convert it back to an integer on the Receiver side?

int Result = (RxBuff[0] << 8) + RxBuff[1];

Think I may have mucked it up somewhere.

I am getting a print out on the Sender Serial monitor but nothing on the receiver side.

I cannot get the Receiver sketch to compile

ERROR “RxValueBuff not declared in this scope”

#include "Arduino.h"

// Library to allow a Serial port on arbitrary pins
#include <SoftwareSerial.h>

// These are the pins we'll be talking to the RS485 device on
#define RS485rx		6 // RS485 Receive pin
#define RS485Tx		7 // RS485 Transmit pin
#define RS485inout	5 // RS485 Transmit or Receive status

#define RS485Transmit	HIGH
#define RS485Receive	LOW
#define ledPin			13
#define baudRate		9600
int myVal = 25320;
// Define the RS485 object
SoftwareSerial RS485(RS485rx, RS485Tx);

// The data bytes we're sending or receiving
byte rxValue;
byte txValue;

// -----------------------------------------------------------------
// SETUP         SETUP         SETUP         SETUP         SETUP
// -----------------------------------------------------------------
void setup() /****** SETUP: RUNS ONCE ******/
{
	// Debugging window
	Serial.begin(9600);

	// Set modes for pins
	pinMode(ledPin, OUTPUT);
	pinMode(RS485inout, OUTPUT);

	// Ensure the on-board LED is off
	digitalWrite(ledPin, HIGH);

	// Set RS485 device to read initially
	digitalWrite(RS485inout, RS485Receive);

	// Set the baud rate. The longer the wire the slower you should
	// set the transmission rate. Anything here:
	// 300, 600, 1200, 2400, 4800, 9600, 14400, 19200, 28800, 31250,
	// 38400, 57600, and 115200
	// MUST BE THE SAME AS THE SENDER UNIT!
	RS485.begin(baudRate);
}

// -----------------------------------------------------------------
// LOOP     LOOP     LOOP     LOOP     LOOP     LOOP     LOOP
// -----------------------------------------------------------------
void loop()
{
	
txValue = myVal >> 8;  // high byte
// send it out
txValue = myVal & 0xFF; // low byte
// send it out

    // Set the RS485 to transmit mode and send the value
    digitalWrite(RS485inout, RS485Transmit);
    RS485.write(txValue);
    Serial.print("myVal is....");Serial.print(myVal);Serial.print("  txValue is ....");Serial.println(txValue);
   delay(2000);
    myVal ++;

RECEIVER  

[code]
#include "Arduino.h"

// Library to allow a Serial port on arbitrary pins
#include <SoftwareSerial.h>

// These are the pins we'll be talking to the RS485 device on
#define RS485rx		6 // RS485 Receive pin
#define RS485Tx		7 // RS485 Transmit pin
#define RS485inout	5 // RS485 Transmit or Receive status

#define RS485Transmit	HIGH
#define RS485Receive	LOW
#define ledPin			13
#define baudRate		9600

// Define the RS485 object
SoftwareSerial RS485(RS485rx, RS485Tx);

// The data bytes we're sending or receiving
byte rxValue;
byte txValue;


// -----------------------------------------------------------------
// SETUP         SETUP         SETUP         SETUP         SETUP
// -----------------------------------------------------------------
void setup()
{
  // Debugging window
  Serial.begin(9600);

  // Set modes for pins
  pinMode(ledPin, OUTPUT);
  pinMode(RS485inout, OUTPUT);

  // Set RS485 device to read initially
  digitalWrite(RS485inout, RS485Receive);

  // Set the baud rate. The longer the wire the slower you should
  // set the transmission rate. Anything here:
  // 300, 600, 1200, 2400, 4800, 9600, 14400, 19200, 28800, 31250,
  // 38400, 57600, and 115200
  // MUST BE THE SAME AS THE SENDER UNIT!
  RS485.begin(baudRate);
}

// -----------------------------------------------------------------
// LOOP     LOOP     LOOP     LOOP     LOOP     LOOP     LOOP
// -----------------------------------------------------------------
void loop()
{
  Serial.println (" Inside Void Loop");
  // Is there something on the serial pin?
  if (RS485.available())
  Serial.println("Inside IFRS485Avail Loop");
  {
    
    rxValue = RS485.read();
    int Result = (RxValueBuff[0] << 8) + RxValueBuff[1]; // [i]ERROR RxValueBuff not declared in this scope"[/i]
    
   Serial.println( rxValue);
    delay (2000);
  }   
}

}
[/code]

A very simple failure: you did not define the buffer named "RxValueBuff" - so the compiler can not find it.

Do you really use RS485 (instead of normal RS232) ?

Have amended Receiver sketch as you suggested but now get a compiler error

“int Result = (RxBuff[0] << 8) + RxValueBuff[1]; // ERROR expected identifier before numeric constant”

Have attached error message

error.txt (1.55 KB)

int Result = (RxBuff[0] << 8) + RxValueBuff[1];

RxBuff and RxValueBuff?

Sorry but I dont get what you mean.

Changing code to this:

rxValue = RS485.read();
int Result = (RxValueBuff[0] << 8) + RxValueBuff[1];

gives me a compiling error I originally had:

ERROR “expected identifier before numeric constant”

I realise that from your perspective my error is most basic but I just dont get it I am sorry.

Try this on your receiver:

//Ref: ..Documents\Arduino\sketch_nov09b.ino
//
#include "Arduino.h"

// Library to allow a Serial port on arbitrary pins
#include <SoftwareSerial.h>

// These are the pins we'll be talking to the RS485 device on
#define RS485rx         6 // RS485 Receive pin
#define RS485Tx         7 // RS485 Transmit pin
#define RS485inout      5 // RS485 Transmit or Receive status
#define BUFF_SIZE       10

#define RS485Transmit   HIGH
#define RS485Receive    LOW
#define ledPin          13
#define baudRate        9600

// Define the RS485 object
SoftwareSerial RS485(RS485rx, RS485Tx);

byte
    rxIdx,
    rxBuff[BUFF_SIZE];
    
void setup()
{
    // Debugging window
    Serial.begin(9600);

    // Set modes for pins
    pinMode( ledPin, OUTPUT );
    pinMode( RS485inout, OUTPUT );
    digitalWrite( RS485inout, RS485Receive );   // Set RS485 device to read initially

    // Set the baud rate. The longer the wire the slower you should
    // set the transmission rate. Anything here:
    // 300, 600, 1200, 2400, 4800, 9600, 14400, 19200, 28800, 31250,
    // 38400, 57600, and 115200
    // MUST BE THE SAME AS THE SENDER UNIT!
    RS485.begin(baudRate);
    rxIdx = 0;
    
}//setup

void loop()
{
    if( RS485.available() )  
    {
        do
        {
            rxBuff[rxIdx] = RS485.read();
            rxIdx++;
            if( rxIdx == 2 )
            {
                int Result = (rxBuff[0] << 8) + rxBuff[1];
                Serial.print( "Received: " ); Serial.println( Result );
                rxIdx = 0;
                
            }//if
                        
        }while( RS485.available() );
        
    }//if
    
}//loop

Results are

Sender myVal Sender txVal Receiver Result

12 12 3084

123 123 31611

1234 210 -11566

12345 57 1469

Please show your transmitter code that was used in this test.

#include "Arduino.h"

// Library to allow a Serial port on arbitrary pins
#include <SoftwareSerial.h>

// These are the pins we'll be talking to the RS485 device on
#define RS485rx		6 // RS485 Receive pin
#define RS485Tx		7 // RS485 Transmit pin
#define RS485inout	5 // RS485 Transmit or Receive status

#define RS485Transmit	HIGH
#define RS485Receive	LOW
#define ledPin			13
#define baudRate		9600
int myVal = 132;
// Define the RS485 object
SoftwareSerial RS485(RS485rx, RS485Tx);

// The data bytes we're sending or receiving
byte rxValue;
byte txValue;

// -----------------------------------------------------------------
// SETUP         SETUP         SETUP         SETUP         SETUP
// -----------------------------------------------------------------
void setup() /****** SETUP: RUNS ONCE ******/
{
	// Debugging window
	Serial.begin(9600);

	// Set modes for pins
	pinMode(ledPin, OUTPUT);
	pinMode(RS485inout, OUTPUT);

	// Ensure the on-board LED is off
	digitalWrite(ledPin, HIGH);

	// Set RS485 device to read initially
	digitalWrite(RS485inout, RS485Receive);

	// Set the baud rate. The longer the wire the slower you should
	// set the transmission rate. Anything here:
	// 300, 600, 1200, 2400, 4800, 9600, 14400, 19200, 28800, 31250,
	// 38400, 57600, and 115200
	// MUST BE THE SAME AS THE SENDER UNIT!
	RS485.begin(baudRate);
}

// -----------------------------------------------------------------
// LOOP     LOOP     LOOP     LOOP     LOOP     LOOP     LOOP
// -----------------------------------------------------------------
void loop()
{
	
txValue = myVal >> 8;  // high byte
// send it out
txValue = myVal & 0xFF; // low byte
// send it out

    // Set the RS485 to transmit mode and send the value
    digitalWrite(RS485inout, RS485Transmit);
    RS485.write(txValue);
    Serial.print("myVal is....");Serial.print(myVal);Serial.print("  txValue is ....");Serial.println(txValue);
   delay(2000);
    myVal ++;

    
}

So try this loop() instead:

void loop()
{
    // Set the RS485 to transmit mode and send the value
    digitalWrite(RS485inout, RS485Transmit);

    txValue = myVal >> 8;  // high byte
    RS485.write(txValue);
    txValue = myVal & 0xFF; // low byte
    RS485.write(txValue);
    
    Serial.print("myVal is....");
    Serial.print(myVal);
    Serial.print("  High byte of myVal is ");
    Serial.print( myVal >> 8 );
    Serial.print("  Low byte of myVal is ");
    Serial.println( myVal & 0xff );
   
    delay(2000);
    
    myVal++;

}//loop

Because there are no framing characters to synchronize the transmitter and receiver, turn on the receiver first, then the transmitter.

Thank You,,,,,, Thank You,,,,,,,,,,Thank You.

Works perfectly :slight_smile: :slight_smile: :slight_smile:

I would like to try to understand the workings, is there any simple explanation
for a "newbie" such as my self or anywhere I could read up on it in "Dummy Speak".

Once again Thanks

Have tried to implement these sketches on Arduino Mega boards.

Uno TX Uno RX No Problems over 40 M wires.

MegaTX Uno Rx No probs.

Mega TX Mega Rx No response from RX

Tried a common ground made no difference

RS 485's powered from independent 5V power source.

Use same pins( 5,6 & 7).

Have tried independent 5V to Mega RX board.

Have tried 3 different Mega boards. All will transmit but none will "receive".

Any suggestions