51单片机智能风扇点阵显示温度及按键控制程序(3)

合集下载

基于51单片机的温控风扇程序

基于51单片机的温控风扇程序

基于51单片机的温控风扇程序#include //调用单片机头文件#define uchar unsigned char //无符号字符型宏定义变量范围0~255#define uint unsigned int //无符号整型宏定义变量范围0~65535#include "eeprom52.h"//数码管段选定义 0 1 2 3 4 5 6 7 8 9uchar code smg_du[]={0x28,0xee,0x42,0x52,0xe5,0xa8,0x41,0xe7,0x20,0xa0, 0x60,0x25,0x39,0x26,0x31,0x71,0xff}; //断码//数码管位选定义uchar code smg_we[]={0xef,0xdf,0xbf,0x7f};uchar dis_smg[8] = {0x28,0xee,0x32,0xa2,0xe4,0x92,0x82,0xf8};uchar smg_i = 3; //显示数码管的个位数sbit dq = P2^4; //18b20 IO口的定义bit flag_lj_en; //按键连加使能bit flag_lj_3_en; //按键连3次连加后使能加的数就越大了uchar key_time,key_value; //用做连加的中间变量bit key_500ms ;sbit pwm = P2^3;uchar f_pwm_l ; //越小越暗uint temperature ; //bit flag_300ms ;uchar menu_1; //菜单设计的变量uint t_high = 300,t_low = 100; //温度上下限报警值/***********************1ms延时函数*****************************/void delay_1ms(uint q){uint i,j;for(i=0;i<q;i++)for(j=0;j<120;j++);}/***********************小延时函数*****************************/void delay_uint(uint q){while(q--);}/***********************数码显示函数*****************************/void display(){static uchar i;i++;if(i >= smg_i)i = 0;P1 = 0xff; //消隐P3 = smg_we[i]; //位选P1 = dis_smg[i]; //段选}/******************把数据保存到单片机内部eepom中******************/void write_eeprom(){SectorErase(0x2000);byte_write(0x2000, t_high % 256);byte_write(0x2001, t_high / 256);byte_write(0x2002, t_low % 256);byte_write(0x2003, t_low / 256);byte_write(0x2055, a_a);}/******************把数据从单片机内部eepom中读出来*****************/void read_eeprom(){t_high = byte_read(0x2001);t_high <<= 8;t_high |= byte_read(0x2000);t_low = byte_read(0x2003);t_low <<= 8;t_low |= byte_read(0x2002);a_a = byte_read(0x2055);}/**************开机初始化保存的数据*****************/void init_eeprom()read_eeprom(); //先读if(a_a != 22) //新的单片机初始单片机内问eeprom{t_high = 320;t_low = 280;a_a = 22;write_eeprom(); //保存数据}}/***********************18b20初始化函数*****************************/void init_18b20(){bit q;dq = 1; //把总线拿高delay_uint(1); //15usdq = 0; //给复位脉冲delay_uint(80); //750usdq = 1; //把总线拿高等待delay_uint(10); //110usq = dq; //读取18b20初始化信号delay_uint(20); //200usdq = 1; //把总线拿高释放总线}/*************写18b20内的数据***************/void write_18b20(uchar dat)uchar i;for(i=0;i<8;i++)</q;i++){ //写数据是低位开始dq = 0; //把总线拿低写时间隙开始dq = dat & 0x01; //向18b20总线写数据了delay_uint(5); // 60usdq = 1; //释放总线dat >>= 1;}}/*************读取18b20内的数据***************/ uchar read_18b20(){uchar i,value;for(i=0;i<8;i++){dq = 0; //把总线拿低读时间隙开始value >>= 1; //读数据是低位开始dq = 1; //释放总线if(dq == 1) //开始读写数据value |= 0x80;delay_uint(5); //60us 读一个时间隙最少要保持60us的时间}return value; //返回数据}/*************读取温度的值读出来的是小数***************/uint read_temp(){uint value;uchar low; //在读取温度的时候如果中断的太频繁了,就应该把中断给关了,否则会影响到18b20的时序init_18b20(); //初始化18b20EA = 0;write_18b20(0xcc); //跳过64位ROMwrite_18b20(0x44); //启动一次温度转换命令EA = 1;delay_uint(50); //500usinit_18b20(); //初始化18b20EA = 0;write_18b20(0xcc); //跳过64位ROMwrite_18b20(0xbe); //发出读取暂存器命令low = read_18b20(); //读温度低字节value = read_18b20(); //读温度高字节EA = 1;value <<= 8; //把温度的高位左移8位value |= low; //把读出的温度低位放到value的低八位中value *= 0.625; //转换到温度值小数return value; //返回读出的温度带小数}/*************定时器0初始化程序***************/void time_init(){EA = 1; //开总中断TMOD = 0X11; //定时器0、定时器1工作方式1 ET0 = 1; //开定时器0中断TR0 = 1; //允许定时器0定时ET1 = 1; //开定时器0中断TR1 = 0; //允许定时器0定时}/********************独立按键程序*****************/ uchar key_can; //按键值void key() //独立按键程序{static uchar key_new;key_can = 20; //按键值还原P2 |= 0x07;if((P2 & 0x07) != 0x07) //按键按下{if(key_500ms == 1) //连加{key_500ms = 0;key_new = 1;}delay_1ms(1); //按键消抖动if(((P2 & 0x07) != 0x07) && (key_new == 1)) { //确认是按键按下key_new = 0;switch(P2 & 0x07){case 0x06: key_can = 3; break; //得到k2键值case 0x05: key_can = 2; break; //得到k3键值case 0x03: key_can = 1; break; //得到k4键值}flag_lj_en = 1; //连加使能}}else{if(key_new == 0){key_new = 1;write_eeprom(); //保存数据flag_lj_en = 0; //关闭连加使能flag_lj_3_en = 0; //关闭3秒后使能key_value = 0; //清零key_time = 0;key_500ms = 0;}}}/****************按键处理数码管显示函数***************/ void key_with(){if(key_can == 1) //设置键{f_pwm_l =30;menu_1 ++;if(menu_1 >= 3){menu_1 = 0;smg_i = 3; //数码管显示3位}}if(menu_1 == 1) //设置高温报警{smg_i = 4; //数码管显示4位if(key_can == 2){if(flag_lj_3_en == 0)t_high ++ ; //按键按下未松开自动加三次elset_high += 10; //按键按下未松开自动加三次之后每次自动加10 if(t_high > 990)t_high = 990;}if(key_can == 3){if(flag_lj_3_en == 0)t_high -- ; //按键按下未松开自动减三次elset_high -= 10; //按键按下未松开自动减三次之后每次自动减10 if(t_high <= t_low)t_high = t_low + 1;}dis_smg[0] = smg_du[t_high % 10]; //取小数显示dis_smg[1] = smg_du[t_high / 10 % 10] & 0xdf; //取个位显示dis_smg[2] = smg_du[t_high / 100 % 10] ; //取十位显示dis_smg[3] = 0x64; //H}if(menu_1 == 2) //设置低温报警{smg_i = 4; //数码管显示4位if(key_can == 2){if(flag_lj_3_en == 0)t_low ++ ; //按键按下未松开自动加三次elset_low += 10; //按键按下未松开自动加三次之后每次自动加10 if(t_low >= t_high)t_low = t_high - 1;}if(key_can == 3){if(flag_lj_3_en == 0)t_low -- ; //按键按下未松开自动减三次elset_low -= 10; //按键按下未松开自动加三次之后每次自动加10 if(t_low <= 10)t_low = 10;}dis_smg[0] = smg_du[t_low % 10]; //取小数显示dis_smg[1] = smg_du[t_low / 10 % 10] & 0xdf; //取个位显示dis_smg[2] = smg_du[t_low / 100 % 10] ; //取十位显示dis_smg[3] = 0x3D; //L}}/****************风扇控制函数***************/void fengshan_kz(){// static uchar value;if(temperature >= t_high) //风扇全开{TR1 = 1;pwm = 0;}else if((temperature < t_high) && (temperature >= t_low)) //风扇缓慢{f_pwm_l = 60;TR1 = 1;}else if(temperature < t_low) //关闭风扇{TR1 = 0;pwm = 1;}}/****************主函数***************/void main(){time_init(); //初始化定时器temperature = read_temp(); //先读出温度的值init_eeprom(); //开始初始化保存的数据delay_1ms(650);temperature = read_temp(); //先读出温度的值dis_smg[0] = smg_du[temperature % 10]; //取温度的小数显示dis_smg[1] = smg_du[temperature / 10 % 10] & 0xdf; //取温度的个位显示dis_smg[2] = smg_du[temperature / 100 % 10] ; //取温度的十位显示f_pwm_l = 50;while(1){key(); //按键程序if(key_can < 10){key_with(); //设置报警温度}if(flag_300ms == 1) //300ms 处理一次温度程序{flag_300ms = 0;temperature = read_temp(); //先读出温度的值if(menu_1 == 0){smg_i = 3;dis_smg[0]= smg_du[temperature % 10]; //取温度的小数显示dis_smg[1] = smg_du[temperature / 10 % 10] & 0xdf; //取温度的个位显示dis_smg[2] = smg_du[temperature / 100 % 10] ; //取温度的十位显示}fengshan_kz(); //风扇控制函数}}/*************定时器0中断服务程序***************/ void time0_int() interrupt 1{static uchar value; //定时2ms中断一次TH0 = 0xf8;TL0 = 0x30; //2msdisplay(); //数码管显示函数value++;if(value >= 150){value = 0;flag_300ms = 1;}if(flag_lj_en == 1) //按下按键使能{key_time ++;if(key_time >= 250) //500ms{key_time = 0;key_500ms = 1; //500mskey_value ++;if(key_value > 3){key_value = 10;flag_lj_3_en = 1; //3次后1.5秒连加大些}}}/*******************定时器1用做单片机模拟PWM 调节***********************/void Timer1() interrupt 3 //调用定时器1{static uchar value_l;TH1=0xfe; // 定时10ms中断一次TL1=0x0c; //500usif(pwm==1){value_l+=3;if(value_l > f_pwm_l) //高电平{value_l=0;if(f_pwm_l != 0)pwm=0;}}else{value_l+=3;if(value_l > 100 - f_pwm_l) //低电平{value_l=0;pwm=1;} }。

