|
仿真 代碼 原理圖 PCB實(shí)物已設(shè)計(jì)整理好!各位下載可直接使用
這是本人做的關(guān)于51單片機(jī)的一個(gè)小設(shè)計(jì),主要將論壇里的溫度報(bào)警器和計(jì)算器代碼進(jìn)行了整合,簡單的說可以當(dāng)做計(jì)算器使用也可以當(dāng)做溫度報(bào)警器使用。PCB也對各個(gè)版本進(jìn)行了優(yōu)化,原理圖劃分了功能塊方便看不懂的小伙伴,這主要針對一些不會做手工PCB的小伙伴,而且現(xiàn)在立創(chuàng)和捷配的打樣活動也比自己手工做PCB成本低很多,鑒于能白嫖就白嫖的原則,請大家不要錯(cuò)過。
功能簡單介紹:
一、溫度報(bào)警器功能
插電后打開開關(guān)(開關(guān)可直接短接)初始化完成后LCD1602第一行居中顯示實(shí)時(shí)溫度,第二行顯示HT:60 LT:2表示默認(rèn)設(shè)置的溫度上限以及下限,若溫度超過上限或者低于下限值,對應(yīng)led發(fā)光以提示用戶。按下k2鍵,可進(jìn)入溫度報(bào)警器的設(shè)置模式,此時(shí)lcd顯示屏幕上第一行最末尾出現(xiàn)H或者L,表示此時(shí)可按K3,K4對對應(yīng)的HT或者LT的上下限值進(jìn)行加減來改變報(bào)警閾值,并且這三個(gè)按鍵按下時(shí)蜂鳴器會有響聲提醒。
二、計(jì)算器功能
按下K1鍵可切換為計(jì)算器模式,此時(shí)矩陣鍵盤生效,lcd顯示屏幕清空,進(jìn)入計(jì)算器模式,矩陣鍵盤上PCB絲印字體對應(yīng)按鍵按下的值。其余不多做解釋,按照正常計(jì)算器玩法操作。再按下K1鍵可切換回溫度報(bào)警器模式。
代碼篇幅有限,這里不做介紹,上傳文件中可自行查閱。有其他建議聯(lián)系我哈。
制作出來的實(shí)物圖如下:
Altium Designer畫的原理圖和PCB圖如下:(51hei附件中可下載工程文件)
原理圖
單片機(jī)源程序如下:
- /*******************************************************************************
- * 標(biāo)題: LCD1602簡易計(jì)算器 *
- * *
- * 實(shí)驗(yàn)說明:1602簡易計(jì)算器,可以實(shí)現(xiàn)四位數(shù)以內(nèi)的加減乘除, *
- ********************************************************************************
- * 實(shí)驗(yàn)心得:當(dāng)內(nèi)部ram不夠用的時(shí)候,可以定義成xdata,使用外部ram,但是有一個(gè)問題*
- 就是在用proteus仿真的時(shí)候,如果有xdata的代碼,可能仿真會出現(xiàn)點(diǎn)問題,因?yàn)閜eoteus*
- 不支持外部擴(kuò)展ram *
- ********************************************************************************/
- #include<reg52.h>
- #include"lcd.h"
- #include"math.h"
- #include"temp.h"
- #include"intrins.h"
- //--定義使用的IO口--//
- #define GPIO_KEY P1
- sbit K_set=P3^3;
- sbit K_up=P3^5;
- sbit K_down=P3^6;
- sbit bee_key=P3^7;
- sbit ledL=P2^3;
- sbit ledH=P2^4;
- unsigned char setting_flag=0,up_flag=0,down_flag=0;
- //--定義全局變量--//
- unsigned char code XuJian[16]="01470258=369+-x/";
- long value[16];
- unsigned char Num[8];//此處寫成unsigend char xdata Num[8]時(shí),實(shí)物可以用,但是仿真有點(diǎn)問題,因?yàn)閜roteus不支持外部擴(kuò)展ram.
- unsigned long result;//運(yùn)算結(jié)果
- unsigned int flag=0;//標(biāo)志位
- unsigned int m;
- unsigned int c=0;
- long First=0;//輸入的第一位數(shù)
- long Second=0;//輸入的第二位數(shù)
- unsigned int Key;//符號判斷,如果key=12,為+,13,為-,14為×,15為/。
- unsigned char KeyValue=-1;
- //用來存放讀取到的鍵值
- //--聲明全局函數(shù)--//
- int KeyScan(void);//鍵值判斷函數(shù)
- void Delay10ms(unsigned int c); //誤差 0us
- void RES();//結(jié)果運(yùn)算函數(shù)
- //
- //模式切換標(biāo)致
- unsigned char moshi_flag=0,temp_max=60,temp_min=2,lcd_flag=0;
- unsigned int temp=0;
- uchar code Init1[]=" DB:000 "; //初始化時(shí)1行顯示
- uchar code Init2[]=" HT:000 LT:000 "; //初始化時(shí)2行顯示
- void Init1602_temp()
- {
- uchar i=0;
- LcdWriteCom(0x38);//屏幕初始化
- LcdWriteCom(0x0c);//打開顯示 無光標(biāo) 無光標(biāo)閃爍
- LcdWriteCom(0x06);//當(dāng)讀或?qū)懸粋€(gè)字符是指針后一一位
- LcdWriteCom(0x01);//清屏
- LcdWriteCom(0x80);//設(shè)置位置
- for(i=0;i<16;i++)
- {
- LcdWriteData(Init1[i]); //1行初始化顯示
- }
- LcdWriteCom(0x80+0x40);
- for(i=0;i<16;i++)
- {
- LcdWriteData(Init2[i]);//2行初始化顯示
- }
- }
- //顯示實(shí)時(shí)溫度
- void display_temp(unsigned int temp)
- {
- unsigned char a,b,c;
-
- a=temp/1000%10;
- b=temp/100%10;
- c=temp/10%10;
-
- LcdWriteCom(0x80+7);
- LcdWriteData(a+0x30);
- LcdWriteData(b+0x30);
- LcdWriteData('.');
- LcdWriteData(c+0x30);
- }
- //顯示溫度上下限
- void display_temp_M(unsigned char temp_max,unsigned char temp_min)
- {
- unsigned char a,b,c;
- a=temp_max/100;
- b=temp_max/10%10;
- c=temp_max%10;
- LcdWriteCom(0x80+0x40+5);
- LcdWriteData(a+0x30);
- LcdWriteData(b+0x30);
- LcdWriteData(c+0x30);
- a=temp_min/100;
- b=temp_min/10%10;
- c=temp_min%10;
- LcdWriteCom(0x80+0x40+12);
- LcdWriteData(a+0x30);
- LcdWriteData(b+0x30);
- LcdWriteData(c+0x30);
- }
- void Delay500us() //@11.0592MHz
- {
- unsigned char i, j;
- _nop_();
- _nop_();
- i = 6;
- j = 93;
- do
- {
- while (--j);
- } while (--i);
- }
- void bee_anjian(unsigned int c )
- {
- unsigned char a, b;
- bee_key=0;
- //--c已經(jīng)在傳遞過來的時(shí)候已經(jīng)賦值了,所以在for語句第一句就不用賦值了--//
- for (;c>0;c--)
- {
- bee_key=!bee_key;
- Delay500us();
-
- }
- bee_key=0;
- }
- void temp_scan()//按鍵掃描
- { unsigned char dis_play_flag=0;
- if(K_set==0) //判斷設(shè)置是否按下
- {
- Delay10ms(1);
- if(K_set==0)
- { bee_key=0;
- setting_flag=setting_flag+1;
- dis_play_flag=1;
- if(setting_flag>2)
- {setting_flag=0;}
- // bee_anjian(100);
- //bee_anjian(100);
- Delay10ms(50);
-
- }
- }
- if(dis_play_flag)
- {
-
- if(setting_flag==1)
- {
- LcdWriteCom(0x80+15);
- LcdWriteData('H');
- }
- else if(setting_flag==2)
- {
- LcdWriteCom(0x80+15);
- LcdWriteData('L');
- }
- else
- {
- LcdWriteCom(0x80+15);
- LcdWriteData(' ');
- }
- dis_play_flag=0;
-
- }
- if(setting_flag) //設(shè)置按下
- {
- if(K_up==0)
- {
- Delay10ms(1);
- if(K_up==0)
- {
- bee_key=0;
- up_flag=1;
- }
- }
- }
- if(setting_flag)
- {
- if(K_down==0)
- {
- Delay10ms(1);
- if(K_down==0)
- {
- bee_key=0;
- down_flag=1;
- }
- }
- }
- if(up_flag==1)
- {
- if(setting_flag==1)
- {
- temp_max=temp_max+1;
- if(temp_max>99)
- {temp_max=99;}
- display_temp_M(temp_max,temp_min);
-
- // bee_anjian(50);
- //bee_anjian(100);
- Delay10ms(50);
- up_flag=0;
- }
- else if(setting_flag==2)
- {
- temp_min=temp_min+1;
- if(temp_min>99)
- {temp_min=99;}
- display_temp_M(temp_max,temp_min);
- // bee_anjian(50);
- //bee_anjian(100);
- Delay10ms(50);
- up_flag=0;
- }
- }
- if(down_flag==1)
- {
- if(setting_flag==1)
- {
- temp_max=temp_max-1;
- if(temp_max<1)
- {temp_max=1;}
- display_temp_M(temp_max,temp_min);
- Delay10ms(50);
- // bee_anjian(100);
- down_flag=0;
- }
- else if(setting_flag==2)
- {
- temp_min=temp_min-1;
- if(temp_min<1)
- {temp_min=1;}
- display_temp_M(temp_max,temp_min);
- Delay10ms(50);
- //bee_anjian(100);
- down_flag=0;
- }
- }
- bee_key=1;
- }
- //中斷函數(shù)初始化
- void Init_INT()
- {
- IT0 = 1; //設(shè)置為下降沿觸發(fā)
- EX0 = 1; //外部中斷0中斷允許位
- EA = 1;
- }
- void EX0_ISR(void) interrupt 0 //中斷服務(wù)函數(shù)的書寫格式
- {
-
- moshi_flag=!moshi_flag;
- lcd_flag=moshi_flag+1;
-
-
- }
- /*******************************************************************************
- * 函 數(shù) 名 : main
- * 函數(shù)功能 : 主函數(shù)
- * 輸 入 : 無
- * 輸 出 : 無
- *******************************************************************************/
- void main(void)
- {
- LcdInit();
- // for(i=0;i<7;i++)
- // {
- // LcdWriteData(TiShi[i]);
- // }
- Init_INT();//開啟外部中斷
- Init1602_temp();
- bee_anjian();
- while(1)
- {
- if(lcd_flag==1)
- {
- Init1602_temp();
- lcd_flag=0;
- }
- else if(lcd_flag==2)
- {
- LcdInit();
- lcd_flag=0;
- }
- if(moshi_flag==1)
- {
- KeyValue=KeyScan();
- switch(KeyValue)
- {
- case(0):
- LcdWriteCom(0x01);
- KeyValue=-1;
- First=0;
- Second=0;
- c=0;
- break;
- case(1):
- if(flag==0)//flag為0時(shí),正常計(jì)算
- {
- LcdWriteData(XuJian[1]);
- KeyValue=-1;
- if(c==0)
- First=10*First+1;
- else if(c==1)
- Second=10*Second+1;
- }
- else if(flag==1)//flag為1時(shí),可以在第一次運(yùn)算好后,繼續(xù)輸入數(shù)字,開始第二次計(jì)算
- {
- LcdWriteCom(0x01);
- LcdWriteData(XuJian[1]);
- KeyValue=-1;
- First=0;
- Second=0;
- c=0;
- flag=0;
-
- ................限于篇幅代碼請下載附件................
- do
- {
- value[i]=result%10;
- result/=10;
- i++;
- }while((result/10)!=0);
- value[i]=result;
- m=i;
- for(j=0;j<=i;j++) //for循環(huán)如果是for(j=i;j>=0;j++)就會出現(xiàn)不同的結(jié)果,很奇怪
- {
- Num[j]=value[j]+'0';
- }
- for(i=0;i<=m;i++)//這里的for循環(huán)也是和上面一樣的結(jié)果,改成for(i=m;i>=0;i--)就會出現(xiàn)奇怪的結(jié)果,有興趣的可以試試。
- {
- LcdWriteData(Num[m-i]);
- }
-
- }
- /*******************************************************************************
- * 函 數(shù) 名 : KeyScan
- * 函數(shù)功能 : 檢測有按鍵按下并讀取鍵值
- * 輸 入 : 無
- * 輸 出 : 無
- *******************************************************************************/
- int KeyScan(void) //測試行(row)的時(shí)候就是線是豎著的的那一列為1,測試列(col)的時(shí)候就是線是橫著的那幾行為1
- {
- char a = 0;
- GPIO_KEY=0x0f;
- if(GPIO_KEY!=0x0f)//讀取按鍵是否按下
- {
- Delay10ms(1);//延時(shí)10ms進(jìn)行消抖
- if(GPIO_KEY!=0x0f)//再次檢測鍵盤是否按下
- {
-
- //測試列
- GPIO_KEY=0X0F;
- switch(GPIO_KEY)
- {
- case(0X07): KeyValue=0;break;
- case(0X0b): KeyValue=4;break;
- case(0X0d): KeyValue=8;break;
- case(0X0e): KeyValue=12;break;
- }
- //測試行
- GPIO_KEY=0XF0;
- switch(GPIO_KEY)
- {
- case(0X70): KeyValue=KeyValue+3;break;
- case(0Xb0): KeyValue=KeyValue+2;break;
- case(0Xd0): KeyValue=KeyValue+1;break;
- case(0Xe0): KeyValue=KeyValue;break;
- }
- while((a<50) && (GPIO_KEY!=0xf0)) //檢測按鍵松手檢測
- {
- Delay10ms(1);
- a++;
- }
- }
- }
- return KeyValue;
- }
- /*******************************************************************************
- * 函 數(shù) 名 : Delay10ms
- * 函數(shù)功能 : 延時(shí)函數(shù),延時(shí)10ms
- * 輸 入 : 無
- * 輸 出 : 無
- *******************************************************************************/
- void Delay10ms(unsigned int c) //誤差 0us
- {
- unsigned char a, b;
- //--c已經(jīng)在傳遞過來的時(shí)候已經(jīng)賦值了,所以在for語句第一句就不用賦值了--//
- for (;c>0;c--)
- {
- for (b=38;b>0;b--)
- {
- for (a=130;a>0;a--);
- }
- }
- }
復(fù)制代碼
所有資料51hei提供下載:
溫度報(bào)警加簡易計(jì)算器資料.7z
(3.52 MB, 下載次數(shù): 79)
2021-4-4 04:21 上傳
點(diǎn)擊文件名下載附件
|
評分
-
查看全部評分
|