久久久久久久999_99精品久久精品一区二区爱城_成人欧美一区二区三区在线播放_国产精品日本一区二区不卡视频_国产午夜视频_欧美精品在线观看免费

 找回密碼
 立即注冊

QQ登錄

只需一步,快速開始

搜索
查看: 7740|回復: 4
打印 上一主題 下一主題
收起左側

PIC16F877單片機DS18B20數碼管溫度計仿真程序 可顯示負溫度

  [復制鏈接]
跳轉到指定樓層
樓主
電路原理圖如下:


//*********************************************************
//        實現的功能:數碼管顯示實時溫度,支持負溫度
//        芯片PIC16F877
//        XT:4MHZ
//*********************************************************
#include <pic.h>       //包含單片機內部資源預定義
#define LVP 0x3f39

// 晶振:XT;代碼:沒有代碼保護;上電延時定時器關閉;
// 低電壓復位禁止;看門狗關閉 ;低電壓編程禁止
__CONFIG (XT & UNPROTECT & PWRTDIS & BORDIS & WDTDIS & LVP);

#define  uch  unsigned char                     //給unsigned char起別名 uch
#define DQ RA2                                //定義18B20數據端口
#define DQ_DIR TRISA2                         //定義18B20D口方向寄存器
#define DQ_HIGH() DQ_DIR =1                   //設置數據口為輸入
#define DQ_LOW() DQ_DIR = 0;DQ = 0            //設置數據口為輸出

const unsigned char ledcode[12]={0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,0x7F,0x6F,0x00,0x40};
//不帶小數點的共陰極數碼管0123456789段碼,正負符號位
const unsigned char ledcode1[12]={0xBF,0x86,0xDB,0xCF,0xE6,0xED,0xFD,0x87,0xFF,0xEF,0x00,0x40};   
//帶小數點的共陰極數碼管0123456789段碼 ,正負符號位

void init_port(void);
void delay(char x,char y);
void delay_1ms(void);
void delay_ms(unsigned int time);
void interrupt dealtime();
void tmint(void);
void timetoseg(uch fh_temp,uch bai_temp,uch shi_temp,uch ge_temp,uch sf_temp,uch bf_temp,uch qf_temp,uch wf_temp);
void binary_temp(uch TL , signed char TH);
void reset(void);
void write_byte(uch val);
uch read_byte(void);
void get_temp(void);

unsigned char display_data[8];
unsigned char intcount=0;
uch  TLV=0 ;                        //采集到的溫度高8位
uch  THV=0;                         //采集到的溫度低8位

union temp                         //定義一個聯合體
{
int T;        
uch TV[2];        
}temp;

signed char TZ=0;                     //轉換后的溫度值整數部分,有符號位
uch TX=0;                            //轉換后的溫度值小數部分

unsigned int wd;                              //轉換后的溫度值BCD碼形式

unsigned char fh;                               //符號位
unsigned char bai;                             //整數百位
unsigned char shi;                             //整數十位
unsigned char ge;                              //整數個位
unsigned char shifen;                          //十分位
unsigned char baifen;                          //百分位
unsigned char qianfen;                         //千分位
unsigned char wanfen;                          //萬分位


//*********************************************************
//                        主程序
//*********************************************************
void main(void)
{
init_port();
tmint();
while(1)
  {         
   get_temp();
   timetoseg(fh,bai,shi,ge,shifen,baifen,qianfen,wanfen);  

  }
}
//*********************************************************
//        端口初始化
//        PORTD作為數碼管段驅動(高有效)
//        PORTE作為數碼管位選擇驅動(低有效)
//*********************************************************
void init_port(void)
{
  RBPU=0;
//  PORTB=0xFF;
  TRISB=0xFF;
  PORTD=0x00;           //
  TRISC=0x00;           //C口控制LED指示燈,設置成輸出
  TRISD=0;                   //D口當作數碼管段,設置成輸出
  ADCON1=0x07;                //使A口,E口全為數字I/O口
  TRISE=0x00;           //E口當作數碼管位選擇控制腳,設置成輸出   
  PORTE=0x00;
}
//*********************************************************
//                延時程序
//*********************************************************
void delay(char x,char y)
{
  char z;
  do{
      z=y;
      do{;}while(--z);
     }while(--x);
}
//其指令時間為:7+(3*(Y-1)+7)*(X-1)如果再加上函數調用的call 指令、頁面設定、傳遞參數花掉的7 個指令。
//則是:14+(3*(Y-1)+7)*(X-1)。
//*********************************************************
//                延遲程序
//*********************************************************
void delay_1ms(void)
{
  unsigned int n;
  for(n=0;n<50;n++)
   {
    NOP();
   }
}
//*********************************************************
void delay_ms(unsigned int time)
{
  for(;time>0;time--)
   {
    delay_1ms();
   }
}