智能风扇程序,数码管显示温度

智能风扇程序,数码管显示温度

#include<reg52.h>#define uchar unsigned char#define uint unsigned intsbit du=P2^0;sbit we=P2^1;sbit LCD_RS = P3^5;sbit LCD_RW = P3^6;sbit LCD_EN = P3^4;sbit LCD_PSB = P3^7;sbit dianji=P1^7;sbit jia=P3^0;sbit jian=P3^1;sbit in1=P1^4;sbit in2=P1^5;sbit ds=P2^2;sbit dula=P2^6;sbit wela=P2^7;uint temp;float tt;uchar num=0;show=1;gao=1;di=3;uchar code table[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f,0x77,0x7c,0x39,0x5e,0x79,0x71};uchar code table1[]={0xbf,0x86,0xdb,0xcf,0xe6,0xed,0xfd,0x87,0xff,0xef};//uchar code table[]={0x30,0x31,0x32,0x33,0x34,0x35,0x36,0x37,0x38,0x39} ;uchar code hang3[]= {"当前温度:"};uchar code hang4[]= {"度"};uchar code hang5[]= {"当前档位:"};uchar code hang6[]= {"档"};void delay(uint i){while(i--);}void yan(uchar z){uint x,y;for(x=z;x>0;x--)for(y=110;y>0;y--);}void display(uint temp1){uchar shi,ge,wei;shi=temp1/100;ge=temp1%100/10;wei=temp1%10;P0=table[shi]; //十位;dula=1;dula=0;P0=0xff;P0=0xfe;wela=1;wela=0;yan(2);P0=table1[ge]; //个位;dula=1;dula=0;P0=0xff;P0=0xfd;wela=1;wela=0;yan(2);P0=table[wei]; //小数点一位;dula=1;dula=0;P0=0xff;P0=0xfb;wela=1;wela=0;yan(2);P0=0x39; //摄氏度;dula=1;dula=0;P0=0xff;P0=0xf7;wela=1;wela=0;yan(2);}void chushihua() //初始化函数;{ds=1;delay(2);ds=0;delay(100);ds=1;delay(15);if(ds==0){delay(90);}ds=1;}void xiehanshu(uchar dat) //写函数; {uchar i=0;for(i=8;i>0;i--){ds=0;ds=dat&0x01;delay(6);ds=1;dat>>=1;}ds=1;}uchar duhanshu(void) //读函数;{uchar i=0;uchar dat=0;for(i=8;i>0;i--){ds=0;dat>>=1;ds=1;if(ds==1)dat|=0x80;delay(3);}return(dat);}void kaishi(){uchar a=0;uchar b=0;chushihua();xiehanshu(0xcc); // 写跳过读ROM指令;xiehanshu(0x44); // 写温度转换指令;delay(30);chushihua();xiehanshu(0xcc);xiehanshu(0xbe);delay(15);a=duhanshu(); //读低八位;b=duhanshu(); //读高八位;temp=b;temp<<=8; //两个字节组合为一个字;temp=temp|a;tt=temp*0.0625; //温度在寄存器中是12位,分辨率是0.0625temp=tt*10+0.5; //乘10表示小数点后只取1位,加0.5是四折五入temp+=0.05;display(temp);if(temp>37) num=3;else if(temp>36) num=2;else if(temp>35) num=1;else if(temp>33)num=0;else if(temp<32)num=4;}void dispose(){switch(num){case 0:gao=1;di=3;break;case 1:gao=2;di=2;break;case 2:gao=3;di=1;break;case 3:gao=4;di=0;break;case 4:gao=0;di=4;}}void qudong(){ uchar i;in1=1;in2=0;if(di!=0){for(i=0;i<di;i++){dianji=0;yan(1);}}for(i=0;i<gao;i++){dianji=1;yan(2);}}void write_cmd(uchar cmd) //写指令数据到LCD;{LCD_RS=0;LCD_RW=0;LCD_EN=0;P0=cmd;delay(5);LCD_EN=1;delay(5);LCD_EN=0;}void write_dat(uchar dat) //写显示数据到LCD;{LCD_RS=1;LCD_RW=0;LCD_EN=0;P0=dat;delay(5);LCD_EN=1;delay(5);LCD_EN=0;}void lcd_pos(uchar X,uchar Y) //设定显示位置;{uchar pos;if(X==0){X=0x80;}else if(X==1){X=0x90;}else if(X==2){X=0x88;}else if(X==3){X=0x98;}pos=X+Y;write_cmd(pos);}void lcd_init() //LCD初始化设定;{LCD_PSB=1;write_cmd(0x30);delay(5);write_cmd(0x0C);delay(5);write_cmd(0x01);delay(5);}void Clear_GDRAM(void){uchar i,j,k;write_cmd(0x34);i=0x80;for(j=0;j<32;j++){write_cmd(i++);write_cmd(0x80);for(k=0;k<16;k++){write_dat(0x00);}}i=0x80;for(j=0;j<32;j++){write_cmd(i++);write_cmd(0x88);for(k=0;k<16;k++){write_dat(0x00);}}write_cmd(0x30);}/***********************************************************欢迎界面*********************************************************** */void main(){while(1){dianji=0;kaishi();dispose();qudong();}}。

