Introduction: Decoding and Sending 433MHz RF Codes With Arduino and Rc-switch

Picture of Decoding and Sending 433MHz RF Codes With Arduino and Rc-switch

Originally published at www.liwen.id.au/arduino-rf-codes

In this tutorial I’ll show you how to use an Arduino to decode signals from RF remotes, and re-send them to remotely control some mains switches and a garage door.

Note: This guide was written for Australia, where it's legal to operate low powered devices (25mW) in the 433MHz band without a licence. Check what's legal in your own country. If you're transmitting to (or on the same frequency as) a garage door opener / RC toy etc that you bought in your own country, it should be fine, provided you stick to the power limit.

Step 1: Stuff You Need

Picture of Stuff You Need
  1. Arduino - I'm using an Arduino Uno Rev3.
  2. 433.92Mhz RF Transmitter and Receiver Pair - I got mine from eBay for the ridiculously cheap price of $1.45:
    Transmitter Model No: MX-FS-03V (marked XD-FST)
    Receiver Model No: MX-05V (marked XD-RF-5V)
    They work just fine - the main problem is that there is no datasheet or documentation available. Some basic specs are available on hobbycomponents.com but that's about it. Similar modules should also be available at your local electronics shop e.g. Jaycar.
  3. Breadboard and jumpers – also available from eBay or Jaycar.
  4. rc-switch
  5. A remote-controlled garage door, and/or:
  6. Some remote controlled mains switches. Mine are “PowerTran” model A0342.
  7. A basic knowledge of Arduino and C++

Step 2: Connect Transmitter and Receiver to Arduino

The rc-switch wiki has connection diagrams for both the transmitter and receiver.

Step 3: Identify Your Remote Controls

Picture of Identify Your Remote Controls

Most RF controlled devices should work with rc-switch, but if you want you can open up the remote and check that the encoder chipset is on the list of compatible chipsets.

I’ve got two remote controls – one for my garage door (EV1527 chipset), and one for my RC mains switches (LX2262A-R4 chipset).

Step 4: Decode Signals From Your Remote Controls

rc-switch has built-in functions that sends codewords for certain natively supported devices – so If you have one of these devices (I don’t) you may be able to skip this step.

Open the rc-switch “ReceiveDemo_Advanced” example sketch. Upload it and open the serial monitor. Hold your remote near your receiver module and press a button. The Arduino should decode the signal and print the results in the serial monitor. This is what I got for my remote-controlled mains switch when I press the button to turn channel 5 on:

Decimal: 3932352 (24Bit)
Binary: 001111000000000011000000
Tri-State: 011000001000
PulseLength: 232 microseconds
Protocol: 1
Raw data: 7244,232,692,124,792,592,328,596,324,596,328,596,324,140,784,144,788,120,792,136,780,136,788,140,788,128,784,144,796,124,780,140,784,596,336,588,968,96,36,104,908,132,1412,68,248,64,28,484,56,

The LX2262A-R4 uses a 12 tri-state bit codeword comprising 8 address bits followed by 4 data bits. For the tri-state codeword above – 011000001000 - the address is 01100000 (channel 5) and the data/command is 1000 (turn on).

My mains switches can have up to 8 addresses with a separate on and off command for each. By pressing every button and decoding the signals I worked out the codes for all the addresses and commands:

Address Bits: 8
Channel 1 = 01110000
Channel 2 = 00110000
Channel 3 = 01010000
Channel 4 = 00010000
Channel 5 = 01100000
Channel 6 = 00100000
Channel 7 = 01000000
Channel 8 = 00000000

Data Bits: 4
Turn On = 1000
Turn Off = 0000

I suspect the address codewords will be the same for all devices of the same make & model – if anyone can confirm this please let me know.

The EV1527 chipset in my garage door remote uses a 24-bit codeword comprising 20 address bits followed by 4 data bits. The codes I got from my garage door remote are:

Button 1:
Decimal: 8571080 (24Bit)
Binary: 100000101100100011001000
Tri-State: not applicable
PulseLength: 321 microseconds
Protocol: 1
Raw data: 9964,956,332,312,976,312,976,308,980,304,980,308,980,952,340,304,980,956,336,188,908,276,728,264,124,168,308,60,24,60,236,88,88,204,88,76,80,56,1020,284,440,56,24,40,100,84,12,36,56,

Button Address Data
Button 1: 10000010110010001100 1000
Button 2: 10000010110010001100 0100
Button 3: 10000010110010001100 0010
Button 4: 10000010110010001100 0001

Step 5: Write Code for Your Device

rc-switch has built-in functions that sends codewords for certain natively supported devices - so If you have one of these devices (I don’t) you should be able to use the RCSwitch::switchOn() and RCSwitch::switchOff() methods in the TypeX example sketches.

If not, you’ll need to manually set the PulseLength and Protocol and send raw codes using the RCSwitch::send() or RCSwitch::sendTriState() methods, as shown below.