//-----------------------------------------------
//復位DS18B20函數
void reset(void)
{
  uch presence=1;
  while(presence)
  {
    DQ_LOW() ;                                //主機拉至低電平
    delay(2,90);                              //延時>480503us
    DQ_HIGH();                                //釋放總線等電阻拉高總線,并保持15~60us
    delay(2,8);                               //延時>60us
    if(DQ==1) presence=1;                     //沒有接收到應答信號,繼續復位
    else presence=0;                          //接收到應答信號
    delay(2,70);                              //延時>240us
   }
  }

//-----------------------------------------------
//寫18b20寫字節函數
void write_byte(uch val)
{
uch i;
uch temp;
for(i=8;i>0;i--)
{
   temp=val&0x01;                            //最低位移出
   DQ_LOW();
   NOP();
   NOP();
   NOP();
   NOP();
   NOP();                                    //從高拉至低電平,產生寫時間隙
   if(temp==1)  DQ_HIGH();                   //如果寫1,拉高電平
   delay(2,7);                               //延時63us
   DQ_HIGH();
   NOP();
   NOP();
   val=val>>1;                               //右移一位
  }
}

//------------------------------------------------
//18b20讀字節函數
uch read_byte(void)
{
uch i;
uch value=0;                                //讀出溫度
static bit j;
for(i=8;i>0;i--)
{
   value>>=1;
   DQ_LOW();          //每次讀時隙由主機發起,拉低總線至少1μs。
   NOP();
   NOP();
   NOP();
   NOP();
   NOP();
   NOP();                                   //6us
   DQ_HIGH();          //讀時隙開始后的15μs內釋放總線,拉至高電平,準備采樣總線。
   NOP();
   NOP();
   NOP();  
   NOP();
   NOP();                                  //5us
   j=DQ;               //采樣總線
   if(j) value|=0x80;  //把采樣到的數據放入value
   delay(2,7);               //所有讀時隙至少60μs,這里大約63us
  }
  return(value);
}

//-------------------------------------------------
//啟動溫度轉換函數
void get_temp()
{
int i;
DQ_HIGH();
reset();                                 //復位等待從機應答
write_byte(0XCC);                        //忽略ROM匹配
write_byte(0X44);                        //發送溫度轉化命令  
for(i=10;i>0;i--)
    {   
        delay(201,132);                       
    }   

reset();                                 //再次復位,等待從機應答
write_byte(0XCC);                        //忽略ROM匹配
write_byte(0XBE);                        //發送讀溫度命令

TLV=read_byte();                  //讀出溫度低8位
THV=read_byte();                  //讀出溫度高8位

DQ_HIGH();                               //釋放總線


TZ=(TLV>>4)|(THV<<4);           //溫度整數部分
TX=TLV<<4;                      //溫度小數部分,注意TX的后四位無效碼
binary_temp(TX, TZ );   //將相應的溫度二進制值轉換成十進制數
}

//將相應的溫度溫度整數部分和小數部分的二進制值轉換成十進制數

void binary_temp(char TL , signed char TH)
{
  if(TH>=0)                          //如果是正溫度
  {
    fh=0x0A;                                 //正數符號位
    bai=TH/100;                               //整數部分百位
    shi=(TH%100)/10;//十位                   //整數十位
    ge=(TH%100)%10;//個位                          //整數部分個位

    wd=0;  
    if (TL & 0x80) wd=wd+5000;
    if (TL & 0x40) wd=wd+2500;
    if (TL & 0x20) wd=wd+1250;
    if (TL & 0x10) wd=wd+625;                //以上4條指令把小數部分轉換為BCD碼形式            

    shifen=wd/1000;                          //十分位                    
    baifen=(wd%1000)/100;                    //百分位
    qianfen=(wd%100)/10;                     //千分位
    wanfen=wd%10;                            //萬分位
    NOP();
   }
else                                       //否則,是負溫度,要求補碼
{
  temp.TV[0]=TL;temp.TV[1]=TH ;
  temp.T=(~temp.T)+0x0010;              //補碼形式,起反加1      
  TL=temp.TV[0];
  TH=temp.TV[1];

    fh=0x0B;                                //負數符號位
    bai=TH/100;                               //整數部分百位
    shi=(TH%100)/10;//十位                   //整數十位
    ge=(TH%100)%10;//個位                          //整數部分個位

    wd=0;  
    if (TL & 0x80) wd=wd+5000;
    if (TL & 0x40) wd=wd+2500;
    if (TL & 0x20) wd=wd+1250;
    if (TL & 0x10) wd=wd+625;                //以上4條指令把小數部分轉換為BCD碼形式            

    shifen=wd/1000;                          //十分位                    
    baifen=(wd%1000)/100;                    //百分位
    qianfen=(wd%100)/10;                     //千分位
    wanfen=wd%10;                            //萬分位
    NOP();
}               
}

//          溫度值各位轉換成段碼
//*********************************************************
void timetoseg(uch fh_temp,uch bai_temp,uch shi_temp,uch ge_temp,uch sf_temp,uch bf_temp,uch qf_temp,uch wf_temp)
{
   display_data[0] = ledcode[wf_temp];
   display_data[1] = ledcode[qf_temp];
   display_data[2] = ledcode[bf_temp];
   display_data[3] = ledcode[sf_temp];
   display_data[4] = ledcode1[ge_temp];
   display_data[5] = ledcode[shi_temp];
   display_data[6] = ledcode[bai_temp];
   display_data[7] = ledcode[fh_temp];
}


