引言: 本片文章想给大家分享一下使用HAL库驱动SI7006和AP3216C, 这两款常见的芯片的手册会在文章的末尾提供给大家。
一、SI7006和AP3216C简介
- SI7006
SI7006是一款数字湿度和温度传感器,由Silicon Labs(全称Silicon Laboratories Inc.)生产。SI7006使用了集成式微控制器和感测技术,可以准确测量环境中的温度和湿度。
SI7006的主要特点包括:
1. 温湿度测量:SI7006可以同时测量环境的温度和湿度。其温度测量范围为-40°C至+125°C,湿度测量范围为0%至100%相对湿度。
2. 高精确度:SI7006具有高精度的温湿度测量能力,其温度测量精度为±0.4°C,湿度测量精度为±3%RH。
3. 数字输出:SI7006将温湿度测量结果以数字形式输出,使用标准的I2C(Inter-Integrated Circuit)总线接口进行通信。这种数字输出形式方便了传感器与微控制器或其他数字系统的集成和数据处理。
4. 低功耗:SI7006采用低功耗设计,使其适用于电池供电或节能型应用场景。在测量时,SI7006的工作电流非常低,一般在200μA以下。
5. 低失真滤波:SI7006内置了低失真数字滤波器,可以减少测量结果的噪声和变化。
6. 温度传感器补偿:SI7006内部集成了温度传感器补偿功能,可以通过检测温度对湿度进行修正,提高测量精度。
总之,SI7006是一款高精度、数字输出的温湿度传感器,适用于多种应用场景,如气象观测、室内环境监测、自动控制系统等。它具有低功耗、高精确度和方便集成的特点,可以提供准确可靠的环境温湿度测量数据。
- AP3216C
AP3216C是一款集成式环境光和接近传感器,由AMS(Austriamicrosystems)公司生产。AP3216C可以用于测量环境光强度和检测物体的接近距离。
AP3216C的主要特点包括:
1. 环境光测量:AP3216C可以测量环境中的光照强度。它采用红外LED发射器和光敏电阻来实现对光照强度的感测。通过调整集成电路中的工作模式和增益,能够适应不同的光照条件。
2. 接近传感器:AP3216C还内置了接近传感器,可以检测物体与传感器之间的距离。它使用红外LED发射器和接收器之间的反射光信号来判断物体的接近情况。
3. 数字输出:AP3216C的测量结果以数字形式输出,使用标准的I2C总线接口进行通信。这种数字输出形式方便了传感器与微控制器或其他数字系统的集成和数据处理。
4. 低功耗:AP3216C采用低功耗设计,适合电池供电或节能型应用场景。在测量时,AP3216C的工作电流较低,一般在100μA左右。
5. 环境适应性:AP3216C采用了自适应环境补偿技术,能够自动调整测量范围和增益,提高测量精度和稳定性。
6. 多种光照模式:AP3216C支持多种光照模式,如主动模式和待机模式,可以根据实际需求选择不同的模式进行工作。
总之,AP3216C是一款集成式环境光和接近传感器,具有测量环境光强度和检测物体接近距离的功能。它具有数字输出、低功耗和自适应环境补偿等特点,适用于各种光照环境和接近检测应用场景,如智能手机、平板电脑、智能家居等。
二、硬件接线
三、代码实现
- 读取温湿度信息
#ifndef Si7006_H
#define Si7006_H
#define Si7006_SLAVE_ADDR (0x80) //最低位默认是主机发送
#define BUS_READ (0X01)
#define BUS_WRITE (0x00)
#define READ_TEMP (0xE3)
#define READ_HUMIDITY (0xE5)
#define SI7006_RESET (0xFE)
extern void Si7006_Init(void);
extern void
#endif
#include "Si7006.h"
extern I2C_HandleTypeDef hi2c1 //Cubemx自动帮我们生成的
void Si7006_Init(void)
{
//01 初始化i2c通道
HAL_I2C_Init(&hi2c1);
//02 发送复位指令给Si7006
Si7006_WriteByte(SI7006_RESET);
//03 延时一会
HAL_Delay(50);
}
uint8_t Si7006_WriteByte(uint8_t data)
{
uint8_t temp_buf = data;
HAL_StatusTypeDef flag;
//01 调用hal库的i2c发送函数将设备的地址发送出去
flag = HAL_I2C_Master_Transmit(&hi2c1, Si7006_SLAVE_ADDR|BUS_WRITE, &temp_buf, sizeof(temp_buf), 300);
if(flag != HAL_OK)
{
Error_Handler();
}
//02 等待数据发送完成
while(HAL_I2C_GetState(&hi2c1) != HAL_I2C_STATE_READY);
return 0;
}
uint16_t Si7006_Read_HalfWord(uint8_t reg)
{
uint16_t read_data = 0;
HAL_StatusTypeDef flag;
//01 发送从机地址和需要写的数据
flag = HAL_I2C_Master_Transmit(&hi2c1, Si7006_SLAVE_ADDR|BUS_WRITE, ®, sizeof(reg), 300);
if(flag != HAL_OK)
{
Error_Handler();
}
while(HAL_I2C_GetState(&hi2c1) != HAL_I2C_STATE_READY);
//需要改变数据的传输方向
if(HAL_I2C_Master_Receive(&hi2c1, SI7006_ADDR | SI7006_R , (uint8_t*)&read_data, 2,300) != HAL_OK)
{
Error_Handler();
}
return read_data;
}
//进行高低字节的转换
void Real_Read_Data(uint8_t cmd)
{
uint16_t data = 0, low_data = 0, high_data = 0;
data = Si7006_Read_HalfWord(cmd);
low_data = data & 0xff;
high_data = (data >> 8) & 0xff;
data = (low_data << 8) + high_data;
return data;
}
void read_temp_humi_test(void)
{
uint16_t tem, humi;
tem = Real_Read_Data(READ_TEMP);
humi = Real_Read_Data(READ_HUMIDITY);
//按照手册提供的公式对数据进行转换
tem = ((17572*tem)/65536 - 4685);
hum = (125*hum/65536 - 6);
tem_1 = tem/100;
tem_2 = tem%100;
printf("\r hum = %d%% \n", hum);
printf("\r tem = %d.%d\n", tem_1,tem_2);
}
/*将printf的输出从定向到屏幕*/
#ifdef __GNUC__
#define PUTCHAR_PROTOTYPE int __io_putchar(int ch)
PUTCHAR_PROTOTYPE
{
HAL_UART_Transmit(&huart4,(uint8_t*)&ch,1,HAL_MAX_DELAY);
return ch;
}
#endif
- 读取光照强度
/*
* ap3216c.h
*
* Created on: Dec 28, 2023
* Author: 哈西好多
*/
#ifndef INC_AP3216C_H_
#define INC_AP3216C_H_
#include "main.h"
#define AP3216_ADDR (0x3C)
#define AP3216_W (0x00)
#define AP3216_R (0x01)
/**************** System Register ****************/
#define SYS_CONFIG_ADDR (0x00) // System Configuration, Default:0x00,Bits[2:0],System Mode
#define SYS_ALS_ACT (0x01) // 0x01: ALS function active
#define SYS_SW_RESET (0x04) // 0x04: SW reset
#define ALS_DATA_LOW (0x0C) // Bits[7:0](RO) ALS lower byte of ADC OUTPUT
#define ALS_DATA_HIGH (0x0D) // Bits[7:0](RO) ALS Higher byte of ADC OUTPUT
extern uint8_t AP3216_Init(void);
extern uint8_t AP3216_WriteOneByte(uint8_t reg, uint8_t data);
extern uint8_t AP3216_ReadOneByte(uint8_t reg);
extern uint16_t AP3216_Read_ALS_Data();
#endif
/*
I2C驱动ap216c模块读取环境的光照信息
*/
uint8_t AP3216_Init(void)
{
uint8_t ret_value = 0;
AP3216_WriteOneByte(SYS_CONFIG_ADDR, SYS_SW_RESET);
HAL_Delay(50);
AP3216_WriteOneByte(SYS_CONFIG_ADDR, SYS_ALS_ACT);
HAL_Delay(50);
ret_value = AP3216_ReadOneByte(SYS_CONFIG_ADDR);
if(ret_value != SYS_ALS_ACT)
{
printf("read error \n");
}
printf("\r I2C Configuration register: 0x%x \n", SYS_CONFIG_ADDR);
printf("\r I2C Read configuration value: 0x%x \n", ret_value);
return 0;
}
/*往i2c总线上写一个字节的数据*/
uint8_t AP3216_WriteOneByte(uint8_t reg, uint8_t data)
{
uint16_t write_data = reg | (data<<8);
/*先发送高位*/
if(HAL_I2C_Master_Transmit(&hi2c1, AP3216_ADDR | AP3216_W , (uint8_t*)&write_data, 2, 300) != HAL_OK)
{
Error_Handler();
}
while (HAL_I2C_GetState(&hi2c1) != HAL_I2C_STATE_READY);
return 0;
}
uint8_t AP3216_ReadOneByte(uint8_t reg)
{
uint8_t read_data = 0;
if(HAL_I2C_Master_Transmit(&hi2c1, AP3216_ADDR | AP3216_W , (uint8_t*)®, 1, 300) != HAL_OK)
{
Error_Handler();
}
while (HAL_I2C_GetState(&hi2c1) != HAL_I2C_STATE_READY);
if(HAL_I2C_Master_Receive(&hi2c1, AP3216_ADDR | AP3216_R , (uint8_t*)&read_data, 1, 300) != HAL_OK)
{
Error_Handler();
}
return read_data;
}
uint16_t AP3216_Read_ALS_Data()
{
uint8_t als_l = 0, als_h = 0;
uint16_t data;
als_l = AP3216_ReadOneByte(ALS_DATA_LOW);
als_h = AP3216_ReadOneByte(ALS_DATA_HIGH);
data = (als_h<<8) | (als_l);
printf("%d\n",data);
return data;
}
本文只是提供一个代码参考, 当然整体的读取数据的代码思路还是一样的, 大家读取到的数据根据自己的需求就行相应的逻辑处理。
芯片手册:
链接:https://pan.baidu.com/s/1SZMo-wfXccfckpy8beoLjw
提取码:1234