基于ESP-IDF开发环境使用ESP32读取DS18B20温度

文章目录[隐藏]

一、原理

        在只有一个DS18B20的时候,仅需三个部分就能完成读取温度的操作。

        (1)先初始化

        (2)写数据操作

        (3)读数据操作

二、代码

​​​​​​DS18B20参考代码链接,此链接有完整的基于ESP-IDF环境的ds18b20程序,有兴趣的可以去看看。

笔者的代码是参考以上链接的代码进行编写

以下代码仅供参考,代码仅为简单的读取温度操作,并未做出超出温度范围的限制。需要注意的是,此示例用的是4号引脚能正常读取数据,笔者的2、5号暂时不能读取,具体原因并未寻找,有能力的可以参照此示例去试试查看是何种问题导致的。(本文使用ESP32 DEVKIT V1开发板)

#include <stdio.h>
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "driver/gpio.h"
#include "sdkconfig.h"

#define DS18_PIN 4    //定义引脚
#define ESP_HIGH gpio_set_level(DS18_PIN, 1)    //设置高电平
#define ESP_LOW gpio_set_level(DS18_PIN, 0)    //设置低电平
#define ESP_GET gpio_get_level(DS18_PIN)    //读取电平
#define ESP_OUT_MODE gpio_set_direction(DS18_PIN, GPIO_MODE_OUTPUT)    //设置输出模式
#define ESP_INPUT_MODE gpio_set_direction(DS18_PIN, GPIO_MODE_INPUT)    //设置输入模式

#define SKIP_ROM 0xCC    //跳过ROM操作
#define TRANSFORMATION_TEMP 0x44    //转换温度操作
#define READ_TEMP 0xBE    //读数据操作

/*************************初始化操作*************************/
unsigned char init_DS18(void)
{
    unsigned int init_state = 0;
    ESP_OUT_MODE;
    ESP_LOW;
    ets_delay_us(480);
    ESP_HIGH;

    ESP_INPUT_MODE;//设置输入模式,就是高阻态,此时上拉电阻提供高电平
    ets_delay_us(70);
    init_state = (gpio_get_level(DS18_PIN) == 0);

    ets_delay_us(410);
    printf("初始化状态:%d", init_state);
    return init_state;
}
/*************************写位操作*************************/
void DS18_Write_bit(char bit)
{
/*******写1操作********/
    if (bit & 1)
    {
        ESP_OUT_MODE;
        ESP_LOW;
        ets_delay_us(6);
        ESP_INPUT_MODE;//设置输入模式,就是高阻态,此时上拉电阻提供高电平
        ets_delay_us(64);
    }
/*******写0操作********/
    else
    {
        ESP_OUT_MODE;
        ESP_LOW;
        ets_delay_us(60);
        ESP_INPUT_MODE;//设置输入模式,就是高阻态,此时上拉电阻提供高电平
        ets_delay_us(10);
    }
}
/*************************读位操作*************************/
unsigned char DS18_Read_bit(void)
{
    unsigned char bit = 0;
    ESP_OUT_MODE;
/*******拉低电平,开始读取数据********/
    ESP_LOW;
    ets_delay_us(6);
    ESP_INPUT_MODE;//设置输入数据
    ets_delay_us(9);
    bit = ESP_GET;
    ets_delay_us(55);

    return bit;
}
/*************************写数据操作*************************/
void DS18_Write_byte(unsigned char data)
{
    unsigned char i;
    unsigned char a_data;
/*******写8次,一次为一位********/
    for (i = 0; i < 8; i++)
    {
        a_data = data >> i;//每写一位数据,就向右移一位,保证8位数据都能写入
        a_data &= 0x01;//与操作,只留刚刚右移的一位数据
        DS18_Write_bit(a_data);//写入一位数据
    }
    ets_delay_us(100);
}
/*************************读数据操作*************************/
unsigned char DS18_Read_byte(void)
{
    unsigned char i;
    unsigned char data = 0;
/*******读取8次,一次为一位********/
    for (i = 0; i < 8; i++)
    {
        if (DS18_Read_bit())
            data |= 0x01 << i;//读取到1就会向左移相应的位数
        ets_delay_us(15);
    }
    return data;
}

void app_main(void)
{
    gpio_pad_select_gpio(DS18_PIN);
    while (1)
    {
        unsigned char TEMP_LOW, TEMP_HIGH;
        float TEMP = 0;
/*************************温度转换过程*************************/
        while(!init_DS18())
        {
            printf("正在尝试初始化...");
        }
        DS18_Write_byte(SKIP_ROM);
        DS18_Write_byte(TRANSFORMATION_TEMP);

        vTaskDelay(750 / portTICK_PERIOD_MS);
/*************************读取温度过程*************************/
        while(!init_DS18())
        {
            printf("正在尝试初始化...");
        }
        DS18_Write_byte(SKIP_ROM);
        DS18_Write_byte(READ_TEMP);
        TEMP_LOW = DS18_Read_byte();
        TEMP_HIGH = DS18_Read_byte();

/*************************把数据转换成十进制*************************/
        TEMP = (float)(TEMP_LOW + (TEMP_HIGH * 256)) / 16;

        printf("温度=%f", TEMP);
        vTaskDelay(2000 / portTICK_PERIOD_MS);
    }
}

版权声明:本文为CSDN博主「lanVastZ」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/u011594289/article/details/122787748

生成海报
点赞 0

lanVastZ

我还没有学会写个人说明!

暂无评论

发表评论

相关推荐

ESP32学习记录<四>ADC和DAC

ESP32学习记录ADC和DAC 前言 ADC和DAC是单片机比较常用的,ESP32具有12位的ADC和8位的DAC。今天我就简单地记录它们的使用。 一、ADC ADC也就是我们通常所说的模数转换,模拟信号

ESP32_IDF学习(2)--GPIO

简介 ESP32 芯片有 40 个物理 GPIO pad。每个 pad 都可用作一个通用 IO,或连接一个内部的外设信号。IO_MUX、RTC IO_MUX 和 GPIO 交换矩阵用于将信号从外设传输至 GPIO pad。这些模块