以下代码在STC15W408AS单片机进行测试,后面还有自制的PCB的原理图和layout设计(因某些原因需要制作这样一块显示温度的小项目,又想节约成本,于是画的十分简陋…)

DS18B20驱动代码

#include "stc15.h" //此处应修改为相应的单片机库

sbit DQ = P1^1;  //此处为连接DS18B20的引脚号

//单总线延时函数
void Delay_OneWire(unsigned int t)  //STC89C52RC
{
	unsigned char i;
	while(t--)
	{
		for(i=0;i<12;i++);
	}
}

//通过单总线向DS18B20写一个字节
void Write_DS18B20(unsigned char dat)
{
	unsigned char i;
	for(i=0;i<8;i++)
	{
		DQ = 0;
		DQ = dat&0x01;
		Delay_OneWire(5);
		DQ = 1;
		dat >>= 1;
	}
	Delay_OneWire(5);
}

//从DS18B20读取一个字节
unsigned char Read_DS18B20(void)
{
	unsigned char i;
	unsigned char dat;
  
	for(i=0;i<8;i++)
	{
		DQ = 0;
		dat >>= 1;
		DQ = 1;
		if(DQ)
		{
			dat |= 0x80;
		}	    
		Delay_OneWire(5);
	}
	return dat;
}

//DS18B20设备初始化
bit init_ds18b20(void)
{
  	bit initflag = 0;
  	
  	DQ = 1;
  	Delay_OneWire(12);
  	DQ = 0;
  	Delay_OneWire(80);
  	DQ = 1;
  	Delay_OneWire(10); 
    initflag = DQ;     
  	Delay_OneWire(5);
  
  	return initflag;
}

 unsigned char rd_temperature(void)
{
    unsigned char low,high;
  	char temp;
  
  	init_ds18b20();
  	Write_DS18B20(0xCC);
  	Write_DS18B20(0x44); //启动温度转换
  	Delay_OneWire(200);

  	init_ds18b20();
  	Write_DS18B20(0xCC);
  	Write_DS18B20(0xBE); //读取寄存器

  	low = Read_DS18B20(); //低字节
  	high = Read_DS18B20(); //高字节
  
  	temp = high<<4;
  	temp |= (low>>4);
  
  	return temp;
}

PCB文件及其示意图

PCB文件以压缩包形式打包。戳我下载
注:我画的是拼板,右侧的那块可能地线没有接到一起。

PCB原件布局

pcb.jpg

BOM表

CommentDescriptionFootprintQuantity
5261AS二位共阴数码管5261AS1
LED发光二极管06031
Header 4Header, 4-PinHDR1X41
Res10K06031
Res5.1R06031
STC15W408ASC51单片机SOP-161
DS18B20模组DS18B20模组DS18B20模组1

DS18B20模组相关文件由淘宝商家提供,以下是淘宝商家公开的百度网盘连接。
https://pan.baidu.com/s/19CwH6CAaWgVBMKmCA28ygQ 提取码:lggj

单片机代码

#include "stc15.h"
#include "intrins.h"
#include "onewire.h"
#include "absacc.h"

#define uchar unsigned char
#define uint unsigned int

sbit LED = P3 ^ 2; //H有效
sbit DIGITAL_a = P1 ^ 2;
sbit DIGITAL_b = P1 ^ 3;
sbit DIGITAL_c = P1 ^ 4;
sbit DIGITAL_d = P1 ^ 5;
sbit DIGITAL_e = P5 ^ 4;  //sbit DIGITAL_e = P2 ^ 4;
sbit DIGITAL_f = P5 ^ 5;  //sbit DIGITAL_e = P2 ^ 5;
sbit DIGITAL_g = P1 ^ 0;
sbit DIGITAL_dp = P3 ^ 7;
sbit DIGITAL_H = P3 ^ 6;
sbit DIGITAL_L = P3 ^ 3;
//sbit DQ = P1 ^ 1;

bit temper_flag = 0; //温度读取标志
int temp = 0;
int intr = 0;

