433MHz RF remote control system based on PIC microcontroller

5-Channel RF (Radio Frequency) remote control transmitter/receiver using PIC18F4550 microcontroller
Today RF modules are widely used in many applications (wireless data transmission, quadcopter, car remote control….).
This project shows how to use low cost 433MHz RF transmitter/receiver modules to build a 5-channel wireless RF remote control system using 2xPIC18F4550 microcontrollers.
The used RF modules in this project are cheap and easy to use with any microcontroller. These modules are shown below with pin configuration:433MHz RF remote control system based on PIC microcontroller
The following video shows how to get started with low cost RF modules:

Communication protocol:
In this RF project data is transmitted from the transmitter circuit to the receiver circuit using NEC protocol. The NEC protocol uses pulse distance encoding of the bits. Each pulse is a 562.5Β΅s long.
Logic 0: 562.5Β΅s pulse burst followed by a 562.5Β΅s space, with a total transmit time of 1125Β΅s (562.5 x 2).
Logic 1: a 562.5Β΅s pulse burst followed by a 1687.5Β΅s (562.5 x 3) space, with a total transmit time of 2250Β΅s (562.5 x 4).433MHz RF remote control system based on PIC-microcontroller

The complete extended NEC protocol message is started by 9ms burst followed by 4.5ms space which is then followed by the Address and Command. The address is 16-bit length and the command is transmitted twice (8 bits + 8 bits) where in the second time all bits are inverted and can be used for verification of the received message. The following drawing shows an extended NEC message example.

5-Channel RF remote control using PIC18F4550 microcontroller:
This 433MHz RF remote control system has 2 circuits which are transmitter circuit which transmits the RF signals and receiver circuit which receives the RF signals.
RF Transmitter circuit:
The following image shows the RF transmitter circuit schematic diagram where PIC18F4550 microcontroller is used.
In the circuit there are five (5) pushbuttons as shown, each pushbutton sends a different RF signal code via an RF transmitter.

PIC18F4550 internal oscillator is used (8MHz) and MCLR is disabled.

RF Transmitter using PIC18F4550 CCS C code:
The following C code is the full code used for the transmitter circuit microcontroller which is written with CCS PIC C compiler PCWHD version 5.0.51.

//Β 5-ChannelΒ RFΒ remoteΒ controlΒ usingΒ PIC18F4550Β transmitterΒ CCSΒ CΒ code
//Β http://ccspicc.blogspot.com/
//Β [email protected]

#include <18F4550.h>
#fuses NOMCLR INTRC_IO
#use delay(clock = 8000000)
#use fast_io(B)
#use fast_io(D)

void send_signal(unsigned int32 number){
Β Β int8 i;
Β Β // Send 9ms pulse
Β Β output_high(PIN_D0);
Β Β delay_ms(9);
Β Β // Send 4.5ms space
Β Β output_low(PIN_D0);
Β Β delay_us(4500);
Β Β // Send data
Β Β for(i = 0; i < 32; i++){
Β Β Β Β // If bit is 1 send 560us pulse and 1680us space
Β Β Β Β if(bit_test(number, 31 - i)){
Β Β Β Β Β Β output_high(PIN_D0);
Β Β Β Β Β Β delay_us(560);
Β Β Β Β Β Β output_low(PIN_D0);
Β Β Β Β Β Β delay_us(1680);
Β Β Β Β }
Β Β Β Β // If bit is 0 send 560us pulse and 560us space
Β Β Β Β else{
Β Β Β Β Β Β output_high(PIN_D0);
Β Β Β Β Β Β delay_us(560);
Β Β Β Β Β Β output_low(PIN_D0);
Β Β Β Β Β Β delay_us(560);
Β Β Β Β }
Β Β }
Β Β // Send end bit
Β Β output_high(PIN_D0);
Β Β delay_us(560);
Β Β output_low(PIN_D0);
Β Β delay_us(560);
}
void main(){
Β Β setup_oscillator(OSC_8MHZ);Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β // Set internal oscillator to 8MHz
Β Β setup_adc_ports(NO_ANALOGS);Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β // Configure AN pins as digital
Β Β output_b(0);Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β // PORTB initial state
Β Β set_tris_b(0x1F);Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β // Configure RB0-to-RB4 as inputs
Β Β port_b_pullups(TRUE);Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β // Enable PORTB internal pull-ips
Β Β output_d(0);Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β // PORTD initial state
Β Β set_tris_d(0);Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β // Configure PORTD pins as outputs
Β Β while(TRUE){
Β Β Β Β while(!input(PIN_B0)){
Β Β Β Β Β Β send_signal(0x40BF00FF);
Β Β Β Β Β Β delay_ms(500);
Β Β Β Β }
Β Β Β Β while(!input(PIN_B1)){
Β Β Β Β Β Β send_signal(0x40BF807F);
Β Β Β Β Β Β delay_ms(500);
Β Β Β Β }
Β Β Β Β while(!input(PIN_B2)){
Β Β Β Β Β Β send_signal(0x40BF40BF);
Β Β Β Β Β Β delay_ms(500);
Β Β Β Β }
Β Β Β Β while(!input(PIN_B3)){
Β Β Β Β Β Β send_signal(0x40BF20DF);
Β Β Β Β Β Β delay_ms(500);
Β Β Β Β }
Β Β Β Β while(!input(PIN_B4)){
Β Β Β Β Β Β send_signal(0x40BFA05F);
Β Β Β Β Β Β delay_ms(500);
Β Β Β Β }
Β Β }
}