//*********************************************************
//                        定時中斷初始化(OPTION_REG)
//*********************************************************
void tmint(void)
{
  T0CS=0;             //時鐘源為內部指令周期                  
  PSA=0;           //分頻器分配給TMR0
//  
  PS2=0;          //TMR0的分頻比為1:16         
  PS1=1;
  PS0=1;
//
  GIE=1;          //允許總中斷
  T0IE=1;         //允許定時器0溢出中斷
  T0IF=0;         //清楚定時器0中斷標志
  TMR0=0X06;      //預置初值 T=(256-6)x16=4000uS
}
//*********************************************************
void interrupt dealtime()   //中斷入口,該中斷完成數碼管的動態掃描
{                          //每中斷一次的時間為4毫秒
    T0IF=0;
    TMR0=0X06;

    PORTD = 0x00;            //先關閉顯示
   if(intcount==0)
     {
      PORTD = display_data[0];
      PORTE=0x00;
      intcount+=1;
     }
   else if(intcount==1)
     {
      PORTD = display_data[1];
      PORTE=0x01;
      intcount+=1;
     }
   else if(intcount==2)
     {
      PORTD = display_data[2];
      PORTE=0x02;
      intcount+=1;
     }
   else if(intcount==3)
     {
      PORTD = display_data[3];
      PORTE=0x03;
      intcount+=1;
     }
   else if(intcount==4)
     {
      PORTD = display_data[4];
      PORTE=0x04;
      intcount+=1;
     }
   else if(intcount==5)
     {
      PORTD = display_data[5];
      PORTE=0x05;
      intcount+=1;
     }
   else if(intcount==6)
     {
      PORTD = display_data[6];
      PORTE=0x06;
      intcount+=1;
     }   
    else if(intcount==7)
     {
      PORTD = display_data[7];
      PORTE=0x07;
      intcount = 0;
     }   

}



PIC16F877+DS18B20+數碼管.rar (25.75 KB, 下載次數: 139)





評分

參與人數 6黑幣 +105 收起 理由
zwk34 + 10 共享資料的黑幣獎勵!
鉆牛尖滴劉尖尖 + 10
shuisheng + 15 贊一個!
Trump1438 + 10 贊一個!
Sawardeakar + 10 贊一個!
admin + 50 共享資料的黑幣獎勵!

查看全部評分

分享到:  QQ好友和群QQ好友和群 QQ空間QQ空間 騰訊微博騰訊微博 騰訊朋友騰訊朋友
收藏收藏6 分享淘帖 頂3 踩
回復

使用道具 舉報

沙發
ID:297903 發表于 2022-2-15 09:03 | 只看該作者
下載來測試下,謝謝!!
回復

使用道具 舉報

板凳
ID:582276 發表于 2022-4-7 23:15 | 只看該作者
放到XC8中轉換試下
回復

使用道具 舉報

地板
ID:362692 發表于 2022-5-4 12:11 | 只看該作者
你怎么回事?  源文件發一下不是更省事
回復

使用道具 舉報

5#
ID:192215 發表于 2022-5-27 11:30 | 只看該作者
下載資料包里面沒有源文件嗎?
回復

使用道具 舉報

您需要登錄后才可以回帖 登錄 | 立即注冊

本版積分規則

手機版|小黑屋|51黑電子論壇 |51黑電子論壇6群 QQ 管理員QQ:125739409;技術交流QQ群281945664

Powered by 單片機教程網

快速回復 返回頂部 返回列表
主站蜘蛛池模板: 久久亚洲国产 | 亚洲精品亚洲人成人网 | 欧美综合一区 | 欧美jizzhd精品欧美巨大免费 | 成人亚洲精品 | 日日骚av | 亚洲欧美在线观看 | 精品国产18久久久久久二百 | 国产一区二区三区久久 | 久久精品在线 | a级毛片免费高清视频 | 欧美日韩国产三级 | 精品久久久久国产免费第一页 | 岛国毛片| 先锋av资源网 | 精品免费视频 | 日日摸日日添日日躁av | www.887色视频免费 | 久久久久久久久久久久久久久久久久久久 | 在线免费看黄 | 欧洲免费视频 | 美女网站视频免费黄 | 精品国产视频在线观看 | 国产精品99久久久久久久久 | 中文字幕在线看第二 | 99国产视频 | 欧美国产日韩在线观看 | 激情a| 91久久综合 | 免费精品| 久久综合一区二区 | 亚洲人成在线播放 | 午夜电影福利 | 超碰免费在 | 人人精品 | 亚洲成人午夜在线 | 成人黄页在线观看 | av在线免费观看网站 | 亚洲国产精品一区二区久久 | 色爱综合 | 国产成人精品一区二 |