/*数码管显示数字*/
void printf_num(num)
{
    if (num == 0)
    {
        DIGITAL_a = 1;
        DIGITAL_b = 1;
        DIGITAL_c = 1;
        DIGITAL_d = 1;
        DIGITAL_e = 1;
        DIGITAL_f = 1;
        DIGITAL_g = 0;
        DIGITAL_dp = 0;
    }
    /*显示1*/
    if (num == 1)
    {
        DIGITAL_a = 0;
        DIGITAL_b = 1;
        DIGITAL_c = 1;
        DIGITAL_d = 0;
        DIGITAL_e = 0;
        DIGITAL_f = 0;
        DIGITAL_g = 0;
        DIGITAL_dp = 0;
    }
    /*显示2*/
    if (num == 2)
    {
        DIGITAL_a = 1;
        DIGITAL_b = 1;
        DIGITAL_c = 0;
        DIGITAL_d = 1;
        DIGITAL_e = 1;
        DIGITAL_f = 0;
        DIGITAL_g = 1;
        DIGITAL_dp = 0;
    }
    /*显示3*/
    if (num == 3)
    {
        DIGITAL_a = 1;
        DIGITAL_b = 1;
        DIGITAL_c = 1;
        DIGITAL_d = 1;
        DIGITAL_e = 0;
        DIGITAL_f = 0;
        DIGITAL_g = 1;
        DIGITAL_dp = 0;
    }
    /*显示4*/
    if (num == 4)
    {
        DIGITAL_a = 0;
        DIGITAL_b = 1;
        DIGITAL_c = 1;
        DIGITAL_d = 0;
        DIGITAL_e = 0;
        DIGITAL_f = 1;
        DIGITAL_g = 1;
        DIGITAL_dp = 0;
    }
    /*显示0*/
    if (num == 5)
    {
        DIGITAL_a = 1;
        DIGITAL_b = 0;
        DIGITAL_c = 1;
        DIGITAL_d = 1;
        DIGITAL_e = 0;
        DIGITAL_f = 1;
        DIGITAL_g = 1;
        DIGITAL_dp = 0;
    }
    /*显示6*/
    if (num == 6)
    {
        DIGITAL_a = 1;
        DIGITAL_b = 0;
        DIGITAL_c = 1;
        DIGITAL_d = 1;
        DIGITAL_e = 1;
        DIGITAL_f = 1;
        DIGITAL_g = 1;
        DIGITAL_dp = 0;
    }
    /*显示7*/
    if (num == 7)
    {
        DIGITAL_a = 1;
        DIGITAL_b = 1;
        DIGITAL_c = 1;
        DIGITAL_d = 0;
        DIGITAL_e = 0;
        DIGITAL_f = 0;
        DIGITAL_g = 0;
        DIGITAL_dp = 0;
    }
    /*显示8*/
    if (num == 8)
    {
        DIGITAL_a = 1;
        DIGITAL_b = 1;
        DIGITAL_c = 1;
        DIGITAL_d = 1;
        DIGITAL_e = 1;
        DIGITAL_f = 1;
        DIGITAL_g = 1;
        DIGITAL_dp = 0;
    }
    /*显示9*/
    if (num == 9)
    {
        DIGITAL_a = 1;
        DIGITAL_b = 1;
        DIGITAL_c = 1;
        DIGITAL_d = 1;
        DIGITAL_e = 0;
        DIGITAL_f = 1;
        DIGITAL_g = 1;
        DIGITAL_dp = 0;
    }
}

/*数码管显示温度*/
void printf_wendu(num)
{
    //	printf_num(num/10);
    DIGITAL_H = 0;
    printf_num(num / 10);
    //    DIGITAL_H = 0;
    DIGITAL_H = 1;

    DIGITAL_a = 0;
    DIGITAL_b = 0;
    DIGITAL_c = 0;
    DIGITAL_d = 0;
    DIGITAL_e = 0;
    DIGITAL_f = 0;
    DIGITAL_g = 0;
    DIGITAL_dp = 0;

    //	Delay_printf_wendu();
    //	printf_num(num%10);
    DIGITAL_L = 0;
    printf_num(num % 10);
    //    DIGITAL_L = 0;
    DIGITAL_L = 1;

    DIGITAL_a = 0;
    DIGITAL_b = 0;
    DIGITAL_c = 0;
    DIGITAL_d = 0;
    DIGITAL_e = 0;
    DIGITAL_f = 0;
    DIGITAL_g = 0;
    DIGITAL_dp = 0;

    //	Delay_printf_wendu();
}

void main(void)
{
	float temperature;
	    while (1)
    {
        if (temper_flag)
        {
            temper_flag = 0;
            temperature = rd_temperature(); //读温度
			temp = temperature;
        }
        
		printf_wendu(temp);
		intr++;
	    if (intr == 100) //1ms执行一次
	    {
	        intr = 0;
	        temper_flag = 1; //100ms温度读取标志位置1
	    }

    }

}

本站由 子书承宇 使用 Stellar 1.26.8 主题创建。本站总访问量
本博客所有文章除特别声明外,均采用 CC BY-NC-SA 4.0 许可协议,转载请注明出处。

载入天数... 载入时分秒...