51单片机的液晶显示温度计程序

51单片机的液晶显示温度计程序

51单片机的液晶显示温度计程序51单片机的液晶显示温度计程序#include&lt;reg51.h&gt;#include &lt;intrins.h&gt;sbit RST = P2^0;sbit CLK = P2^1;sbit DQ = P2^2;sbit TSOR = P2^3;sbit ALERT =P2^4;sbit RS = P2^7;sbit RW = P2^6;sbit EN = P2^5;/*------------------------------------------全局变量-------------------------------------------------------*/static unsigned char temp1,temp2; //温度值的整数部分、小数部分static unsigned char pos,posset; //数字电位器电位值、设定值static unsigned char min,sec; //分钟、秒static unsigned char count; //Timer0中断计数static unsigned char minset; //设定的分钟数static unsigned char status1,status2; //状态标志bit stop,timeover; //定时停止、结束static char line0[] =" 00:00 ";static char line1[] =" . CW";/*-------------------------------------------------------------------------------------------------------------*/void InitInterupt();void KeyboardDelay();/*-------------------------------------------LCD驱动函数------------------------------------------------*/void DelayL();void DelayS();void WriteCommand(unsigned char c);void WriteData(unsigned char c);void ShowChar(unsigned char pos,unsigned char c); void ShowString(unsigned char line,char *ptr);void InitLcd();/*----------------------------------------------键盘-程序--------------------------------------------------*/unsigned char GetKey();/*---------------------------------------------数字温度计驱动-------------------------------------------*/void ChangePos(bit sel,unsigned char pos1,unsigned char pos2);/*------------------------------------------温度传感器驱动----------------------------------------------*/void Delay15();void Delay60();void Delay100ms();void Write0TS();void Write1TS();bit ReadTS();void ResetTS();void WriteByteTS(unsigned char byte); unsigned char ReadByteTS();void InitTS();void GetTempTS();/*-------------------------------------------------主程序---------------------------------------------------*/void main (void) {char code str1[] =" Hello World! ";char code str2[] =" 2002-10-20 "; unsigned char i; SP=0x50;ALERT=0; //报警灯灭TSOR=1; //1-wire总线释放DelayL();InitLcd(); //初始化LCDDelayL();ShowString(0,str1); //启动画面ShowString(1,str2);for(i=0;i&lt;15;i++)Delay100ms();InitInterupt(); //初始化中断设置minset=10; //缺省定时10分钟posset=0; //缺省电位器值0min=minset; //初始化数据pos=posset;sec=0;count=0;P1=0xF0;status1=0;status2=0;stop=1;timeover=0; ChangePos(0,255-pos,255-pos); //设置电位器InitTS(); //初始化温度计while(1) //循环显示温度值{GetTempTS();line1[0]=0x20;i=temp1;if(i&gt;39) //超过40摄氏度,告警灯亮ALERT=1;if(i&gt;99) //超过100摄氏度,显示温度的百位{line1[0]=0x31;i-=100;}line1[1]=i/10+0x30; //显示温度的十位line1[2]=i%10+0x30; //显示个位line1[4]=temp2+0x30; //显示小数位if(timeover) //若定时结束,则电位器缓慢复0{for(;pos&gt;0;pos--){ChangePos(0,255-pos,255-pos);_nop_();_nop_();}timeover=0;posset=0;}if(pos&gt;posset) //若按键修改电位器位置{for(;pos&gt;posset;pos--) //则缓变到设定值{ChangePos(0,255-pos,255-pos);_nop_();_nop_();}ChangePos(0,255-pos,255-pos);}else if(pos&lt;posset){for(;pos&lt;posset;pos++){ChangePos(0,255-pos,255-pos);_nop_();_nop_();}ChangePos(0,255-pos,255-pos);}i=pos;line1[9]=0x20; //显示电位器等级值if(i&gt;99){line1[9]=i/100+0x30;i=i%100;}line1[10]=i/10+0x30;line1[11]=i%10+0x30;ShowString(1,line1);line0[5]=min/10+0x30; //显示时间line0[6]=min%10+0x30;line0[8]=sec/10+0x30;line0[9]=sec%10+0x30;ShowString(0,line0);Delay100ms();}}void InitInterupt(){TMOD=0x21; //初始化中断设置TL1=0xFD;TH1=0xFD;PX0=1;EA=1;ES=1;PCON=0;TR1=1;SCON=0x50;TL0=0x00; //定时0.05mTH0=0x4C;ET0=1; EX0=1;IT0=1;}void KeyboardDelay() //按键中断延时{unsigned char i,j;i=0x40;j=0xFF;while(i--)while(j--);}/*--------------------------------------------中断处理-----------------------------------------------------*/Int0_process() interrupt 0 using 0{unsigned char key;unsigned char keycode[]= "TP";unsigned char step[3]={1,2,5};EA=0;key=GetKey(); //获得按键值switch(key){case 0:stop=!stop;min=minset;sec=0;break;case 1:case 2:case 3:if(stop){minset+=step[key-1];if(minset&gt;60)minset=0;min=minset;}break;case 5:case 6:case 7:if(stop){minset-=step[key-5]; if(minset&gt;60) minset=0;min=minset;}break;case 9:case 10:case 11:posset+=step[key-9];break;case 13:case 14:case 15:posset-=step[key-13];break;default:break;}TR0=!stop;KeyboardDelay();P1=0xF0;EA=1;}Timer0_process() interrupt 1 using 0{EA=0;TR0=0;TL0=0x00;TH0=0x4C;count++;if(count==20) //如果到累计定时到达1s {if(sec==0) //定时处理{if(min==0) //总定时到,则置结束标志timeover=1;else{min--;sec=59;}}elsesec--;count=0;}TR0=1;EA=1;}/*--------------------------------------LCD驱动子程序--------------------------------------------------*/void DelayL(){unsigned char i,j;i=0xF0;j=0xFF;while(i--)while(j--);}void DelayS(){unsigned char i;i=0x1F;while(i--);}void WriteCommand(unsigned char c) {DelayS();EN=0;RS=0;RW=0;_nop_();EN=1;P0=c;EN=0;}void WriteData(unsigned char c){DelayS();EN=0;RS=1;RW=0;_nop_();EN=1;P0=c;EN=0;RS=0;}void ShowChar(unsigned char pos,unsigned char c) {unsigned char p;if(pos&gt;=0x10)p=pos+0xB0;elsep=pos+0x80;WriteCommand(p);WriteData(c);}void ShowString(unsigned char line,char *ptr){unsigned char l,i;l=line&lt;&lt;4;for(i=0;i&lt;16;i++)ShowChar(l++,*(ptr+i));} void InitLcd(){DelayL();WriteCommand(0x38);WriteCommand(0x38);WriteCommand(0x06);WriteCommand(0x0C);WriteCommand(0x01);WriteCommand(0x80);}/*---------------------------------------------键盘子程序-------------------------------------------------*/ unsigned char GetKey(){unsigned k,t,i,j;k=P1;k=k&amp;0xF0;i=0;while((k&amp;0x10)&amp;&amp;i&lt;4) {i++;k=k&gt;&gt;1;}k=0x01;j=0;while(j&lt;4){P1=0xFF^k;_nop_();t=P1;t=t^0xFF;t=t&amp;0xF0;if(t)break;j++;k=k&lt;&lt;1;}k=j*4+i;return k;}/*-----------------------------------------数字温度计驱动子程序--------------------------------------*/void ChangePos(bit sel,unsigned char pos1,unsigned char pos2){ unsigned char i;RST=0;DQ=0;CLK=0;RST=1;DQ=sel;_nop_();CLK=1;_nop_();CLK=0;for(i=0;i&lt;8;i++) {if(pos1&amp;0x80)DQ=1;elseDQ=0;_nop_();CLK=1;_nop_();CLK=0;pos1=pos1&lt;&lt;1; }for(i=0;i&lt;8;i++) {if(pos2&amp;0x80)DQ=1;elseDQ=0;_nop_();CLK=1;_nop_();CLK=0;pos2=pos2&lt;&lt;1;}RST=0;}/*------------------------------------------温度传感器子程序-------------------------------------------*/void Delay100ms() //延时100ms {unsigned char i,j,k;for(i=0;i&lt;8;i++)for(j=0;j&lt;25;j++)for(k=0;k&lt;250;k++);}void Delay15() //延时15us{unsigned char i;for(i=0;i&lt;8;i++);}void Delay60() //延时60us{unsigned char i;for(i=0;i&lt;30;i++);}void Write0TS() //写bit 0 {TSOR=1;TSOR=0;Delay15();Delay15();Delay15();Delay15();TSOR=1;_nop_();_nop_();}void Write1TS() //写bit 1 {TSOR=1;TSOR=0;_nop_();_nop_();_nop_();_nop_();_nop_();_nop_();_nop_();TSOR=1;_nop_(); _nop_();_nop_();_nop_();_nop_();_nop_();_nop_();Delay15();Delay15();Delay15(); }bit ReadTS() {bit b;TSOR=1;TSOR=0; _nop_();_nop_();_nop_();_nop_();TSOR=1;_nop_();_nop_();_nop_();_nop_();_nop_();b=TSOR;Delay15();Delay15();Delay15();_nop_();_nop_();return b;}void ResetTS() //复位{unsigned char i; TSOR=1;TSOR=0;for(i=0;i&lt;8;i++)Delay60();TSOR=1;while(TSOR);for(i=0;i&lt;8;i++)Delay60();}void WriteByteTS(unsigned char byte) //写一个字节(byte){unsigned char i;for(i=0;i&lt;8;i++){if(byte&amp;0x01)Write1TS();elseWrite0TS();byte=byte&gt;&gt;1;}}unsigned char ReadByteTS() //读一个字节(byte){unsigned char i,j;bit b;j=0;for(i=0;i&lt;8;i++){b=ReadTS();if(b)j+=1;j=_cror_(j,1);}return j;}void InitTS() //初始化温度转换{ResetTS();WriteByteTS(0xCC);WriteByteTS(0x4E);WriteByteTS(0x64);WriteByteTS(0x8A);WriteByteTS(0x1F);}void GetTempTS() //获取温度{ResetTS();WriteByteTS(0xCC);WriteByteTS(0x44);Delay100ms();ResetTS();WriteByteTS(0xCC);WriteByteTS(0xBE);temp2=ReadByteTS();temp1=ReadByteTS();ReadByteTS();ReadByteTS();ReadByteTS();ReadByteTS();ReadByteTS();ReadByteTS();ReadByteTS();temp1=temp1&lt;&lt;4;temp1+=(temp2&amp;0xF0)&gt;&gt;4;temp2=(temp2&amp;0x0F)?5:0;}液晶显示温度计程序。

51单片机多功能红外遥控电风扇(自然风+阵风+多档风速+定时)

51单片机多功能红外遥控电风扇(自然风+阵风+多档风速+定时)

51单片机多功能红外遥控电风扇(自然风+阵风+多档风速+定时)#include "AT89x051.H"#define uchar unsigned char#define uint unsigned int#define b1 0xe200#define b2 0xe210#define b3 0xe208#define b4 0xe218#define b5 0xe204#define b6 0xe214#define b7 0xe20c //阵风#define b8 0xe21c //自然风#define b9 0xe280 //自动档#define on_off 0xe240 //电源开关#define ch_a 0xe250 //加档#define ch_s oxe248 //减档#define time 0xe2e8 //定时#define louver 0xe24c //转页#define count_num 500 //显示次数#define time1_num 18000#define time2_num 100#define bell P3_4#define c_f 0xd4 //"F"#define c_h 0xce //"H"#define c_g 0x81 //"="uint time1=time1_num; //18000*100*2ms=1huchar time2=time2_num;uint count=count_num; //显示次数uchar sort=3; //显示offuchar dis_bit=0; //显示的位uchar code_length=16;uchar data dis[4]={0x02,0x02,0x00,0xff}; //显示数据区uchar temperature;uint code_t=0;uchar code1=0;uchar code2=0;bit bdata code_start=0; //代码起始标志bit bdata button=0; //无键按下bit bdata i_flag=0; // 有无中断标志bit bdata t_flag=0;//测温标志bit bdata bt=0; //判断是否是定时键bit bdata off=0; //为0无定时uchar code TAB[11]={0x5f,0x0a,0x9d,0x9b,0xca,0xd3,0xd7,0x5a,0xdf,0xdb,0x 75};void timer_0(void);void dis_t(void); //温度显示void dis_s(void); //档位显示void dis_h(void); //时间void dis_off(void); //关机显示void delay(uint t); //延时uchar d_code(uint t); //解码uchar begin=0; //开始补偿void c_code(void); //键号转换void off_time(void); //定时关void measure_temperature(void);void key_time(void); //定时按钮void sort_key(void); //风类按钮void mov_p1(uchar t0,t1,t2); //显示void button_process(void); //按键处理//********定时关机*********void off_time(void){if(off==1){if(time1--==0){time2--;time1=time1_num;}if(time2==0){dis[3]=dis[3]-1;time2=time2_num;}if(dis[3]==0){code_t=on_off; //关机c_code();}}}//********定时器0中断********* void timer0() interrupt 1 using 2 {off_time();if(dis_bit==0&&t_flag==0){key_time();sort_key();}switch(sort){case 0:if(count!=0){mov_p1(dis[0],dis[1],TAB[10]); //显示温度count--;}break;case 1:if(count!=0){mov_p1(c_f,c_g,TAB[dis[2]]); //显示档位count--;}break;case 2:if(count!=0){dis_h(); //显示时间count--;}break;case 3:mov_p1(0x5f,c_f,c_f);//显示关机default:break;}timer_0();if(count==0) //轮流显示{P3_0=P3_1=P3_5=1;if(i_flag==0&&t_flag==0) measure_temperature();count=count_num;sort=(sort&0x03)+1;if(sort>=3)sort=0; //完成一轮显示}}//***********定时按钮************ void key_time(void){bit i=P1_2;P1_2=1;if(P1_2==0){delay(50);if(P1_2==0) //确认有按键{bell=0;delay(100);bell=1;while(P1_2==0){;}if(dis[3]==0xff){dis[3]=1;off=0; //取反后为1,定时}else{if(dis[3]<9){dis[3]=dis[3]+1;off=0; //取反后为1,定时}elseoff=1; //取反后为0,取消定时}sort=2;code_t=time; //显示时间c_code();//bt=0; //恢复}}P1_2=i;i_flag=0; //恢复执行其它任务}//***********换档按钮************ void sort_key(void){bit i=P1_1;P1_1=1;if(P1_1==0){delay(50);if(P1_1==0){button=1;bell=0;delay(200);bell=1;while(P1_1==0){;}if(dis[2]<9){dis[2]=dis[2]+1;code2=dis[2];}else{dis[2]=0;code2=10; //power off}delay(100);sort=1;count=5000;//TF0=1;}}P1_1=i;i_flag=0; //恢复执行其它任务}//********定时器1中断测温************ void timer1() interrupt 3 using 3{uint temp;TR0=0; //计数停TR1=0; //定时停temp=TH0*256+TL0; //取温度值temperature=(7000-temp)/11; //计算温度//if(dis[2]!=0)// temperature--; //工作时补偿1度/*if(F0==0&&begin<=10) //开始温度加3度temperature+=3;if(F0==0&&begin<=60&&begin>10) temperature+=2;if(F0==0&&begin<=150&&begin>60) temperature+=1;*/dis[0]=TAB[temperature/10];dis[1]=TAB[temperature%10];IE0=0;t_flag=0;timer_0();EX0=1;}//**********判断代码************ uchar d_code(uint t){if(t<=0x220&&t>=0x190)return 0;else{if(t<=0x430&&t>=0x390)return 1;elsereturn 0xff;}}//***********键号转换************ void c_code(void){bit bdata i=0;switch(code_t){case b1:code1=1;break;case b2:code1=2;break;case b3:code1=3;break;case b4:code1=4;break;case b5:code1=5;break;case b6:code1=6;break;case b7:code1=7;break;case b8:code1=8;break;case b9:code1=9;break;case on_off:code1=10; //关机dis[3]=0xff;//#####标志复位############ button=0; //无键按下i_flag=0; // 无中断标志bt=0; //无定时键按下off=0; //无定时time1=time1_num; //定时初值复位time2=time2_num;count=count_num; //显示次数break;case time:off=~off;if(off==0)dis[3]=0xff; //取消定时i=1;bt=1;count=5000; //延长显示sort=2; //显示时间TF0=1;break;case louver:P3_3=~P3_3;code1=code2;break;default:code1=0;break;}if(bt==1&&i==0) //装载代码{if(code1<9) //定时最大9h {dis[3]=code1;bt=0;}}elseif(i==0){code2=code1;count=5000; //延长显示if(code1==10){dis[2]=0; //F=0sort=3; //显示关机}else{dis[2]=code1;sort=1; //显示风类}TF0=1;}}//*********** 接收代码中断 ************void receive_code() interrupt 0 using 1{uint temp,i;ET0=0;i_flag=1; //暂停其它任务if(TR1==0){TR1=0;TMOD=0x11;TH1=TL1=0;TR1=code_start=1;}else{TR1=code_start=0;temp=TH1*256+TL1;if((d_code(temp)==0||d_code(temp)==1)&&code_length!=0) {TH1=TL1=0;TR1=code_start=1;code_t=(code_t<<1)+d_code(temp);code_length--;}else{if(code_length==0&&((code_t&0xff00)==0xe200)) //除掉误码{code_length=16;bell=0; //正确收到,响声提示c_code(); //转换代码for(i=0;i<6000;i++){EX0=0;P3_0=P3_1=P3_5=1;if(i>800)bell=1;IE0=0;if(P3_2==0)i--;button=1; //有按键需要处理}i_flag=0; //恢复执行其它任务}else //误码{code_length=16;for(i=0;i<6000;i++){IE0=0;if(P3_2==0)i--;i_flag=0; //恢复执行其它任务}}timer_0();EX0=1;}}}//***********显示代码送P1口************ void mov_p1(uchar t0,t1,t2){switch(dis_bit){case 0:P1=t0;P3_1=P3_5=1;P3_0=0;dis_bit=1;break;case 1:P1=t1;P3_0=P3_5=1;P3_1=0;dis_bit=2;break;P1=t2;P3_1=P3_0=1;P3_5=0;dis_bit=0;break;}}//***********显示定时时间************ void dis_h(void){switch(dis_bit){case 0:P1=c_h; //"H"P3_1=P3_5=1;P3_0=0;dis_bit=1;break;case 1:P1=c_g; //"="P3_0=P3_5=1;P3_1=0;dis_bit=2;break;case 2:if(dis[3]>10) //无定时P1=TAB[0]; //显示H=0elseP1=TAB[dis[3]];P3_1=P3_0=1;P3_5=0;dis_bit=0;break;}}//********定时器0************ void timer_0(void){TMOD=0x01; //T0定时方式1 TR0=0;TH0=0xfc;TL0=0x55; //2ms ET0=1;TR0=1;}//*********** 延时 ************ void delay(uint t){uint i,j;for(i=0;iif(button==0)for(j=0;j<10;j++);}//*********** 测温度 ************void measure_temperature(void){t_flag=1;ET1=1;EX0=0;ET0=0;TMOD=0x15; //T0计数方式1,T1定时方式1 TH1=0x3c;TL1=0xb0; //置初值100msTH0=0x00;TL0=0x00; //清零TR0=1; //计数开始TR1=1;}//***********风速 ************void s1(void){P3_7=0;}void s2(void){P3_7=0;delay(230);P3_7=1;delay(25);}void s3(void){P3_7=0;delay(180); P3_7=1; delay(40);}void s4(void) {P3_7=0; delay(130); P3_7=1; delay(40);}void s5(void) {P3_7=0; delay(90);P3_7=1; delay(40);}void s6(void) {P3_7=0; delay(50);P3_7=1; delay(50);}void gust(void) //阵风{uchar i,j;if(button==1) //中止任务j=255;elsej=0;//P3_7=0;//delay(5000);for(i=j;i<50;i++)s6();P3_7=0;delay(5000);for(i=j;i<25;i++)s2();for(i=j;i<35;i++)s3();for(i=j;i<25;i++)s5();delay(6000);}void natural(void) //自然风{uchar i;uchar code *p; //随机数for(i=0;i<100;i++){if(button==0) //有键按下,中止当前任务{P3_7=0;delay((*p++)*8); //放大P3_7=1;if(*p<10)delay(7000); //低速档时间补偿elsedelay(300);}}}void automation(void) //自动档{if(temperature<=29)s6();elseif(temperature<=30)gust();elseif(temperature==31)s5();elseif(temperature==32)s4();elseif(temperature<=33)s3();if(temperature==34)s2();elses1();}//***********按键处理 ************ void button_process(void){button=0;switch(code2){case 1:s1();break;case 2:s2();break;case 3:s3();break;case 4:s4();break;case 5:s5();break;case 6:s6();case 7:gust();break;case 8:natural();break;case 9:automation();break;case 10:P3_7=1; //关风扇P3_3=1; //关转页break;default:break;}}//********************************** //***********主程序开始 ************ //**********************************void main(void){EA=1;IT0=1; //边沿触发EX0=1; //外部中断0允许measure_temperature();delay(1000);timer_0();while(1){if(F0==0&&begin<255) begin++;elseF0=1;button_process();}}。

基于51单片机的智能温控风扇系统的设计

基于51单片机的智能温控风扇系统的设计

基于51单片机的智能温控风扇系统的设计题目:基于51单片机的智能温控风扇系统的设计一、需求分析在炎热的夏天人们常用电风扇来降温,但传统电风扇多采用机械方式进行控制,存在功能单一,需要手动换挡等问题。

随着科技的发展和人们生活水平的提高,家用电器产品趋向于自动化、智能化、环保化和人性化,使得智能电风扇得以逐渐走进了人们的生活中。

智能温控风扇可以根据环境温度自动调节风扇的启停与转速,在实际生活的使用中,温控风扇不仅可以节省宝贵的电资源,也大大方便了人们的生活。

二、系统总体设计1、硬件本系统由集成温度传感器、单片机、LED数码管、及一些其他外围器件组成。

使用89C52单片机编程控制,通过修改程序可方便实现系统升级。

系统的框图结构如下:图1-1硬件系统框图其中,单片机为STC89C52,这个芯片与我开发板芯片相同,方便拷进去程序。

晶振电路和复位电路为单片机最小系统通用设置,温度采集电路,使用的是DS18B20芯片,数码管使用的是4位共阳数码管,风扇驱动芯片使用的是L298N,按键为按钮按键,指示灯为发光二级管。

2、软件要实现根据当前温度实时的控制风扇的状态,需要在程序中不时的判断当前温度值是否超过设定的动作温度值范围。

由于单片机的工作频率高达12MHz,在执行程序时不断将当前温度和设定动作温度进行比较判断,当超过设定温度值范围时及时的转去执行超温处理和欠温处理子程序,控制风扇实时的切换到关闭、低速、高速三个状态。

显示驱动程序以查七段码取得各数码管应显数字,逐位扫描显示。

主程序流程图如图4-1所示。

图1-2软件系统框图这是该系统主程序的运行流程,当运行时,程序首先初始化,然后调用DS18B20初始化函数,然后调用DS18B20温度转换函数,接着调用温度读取函数,到此,室内温度已经读取,调用按键扫描函数这里利用它设置温度上下限,然后就是调用数码管显示函数,显示温度,之后调用温度处理函数,再调用风扇控制函数使风扇转动。

基于51单片机的智能温控风扇设计各部块的设计

基于51单片机的智能温控风扇设计各部块的设计

基于51单片机的智能温控风扇设计各部块的设计智能温控风扇是一种能够自动根据温度变化调节风扇转速的风扇,其应用广泛,如家庭、办公室、工业生产等。

本文主要介绍基于51单片机实现智能温控风扇的各部分设计。

一、传感器模块设计温度传感器是实现智能控制的重要模块。

常用的温度传感器有NTC、PTC、热电偶、DS18B20等。

这里选用DS18B20数字温度传感器。

其具有精度高、反应速度快、与单片机通信简单等优点。

将DS18B20以三线方式连接至单片机,通过调用它的相关函数来读取温度值。

二、风扇驱动模块设计风扇驱动模块是指控制风扇正反转的电路。

这里选用H桥驱动芯片L298N。

它可以控制直流电动机、步进电机等多种负载的正反转,具有过流保护、过温保护等功能。

将H桥驱动芯片通过引脚连接至单片机,通过编写控制程序,实现控制风扇的正反转及转速控制。

三、单片机模块设计单片机模块是整个系统的控制中心,它通过编写程序控制温度传感器和风扇驱动芯片实现智能控制。

这里选用常用的STC89C52单片机,具有较强的通用性和高性价比。

编写的程序主要实现以下功能:1. 读取温度值并进行比较,根据温度值控制风扇的启停及转速。

2. 设置风扇的最低速度和最高速度。

3. 实现温度设置功能,用户可通过按钮设置所需的温度值。

4. 实现显示屏幕功能,将当前温度值及系统状态等信息显示在屏幕上。

四、供电模块设计供电模块是系统的电源模块,它通过转换器将交流电转化为所需的直流电。

为保证系统稳定工作,供电模块应具有过载保护、过压保护、过流保护等功能。

五、外壳设计外壳设计是将控制模块和风扇固定在一起,并起到保护作用的模块。

可采用塑料或金属等材质制作外壳,将控制模块、风扇和电源线等固定在外壳内部。

外壳应符合美观、实用及安全的设计原则。

以上是基于51单片机的智能温控风扇设计各部块的相关参考内容,其中传感器模块、风扇驱动模块、单片机模块、供电模块及外壳设计五个部分是实现智能温控风扇的核心部分。

51单片机的温度和时间显示源程序

51单片机的温度和时间显示源程序
}
}
uintget_tem()
{
uchartem_L,tem_H;
DS18B20_init();
delay(1);
temwritebyte(0xcc); //写跳过ROM指令;
temwritebyte(0xbe); //读数据
tem_L=temreadbyte();
tem_H=temreadbyte();
write_1602dat('E');
break;
case 3:write_1602dat('W'); //星期数据为3时显示
write_1602dat('E');
write_1602dat('D');
break;
case 4:write_1602dat('T'); //星期数据为4是显示
write_1602dat('H');
tem=tem_H<<8|tem_L;
f_tem=tem*0.0625;
tem=f_tem;//*10+0.5;****好啊家0.5缩小误差;
return (tem);
}
/********液晶写入指令函数与写入数据函数,以后可调用**************/
write_1602com(ucharcom) //****液晶写入指令函数****
dat=0;
for(i=0;i<8;i++)
{
j=temreadbit() ;
dat=;
}
return(dat);
}
voidtemwritebyte(ucharinstru)

基于51单片机智能温控风扇的系统设计