The following code – based on the “SendDemo” sketch – switches one of my remote controlled mains switches on and off every 1 second. Note the pulse length has to be manually set because it differs from the default pulse length for Protocol 1. I’ve created a function – command() – which accepts channel number and on/off as integer arguments and looks up the corresponding address and data commands specific to my device. For your device you could create a similar function, or just send the raw codes.

#include <RCSwitch.h>

RCSwitch mySwitch = RCSwitch();

void setup() {

Serial.begin(9600);

// Transmitter is connected to Arduino Pin #10 mySwitch.enableTransmit(10);

// Optional set pulse length. mySwitch.setPulseLength(321);

// set protocol (default is 1, will work for most outlets) // mySwitch.setProtocol(2);

// Optional set number of transmission repetitions. // mySwitch.setRepeatTransmit(15);

pinMode(13,OUTPUT);

}

void loop() { mySwitch.send("100000101100100011001000"); digitalWrite(13,HIGH); delay(500); digitalWrite(13,LOW); delay(10000); }

Here is the code which opens and closes my garage door (simulates button 1) every 10 seconds. It also flashes the on-board LED to indicate a command has been sent.

#include <RCSwitch.h>
RCSwitch mySwitch = RCSwitch();

void setup() {

Serial.begin(9600);

// Transmitter is connected to Arduino Pin #10 mySwitch.enableTransmit(10);

// Optional set pulse length. mySwitch.setPulseLength(321);

// set protocol (default is 1, will work for most outlets) // mySwitch.setProtocol(2);

// Optional set number of transmission repetitions. // mySwitch.setRepeatTransmit(15);

pinMode(13,OUTPUT);

}

void loop() { mySwitch.send("100000101100100011001000"); digitalWrite(13,HIGH); delay(500); digitalWrite(13,LOW); delay(10000); }

Step 6: It Works!

Picture of It Works!

Step 7: Notes

The transmitter module seems to have a range of several metres without an antenna. If you require more range, you can add an external antenna by soldering a length of insulated wire to the “ANT” via on the transmitter. Recommended length is 1/4 wavelength, which is approx 17cm @ 433MHz.

Step 8: Future Work and Applications

Things I plan to do in future include:

  1. Include control of IR devices e.g. TV and air-conditioning remotes.
  2. Switch appliances, lights etc on/off via a webpage or phone app.
  3. Switch lights, TV, radio etc on and off on a schedule whilst I’m holidays so it looks like I’m still at home. To improve the illusion, the schedule could be varied randomly.
  4. Automatically turn off appliances & lights if unintentionally left on.
  5. P̶l̶a̶y̶ ̶p̶r̶a̶n̶k̶s̶ ̶o̶n̶ ̶p̶e̶o̶p̶l̶e̶ ̶b̶y̶ ̶r̶a̶n̶d̶o̶m̶l̶y̶ ̶o̶p̶e̶n̶i̶n̶g̶ ̶a̶n̶d̶ ̶c̶l̶o̶s̶i̶n̶g̶ ̶t̶h̶e̶i̶r̶ ̶g̶a̶r̶a̶g̶e̶ ̶d̶o̶o̶r̶s̶.̶ (You shouldn’t do this, it’s naughty.)
  6. Port to Raspberry Pi (rc-switch has a rpi port).

Step 9: References

Comments

Dangerously Explosive (author)2017-10-14

Cool. One question. Do you have to use binary? (As in, can I use this to send a string of random characters to another arduino?) I am trying to make a robot and this looks like a good way to give it a remote control mode.

iPierreP (author)2017-04-19

Using this method, can you read the value of the external temperature sensor and display it graphically?

LHC1234 (author)2015-10-28

Hi there, thanks for sharing this awesome project.

I managed to decode the signals from a switch I have to control a light with your
setting, but somehow I can't send control signals.

Here are some examples of signals I decoded with the receiver module:

Decimal: 4460821 (24Bit) Binary: 010001000001000100010101 Tri-State: F0F00F0F0FFF PulseLength: 328 microseconds Protocol: 1

Decimal: 4460820 (24Bit) Binary: 010001000001000100010100 Tri-State: F0F00F0F0FF0 PulseLength: 329 microseconds Protocol: 1

I than wrote a script to send those codes via the transmitter. But for
some reason the data gets send at a different PulseLength as set in my
code and does not get accepted by the device.

Example signal:

Decimal: 4460821 (24Bit) Binary: 010001000001000100010101 Tri-State:
F0F00F0F0FFF»÷iÿÿ PulseLength: 353 microseconds Protocol: 1

Code:

#include <RCSwitch.h>

RCSwitch mySwitch = RCSwitch();
RCSwitch sendSwitch = RCSwitch();

