CubeMX配置
- 打开i2c
- 打开与电脑通信的串口
硬件连接
使用的是野火的指南者,型号是stm32f103ve
ADDR引脚接地
代码
bh1750.c
#include "bh1750.h"
#include "i2c.h"
/*i2c句柄*/
#define bh1750_i2c hi2c1
/*内部函数声明区*/
static uint8_t BH1750_Send_Cmd(BH1750_MODE cmd);
static uint8_t BH1750_Read_Dat(uint8_t* dat);
static uint16_t BH1750_Dat_To_Lux(uint8_t* dat);
/**
* @brief 向BH1750发送一条指令
* @param cmd —— BH1750工作模式指令(在BH1750_MODE中枚举定义)
* @retval 成功返回HAL_OK
*/
static uint8_t BH1750_Send_Cmd(BH1750_MODE cmd)
{
return HAL_I2C_Master_Transmit(&bh1750_i2c, BH1750_ADDR_WRITE, (uint8_t*)&cmd, 1, 0xFFFF);
}
/**
* @brief 从BH1750接收一次光强数据
* @param dat —— 存储光照强度的地址(两个字节数组)
* @retval 成功 —— 返回HAL_OK
*/
static uint8_t BH1750_Read_Dat(uint8_t* dat)
{
return HAL_I2C_Master_Receive(&bh1750_i2c, BH1750_ADDR_READ, dat, 2, 0xFFFF);
}
/**
* @brief 将BH1750的两个字节数据转换为光照强度值(0-65535)
* @param dat —— 存储光照强度的地址(两个字节数组)
* @retval 成功 —— 返回光照强度值
*/
static uint16_t BH1750_Dat_To_Lux(uint8_t* dat)
{
uint16_t lux = 0;
lux = dat[0];
lux <<= 8;
lux |= dat[1];
lux = (int)(lux / 1.2);
return lux;
}
/**
* @brief 返回光照强度值
* @param 无
* @retval 成功 —— 返回光照强度值
*/
uint16_t Get_BH1750_Value(void)
{
uint8_t dat[2] = {0}; //dat[0]是高字节,dat[1]是低字节
uint16_t lux;
if(HAL_OK != BH1750_Send_Cmd(ONCE_H_MODE))
{
return 0;
}
HAL_Delay(120);
if(HAL_OK != BH1750_Read_Dat(dat))
{
return 0;
}
lux = BH1750_Dat_To_Lux(dat);
return lux;
}
bh1750.h
#ifndef __BH1750_H_
#define __BH1750_H_
#include "stdint.h"
/*外部函数区*/
/*通过指针获取光照强度值*/
uint16_t Get_BH1750_Value(void);
/* //用法
uint16_t bh1750_lux;
bh1750_lux = Get_BH1750_Value();
printf("current: %5d lux\r\n", bh1750_lux);
*/
/*bh1750地址*/
#define BH1750_ADDR_WRITE 0x46 //01000110
#define BH1750_ADDR_READ 0x47 //01000111
typedef enum
{
POWER_OFF_CMD = 0x00, //断电:无激活状态
POWER_ON_CMD = 0x01, //通电:等待测量指令
RESET_REGISTER = 0x07, //重置数字寄存器(在断电状态下不起作用)
CONT_H_MODE = 0x10, //连续H分辨率模式:在11x分辨率下开始测量,测量时间120ms
CONT_H_MODE2 = 0x11, //连续H分辨率模式2:在0.51x分辨率下开始测量,测量时间120ms
CONT_L_MODE = 0x13, //连续L分辨率模式:在411分辨率下开始测量,测量时间16ms
ONCE_H_MODE = 0x20, //一次高分辨率模式:在11x分辨率下开始测量,测量时间120ms,测量后自动设置为断电模式
ONCE_H_MODE2 = 0x21, //一次高分辨率模式2:在0.51x分辨率下开始测量,测量时间120ms,测量后自动设置为断电模式
ONCE_L_MODE = 0x23 //一次低分辨率模式:在411x分辨率下开始测量,测量时间16ms,测量后自动设置为断电模式
} BH1750_MODE;
#endif /*__BH1750_H_*/
main.c
头文件
#include "bh1750.h"
#include "stdio.h"
初始化
uint16_t bh1750_lux;
while循环
bh1750_lux = Get_BH1750_Value();
PrintfDebug("current: %05d lux\r\n", bh1750_lux);
HAL_Delay(100);
演示现象
注:当手电筒照射时才会有较高值。