前言:作者想要帮助一些童鞋和爱好者进行项目构建,但自知能力有限,不喜可论,创作不易,勿喷。
系统采用STC12C5A60S2芯片进行的单片机恒温箱,能够实现恒温加热,超温报警。上代码。
main.c
#include#include uchar cp,cp1,cp2,cp3,mode=0,sec,min,hour,mode1=0; uchar temp,ad0,temp_x; unsigned char TL=0,TH=0,TD=0,TN=0,count; #include <18b20.c> uchar bit0=0,bit1=0,bit2=0,bit3=0,flag=0; #include "key.c" //uint T0_H,T0_L,T1_H,T1_L; #include void Timer_isr(void)interrupt 1 { TH0 =64535/256; TL0 =64535%256; cp++; if(cp >= 250) { cp = 0; cp1++; key(); ReadTemp(); if(cp1 >= 240)//min 240=1min { cp1 = 0; min++; if(min >= 2) { min = 0; if(bit0 == 1)bit0 = 0; if(bit1 == 1)bit1 = 0; if(bit2 == 1)bit2 = 0; if(bit3 == 1)bit3 = 0; } } } } void Timer_Init() { TMOD = 0x01; TH0 =64535/256; TL0 =64535%256; TR0 = 1; ET0 = 1; EA =1; } void T_mode() { if(flag == 0) { // mode1 = 0; cp1 = 0; flag = 1; bit0 = 1; } if(bit0 == 0){ if(flag == 1) { // mode1 = 1; cp1 = 0; flag = 2; bit1 = 1; } if(bit1 == 0){ if(flag == 2) { // mode1 = 2; cp1 = 0; flag = 3; bit2 = 1; } if(bit2 == 0){ if(flag == 3) { cp1 = 0; flag = 4; bit3 = 1; } if(bit3 == 0){ flag = 0; mode = 0; } } } } } void temp_mode(uchar aa,bb,cc,dd) { if( bit0 == 1) { if(TN > aa) P20 = 0; if(TN <= aa) P20 = 1; } if( bit1 == 1) { if(TN > bb) P20 = 0; if(TN <= bb) P20 = 1; } if( bit2 == 1) { if(TN > cc) P20 = 0; if(TN <= cc) P20 = 1; } if( bit3 == 1) { if(TN > dd) P20 = 0; if(TN <= dd) P20 = 1; } } void main() { Timer_Init(); init_1602(); LCD_clr1602(); delayus(20); // ReadTemp(); while(1) { if(mode == 0)P20= 0; else T_mode(); if(mode == 1)temp_mode(100,90,80,70); if(mode == 2)temp_mode(90,80,70,60); if(mode == 3)temp_mode(80,70,60,50); if(mode == 4)temp_mode(70,60,50,40); display(); } }
DS1602.c
#define uchar unsigned char
#define uint unsigned int
sbit RS = P2^5;//数据/命令
sbit RW = P2^6;//读/写
sbit E = P2^7;//使能
uchar i;
uchar str[] = {"Internet of Things00"};
uchar num[] = {"0123456789"};
void delayus(uint x) //延时函数
{
while(x--);
}
void write_com(uchar com)//写命令
{
RW = 0;
RS = 0;
E = 1;
P0 = com;
delayus(100);
E = 0;
}
void write_data(uchar da)//写入数据
{
RW = 0;
RS = 1;
E = 1;
P0 = da;
delayus(100);
E = 0;
}
void init_1602() //LCD1602 初始化
{
write_com(0x3c);//设定数据总线的个数4/8,显示一行/两行
write_com(0x0c);// //光标不显示
write_com(0x06);// //光标随字符右移
}
void LCD_clr1602() //LCD1602 清屏
{
write_com(0x01); // 对字符串清0
write_com(0x02); //对光标清0
}
void goto_xy(uchar y,uchar x) //定位显示位置
{
if(y == 1)
write_com(x + 0x80); //定位第一行
else
write_com(x + 0x80 + 0x40); //定位第二行
}
void display_num(unsigned char x) //显示数字
{
write_data(num[x / 10%10]);
write_data(num[x % 10]);
}
void display_num1(unsigned int x) //显示数字
{
write_data(num[x / 1000 % 10]);
write_data(num[x / 100 % 10]);
write_data(num[x / 10 % 10]);
write_data(num[x % 10]);
}
void display_string(uchar *p) //显示字符
{
while(*p)
{
write_data(*p);
p++;
}
}
void display_xnum2(float x) //显示数字
{
uint y,x1;
y = (int)x;
write_data(num[y / 10]);
write_data(num[y % 10]);
x1 = (int)((x -(float)y)*1000);
display_string(".");
write_data(num[x1 / 100 % 10]);
// write_data(num[x1 / 10 % 10]);
// write_data(num[x1 % 10]);
}
void display_xnum1(float x) //显示数字
{
uint y,x1;
y = (int)x;
write_data(num[y / 100%10]);
write_data(num[y / 10%10]);
write_data(num[y % 10]);
x1 = (int)((x -(float)y)*1000);
display_string(".");
write_data(num[x1 / 100 % 10]);
write_data(num[x1 / 10 % 10]);
}
18b20.c
/
sbit DQ = P2^4;
void delay_18B20(unsigned int i)
{
while(i--);
}
void Init_DS18B20(void)
{
unsigned char x=0;
DQ = 1; //DQ复位
delay_18B20(8); //稍做延时
DQ = 0; //单片机将DQ拉低
delay_18B20(80); //精确延时 大于 480us
DQ = 1; //拉高总线
delay_18B20(14);
x=DQ; //稍做延时后 如果x=0则初始化成功 x=1则初始化失败
delay_18B20(20);
}
unsigned char ReadOneChar(void)
{
uchar i=0;
uchar dat = 0;
for (i=8;i>0;i--)
{
DQ = 0; // 给脉冲信号
dat>>=1;
DQ = 1; // 给脉冲信号
if(DQ)
dat|=0x80;
delay_18B20(4);
}
return(dat);
}
void WriteOneChar(uchar dat)
{
unsigned char i=0;
for (i=8; i>0; i--)
{
DQ = 0;
DQ = dat&0x01;
delay_18B20(5);
DQ = 1;
dat>>=1;
}
}
void ReadTemp()
{
Init_DS18B20();
WriteOneChar(0xCC); // 跳过读序号列号的操作
WriteOneChar(0x44); // 启动温度转换
delay_18B20(100); // this message is wery important
Init_DS18B20();
WriteOneChar(0xCC); //跳过读序号列号的操作
WriteOneChar(0xBE); //读取温度寄存器等(共可读9个寄存器) 前两个就是温度
TL=ReadOneChar(); //先读的是温度值低位
TH=ReadOneChar(); //接着读的是温度值高位
TN=TH*16+TL/16; //实际温度值=(TH*256+TL)/16,即:TH*16+TL/16
//这样得出的是温度的整数部分,小数部分被丢弃了
TD=(TL%16)*100/16; //计算温度的小数部分,将余数乘以10再除以16取整,
//这样得到的是温度小数部分的第一位数字(保留1位小数)
}
key.c
void key()
{
if(P32 == 0)
{
while(P32 == 0);
mode = 1;
}
if(P33 == 0)
{
while(P33 == 0);
mode = 2;
}
if(P34 == 0)
{
while(P34 == 0);
mode = 3;
}
if(P35 == 0)
{
while(P35 == 0);
mode = 4;
}
}
display.c
void display()
{
goto_xy(1,0);
display_string("temp:");
display_num(TN);
display_string(".");
display_num(TD);
display_string(" ");
display_num(mode);
goto_xy(2,5);
display_num(bit0);
display_num(bit1);
display_num(bit2);
display_num(bit3);
}
原理图
Pcb
资源区会上传相关资源,积分下载