基于51单片机智能温控风扇的系统设计
关键词:温控风扇;单片机;计说明书
目录 第 1 章 引 言.................................................................................................... 5
3
张家界航空工业职业技术学院毕业设计说明书
5.2.2 传感器 DS18B20 温度采集部分调试........................................ 23 5.2.3 电动机调速电路部分调试........................................................ 23 5.3 系统功能............................................................................................... 23 5.3.1 系统实现的功能........................................................................ 23 5.3.2 系统功能分析............................................................................ 24 5.4 故障分析............................................................................................... 24 5.4.1 按键显示部分............................................................................ 24 5.4.2 传感器 DS18B20 温度采集部分................................................ 25 第 6 章 产品使用说明...................................................................................... 26 6.1 功能描述............................................................................................... 26 6.2 使用说明............................................................................................... 26 第 7 章 心得体会.............................................................................................. 28 致 谢.................................................................................................................. 29 参 考 文 献........................................................................................................ 30 附 录.................................................................................................................... 31 附件一:总原理图:............................................................................................ 31 附件二:元件清单.............................................................................................. 32 附件三:安装接线图.......................................................................................... 33 附件四:装配图.................................................................................................. 34 附件五:主要程序代码...................................................................................... 35
  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
unsigned char idata TMP_d;
unsigned char f;
unsigned char rd_ds18_1();
unsigned int TemH,TemL;
unsigned int count;
void delay()
{
unsigned int c;
c=50;
while(c--){}
unsigned char code b[80]={
//0
0x60,
0x90,
0x90,
0x90,
0x90,
0x90,
0x90,
0x60,
//1
0x20,
0x60,
0x20,
0x20,
0x20,
0x20,
0x20,
0x20,
//2
0x60,
0x90,
0x10,
0x10,
0x20,
0x40,
0x80,
{
q=0;
w=1;
e=1;
r=0;
delay1(1);
a=0;
delay1(20);
flag2=1;
}
}
if(P1_2==1)
{
delay();
if(P1_2==1)
{
flag2=0;
a=1;
}
}
if(P1_3==0&&flag3==0)
{
delay();
if(P1_3==0&&flag3==0)
{
DQ1=1;
return;
}
void check_pre_1(void)
{
while(DQ1);
while(~DQ1);
time_delay(30);
}
void read_ROM(void)
{
int n;
ds_reset_1();
check_pre_1();
wr_ds18_1(0x33);
for(n=0;n<8;n++){ROM[n]=rd_ds18_1();}
unsigned char rd_ds18_1()
{
unsigned char idata i,j,dat=0;
for(i=1;i<=8;i++)
{
j=tmrbit_1();
dat=(j<<(i-1))|dat;
}
return dat;
}
/*****************************************************/
/* write a bety from ds18b20写字节*/
/****************************************************/
void wr_ds18_1(char dat)
{
signed char idata i=0;
unsigned char idata j;
}
/*****************************************************/
/* Read a bit from 1820位读取*/
/*****************************************************/
bit tmrbit_1(void)
/* reset ds18b20 */
/*****************************************************/
void ds_reset_1(void)
{
unsigned char idata count=0;
DQ1=0;
time_delay(240);
time_delay(240);
}
/***************延时程序,单位us,大于10us*************/
void time_delay(unsigned char time)
{
time=time-10;
time=time/6;
while(time!=0)time--;
}
/*****************************************************/
bit testb;
for(j=1;j<=8;j++)
{
testb=dat & 0x01;
dat = dat>>1;
if(testb)
{
DQ1=0;
_nop_();
_nop_();
DQ1=1;
time_delay(60);
}
else
{
DQ1=0;
time_delay(50);
DQ1=1;
_nop_();
void delay1(unsigned int z);
bit flag=0,flag1=0,flag2=0,flag3=0,flag4=0,flag5=0;//包含头文件
#define BUSY1 (DQ1==0)//定义busy信号
//打开本定义为显示笑脸(默认打开),注意b数组不可以重复定义,打开一组,应该关闭前一组
0x80,
0xF0,
0x90,
0x90,
0x60,
//7
0xF0,
0x10,
0x10,
0Hale Waihona Puke 20,0x40,0x40,
0x40,
0x40,
//8
0x60,
0x90,
0x90,
0x60,
0x90,
0x90,
0x90,
0x60,
//9
0x60,
0x90,
0x90,
0x90,
0x70,
0x10,
0x90,
0x60
if(P1_1==0&&flag1==0)
{
q=0;
w=1;
e=0;
r=1;
delay1(1);
a=0;
delay1(20);
flag1=1;
}
}
if(P1_1==1)
{
delay();
if(P1_1==1)
{
flag1=0;
a=1;
}
}
if(P1_2==0&&flag1==0)
{
delay();
if(P1_2==0&&flag1==0)
0xF0,
//30
0x60,
0x90,
0x10,
0x60,
0x10,
0x10,
0x90,
0x60,
//4
0x10,
0x20,
0x60,
0xA0,
0xA0,
0xF0,
0x20,
0x20,
//5
0xF0,
0x80,
0x80,
0xE0,
0x10,
0x10,
0x90,
0x60,
//6
0x60,
0x90,
0x80,
time_delay(255);
ds_reset_1();
}
void ds_getT(void)
{
wr_ds18_1(0xcc);
wr_ds18_1(0xbe);
TemH=get_temp_1();
TemL=get_temp_d();
TemH&=0x00ff;
TemL&=0x00ff;
count=(TemH*256+TemL)*6.25;
/*
必要操作:正确连接点阵到学习板
*/
#include "INTRINS.H"
#include <AT89X52.H>
sbit a=P3^4; //蜂鸣器
sbit q=P3^6;//总开关
sbit w=P3^3; //三档
sbit e=P3^2;//二档
sbit r=P3^1;//一档
sbit t=P1^7;//摇头
q=1;
w=1;
e=1;
r=1;
t=1;
delay1(1);
a=0;
delay1(20);
flag3=1;
}
}
if(P1_3==1)
{
delay();
if(P1_3==1)
{
flag3=0;
a=1;
}
}
//if(P1_4==0&&flag4==0)
//{
//delay();
// if(P1_4==0&&flag4==0)
q=1;
w=1;
e=1;
r=1;
delay1(2000);
q=0;
w=1;
e=1;
r=0;
delay1(2000);
//flag4=1;
}
//}
//if(P1_4==1)
//{
// delay();
//if(P1_4==1)
//{
//flag4=0;
//a=1;
// }
// }
if(P1_5==0&&flag5==0)
{
dis[j]=b[(TemH/10%10)*8+j]|(b[(TemH%10)*8+j]>>4);
}
for(i=0;i<8;i++)//点阵8列动态扫描法显示,每次扫描一列并发送数据码
相关文档
最新文档