Skip to content

Instantly share code, notes, and snippets.

@0xD9D0
Last active May 7, 2018 16:11
Show Gist options
  • Save 0xD9D0/c1c35b632a974473d9007c64bafa90ae to your computer and use it in GitHub Desktop.
Save 0xD9D0/c1c35b632a974473d9007c64bafa90ae to your computer and use it in GitHub Desktop.
Temperature controller using PIC16F877

Smart temperature controller using PIC16F877

This program consists of designing, implementing and building an small temperature controller. This controller measures the temperature in the room and turns on or off an air conditioner as needed. The user should also be able to program the controller with different temperatures for the different parts of the day.

  • The controller must contain its own clock. The user will start by setting the clock, then the controller must manage on its own.
  • Interface 8 switches to one of the input ports to simulate reading the ambient temperature in BCD format.
  • Interface an LCD and use it to constantly display the clock, the current ambient temperature, the current temperature setting and the status of the A/C (ON/OFF).
  • If the clock has not been set, 12:00 should flash on the LCD. Add a push-button input to allow the user to set the desired temperature (in non-program mode).
  • Add two push buttons to increase/decrease the current setting.
  • The default setting is 15 degrees. This is also the minimum allowed setting. The maximum is 32 degrees.
  • The program should display the new setting as it is being incremented/decremented.
  • Add a push-button input to allow setting the clock.
  • Use 4 push-buttons to increase/decrease the current setting. 2 for the hours and 2 for the minutes.
  • Add a push-button to allow programming the controller.
  • Another push-button determines program 1/program 2. (Cycle through).
  • The push-buttons for setting the temperature and clock are used to set the desired temperature and the start time.
  • Add a push-button for canceling whatever current operation is being done.
  • The controller must read the ambient temperature every second. Allow a threshold of 2 degrees.
  • The ambient temperature needs to increase by 2 degrees over the setting before the A/C is turned on. It needs to drop by 2 degrees below the setting before the A/C is turned off.
// Lcd pinout settings
sbit LCD_RS at RA1_bit;
sbit LCD_RW at RA2_bit;
sbit LCD_EN at RA3_bit;
sbit LCD_D7 at RD7_bit;
sbit LCD_D6 at RD6_bit;
sbit LCD_D5 at RD5_bit;
sbit LCD_D4 at RD4_bit;
// Pin direction
sbit LCD_RS_Direction at TRISA1_bit;
sbit LCD_RW_Direction at TRISA2_bit;
sbit LCD_EN_Direction at TRISA3_bit;
sbit LCD_D4_Direction at TRISD4_bit;
sbit LCD_D5_Direction at TRISD5_bit;
sbit LCD_D6_Direction at TRISD6_bit;
sbit LCD_D7_Direction at TRISD7_bit;
sbit progs at RB3_bit;
sbit tempUP at RB1_bit;
sbit tempDOWN at RB2_bit;
bit prog,acon;
int counterr=0;
int secondss=0;
int minutess=0;
int hourss=12;
int desT = 15;
char hh[3],mm[3],ss[3],tembcd1,tembcd2,amb_temp,des_temp[3];
void bcdconv();
void interrupt()
{
if (INTCON.INTF)
{
INTCON.INTF=0;
secondss=0;
minutess=0;
hourss=12;
desT = 15;
prog=1;
}
else if(INTCON.T0IF ){
counterr ++;
TMR0 = 39;
INTCON.T0IF = 0 ;
if (counterr==36 ){
counterr=0;
bcdconv();
if ((DesT-amb_temp)>=2)
acon=0;
if ((DesT-amb_temp)<=-2)
acon=1;
if (!prog){
secondss++;
if (secondss==60)
{
secondss=0;
minutess++;
if (minutess==60)
{
minutess=0;
hourss++;
if (hourss==24)
hourss==0;
}}}
}
}
} //end of interrupt isr
void printclk();
void main(){
TRISB=0xff; // RB0= push button for cancellation , RB1:2 = 2 push buttons for desired temp. ,
//RB3= push button for programming mode, and RB4:7 = high nibble of the switches
TRISC=0x0f; // matrix keypad, RC7:4=0xE , RC3:0 = four push buttons for the clock.
TRISA=0x00; // RA1:3= for the LCD the rest unimplemented
TRISD=0x0f; // RD3:0 = low nibble of the switches , RD4:7 for the LCD
PORTC.RC7=1;
PORTC.RC6=1;
PORTC.RC5=1;
PORTC.RC4=0;
ADCON1=0x06;
LCD_D7=0;
LCD_D6=0;
LCD_D5=0;
LCD_D4=0;
OPTION_REG = 0x46;
TMR0 = 39;
INTCON=0b11110000;
Lcd_Init();
Lcd_Cmd(_LCD_CLEAR);
Lcd_Out(2,1,"AmT:");
Lcd_Out(2,9,"DeT:");
Lcd_Out(1,11,"AC:");
prog=1;
acon=0;
progm: while(prog)
{
printclk();
delay_ms(40);
switch (PORTC)
{
case 0xE7: hourss++;
if (hourss>=24)
hourss=0;
break;
case 0xEB: hourss--;
if (hourss<0)
hourss=23;
break;
case 0xED: minutess++;
if(minutess>=60)
minutess=0;
break;
case 0xEE: minutess--;
if (minutess<0)
minutess=59;
break;
}
if(!tempUP){
delay_ms(25);
while(!tempUP);
if (desT==32)
desT=15;
else
desT++;
}
if(!tempDOWN)
{
delay_ms(25);
while(!tempDOWN);
if (desT==15)
desT=32;
else
desT--;
}
if (!progs){
delay_ms(25);
while(!progs);
prog=~prog;
}
}
nprog: while (!prog)
{
printclk();
if(!tempUP){
delay_ms(25);
while(!tempUP);
if (desT==32)
desT=15;
else
desT++;
}
if(!tempDOWN)
{
delay_ms(25);
while(!tempDOWN);
if (desT==15)
desT=32;
else
desT--;
}
if (!progs){
delay_ms(25);
while(!progs);
prog=~prog;
}
}
goto progm;
}
void printclk(){
sprinti(ss,"%2u",secondss);
sprinti(mm,"%2u",minutess);
sprinti(hh,"%2u",hourss);
sprinti(des_temp,"%2u",desT);
Lcd_Out(1,1,hh);
Lcd_Out(1,4,":");
Lcd_Out(1,5,mm);
//Lcd_Out(1,8,":");
//Lcd_Out(1,9,ss);
Lcd_Chr(2,5,tembcd2);
Lcd_Chr(2, 6,tembcd1);
Lcd_Out(2,13,des_temp);
if (acon)
Lcd_Out(1,14,"ON ");
else
Lcd_Out(1,14,"OFF");
if (prog){
Lcd_Out(1,1," ");
//Lcd_Out(1,1," ");
delay_ms(25);
}
}
void bcdconv(){
tembcd1=PORTD;
tembcd1=tembcd1 & 0x0f;
tembcd2=PORTB;
tembcd2=tembcd2 & 0xf0;
tembcd2=tembcd2>>4;
if (tembcd1>9 || tembcd2>9)
{tembcd1=0x0f;
tembcd2=0x0f;
goto here;
}
amb_temp=tembcd2*10 + tembcd1;
here:tembcd1=tembcd1 | 0b00110000;
tembcd2=tembcd2 | 0b00110000;
return;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment