Xbee Pager

 

Xbee Pager

A few days ago my co-worker and friend, Bunni Sherman asked me to come up with a simple wayto alert me whenever she needed my assistance. My first thought was to use Xbees because they are great radio modules that make wireless communication very easy. If you have not read our previous tutorial about Xbees click on the link below to check it out.

https://jayconsystems.com/blog/working-with-an-arduino-compatible-wireless-xbee-shield

In this tutorial we are going to show you how to pair two Xbees Series 2, and set them up as either a coordinator or a router. We will also show you how to send AT commands from the coordinator to the router to control the router’s digital pins.

 When it is completed we will be able to send a signal from the coordinator to the router. Which will allow you to light up the LED when the button is pressed, and it will also trigger a vibration motor on the receiving end.

Materials

Xbee Coordinator Setup

Place on of the Xbees in the Xbee Explorer and connect it to to the computer.

Open X-CTU and select the COM port that the Xbee is using and enable API.

Coordinator.JPG

You can click on Test / Query to make sure that the device is communicating with your computer.

tets.JPG

Now go to the Modem Configuration tab. It is recommended to click on Download new version, to make sure that our version is up to date. When asked for the Update source, click on Web. After some time you will get a window like this:

update.JPG

Click on OK and then Done. Then click on Always Update Firmware and Read. In the Modem: XBEE dropdown menu select XB24-ZB. In the Function Set dropdown menu select ZIGBEE COORDINATOR API. Also make sure that the latest Version is selected from the dropdown menu.

read.JPG

Now go to Networking and in PAN ID select a unique identification number. In our case we chose 7531. This is the Personal Area Network ID that serves to define a network. All devices in the same network must have the same PAN ID. Then click on Write.

pan id.JPG

Xbee Router Setup

Disconnect the Xbee from the Explorer and connect the other Xbee, then click on Read. Select the Modem: XBEE to be XB24-ZB, and set Function Set to ZIGBEE ROUTER AT. Next write the same PAN ID number as before, 7531. Also set JV to 1 (Enable) so that the router can verify if a coordinator exists on the same channel after joining. If no coordinator is found, the router will leave the network. Finally click on Write.

router.JPG

Your Xbees are now ready to be used.

Wiring

Coordinator

Solder the headers to the Shield. Also, since we will be using pins 4 and 5 for serial communication, solder TX and RX, and switch to D4/D5.

BunniBuzzer_26.jpg
BunniBuzzer_30.jpg
BunniBuzzer_29.jpg
BunniBuzzer_27.jpg
BunniBuzzer_28.jpg

Mount the Xbee shield on to the Arduino UNO

BunniBuzzer_13.jpg
BunniBuzzer_12.jpg

Mount the Xbee Coordinator on to the Xbee Shield

BunniBuzzer_11.jpg

Connect the Antenna

BunniBuzzer_10.jpg

Place a push button on the center of a breadboard

10.jpg

Place the breadboard on top of the Xbee Shield

BunniBuzzer_8.jpg

Connect 3.3V from Arduino to one end of the pushbutton

DCS_6318.jpg

Connect the other end of the button to Pin 2

DCS_6319.jpg

Add a 10k ohm resistor that goes from ground to the button end that is connected to pin 2

Labeled_2.jpg

The circuit diagram for the button should look as shown below:

button.JPG

Now connect pin 8 to the anode side of an LED. Then connect the cathode side to a 330 ohm resistor and the other end of the resistor to ground.

Labeled_1.jpg

Now your circuit should look like this

DCS_6320.jpg
led.JPG

Router

Place the Xbee Explorer on a breadboard

BunniBuzzer_25.jpg

Mount the Xbee router on it

BunniBuzzer_23.jpg

Connect the Antenna

BunniBuzzer_22.jpg

Place an LED on the protoboard

DCS_6321.jpg

Connect the cathode side to ground and the anode side to a 330 ohm resistor. Connect the other end of the resistor to pin D3

Labeled_8.jpg
Labeled_3.jpg

Place the transistor on the protoboard

DCS_6325.jpg

Connect the emitter of the transistor to ground

Labeled_4.jpg

Connect the base of the transistor to pin D1

Labeled_7.jpg

Connect one end of the motor to 3.3V and the other end to the collector of the transistor

Labeled_5.jpg
Labeled_6.jpg

In the end your circuit should look something like this:

BunniBuzzer_14.jpg

 *Note: We used a PNP transistor since the digital outputs from the Xbee’s pinswere not capable of triggering the vibration motor. Therefore, we connected the motor directly to the 3.3V source.  

Code

#include SoftwareSerial mySerial(4, 5); int button = 2; int buttonState = 0; int led = 8; void setup() { Serial.begin(9600); mySerial.begin(9600); pinMode(button, INPUT); pinMode(led, OUTPUT); digitalWrite(led,LOW); } void loop() { buttonState=digitalRead(button); Serial.print(buttonState); if(buttonState==1){ digitalWrite(led,HIGH); setRemoteState(0x5, 'D', '3'); setRemoteState(0x5, 'D', '1'); delay(5000); digitalWrite(led,LOW); setRemoteState(0x4, 'D', '3'); setRemoteState(0x4, 'D', '1'); } } void setRemoteState(char value, char a, char b) { mySerial.write(0x7E); //Start byte mySerial.write((byte)0x0); //Length high part mySerial.write(0x10); //length low part mySerial.write(0x17); //Frame type: AT command mySerial.write((byte)0x0); //Frame ID no need of acknowledgement from receiving part mySerial.write((byte)0x0); // mySerial.write((byte)0x0); // mySerial.write((byte)0x0); // mySerial.write((byte)0x0); // => Destination address. Set to send to AT command to all Xbees in network mySerial.write((byte)0x0); // mySerial.write((byte)0x0); // mySerial.write(0xFF); // mySerial.write(0xFF); // mySerial.write(0xFF); //Recipient destination network address mySerial.write(0xFE); //Set to send a broadcast mySerial.write(0x02); //Remote command option (Set to 0x02 to apply changes immediately) mySerial.write(a); //Select I/O D3 from remote Xbee mySerial.write(b); // mySerial.write(value); //Set output high long sum = 0x17 + 0xFF + 0xFF + 0xFF + 0xFE + 0x02 + a + b + value; mySerial.write(0xFF-(sum&0xFF)); //Checksum byte }

Code Explanation

#include SoftwareSerial mySerial(4, 5);

Here we include the SoftwareSerial library to set pins 4 and 5 as RX and TX respectively. These are the channels through which the Xbee will communicate with the Arduino UNO.   

void setup() { mySerial.begin(9600); pinMode(button, INPUT); pinMode(led, OUTPUT); digitalWrite(led,LOW); }

In the setup section we set the baud rate for serial communication to 9600. Then we set the LED as an output and turn it off. Lastly we declare the button as an input.

void loop() { buttonState=digitalRead(button); if(buttonState==1){ digitalWrite(led,HIGH); setRemoteState(0x5, 'D', '3'); setRemoteState(0x5, 'D', '1'); delay(5000); digitalWrite(led,LOW); setRemoteState(0x4, 'D', '3'); setRemoteState(0x4, 'D', '1'); } }

In the loop section we read the state of the button. Then we check if the value of the button is equal to one (meaning that the button has been pressed). If the case is true, then we turn the LED on and call the function setRemoteState to trigger the vibration motor and LED in the router side. After five seconds we turn the LED off and call the function setRemoteState again to turn off the vibration motor and LED on the router side.

void setRemoteState(char value, char a, char b) { mySerial.write(0x7E); //Start byte mySerial.write((byte)0x0); //Length high part mySerial.write(0x10); //length low part mySerial.write(0x17); //Frame type: AT command mySerial.write((byte)0x0); //Frame ID no need of acknowledgement from receiving part mySerial.write((byte)0x0); // mySerial.write((byte)0x0); // mySerial.write((byte)0x0); // mySerial.write((byte)0x0); // => Destination address. Set to send to AT command to all Xbees in network mySerial.write((byte)0x0); // mySerial.write((byte)0x0); // mySerial.write(0xFF); // mySerial.write(0xFF); // mySerial.write(0xFF); //Recipient destination network address mySerial.write(0xFE); //Set to send a broadcast mySerial.write(0x02); //Remote command option (Set to 0x02 to apply changes immediatly) mySerial.write(a); //Select I/O D3 from remote Xbee mySerial.write(b); // mySerial.write(value); //Set output high long sum = 0x17 + 0xFF + 0xFF + 0xFF + 0xFE + 0x02 + a + b + value; mySerial.write(0xFF-(sum&0xFF)); //Checksum byte }

The setRemoteState function passes three arguments: a hex value and two character values. The hex value serves to select the state that we want the digital pin to have. In this case the value 0x5 turns the digital output high, while 0x4 turns the digital output low. The two characters are used to identify the digital pin that we want to modify. The numbers and characters are taken from the I/O configuration in X-CTU. If you scroll down to the I/O Settings section in X-CTU and click on one of the digital pins you will find a drop down menu as the one below:

Hex.JPG

Here we can see the names of the digital pins (D0, D1, ...) and the five states each one of them can adopt.    

When we send AT commands we send them in the form of a frame that consists of several hex values. Below is an example of a frame data with the description of each hex value.

Byte

Hex Value

Description

0

0x7E

Start byte. Indicates start of frame data

1

0x00

Length of data. Does not include bytes 0, 1, 2 and 19. First byte is always zero. Second byte represents 16 in decimal

2

0x10

3

0x17

Frame type. 0x17 is used for AT command request

4

0x00

Frame ID. Leave this as zero.

5

0x00  

Destination address. This is the address of the router (found in the back of the Xbee). Set it up like this to send a broadcast. This way the coordinator will send the AT command frame to all Xbees in the network.

6

0x00

7

0x00

8

0x00

9

0x00

10

0x00

11

0xFF

12

0xFF

13

0xFF

Destination network address. Set it up like this if it is unknown. This sends a broadcast. Otherwise, look it up using X-CTU under the Addressing section

14

0xFE

15

0x02

Hex value 0x02 applies immediate changes to Xbee

16

0x44

0x44 represents ‘D’, while 0x03 represents ‘3’. Used to represent the digital pin we want to modify.

17

0x03

18

0x05

Represents the state we want the digital pin to have. Based on the drop down menu from X-CTU.

19

0x6F

Checksum. Adds hex values (does not include start byte and length). Serves to verify that the data packet is valid. If the Xbee receives a data packet with a different checksum, the data will be ignored.

Bytes 16, 17, and 18 are represented in our code by the variables a, b, and value respectively. So when the button is pressed, we send an AT command packet that turns on the LED. Then we send another AT command packet that turns on the vibration motor. After five seconds we send two more packets, one to turn off the LED and another to turn off the vibration motor. We are sending these packets from the coordinator to all the Xbees in the network, which in this case is just one.

Results


This article was published by the Jaycon team. Learn more about how we can take your product design and hardware idea to the next level here.