void setup() {
Serial.begin(9600);
mySwitch.enableReceive(0); // Receiver on inerrupt 0 => that is pin #2

// Transmitter is connected to Arduino Pin #10
sendSwitch.enableTransmit(10);

// Optional set pulse length.
sendSwitch.setPulseLength(328);

// Optional set protocol (default is 1, will work for most outlets)
sendSwitch.setProtocol(1);

// Optional set number of transmission repetitions.
sendSwitch.setRepeatTransmit(15);

pinMode(13,OUTPUT);
}

void loop() {
sendSwitch.send("010001000001000100010101");
digitalWrite(13,HIGH);
delay(2000);
if (mySwitch.available()) {
output(mySwitch.getReceivedValue(), mySwitch.getReceivedBitlength(), mySwitch.getReceivedDelay(), mySwitch.getReceivedRawdata(),mySwitch.getReceivedProtocol());
mySwitch.resetAvailable();
}

digitalWrite(13,LOW);
sendSwitch.send("010001000001000100010100");
if (mySwitch.available()) {
output(mySwitch.getReceivedValue(), mySwitch.getReceivedBitlength(), mySwitch.getReceivedDelay(), mySwitch.getReceivedRawdata(),mySwitch.getReceivedProtocol());
mySwitch.resetAvailable();
}
}

EricK155 made it! (author)LHC12342016-12-16

what is pin 13 connected to

liwenyip (author)EricK1552017-04-13

The on-board LED.

diy_bloke (author)LHC12342016-01-15

LHC, not sure if u managed by now but what is the make and model of your remote?

pintumbdig (author)2016-07-23

I'm just getting into this but could you record all kinds of signals(cars locks, garage doors, ceiling fans, etc) and ride around in a car with like a 5000 watt amplifier hooked up to this thing?

pintumbdig (author)pintumbdig2016-07-23

something else too this is sort of unrelated but i've always wondered.. okay without there being adequate amplification the signal won't reach the receiver so how do cell phones work? how does that small battery get the signal to the tower miles away? or how do they send a radio transmission from the planet mars? like i said i'm just getting into this so i should probably research it.. thanks for this though

liwenyip (author)pintumbdig2017-04-13

Very clever encoding and error correction techniques, very clever antenna design, and very strong amplification at the receiving end.

liwenyip (author)pintumbdig2017-04-13

Yes, but that would be very illegal.

John T MacF Mood (author)2015-10-05

Depending on the country you are in, this frequency spectrum may be shared or strictly allocated to a specific radio service. Check National communications law. In the US, The Federal Communications Commission would be the people to check with. Your device may be subject to all interference from authorized users of spectrum chosen. Looks like a great project, subject to some caveats.

I've added a note to the top of the article based on your comment. Thanks!

RuiMonteiro (author)2017-01-22

To make it perfect you could add the pins connections layout for each module...

RudiA4 (author)2017-01-17

How secure is this? Or, rather, how easy would it be for someone else to hack into my system, If I had to use this to open the gate and deactivate the alarm system?

liwenyip (author)RudiA42017-04-13

As secure as using a normal RF remote - not very secure.

DougM123 (author)2017-02-12

Have set this up, got the codes from the remote. Can send transmitter to receiver, but the actual switch does not seem to respond at all.

Have set the Pulse length the same as the delay (I think this is right)
Any thoughts why?

ShaneT41 (author)2016-11-20

Hi guys,

Does this work with HomeBridge? Whats the range?

Milan RamanathK (author)2016-05-31

hi can we connect no of rf receiver to one rf transmitter?

JangoF (author)2016-03-31

does any one know how to do it in raspberry pi and livolo brand light switches?

RoccoM1 (author)2016-03-08

Let me show you this open source project to have a ready to go environment to control all your 433mhz devices: https://github.com/roccomuso/iot-433mhz

diy_bloke (author)2016-01-15

Nice work!!
For the ones that are interested, I recognize your PowerTran remote as what is/was sold in Eurpe as the SelectRemote Nr. 1728029. The socket is ofcourse a bit different for europe, but the transmitter looks exactly the same. The protocol of that one is quite known.
You refer to those specific protocols in your step 4 am not sure how it is in RC switch, but in the other major library (RemoteSwitch) I just do

blokkerTransmitter.sendSignal(1, true)

to switch nr 1 on

No need to sniff the code for that particular one. (I couldnt as my transmitter was broken).
I am not sure which protocols are known by RCSwitch, but I would be surprised if it was not in there.
Anyway, it is definitely worth trying the various existing protocols.

laith mohamed (author)2015-12-14

I like your work man

JaydenLawson (author)2015-10-19

So good!! Thanks for the project mate.

rramesh68 (author)2015-10-13

Can I use a BLE shield in tandem with this circuit (for controlling something else)?

DIY Hacks and How Tos (author)2015-10-03

Welcome to Instructables. This is really cool. Thanks for sharing.

About This Instructable

212,600views

559favorites

License:

Add instructable to: