打印
[Cortex-M0技术交流]

第五批 学习笔记第三篇——18B20温度报警

[复制链接]
2567|5
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
发个18B20测温的程序,程序早都写好了,就是一直没时间发,18B20温度传感器的文档大叔的资料里有,而且有例程,我只是根据自己的硬件改了一下。温度值是通过12864液晶显示出来的。加入了报警功能,当温度超出按键设定的温度值之后会蜂鸣报警,当温度再次降低到报警之下时停止报警。
先上图


工程在这里 18B20测温_LCM.rar (2.9 MB)
下面贴出代码
 
主函数
#include <stdio.h>
#include "NUC1xx.h"
#include "DrvADC.h"
#include "DrvGPIO.h"
#include "DrvUART.h"
#include "DrvSYS.h"
#include "ds18b20.h"
unsigned char DS18B20_ID[8]={0,0,0,0,0,0,0,0,};
unsigned char NOW_TEMP[6]={0};
void bee (void)
{
int i=100;
for(i=100;i>0;i--)
{

DrvGPIO_SetBit(E_GPB, 10);
DrvSYS_Delay(500);
DrvGPIO_ClrBit(E_GPB, 10);
DrvSYS_Delay(500);  
}
}
int main (void)
{
unsigned int temp=0;
unsigned int temp_H=0;
unsigned int temp_L=0;
unsigned char i=0;
unsigned int bv=30;
unsigned char   flag    ;
UNLOCKREG();               //  芯片注册解锁
    SYSCLK->PWRCON.XTL12M_EN = 1;           //  设定12M外部晶振
    DrvSYS_Delay(5000);              //  等待时钟就绪
LOCKREG();                //向“0x5000_0100”写入任何值,就可以重锁保护寄存器
//---------------------------------------------------------     // 系统初始化
DrvGPIO_Open(E_GPA, 9, E_IO_OUTPUT);
DrvGPIO_Open(E_GPA, 8, E_IO_OUTPUT);      
DrvGPIO_Open(E_GPA, 7, E_IO_OUTPUT);         
DrvGPIO_Open(E_GPA, 6, E_IO_OUTPUT);        
DrvGPIO_Open(E_GPA, 5, E_IO_OUTPUT);
DrvGPIO_Open(E_GPB, 10, E_IO_OUTPUT);         //  设置GPB10端口为输出模式
DrvGPIO_Open(E_GPA, 9, E_IO_OUTPUT);
  DrvSYS_Delay(6000);
DrvGPIO_Open( E_GPB, 14, E_IO_INPUT );   //按键端口设置为输入
    DrvGPIO_Open( E_GPB, 15, E_IO_INPUT );
DrvGPIO_ClrBit(E_GPB, 10);  
DrvSYS_Delay(6000);
LCMInit();
Chn_disp_char("现在温度",1,1)   ;
Chn_disp_char("报警设定值",2,1)   ;
while(1)
  {
   temp  = readTempDS18B20();
   temp_H  = temp/100;
   temp_L  =   temp%100;
            Digtal_disp(temp_H,1,5);
    WriteLCM(1,0x2e) ;
   Digtal_disp(temp_L,1,0);
    Chn_disp_char("度",1,7)    ;
     Digtal_disp(bv,2,6);
    if(temp_H>=bv)
    bee();
   
if (DrvGPIO_GetBit(E_GPB,14) == 0)     // 键按下检测
  {
  bv++;
  DrvGPIO_SetBit(E_GPB, 10);
  DrvSYS_Delay(100);
  DrvGPIO_ClrBit(E_GPB, 10);
  }
  
if (DrvGPIO_GetBit(E_GPB,15) == 0)     // 键按下检测
  {
  bv--;
  DrvGPIO_SetBit(E_GPB, 10);
  DrvSYS_Delay(100);
  DrvGPIO_ClrBit(E_GPB, 10);
  DrvSYS_Delay(60000);
   }
    DrvSYS_Delay(60000);
  }
}


18B20.c
 
/***************************************************/
/*     烈火狂龙   论坛ID:plc_avr   QQ:16053729    */
/*     移值于其它MCU时,注意修改端口和延时函数    */
/*     2011、03、30           */
/*-------------------------------------------------*/
#include "ds18b20.h"
unsigned char DS18B20_sign_flag=0;
/**********************************************************************
延时
**********************************************************************/
void delay_nus(unsigned int t)
{
unsigned int i=0;
while(t--)
   {
    for(i=0;i<1;i++);
    }
}
/**********************************************************************
functionName: unsigned char resetDS18B20(void)
description :DS18B20初始化
**********************************************************************/
unsigned char resetDS18B20(void)
{
    unsigned char errTime=0;
    HLD_DS18B20;     //控制总线
    CLR_DS18B20;     //强制拉低      
    delay_nus(260);        //以上延时大于480us
    SET_DS18B20;
    RLS_DS18B20;     //释放总线,总线自动上拉 DDR
    delay_nus(7);          //15~60us
    while (STU_DS18B20)
    {
        delay_nus(3);    //5.15us
        errTime++;
        if (errTime>20)
            return(0x00);  //如果等带大于约 5.15us*20就返回0x00,报告复位失败(实际上只要等待15-60us)
    }
    errTime=0;
    while (!(STU_DS18B20))
    {
        delay_nus(3);    //5.15us
        errTime++;
        if (errTime>50)
            return(0x00);  //如果等带大于约 5.15us*50就返回0x00,报告复位失败(实际上只要等待60-240us)
    }
    HLD_DS18B20;     //控制总线
    SET_DS18B20;     //强制拉高
    return(0xff);
}
/**********************************************************************
functionName: unsigned char readByteDS18B20(void)
description :读DS18B20一个字节
**********************************************************************/
unsigned char readByteDS18B20(void)
{
    unsigned char i;
    unsigned char retVal=0;
    //RLS_DS18B20;     //释放总线
    for (i=8;i>0;i--)
    {
        retVal>>=1;
        HLD_DS18B20;    //控制总线
        CLR_DS18B20;    //强制拉低
        delay_nus(1);    //延时大于1us
        SET_DS18B20;    //释放总线,DS18B20会将总线强制拉低
        RLS_DS18B20;    //释放总线
        delay_nus(1);
        if (STU_DS18B20)
            retVal|=0x80;
        delay_nus(15);   //31us
    }
    HLD_DS18B20;     //控制总线
    SET_DS18B20;     //强制拉高
    return(retVal);
}
/**********************************************************************
functionName: unsigned char readByteDS18B20(void)
description :写DS18B20一个字节
**********************************************************************/
void writeByteDS18B20(unsigned char wb)
{
    unsigned char i;
    unsigned char temp;
    //RLS_DS18B20;         //释放总线
    for (i=0;i<8;i++)
    {
        HLD_DS18B20;  //控制总线
        CLR_DS18B20;  //强制拉低
        delay_nus(1);   //14.92us
        temp=wb>>i;
        if (temp&=0x01)
            SET_DS18B20;    //释放总线
        else
            CLR_DS18B20; //强制拉低
        delay_nus(15);     //30.38us
        SET_DS18B20;  //释放总线
        delay_nus(1);   //2.71us(大于1us就行了)
    }
}
/**********************************************************************
functionName: get_rom(unsigned char* p)
description :读ROM
**********************************************************************/
void get_rom(unsigned char* p)
{
    unsigned char i;
    if (resetDS18B20()==0xff)
    {
        writeByteDS18B20(ds18b20_read_rom);
        for (i=0;i<8;i++)
        {
            *p++ = readByteDS18B20();
        }
    }
}
/**********************************************************************
functionName: void set_ds18b20(char th,char tl,unsigned char config)
description :设定DS18B20模式
**********************************************************************/
void set_ds18b20(char th,char tl,unsigned char config)
{
    if (resetDS18B20()==0xff)
    {
        writeByteDS18B20(ds18b20_skip_rom);
        writeByteDS18B20(ds18b20_write_ram);
        writeByteDS18B20(th);
        writeByteDS18B20(tl);
        writeByteDS18B20(config);
    }
}
/**********************************************************************
functionName: convert_ds18b20(void)
description :写DS18B20一个字节
**********************************************************************/
void convert_ds18b20(void)
{
    if (resetDS18B20()==0xff)
    {
        writeByteDS18B20(ds18b20_skip_rom); //跳过ROM
        writeByteDS18B20(ds18b20_convert_tem); //启动温度转换
    }
}
/**********************************************************************
functionName: unsigned int readTempDS18B20(void)
description :读DS18B20温度   有正负符号标志和两个小数点精度
**********************************************************************/
unsigned int readTempDS18B20(void)
{
    unsigned char tempL,tempH,wm0,wm2;
    unsigned int x;
    if (resetDS18B20()==0)
        return 0;
    writeByteDS18B20(ds18b20_skip_rom); //跳过ROM
    writeByteDS18B20(ds18b20_read_ram); //读数据
    tempL=readByteDS18B20();
    tempH=readByteDS18B20();
    wm0=tempL;
    wm0=wm0>>4;
    tempH=tempH<<4;
    wm2=wm0+tempH; //温度的整数值
    if (wm2&0x80)  //测试符号位
    {
        DS18B20_sign_flag=1;
        wm2=256-wm2;
    }
    else
        DS18B20_sign_flag=0;
    x = wm2*100;   //字符型赋给整形,扩大100倍
    if (tempL&0x08) //提高测试精度
    {
        x=x+50;
    }
    if (tempL&0x04)
    {
        x=x+25;
    }
    if (tempL&0x02)
    {
        x=x+12;
    }
    if (tempL&0x01)
    {
        x=x+6;
    }
    convert_ds18b20();//启动温度转换
    return(x);
}


18B20.h
 
#ifndef __DS18B20__H
#define __DS18B20__H
#include "NUC1xx.h"
#include "DrvGPIO.h"
#define CLR_DS18B20     DrvGPIO_ClrBit(E_GPB, 4)             //数据线强制拉低
#define SET_DS18B20     DrvGPIO_SetBit(E_GPB, 4)             //数据线强制拉高,上拉
#define HLD_DS18B20     DrvGPIO_Open(E_GPB, 4, E_IO_OUTPUT)  //M0控制总线
#define RLS_DS18B20     DrvGPIO_Open(E_GPB, 4, E_IO_QUASI)   //释放总线
#define STU_DS18B20     DrvGPIO_GetBit(E_GPB, 4)             //数据线的状态
#define ds18b20_read_rom           0x33
#define ds18b20_match_rom          0x55
#define ds18b20_skip_rom           0xcc
#define ds18b20_search_rom         0xf0
#define ds18b20_alarm_search_rom   0xec
#define ds18b20_write_ram          0x4e
#define ds18b20_read_ram           0xbe
#define ds18b20_copy_ram           0x48
#define ds18b20_convert_tem        0x44
#define ds18b20_eecall_eeprom      0xb8
#define ds18b20_read_power_supply  0xb4
extern unsigned char DS18B20_sign_flag;
void delay_nus(unsigned int t);
unsigned char resetDS18B20(void);
void get_rom(unsigned char* p);
void set_ds18b20(char th,char tl,unsigned char config);
void convert_ds18b20(void);
unsigned int readTempDS18B20(void);
#endif


 
/////////////////////////////////////////////////////////////////////////////////////////////
//LCM显示程序
//2011.12.30 by xiaowei
/////////////////////////////////////////////////////////////////////////////////////////////
#include <stdio.h>
#include "NUC1xx.h"
#include "DrvGPIO.h"
#include "DrvSYS.h"
#include "lcm.h"
void WriteLCM(int32_t data_comm,int32_t in_com)   //1 for data,0 for comm
{  
   int32_t com,i,j,std;
       DrvSYS_Delay(100);
   com = in_com;
     DrvGPIO_SetBit( E_GPA,8 );  //LCD_CS = 1;
    DrvGPIO_ClrBit( E_GPA,6); //LCD_EN = 0;
       DrvGPIO_SetBit(E_GPA,7);//LCD_STD = 1;
   for(i=5;i>0;i--)
   {
     DrvGPIO_SetBit( E_GPA,6); //LCD_EN = 1;
   DrvGPIO_ClrBit( E_GPA,6); //LCD_EN = 0;   
   }
     DrvGPIO_ClrBit(E_GPA,7);//LCD_STD = 0;
      DrvGPIO_SetBit( E_GPA,6); //LCD_EN = 1;
   DrvGPIO_ClrBit( E_GPA,6); //LCD_EN = 0;
   if(data_comm==1)
    DrvGPIO_SetBit(E_GPA,7);//LCD_STD = 1;
   else
       DrvGPIO_ClrBit(E_GPA,7);//LCD_STD = 0;
      DrvGPIO_SetBit( E_GPA,6); //LCD_EN = 1;
   DrvGPIO_ClrBit( E_GPA,6); //LCD_EN = 0;
         DrvGPIO_ClrBit(E_GPA,7);//LCD_STD = 0;
   DrvGPIO_SetBit( E_GPA,6); //LCD_EN = 1;
   DrvGPIO_ClrBit( E_GPA,6); //LCD_EN = 0;
  
for(j=2;j>0;j--)
{
  for(i=4;i>0;i--)
  {
   
   std=com&0x80;
   if(std==0x80)
    DrvGPIO_SetBit(E_GPA,7);   //LCD_STD = 1;
   else
    DrvGPIO_ClrBit(E_GPA,7);   //LCD_STD = 0;
    com=com<<1;
   DrvGPIO_SetBit( E_GPA,6); //LCD_EN = 1;
   DrvGPIO_ClrBit( E_GPA,6); //LCD_EN = 0;
  }
  DrvGPIO_ClrBit(E_GPA,7);   //LCD_STD = 0;
  for(i=4;i>0;i--)
  {
   DrvGPIO_SetBit( E_GPA,6); //LCD_EN = 1;
   DrvGPIO_ClrBit( E_GPA,6); //LCD_EN = 0;
  }
}
}
////////////////////////////////////////////////////////////////////////////////
void LCMInit(void)  //LCM初始化
{
DrvGPIO_ClrBit(E_GPA,5 );
    DrvSYS_Delay(6000);
  DrvGPIO_SetBit(E_GPA,5 );  
    WriteLCM(0,0x30) ;    //设接口数据位数(DL),显示行数(L),及字型(F)
    DrvSYS_Delay(6000);
WriteLCM(0,0x01) ;   //清屏指令
    DrvSYS_Delay(6000);
WriteLCM(0,0x0c) ;    //设整体显示开关(D),光标开关关(C),及光标位的字符不闪耀(B)
    DrvSYS_Delay(6000);
WriteLCM(0,0x06) ;    //7设光标移动方向并指定整体显示是否移动
    DrvSYS_Delay(6000);
WriteLCM(0,0x01) ;  //清屏指令
    DrvSYS_Delay(6000);  
WriteLCM(0,0x80) ;  //设DDRAM地址,设置后DDRAM数据被发送和接收
}
/////////////////////////////////////////////////////////////////////////
//写汉字
//输入char[]={"显示的字"},行数,列数    显示数字时,如果列数为0,则接着显示
void Chn_disp_char( char *chn, int32_t line_pos, int32_t dis_pos)
{
char i=0,Start_pos;
WriteLCM (comm_flag,0x30);
switch(line_pos)
{
  case 1:
   Start_pos=FirstLine_Start;
   break;
  case 2:
   Start_pos=SecondLine_Start;
   break;  
  case 3:
   Start_pos=ThirdLine_Start;
   break;
  case 4:
   Start_pos=FourthLine_Start;
   break;
}
if(dis_pos!=0)
  WriteLCM (comm_flag,(Start_pos+dis_pos-1));
    while(chn[i]!='\0')
    {
     WriteLCM (data_flag,chn[i]);
     i++;
}
}
////////////////////////////////////////////////////////
//写数字
//输入 (数字,行数,列数)
void Digtal_disp( int32_t digt, int32_t line_pos, int32_t dis_pos)
{
char digt_ []={""};
sprintf(digt_,"%.2d",digt);
Chn_disp_char(digt_,line_pos,dis_pos);
}
/////////////////////////////////////////////////////////////////

lcm.h
 

//用于TG12864
//串口通信
#include <stdio.h>
#include "NUC1xx.h"
#include "DrvGPIO.h"
#include "DrvSYS.h"
#define LCD_CS    E_GPA,8 ;
#define LCD_STD    E_GPA,7 ;
#define LCD_EN   E_GPA,6 ;
#define LCD_RST   E_GPA,5 ;
#define  FirstLine_Start  0x80
#define  SecondLine_Start 0x90
#define  ThirdLine_Start  0x88
#define  FourthLine_Start 0x98
#define  comm_flag  0
#define  data_flag  1
void WriteLCM(int32_t data_comm,int32_t in_com)    ;
void LCMInit(void)         ;
void Chn_disp_char( char *chn, int32_t line_pos, int32_t dis_pos) ;
void Digtal_disp( int32_t digt, int32_t line_pos, int32_t dis_pos) ;

相关帖子

沙发
王紫豪| | 2012-3-7 01:15 | 只看该作者
弄得不错,代码很整洁,支持一下~

使用特权

评论回复
板凳
老鱼探戈| | 2012-3-7 12:56 | 只看该作者
支持一下!

使用特权

评论回复
地板
13301| | 2012-3-7 20:42 | 只看该作者
不赖嘛~~

使用特权

评论回复
5
plc_avr| | 2012-3-8 07:29 | 只看该作者
顶!楼主用心了。

使用特权

评论回复
6
ceflsh| | 2014-4-16 11:31 | 只看该作者
下来用一用,谢谢LZ。

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

0

主题

113

帖子

1

粉丝