【esp32-s3】8.1 I2C——光感BH1750

一、前言

本章介绍使用安信可的esp32s3+合宙的BH1750光照传感器。

二、硬件

在这里插入图片描述
i2c clk – pin0
i2c sda – pin1

三、代码

#include <stdio.h>
#include "esp_log.h"
#include "driver/i2c.h"

//#include "bh1750.h"

const char *TAG = "i2c-bh1750";

#define I2C_MASTER_NUM              0                          /*!< I2C master i2c port number, the number of i2c peripheral interfaces available will depend on the chip */

/*bh1750 pin*/
#define I2C_MASTER_SCL_IO           0      /*!< GPIO number used for I2C master clock */
#define I2C_MASTER_SDA_IO           1      /*!< GPIO number used for I2C master data  */

#define I2C_MASTER_FREQ_HZ_SLOW     100000                     /*!< I2C master clock frequency */
#define I2C_MASTER_FREQ_HZ_FAST     400000                     /*!< I2C master clock frequency */
#define I2C_MASTER_TX_BUF_DISABLE   0                          /*!< I2C master doesn't need buffer */
#define I2C_MASTER_RX_BUF_DISABLE   0                          /*!< I2C master doesn't need buffer */
#define I2C_MASTER_TIMEOUT_MS       100

/* bh1750 addr*/
#define BH1750_SENSOR_ADDR_LOW      0x23        /*address pin low (GND) */
#define BH1750_SENSOR_ADDR_HIGH     0x24        /*address pin high (VCC) */
#define BH1750_SENSOR_ADDR BH1750_SENSOR_ADDR_LOW   /*ADDR PIN (GND)*/

#define BH1750_WHO_AM_I_REG_ADDR    0x75        /*!< Register addresses of the "who am I" register */

#define BH1750_PWR_MGMT_1_REG_ADDR         0x6B        /*!< Register addresses of the power managment register */
#define BH1750_RESET_BIT                   7

// bh1750 registers define
#define BH1750_POWER_DOWN   	   0x00	// power down
#define BH1750_POWER_ON			   0x01	// power on
#define BH1750_RESET			   0x07	// reset
#define BH1750_CON_H_RES_MODE	   0x10	// Continuously H-Resolution Mode
#define BH1750_CON_H_RES_MODE2	   0x11	// Continuously H-Resolution Mode2
#define BH1750_CON_L_RES_MODE	   0x13	// Continuously L-Resolution Mode
#define BH1750_ONE_H_RES_MODE	   0x20	// One Time H-Resolution Mode
#define BH1750_ONE_H_RES_MODE2	   0x21	// One Time H-Resolution Mode2
#define BH1750_ONE_L_RES_MODE	   0x23	// One Time L-Resolution Mode

#define I2C_SEND_DELAY 10

/**
 * @brief Read a sequence of bytes from a BH1750 sensor registers
 */
int bh1750_register_read(uint8_t *data, size_t len)
{
    
    
    int ret=0;
    ret = i2c_master_read_from_device(I2C_MASTER_NUM, BH1750_SENSOR_ADDR, data, len, I2C_MASTER_TIMEOUT_MS / portTICK_RATE_MS);

    if(ret!=0)
        ESP_LOGI(TAG, "%s error [%02X] \n",__FUNCTION__, ret);
    return ret;
}

int bh1750_recv(uint8_t *data, size_t len)
{
    
    
    int ret;
    ret = bh1750_register_read(data, len);

    // ESP_LOGI(TAG, "%s \t 0x[%d][%d]",__FUNCTION__,data[0],data[1]);

    if(ret != 0)
        ESP_LOGI(TAG, "%s error [%02X] \n",__FUNCTION__, ret);
    return ret;
}

/**
 * @brief Write a byte to a BH1750 sensor register
 */
int bh1750_register_write_byte(uint8_t data)
{
    
    
    int ret;
    uint8_t write_buf[2] = {
    
    data, 0x00};

    ret = i2c_master_write_to_device(I2C_MASTER_NUM, BH1750_SENSOR_ADDR, write_buf, 1, I2C_MASTER_TIMEOUT_MS / portTICK_RATE_MS);

    return ret;
}

int bh1750_send(uint8_t data)
{
    
    
    int ret;
    ret = bh1750_register_write_byte(data);

    if(ret != 0)
        ESP_LOGI(TAG, "%s error [%d] send [%d]",__FUNCTION__, ret,data);
    return ret;
}

int bh1750_send2(uint8_t data)
{
    
    
    int ret;
    uint8_t write_buf[2] = {
    
    data, 0x00};

    ret = i2c_master_write_to_device(I2C_MASTER_NUM, BH1750_SENSOR_ADDR, write_buf, 1, I2C_MASTER_TIMEOUT_MS / portTICK_RATE_MS);

    if(ret != 0)
        ESP_LOGI(TAG, "%s error [%d] send [%d]",__FUNCTION__, ret,data);
    return ret;
}

void bh1750_set_measure_mode(uint8_t mode,uint8_t time)
{
    
    
    // ESP_LOGI(TAG, "%s RESET ... ",__FUNCTION__);
    bh1750_send(BH1750_RESET);

    // ESP_LOGI(TAG, "%s SETMODE ... ",__FUNCTION__);
    bh1750_send(mode);

    //wait 180ms to read 
    // ESP_LOGI(TAG, "%s WAIT ... \n",__FUNCTION__);
    vTaskDelay(pdMS_TO_TICKS(time));
}

/**
 * @brief get BH1750 sensor light value
 */
void bh1750_read_light(uint8_t *data)
{
    
    
    bh1750_set_measure_mode(BH1750_CON_H_RES_MODE, 180);

    //get recv
    bh1750_recv(data, 2);
}

/**
 * @brief i2c master initialization
 */
int i2c_master_init(void)
{
    
    
    int i2c_master_port = I2C_MASTER_NUM;

    i2c_config_t conf = {
    
    
        .mode = I2C_MODE_MASTER,
        .sda_io_num = I2C_MASTER_SDA_IO,
        .scl_io_num = I2C_MASTER_SCL_IO,
        .sda_pullup_en = GPIO_PULLUP_ENABLE,
        .scl_pullup_en = GPIO_PULLUP_ENABLE,
        .master.clk_speed = I2C_MASTER_FREQ_HZ_SLOW,
    };

    i2c_param_config(i2c_master_port, &conf);

    return i2c_driver_install(i2c_master_port, conf.mode, I2C_MASTER_RX_BUF_DISABLE, I2C_MASTER_TX_BUF_DISABLE, 0);
}

void app_main(void)
{
    
    
    uint8_t data[2];
    int ret = ESP_OK;
    ESP_ERROR_CHECK(i2c_master_init());
    ESP_LOGI(TAG, "I2C initialized successfully\n");

    /*2. POWER ON*/
    ret = bh1750_send(BH1750_POWER_ON);
    if(ret != 0)
        ESP_LOGI(TAG, "ret = %X\n",ret);

    ESP_LOGI(TAG, "start test\n");

    ESP_LOGI(TAG, "cmd: reset\n");
    bh1750_send(BH1750_RESET);

    int test=1;
    while (1)
    {
    
    
        if(test >20)
            break;
        // ESP_LOGI(TAG, "test %d\n",test);

        bh1750_read_light(data);

        ESP_LOGI(TAG, "%s\t%d \t0x[%02x%02x] [%d]",__FUNCTION__,test,data[0],data[1],data[0]*0x100 + data[1]);

        test++;
    }
    
    ESP_ERROR_CHECK(i2c_driver_delete(I2C_MASTER_NUM));
    ESP_LOGI(TAG, "I2C unitialized successfully");
}

四、结果

在这里插入图片描述

如图,其中测试7-10是手遮挡住光感。

猜你喜欢

转载自blog.csdn.net/qq_38091632/article/details/128358646