RF Receiver circuit:
Receiver circuit schematic diagram is shown below.
PIC18F4550 internal oscillator is used (8MHz) and MCLR is disabled.
In the receiver circuit there are 5 LEDs, each LED is controlled by one pushbutton on the transmitter circuit. The RF receiver receives RF signals transmitted from the RF transmitter on the transmitter circuit.

RF Receiver using PIC18F4550 CCS C code:
The NEC message has 32 bits which are divided into address (16 bits), command (8 bits) and inverted command (8 bits).
The microcontroller waits until the RF receiver receives an RF signal which makes RB0 goes from logic 0 to logic 1 and the command used is:
while(!input(PIN_B0));
After that a function named remote_read() is called, this function checks if the received signal has NEC protocol form all the time with a resolution of 10us then returns the received code.

//Β 5-ChannelΒ RFΒ remoteΒ controlΒ usingΒ PIC18F4550Β receiverΒ CCSΒ CΒ code
//Β http://ccspicc.blogspot.com/
//Β [email protected]

#include <18F4550.h>
#fuses NOMCLR INTRC_IO
#use delay(clock = 8000000)
#use fast_io(B)

unsigned int32 remote_code;
short remote_read(){
Β Β int8 i;
Β Β unsigned int16 count = 0;
Β Β // Check 9ms pulse (remote control sends logic high)
Β Β while((input(PIN_B0) == 1) && (count < 600)){
Β Β Β Β count++;
Β Β Β Β delay_us(10);}
Β Β if( (count > 599) || (count < 500))          // NEC protocol?
Β Β Β Β return FALSE;                          
Β Β countΒ =Β 0;
Β Β // Check 4.5ms space (remote control sends logic low)
Β Β while((input(PIN_B0) == 0) && (count < 300)){
Β Β Β Β count++;
Β Β Β Β delay_us(10);}
Β Β if( (count > 299) || (count < 220))          // NEC protocol?
Β Β Β Β return FALSE;                         
Β Β // Read message (32 bits)
Β Β for(i = 0; i < 32; i++){
Β Β Β Β countΒ =Β 0;
Β Β Β Β while((input(PIN_B0) == 1) && (count < 45)){
Β Β Β Β Β Β count++;
Β Β Β Β Β Β delay_us(10);}
Β Β Β Β if( (count > 44) || (count < 25))          // NEC protocol?
Β Β Β Β Β Β return FALSE;                         
Β Β Β Β countΒ =Β 0;
Β Β Β Β while((input(PIN_B0) == 0) && (count < 120)){
Β Β Β Β Β Β count++;
Β Β Β Β Β Β delay_us(10);}
Β Β Β Β if( (count > 119) || (count < 25))         // NEC protocol?
Β Β Β Β Β Β return FALSE;
Β Β Β Β if( count > 60)                            // If space width > 1ms
Β Β Β Β Β Β bit_set(remote_code,Β (31Β -Β i));Β Β Β Β Β Β Β Β Β Β // Write 1 to bit (31 - i)
Β Β Β Β else                                       // If space width < 1ms
Β Β Β Β Β Β bit_clear(remote_code,Β (31Β -Β i));Β Β Β Β Β Β Β Β // Write 0 to bit (31 - i)
Β Β }
Β Β return TRUE;
}
void main(){
Β Β setup_oscillator(OSC_8MHZ);Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β // Set internal oscillator to 8MHz
Β Β setup_adc_ports(NO_ANALOGS);Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β // Configure AN pins as digital
Β Β output_b(0);Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β // PORTB initial state
Β Β set_tris_b(1);Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β Β // Configure RB0 as digital input pin
Β Β while(TRUE){
Β Β Β Β while(!input(PIN_B0));                     // Wait until RB0 pin goes high
Β Β Β Β if(remote_read()){
Β Β Β Β Β Β if(remote_code == 0x40BF00FF)
Β Β Β Β Β Β Β Β output_toggle(PIN_B1);
Β Β Β Β Β Β if(remote_code == 0x40BF807F)
Β Β Β Β Β Β Β Β output_toggle(PIN_B2);
Β Β Β Β Β Β if(remote_code == 0x40BF40BF)
Β Β Β Β Β Β Β Β output_toggle(PIN_B3);
Β Β Β Β Β Β if(remote_code == 0x40BF20DF)
Β Β Β Β Β Β Β Β output_toggle(PIN_B4);
Β Β Β Β Β Β if(remote_code == 0x40BFA05F)
Β Β Β Β Β Β Β Β output_toggle(PIN_B5);
Β Β Β Β Β Β }
Β Β }
}

5-Channel RF remote control using PIC18F4550 microcontroller video:
The following video shows a prototype hardware circuit for this project.
In this video I used PORTD instead of PORTB for the 5 outputs of the receiver circuit.

 

Source :Β 433MHz RF remote control system based on PIC microcontroller


About The Author

Ibrar Ayyub

I am an experienced technical writer holding a Master's degree in computer science from BZU Multan, Pakistan University. With a background spanning various industries, particularly in home automation and engineering, I have honed my skills in crafting clear and concise content. Proficient in leveraging infographics and diagrams, I strive to simplify complex concepts for readers. My strength lies in thorough research and presenting information in a structured and logical format.

Follow Us:
LinkedinTwitter

Leave a Comment

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed.