HAL库开发BMP280读取压强

基于STM32F103C8T6 IIC读取BMP280传感器的压强与温度,并计算海拔。

计算的海拔高度低于海平面,而实际的海拔高度是高于海平面的,可能与环境温度、计算方法有关。实测压强大于101.325Kpa,误差还是很大的。效果图如下:

参考文档:

GitHub - ciastkolog/BMP280_STM32: BMP280 / BME280 driver STM32 HAL I2C

根据温度、气压计算海拔高度_大强强小强强的博客-CSDN博客_通过气压计算海拔

硬件连接: PA9 TX

PA10 RX

PB6 SCL

PB7 SDA

BMP280模块

移植只需下载bmp.c bmp280.h即可;

或者直接复制下面的部分代码;

main.c

/* USER CODE BEGIN Header */
/**
  ******************************************************************************
  * @file           : main.c
  * @brief          : Main program body
  ******************************************************************************
  * @attention
  *
  * Copyright (c) 2023 STMicroelectronics.
  * All rights reserved.
  *
  * This software is licensed under terms that can be found in the LICENSE file
  * in the root directory of this software component.
  * If no LICENSE file comes with this software, it is provided AS-IS.
  *
  ******************************************************************************
  */
/* USER CODE END Header */
/* Includes ------------------------------------------------------------------*/
#include "main.h"
#include "i2c.h"
#include "usart.h"
#include "gpio.h"

/* Private includes ----------------------------------------------------------*/
/* USER CODE BEGIN Includes */
#include "bmp280.h"
#include "stdio.h"
#include "math.h"
/* USER CODE END Includes */

/* Private typedef -----------------------------------------------------------*/
/* USER CODE BEGIN PTD */

/* USER CODE END PTD */

/* Private define ------------------------------------------------------------*/
/* USER CODE BEGIN PD */

/* USER CODE END PD */

/* Private macro -------------------------------------------------------------*/
/* USER CODE BEGIN PM */


/* USER CODE END PM */

/* Private variables ---------------------------------------------------------*/

/* USER CODE BEGIN PV */

/* USER CODE END PV */

/* Private function prototypes -----------------------------------------------*/
void SystemClock_Config(void);
/* USER CODE BEGIN PFP */

/* USER CODE END PFP */

/* Private user code ---------------------------------------------------------*/
/* USER CODE BEGIN 0 */
double pow(double X,double Y);
double data_conversion(double air_pressure,double temperature)
{
    double conversion_alt;
    conversion_alt=(pow(101325/air_pressure,1/5.257)-1)*temperature/0.0065f;
    return conversion_alt;
}
/* USER CODE END 0 */

/**
  * @brief  The application entry point.
  * @retval int
  */
int main(void)
{
  /* USER CODE BEGIN 1 */
  //    int state=0;
    double Alt;
    bmp280_params_t  params;
    BMP280_HandleTypedef bmp280_dev;
    float pressure, temperature, humidity;
  /* USER CODE END 1 */

  /* MCU Configuration--------------------------------------------------------*/

  /* Reset of all peripherals, Initializes the Flash interface and the Systick. */
  HAL_Init();

  /* USER CODE BEGIN Init */

  /* USER CODE END Init */

  /* Configure the system clock */
  SystemClock_Config();

  /* USER CODE BEGIN SysInit */

  /* USER CODE END SysInit */

  /* Initialize all configured peripherals */
  MX_GPIO_Init();
  MX_I2C1_Init();
  MX_USART1_UART_Init();
    
  /* USER CODE BEGIN 2 */

    bmp280_init_default_params(&params); //BMP280模块配置参数。
    bmp280_dev.addr = BMP280_I2C_ADDRESS_0;
    bmp280_dev.i2c = &hi2c1;
    bmp280_init(&bmp280_dev, &params);
    
//state=bmp280_init(&bmp280_dev, &params);
//    printf("init state = %d \r\n",state);

    bool bme280p = bmp280_dev.id == BME280_CHIP_ID;
    
  /* USER CODE END 2 */

  /* Infinite loop */
  /* USER CODE BEGIN WHILE */
  while (1)
  {
    
    bmp280_read_float(&bmp280_dev, &temperature, &pressure, &humidity);
    Alt=data_conversion(pressure,temperature);
        printf("Pressure: %.2f Pa, Temperature: %.2f C, Alt:%.3f m\r\n", pressure, temperature,Alt);
  if (bme280p)
    printf(", Humidity: %.2f\n", humidity);
  else
    printf("\n");
    HAL_GPIO_TogglePin(GPIOC, GPIO_PIN_13);
    HAL_Delay(500);

    /* USER CODE END WHILE */
    
    /* USER CODE BEGIN 3 */
    
  }
  /* USER CODE END 3 */
}

/**
  * @brief System Clock Configuration
  * @retval None
  */
void SystemClock_Config(void)
{
  RCC_OscInitTypeDef RCC_OscInitStruct = {0};
  RCC_ClkInitTypeDef RCC_ClkInitStruct = {0};

  /** Initializes the RCC Oscillators according to the specified parameters
  * in the RCC_OscInitTypeDef structure.
  */
  RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSE;
  RCC_OscInitStruct.HSEState = RCC_HSE_ON;
  RCC_OscInitStruct.HSEPredivValue = RCC_HSE_PREDIV_DIV1;
  RCC_OscInitStruct.HSIState = RCC_HSI_ON;
  RCC_OscInitStruct.PLL.PLLState = RCC_PLL_ON;
  RCC_OscInitStruct.PLL.PLLSource = RCC_PLLSOURCE_HSE;
  RCC_OscInitStruct.PLL.PLLMUL = RCC_PLL_MUL2;
  if (HAL_RCC_OscConfig(&RCC_OscInitStruct) != HAL_OK)
  {
    Error_Handler();
  }
  /** Initializes the CPU, AHB and APB buses clocks
  */
  RCC_ClkInitStruct.ClockType = RCC_CLOCKTYPE_HCLK|RCC_CLOCKTYPE_SYSCLK
                              |RCC_CLOCKTYPE_PCLK1|RCC_CLOCKTYPE_PCLK2;
  RCC_ClkInitStruct.SYSCLKSource = RCC_SYSCLKSOURCE_PLLCLK;
  RCC_ClkInitStruct.AHBCLKDivider = RCC_SYSCLK_DIV1;
  RCC_ClkInitStruct.APB1CLKDivider = RCC_HCLK_DIV1;
  RCC_ClkInitStruct.APB2CLKDivider = RCC_HCLK_DIV1;

  if (HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_0) != HAL_OK)
  {
    Error_Handler();
  }
}

/* USER CODE BEGIN 4 */
int fputc(int ch,FILE *f){
    HAL_UART_Transmit(&huart1,(uint8_t *)&ch,1,100);
    return ch;
}


/* USER CODE END 4 */

/**
  * @brief  This function is executed in case of error occurrence.
  * @retval None
  */
void Error_Handler(void)
{
  /* USER CODE BEGIN Error_Handler_Debug */
  /* User can add his own implementation to report the HAL error return state */
  __disable_irq();
  while (1)
  {
  }
  /* USER CODE END Error_Handler_Debug */
}

#ifdef  USE_FULL_ASSERT
/**
  * @brief  Reports the name of the source file and the source line number
  *         where the assert_param error has occurred.
  * @param  file: pointer to the source file name
  * @param  line: assert_param error line source number
  * @retval None
  */
void assert_failed(uint8_t *file, uint32_t line)
{
  /* USER CODE BEGIN 6 */
  /* User can add his own implementation to report the file name and line number,
     ex: printf("Wrong parameters value: file %s on line %d\r\n", file, line) */
  /* USER CODE END 6 */
}
#endif /* USE_FULL_ASSERT */

bmp280.c

/**
 * Ciastkolog.pl (https://github.com/ciastkolog)
 * 
*/
/**
 * The MIT License (MIT)
 *
 * Copyright (c) 2016 sheinz (https://github.com/sheinz)
 *
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 * of this software and associated documentation files (the "Software"), to deal
 * in the Software without restriction, including without limitation the rights
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 * copies of the Software, and to permit persons to whom the Software is
 * furnished to do so, subject to the following conditions:
 *
 * The above copyright notice and this permission notice shall be included in
 * all copies or substantial portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 * THE SOFTWARE.
 */

#include "bmp280.h"
/**
 * BMP280 registers
 */
#define BMP280_REG_TEMP_XLSB   0xFC /* bits: 7-4 */
#define BMP280_REG_TEMP_LSB    0xFB
#define BMP280_REG_TEMP_MSB    0xFA
#define BMP280_REG_TEMP        (BMP280_REG_TEMP_MSB)
#define BMP280_REG_PRESS_XLSB  0xF9 /* bits: 7-4 */
#define BMP280_REG_PRESS_LSB   0xF8
#define BMP280_REG_PRESS_MSB   0xF7
#define BMP280_REG_PRESSURE    (BMP280_REG_PRESS_MSB)
#define BMP280_REG_CONFIG      0xF5 /* bits: 7-5 t_sb; 4-2 filter; 0 spi3w_en */
#define BMP280_REG_CTRL        0xF4 /* bits: 7-5 osrs_t; 4-2 osrs_p; 1-0 mode */
#define BMP280_REG_STATUS      0xF3 /* bits: 3 measuring; 0 im_update */
#define BMP280_REG_CTRL_HUM    0xF2 /* bits: 2-0 osrs_h; */
#define BMP280_REG_RESET       0xE0
#define BMP280_REG_ID          0xD0
#define BMP280_REG_CALIB       0x88
#define BMP280_REG_HUM_CALIB   0x88

#define BMP280_RESET_VALUE     0xB6



void bmp280_init_default_params(bmp280_params_t *params) {
    params->mode = BMP280_MODE_NORMAL;
    params->filter = BMP280_FILTER_OFF;
    params->oversampling_pressure = BMP280_STANDARD;
    params->oversampling_temperature = BMP280_STANDARD;
    params->oversampling_humidity = BMP280_STANDARD;
    params->standby = BMP280_STANDBY_250;
}

static bool read_register16(BMP280_HandleTypedef *dev, uint8_t addr, uint16_t *value) {
    uint16_t tx_buff;
    uint8_t rx_buff[2];
    tx_buff = (dev->addr << 1);

    if (HAL_I2C_Mem_Read(dev->i2c, tx_buff, addr, 1, rx_buff, 2, 5000)
            == HAL_OK) {
        *value = (uint16_t) ((rx_buff[1] << 8) | rx_buff[0]);
        return true;
    } else
        return false;

}

static inline int read_data(BMP280_HandleTypedef *dev, uint8_t addr, uint8_t *value,
        uint8_t len) {
    uint16_t tx_buff;
    tx_buff = (dev->addr << 1);
//IIC的配置信息结构体    七位地址  内部内存地址 内部内存地址大小 指向数据缓冲区的指针 发送的数据量 超时时间
    if (HAL_I2C_Mem_Read(dev->i2c, tx_buff, addr, 1, value, len, 5000) == HAL_OK)
        return 0;
    else
        return 1;

}

static bool read_calibration_data(BMP280_HandleTypedef *dev) {

    if (read_register16(dev, 0x88, &dev->dig_T1)
            && read_register16(dev, 0x8a, (uint16_t *) &dev->dig_T2)
            && read_register16(dev, 0x8c, (uint16_t *) &dev->dig_T3)
            && read_register16(dev, 0x8e, &dev->dig_P1)
            && read_register16(dev, 0x90, (uint16_t *) &dev->dig_P2)
            && read_register16(dev, 0x92, (uint16_t *) &dev->dig_P3)
            && read_register16(dev, 0x94, (uint16_t *) &dev->dig_P4)
            && read_register16(dev, 0x96, (uint16_t *) &dev->dig_P5)
            && read_register16(dev, 0x98, (uint16_t *) &dev->dig_P6)
            && read_register16(dev, 0x9a, (uint16_t *) &dev->dig_P7)
            && read_register16(dev, 0x9c, (uint16_t *) &dev->dig_P8)
            && read_register16(dev, 0x9e,
                    (uint16_t *) &dev->dig_P9)) {

        return true;
    }

    return false;
}

static bool read_hum_calibration_data(BMP280_HandleTypedef *dev) {
    uint16_t h4, h5;

    if (!read_data(dev, 0xa1, &dev->dig_H1, 1)
            && read_register16(dev, 0xe1, (uint16_t *) &dev->dig_H2)
            && !read_data(dev, 0xe3, &dev->dig_H3, 1)
            && read_register16(dev, 0xe4, &h4)
            && read_register16(dev, 0xe5, &h5)
            && !read_data(dev, 0xe7, (uint8_t *) &dev->dig_H6, 1)) {
        dev->dig_H4 = (h4 & 0x00ff) << 4 | (h4 & 0x0f00) >> 8;
        dev->dig_H5 = h5 >> 4;

        return true;
    }

    return false;
}

static int write_register8(BMP280_HandleTypedef *dev, uint8_t addr, uint8_t value) {
    uint16_t tx_buff;

    tx_buff = (dev->addr << 1);

    if (HAL_I2C_Mem_Write(dev->i2c, tx_buff, addr, 1, &value, 1, 10000) == HAL_OK)
        
        return false;
    else
        return true;
}

bool bmp280_init(BMP280_HandleTypedef *dev, bmp280_params_t *params) {

    if (dev->addr != BMP280_I2C_ADDRESS_0
            && dev->addr != BMP280_I2C_ADDRESS_1) {
        return false;
    }

    if (read_data(dev, BMP280_REG_ID, &dev->id, 1)) {
        return false;
    }

    if (dev->id != BMP280_CHIP_ID && dev->id != BME280_CHIP_ID) {
        return false;
    }

    // Soft reset.
    if (write_register8(dev, BMP280_REG_RESET, BMP280_RESET_VALUE)) {
        return false;
    }
    
    // Wait until finished copying over the NVP data.
    while (1) {
        uint8_t status;
        if (!read_data(dev, BMP280_REG_STATUS, &status, 1)
                && (status & 1) == 0)
            break;
    }

    if (!read_calibration_data(dev)) {
        return false;
    }

    if (dev->id == BME280_CHIP_ID && !read_hum_calibration_data(dev)) {
        return false;
    }

    uint8_t config = (params->standby << 5) | (params->filter << 2);
    if (write_register8(dev, BMP280_REG_CONFIG, config)) {
        return false;
    }

    if (params->mode == BMP280_MODE_FORCED) {
        params->mode = BMP280_MODE_SLEEP;  // initial mode for forced is sleep
    }

    uint8_t ctrl = (params->oversampling_temperature << 5)
            | (params->oversampling_pressure << 2) | (params->mode);

    if (dev->id == BME280_CHIP_ID) {
        // Write crtl hum reg first, only active after write to BMP280_REG_CTRL.
        uint8_t ctrl_hum = params->oversampling_humidity;
        if (write_register8(dev, BMP280_REG_CTRL_HUM, ctrl_hum)) {
            return false;
        }
    }

    if (write_register8(dev, BMP280_REG_CTRL, ctrl)) {
        return false;
    }

    return true;
}

bool bmp280_force_measurement(BMP280_HandleTypedef *dev) {
    uint8_t ctrl;
    if (read_data(dev, BMP280_REG_CTRL, &ctrl, 1)){
        return false;
        }
    
    //ctrl &= ~0b11;  // clear two lower bits 原文这样写编译不通过
    ctrl &= 0x03;  // clear two lower bits
    
    ctrl |= BMP280_MODE_FORCED;
    if (write_register8(dev, BMP280_REG_CTRL, ctrl)) {
        return false;
    }
    return true;
}

bool bmp280_is_measuring(BMP280_HandleTypedef *dev) {
    uint8_t status;
    if (read_data(dev, BMP280_REG_STATUS, &status, 1))
        return false;
    if (status & (1 << 3)) {
        return true;
    }
    return false;
}

/**
 * Compensation algorithm is taken from BMP280 datasheet.
 *
 * Return value is in degrees Celsius.
 */
static inline int32_t compensate_temperature(BMP280_HandleTypedef *dev, int32_t adc_temp,
        int32_t *fine_temp) {
    int32_t var1, var2;

    var1 = ((((adc_temp >> 3) - ((int32_t) dev->dig_T1 << 1)))
            * (int32_t) dev->dig_T2) >> 11;
    var2 = (((((adc_temp >> 4) - (int32_t) dev->dig_T1)
            * ((adc_temp >> 4) - (int32_t) dev->dig_T1)) >> 12)
            * (int32_t) dev->dig_T3) >> 14;

    *fine_temp = var1 + var2;
    return (*fine_temp * 5 + 128) >> 8;
}

/**
 * Compensation algorithm is taken from BMP280 datasheet.
 *
 * Return value is in Pa, 24 integer bits and 8 fractional bits.
 */
static inline uint32_t compensate_pressure(BMP280_HandleTypedef *dev, int32_t adc_press,
        int32_t fine_temp) {
    int64_t var1, var2, p;

    var1 = (int64_t) fine_temp - 128000;
    var2 = var1 * var1 * (int64_t) dev->dig_P6;
    var2 = var2 + ((var1 * (int64_t) dev->dig_P5) << 17);
    var2 = var2 + (((int64_t) dev->dig_P4) << 35);
    var1 = ((var1 * var1 * (int64_t) dev->dig_P3) >> 8)
            + ((var1 * (int64_t) dev->dig_P2) << 12);
    var1 = (((int64_t) 1 << 47) + var1) * ((int64_t) dev->dig_P1) >> 33;

    if (var1 == 0) {
        return 0;  // avoid exception caused by division by zero
    }

    p = 1048576 - adc_press;
    p = (((p << 31) - var2) * 3125) / var1;
    var1 = ((int64_t) dev->dig_P9 * (p >> 13) * (p >> 13)) >> 25;
    var2 = ((int64_t) dev->dig_P8 * p) >> 19;

    p = ((p + var1 + var2) >> 8) + ((int64_t) dev->dig_P7 << 4);
    return p;
}

/**
 * Compensation algorithm is taken from BME280 datasheet.
 *
 * Return value is in Pa, 24 integer bits and 8 fractional bits.
 */
static inline uint32_t compensate_humidity(BMP280_HandleTypedef *dev, int32_t adc_hum,
        int32_t fine_temp) {
    int32_t v_x1_u32r;

    v_x1_u32r = fine_temp - (int32_t) 76800;
    v_x1_u32r = ((((adc_hum << 14) - ((int32_t) dev->dig_H4 << 20)
            - ((int32_t) dev->dig_H5 * v_x1_u32r)) + (int32_t) 16384) >> 15)
            * (((((((v_x1_u32r * (int32_t) dev->dig_H6) >> 10)
                    * (((v_x1_u32r * (int32_t) dev->dig_H3) >> 11)
                            + (int32_t) 32768)) >> 10) + (int32_t) 2097152)
                    * (int32_t) dev->dig_H2 + 8192) >> 14);
    v_x1_u32r = v_x1_u32r
            - (((((v_x1_u32r >> 15) * (v_x1_u32r >> 15)) >> 7)
                    * (int32_t) dev->dig_H1) >> 4);
    v_x1_u32r = v_x1_u32r < 0 ? 0 : v_x1_u32r;
    v_x1_u32r = v_x1_u32r > 419430400 ? 419430400 : v_x1_u32r;
    return v_x1_u32r >> 12;
}

bool bmp280_read_fixed(BMP280_HandleTypedef *dev, int32_t *temperature, uint32_t *pressure,
        uint32_t *humidity) {
    int32_t adc_pressure;
    int32_t adc_temp;
    uint8_t data[8];

    // Only the BME280 supports reading the humidity.
    if (dev->id != BME280_CHIP_ID) {
        if (humidity)
            *humidity = 0;
        humidity = NULL;
    }

    // Need to read in one sequence to ensure they match.
    size_t size = humidity ? 8 : 6;
    if (read_data(dev, 0xf7, data, size)) {
        return false;
    }

    adc_pressure = data[0] << 12 | data[1] << 4 | data[2] >> 4;
    adc_temp = data[3] << 12 | data[4] << 4 | data[5] >> 4;

    int32_t fine_temp;
    *temperature = compensate_temperature(dev, adc_temp, &fine_temp);
    *pressure = compensate_pressure(dev, adc_pressure, fine_temp);

    if (humidity) {
        int32_t adc_humidity = data[6] << 8 | data[7];
        *humidity = compensate_humidity(dev, adc_humidity, fine_temp);
    }

    return true;
}

bool bmp280_read_float(BMP280_HandleTypedef *dev, float *temperature, float *pressure,
        float *humidity) {
    int32_t fixed_temperature;
    uint32_t fixed_pressure;
    uint32_t fixed_humidity;
    if (bmp280_read_fixed(dev, &fixed_temperature, &fixed_pressure,
            humidity ? &fixed_humidity : NULL)) {
        *temperature = (float) fixed_temperature / 100;
        *pressure = (float) fixed_pressure / 256;
        if (humidity)
            *humidity = (float) fixed_humidity / 1024;
        return true;
    }

    return false;
}

bmp280.h

/**
 * Ciastkolog.pl (https://github.com/ciastkolog)
 * 
*/
/**
 * The MIT License (MIT)
 * Copyright (c) 2016 sheinz (https://github.com/sheinz)
 */
#ifndef __BMP280_H__
#define __BMP280_H__

#include "stm32f1xx_hal.h"
#include <stdint.h>
#include <stdbool.h>

/**
 * BMP280 or BME280 address is 0x77 if SDO pin is high, and is 0x76 if
 * SDO pin is low.
 */

#define BMP280_I2C_ADDRESS_0  0x76
#define BMP280_I2C_ADDRESS_1  0x77

#define BMP280_CHIP_ID  0x58 /* BMP280 has chip-id 0x58 */
#define BME280_CHIP_ID  0x60 /* BME280 has chip-id 0x60 */

/**
 * Mode of BMP280 module operation.
 * Forced - Measurement is initiated by user.
 * Normal - Continues measurement.
 */
typedef enum {
    BMP280_MODE_SLEEP = 0,
    BMP280_MODE_FORCED = 1,
    BMP280_MODE_NORMAL = 3
} BMP280_Mode;

typedef enum {
    BMP280_FILTER_OFF = 0,
    BMP280_FILTER_2 = 1,
    BMP280_FILTER_4 = 2,
    BMP280_FILTER_8 = 3,
    BMP280_FILTER_16 = 4
} BMP280_Filter;

/**
 * Pressure oversampling settings
 * 压力过采样设置
 */
typedef enum {
    BMP280_SKIPPED = 0,          /* no measurement  */
    BMP280_ULTRA_LOW_POWER = 1,  /* oversampling x1 */
    BMP280_LOW_POWER = 2,        /* oversampling x2 */
    BMP280_STANDARD = 3,         /* oversampling x4 */
    BMP280_HIGH_RES = 4,         /* oversampling x8 */
    BMP280_ULTRA_HIGH_RES = 5    /* oversampling x16 */
} BMP280_Oversampling;

/**
 * Stand by time between measurements in normal mode
 */
typedef enum {
    BMP280_STANDBY_05 = 0,      /* stand by time 0.5ms */
    BMP280_STANDBY_62 = 1,      /* stand by time 62.5ms */
    BMP280_STANDBY_125 = 2,     /* stand by time 125ms */
    BMP280_STANDBY_250 = 3,     /* stand by time 250ms */
    BMP280_STANDBY_500 = 4,     /* stand by time 500ms */
    BMP280_STANDBY_1000 = 5,    /* stand by time 1s */
    BMP280_STANDBY_2000 = 6,    /* stand by time 2s BMP280, 10ms BME280 */
    BMP280_STANDBY_4000 = 7,    /* stand by time 4s BMP280, 20ms BME280 */
} BMP280_StandbyTime;

/**
 * Configuration parameters for BMP280 module.
 * Use function bmp280_init_default_params to use default configuration.
 */
typedef struct {
    BMP280_Mode mode;
    BMP280_Filter filter;
    BMP280_Oversampling oversampling_pressure;
    BMP280_Oversampling oversampling_temperature;
    BMP280_Oversampling oversampling_humidity;
    BMP280_StandbyTime standby;
} bmp280_params_t;


typedef struct {
    uint16_t dig_T1;
    int16_t  dig_T2;
    int16_t  dig_T3;
    uint16_t dig_P1;
    int16_t  dig_P2;
    int16_t  dig_P3;
    int16_t  dig_P4;
    int16_t  dig_P5;
    int16_t  dig_P6;
    int16_t  dig_P7;
    int16_t  dig_P8;
    int16_t  dig_P9;

    /* Humidity compensation for BME280 */
    uint8_t  dig_H1;
    int16_t  dig_H2;
    uint8_t  dig_H3;
    int16_t  dig_H4;
    int16_t  dig_H5;
    int8_t   dig_H6;

    uint16_t addr;

    I2C_HandleTypeDef* i2c;

    bmp280_params_t params;

    uint8_t  id;        /* Chip ID */

} BMP280_HandleTypedef;

/**
 * Initialize default parameters.
 * Default configuration:
 *      mode: NORAML
 *      filter: OFF
 *      oversampling: x4
 *      standby time: 250ms
 */
void bmp280_init_default_params(bmp280_params_t *params);

/**
 * Initialize BMP280 module, probes for the device, soft resets the device,
 * reads the calibration constants, and configures the device using the supplied
 * parameters. Returns true on success otherwise false.
 *
 * The I2C address is assumed to have been initialized in the dev, and
 * may be either BMP280_I2C_ADDRESS_0 or BMP280_I2C_ADDRESS_1. If the I2C
 * address is unknown then try initializing each in turn.
 *
 * This may be called again to soft reset the device and initialize it again.
 */
bool bmp280_init(BMP280_HandleTypedef *dev, bmp280_params_t *params);

/**
 * Start measurement in forced mode.
 * The module remains in forced mode after this call.
 * Do not call this method in normal mode.
 */
bool bmp280_force_measurement(BMP280_HandleTypedef *dev);

/**
 * Check if BMP280 is busy with measuring temperature/pressure.
 * Return true if BMP280 is busy.
 */
bool bmp280_is_measuring(BMP280_HandleTypedef *dev);

/**
 * Read compensated temperature and pressure data:
 *
 *  Temperature in degrees Celsius times 100.
 *
 *  Pressure in Pascals in fixed point 24 bit integer 8 bit fraction format.
 *
 *  Humidity is optional and only read for the BME280, in percent relative
 *  humidity as a fixed point 22 bit interger and 10 bit fraction format.
 */
bool bmp280_read_fixed(BMP280_HandleTypedef *dev, int32_t *temperature,
                       uint32_t *pressure, uint32_t *humidity);

/**
 * Read compensated temperature and pressure data:
 *  Temperature in degrees Celsius.
 *  Pressure in Pascals.
 *  Humidity is optional and only read for the BME280, in percent relative
 *  humidity.
 */
bool bmp280_read_float(BMP280_HandleTypedef *dev, float *temperature,
                       float *pressure, float *humidity);


#endif  // __BMP280_H__

猜你喜欢

转载自blog.csdn.net/jiujiumo_/article/details/128925030