找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 1492|回复: 0
收起左侧

温控电路程序

[复制链接]
ID:246573 发表于 2017-11-6 16:09 | 显示全部楼层 |阅读模式
C语言程序
#include<stc15.h>
#define ui unsigned int
#define uc unsigned char    //宏定义
sbit SET=P3^1;             //定义调整键
sbit DEC=P3^2;             //定义减少键
sbit ADD=P3^3;             //定义增加键
sbit BEEP=P3^6;            //定义蜂鸣器
sbit ALAM=P1^2;             //定义灯光报警
sbit ALAM1=P1^4;
sbit DQ =P3^7;             //定义DS18B20总线I/O   
sbit SCL=P1^6;
sbit SDA=P1^7;
sbit DIAN=P0^5;            //小数点
bit bdata shanshuo_st;              //闪烁间隔标志
bit bdata beep_st;                 //蜂鸣器间隔标志
uc x=0;                     //计数器
ui bai,shi,ge;
uc set_st=0;               //状态标志
char shangxian,xiaxian;
codeLEDData[]={0x5F,0x44,0x9D,0xD5,0xC6,0xD3,0xDB,0x47,0xDF,0xD7,0xCF,0xDA,0x9B,0xDC,0x9B,0x8B};
//====================================DS18B20=========================================
/*****延时子程序*****/
void Delay_DS18B20(int num)
{
  while(num--);
}
void delay()//5微秒延时函数
{ ;; }
void start() //开始信号
{   
    SDA=1;
    delay();
    SCL=1;
    delay();
    SDA=0;
    delay();
}
void stop()  //终止信号
{
    SDA=0;
    delay();
    SCL=1;
    delay();
    SDA=1;
    delay();
}
void respons() //应答
{
    uc i;
    SCL=1;
    delay();
    while((SDA==1)&&(i<250))i++;//如果SDA为低应答有效,或者超过一定时间默认应答有效
    SCL=0;
    delay();
}
void init24c04()//I2C总线初始化
{
    SDA=1;
    delay();
    SCL=1;
    delay();
}
void write_byte(uc date)//写操作
{
    uc i,temp;
    temp=date;
    for(i=0;i<8;i++)
    {
        temp=temp<<1;
        SCL=0;
        delay();
        SDA=CY;
        delay();
        SCL=1;
        delay();
    }
    SCL=0;
    delay();
    SDA=1;
    delay();
}
uc read_byte()//读操作
{
    uc i,k;
    SCL=0;
    delay();
    SDA=1;
    delay();
    for(i=0;i<8;i++)
    {
        SCL=1;
        delay();   
        k=(k<<1)|SDA;
        SCL=0;
        delay();   
    }
    return k;
}
void write_add(uc address,uc date)//往任意地址存数据
{
    start();
    write_byte(0xa0);//0xa0代表写入
    respons();
    write_byte(address);
    respons();
    write_byte(date);
    respons();
    stop();
}
uc read_add(uc address)//读随意地址内容
{
    uc date;
    start();
    write_byte(0xa0);//0xa0代表写入
    respons();
    write_byte(address);
    respons();
    start();
    write_byte(0xa1);//0xa1代表读出
    respons();
    date=read_byte();
    stop();
    returndate;//返回值
}
/*****初始化DS18B20*****/
void Init_DS18B20(void)
{
  uc w=0;
  DQ = 1;         //DQ复位
Delay_DS18B20(8);    //稍做延时
  DQ = 0;         //单片机将DQ拉低
Delay_DS18B20(80);   //精确延时,大于480us
  DQ = 1;         //拉高总线
Delay_DS18B20(14);
  w = DQ;           //稍做延时后,如果x=0则初始化成功,x=1则初始化失败
Delay_DS18B20(20);
}
/*****读一个字节*****/
unsigned char ReadOneChar(void)
{
  uc i=0;
  uc dat = 0;
  for(i=8;i>0;i--)
  {
    DQ =0;     // 给脉冲信号
   dat>>=1;
    DQ =1;     // 给脉冲信号
    if(DQ)
    dat|=0x80;
   Delay_DS18B20(4);
  }
  return(dat);
}
/*****写一个字节*****/
void WriteOneChar(uc dat)
{
  uc i=0;
  for (i=8;i>0; i--)
  {
    DQ = 0;
    DQ =dat&0x01;
    Delay_DS18B20(5);
    DQ = 1;
   dat>>=1;
  }
}
/*****读取温度*****/
ui ReadTemperature(void)
{
  ui b=0;
  float tt=0;
Init_DS18B20();
WriteOneChar(0xCC);  //跳过读序号列号的操作
WriteOneChar(0x44);  //启动温度转换
Init_DS18B20();
WriteOneChar(0xCC);  //跳过读序号列号的操作
  WriteOneChar(0xBE);  //读取温度寄存器
a=ReadOneChar();     //读低8位
b=ReadOneChar();    //读高8位
  t=b;
  t<<=8;
  t=t|a;
  tt=t*0.0625;
  t=tt*10+0.5;     //放大10倍输出并四舍五入
  return(t);
}
/*****延时子程序*****/
void Delay(ui num)
{
while( --num);
}
/*****初始化定时器0*****/
void InitTimer(void)
{
    TMOD=0x01;
    TH0=0x3c;
    TL0=0xb0;     //50ms(晶振12M)
}
/*****读取温度*****/
void check_wendu(void)
{
    ui f;
    f=ReadTemperature()-5;              //获取温度值并减去DS18B20的温漂误差
    if(f<0)f=0;
    if(f>999)f=999;
    bai=f/100;                          //计算得到十位数字
    shi=(f%100)/10;                     //计算得到个位数字
    ge=(f%100)%10;                              //计算得到整数位
}
/*****显示开机初始化等待画面*****/
void Disp_init(void)   
{
    P0 =~0x80;      //显示----
    P2 = 0x7F;
    Delay(200);
    P2 = 0xDF;
    Delay(200);   
    P2 = 0xF7;
    Delay(200);
    P2 = 0xFD;
    Delay(200);
    P2 =0xFF;         //关闭显示
}
/*****显示温度子程序*****/
void Disp_Temperature(void)     //显示温度
{
    P0 =~0x98;      //显示C
    P2 = 0x7F;
    Delay(400);
    P0=~LEDData[ge];    //显示个位
    P2 = 0xDF;
    Delay(400);
    P0=~LEDData[shi];    //显示十位
    DIAN =0;         //显示小数点
    P2 = 0xF7;
    Delay(400);
    P0=~LEDData[bai];    //显示百位
    P2 = 0xFD;
    Delay(400);
    P2 =0xff;         //关闭显示
}
/*****显示报警温度子程序*****/
void Disp_alarm(uc baojing)
{
    P0=~0x98;      //显示C
    P2 = 0x7F;
    Delay(200);
    P0=~LEDData[baojing%10]; //显示十位
    P0=~LEDData[baojing/10]; //显示百位
    P2 = 0xF7;
    Delay(200);
    if(set_st==1)P0=~0xCE;
    elseif(set_st==2)P0 =~0x1A; //上限H、下限L标示
    P2 = 0xFD;
    Delay(200);
    P2 =0xff;         //关闭显示
}
/*****报警子程序*****/
void Alarm()
{
    if(x>=10){beep_st=~beep_st;x=0;}
    if((bai*10+shi)>=shangxian&&beep_st==1)
    {
        BEEP=0;
        ALAM1=0;
    }
    elseif((bai*10+shi)>=shangxian&&beep_st==0)
    {
        BEEP=1;
        ALAM1=0;
    }
    if((bai*10+shi)<xiaxian&&beep_st==1)
    {
        BEEP=0;
        ALAM=0;
    }
    elseif((bai*10+shi)<xiaxian&&beep_st==0)
    {
        BEEP=1;
        ALAM=0;
    }
    if(((bai*10+shi)<shangxian)&&((bai*10+shi)>=xiaxian))
    {
        BEEP=1;
        ALAM1=1;
        ALAM=1;
    }
}
/*****主函数*****/
void main(void)
{
    ui z;
    InitTimer();    //初始化定时器
    EA=1;      //全局中断开关
    TR0=1;
    ET0=1;      //开启定时器0
    check_wendu();
    check_wendu();
    shangxian=read_add(10);
    xiaxian=read_add(20);
    for(z=0;z<300;z++)
    {
        Disp_init();        
    }
    while(1)
    {
        if(SET==0)
        {
            Delay(2000);
            do{}
            while(SET==0);
            set_st++;x=0;shanshuo_st=1;
            if(set_st>2)set_st=0;
        }
        if(set_st==0)
        {
            check_wendu();
            Disp_Temperature();
            Alarm();   //报警检测
        }
        elseif(set_st==1)
        {
            BEEP=1;    //关闭蜂鸣器
            ALAM=1;
            ALAM1=1;
            if(x>=10){shanshuo_st=~shanshuo_st;x=0;}
            if(shanshuo_st){Disp_alarm(shangxian);}
            if(ADD==0)
            {
                do{Disp_alarm(shangxian);}
                shangxian++;
                if(shangxian>99)shangxian=99;
                write_add(10,shangxian);
            }
            elseif(DEC==0)
            {
                do{Disp_alarm(shangxian);}
                while(DEC==0);
                shangxian--;
                if(shangxian<xiaxian)shangxian=xiaxian;
                write_add(10,shangxian);
            }
        }
        else if(set_st==2)
        {
            BEEP=1;    //关闭蜂鸣器
            ALAM=1;
            ALAM1=1;
            if(x>=10){shanshuo_st=~shanshuo_st;x=0;}
            if(shanshuo_st){Disp_alarm(xiaxian);}
            if(ADD==0)
            {
                do{Disp_alarm(xiaxian);}
                while(ADD==0);
                xiaxian++;
                if(xiaxian>shangxian)xiaxian=shangxian;
                write_add(20,xiaxian);
            }
            elseif(DEC==0)
            {
                do{Disp_alarm(xiaxian);}
                while(DEC==0);
                xiaxian--;
                if(xiaxian<0)xiaxian=0;
                write_add(20,xiaxian);
            }
        }
    }
}
/*****定时器0中断服务程序*****/
void timer0(void) interrupt 1
{
    TH0=0x3c;
    TL0=0xb0;
    x++;
}file:///C:/Users/Lenovo/AppData/Local/Temp/msohtmlclip1/01/clip_image001.giffile:///C:/Users/Lenovo/AppData/Local/Temp/msohtmlclip1/01/clip_image002.gif

回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|51黑电子论坛 |51黑电子论坛6群 QQ 管理员QQ:125739409;技术交流QQ群281945664

Powered by 单片机教程网

快速回复 返回顶部 返回列表