init: Air780EPM 官方 LuatOS 项目代码基线

- 来源: 合宙 LuatOS 官方仓库 air780epm 模块完整代码
- 路径: luatos/air780epm/module/Air780EPM/demo 含官方 demo(含 mqtt/mqtts/socket/uart 等)
- 后续: 基于 demo 开发 UART<->MQTT 数据上报功能
This commit is contained in:
wangfq
2026-08-31 08:53:49 +08:00
commit 173dd6874f
813 changed files with 125484 additions and 0 deletions
@@ -0,0 +1,315 @@
--[[
@module bme680_demo
@summary BME680 四合一环境传感器演示模块,包含所有功能的演示用例
@version 1.1
@date 2026.08.20
@author 江访
@usage
本文件包含 BME680 的逐项功能演示。
通过 exs_bme680 扩展库的 API 逐一演示数据读取、IIR 滤波切换、过采样率切换、
气体加热器切换、空气质量判断、海拔计算等功能。
通过 MODE 变量选择通信模式(改 MODE 的值即可,无需注释/取消注释代码):
MODE = 1 软件 I2C(默认推荐,仅需 scl/sda 引脚,任意 GPIO 均可,接线最灵活)
MODE = 2 硬件 I2C(指定 i2c_id,占用 CPU 少)
Air780EPM 接线(软件 I2C):
SCL = GPIO31
SDA = GPIO30
]]
-- 加载 exs_bme680 扩展库
-- 该库提供 BME680 的全部驱动功能: 初始化/温度/气压/湿度/气体电阻读取/过采样/滤波/加热器/海拔
local exs_bme680 = require "exs_bme680"
-- ==================== 通信模式选择 ====================
-- 改 MODE 的值选择通信模式:
-- 1 = 软件 I2C(默认) 2 = 硬件 I2C
-- 各模式所需引脚/参数见下方 init_config,接线说明见 readme.md
local MODE = 1
local init_config
if MODE == 1 then
-- 软件 I2CSCL/SDA 用任意 GPIOAir780EPM 接线示例用 GPIO31/GPIO30
init_config = {scl = 31, sda = 30}
elseif MODE == 2 then
-- 硬件 I2Ci2c_id 为总线号(Air780EPM 用 1),不传 scl/sda 时无总线恢复能力
init_config = {i2c_id = 1}
else
log.error("bme680_demo", "MODE 取值错误,应为 1/2")
return
end
--------------------------------------------------------------
-- [1/6] 初始化与数据读取
-- - setup() 自动完成芯片 ID 校验、校准数据读取、采样/滤波/加热器参数配置
-- - get_data() 返回温度(°C)、气压(hPa)、湿度(%RH)、气体电阻(Ω)
--------------------------------------------------------------
local function demo_init_and_read()
log.info("bme680_demo", "===== [1/6] 初始化与数据读取 =====")
-- BME680 默认配置:温度 4X 过采样,气压 4X 过采样,湿度 2X 过采样
-- IIR 滤波 8 次平均,气体加热器 320°C / 150ms
local result = exs_bme680.setup(init_config)
if not result then
log.error("bme680_demo", "BME680 初始化失败")
log.error("bme680_demo", "检查接线: VCC=3.3V GND SCL SDAI2C 地址是否正确(如 0x76/0x77")
return false -- 初始化失败必须返回 false
end
log.info("bme680_demo", "BME680 初始化成功,版本:", exs_bme680.version())
-- 气体预热说明:MOX 气体传感器上电后电阻会从低值缓慢爬升,
-- 新板首次上电需预热 20~30 分钟才稳定,稳定前气体电阻读值无参考意义
log.info("bme680_demo", "预热提示: MOX 气体传感器需预热 20~30 分钟,")
log.info("bme680_demo", "预热期间电阻从低值爬升属正常,稳定前气体电阻读值不可信")
-- 等待传感器稳定,气体传感器需要预热
-- 首次读取气体电阻可能为 0(加热器未稳定),这是正常现象
sys.wait(500) -- 等待传感器稳定,500ms
local data = exs_bme680.get_data()
if data then
local gas_kohm = data.gas_resistance / 1000
log.info("bme680_demo", string.format("温度=%.2f°C 气压=%.2fhPa 湿度=%.1f%%RH 气体=%.1fkΩ",
data.temperature, data.pressure, data.humidity, gas_kohm))
else
log.error("bme680_demo", "读取数据失败")
end
sys.wait(1000) -- 稳定后等待 1 秒进入连续读取
-- 连续读取 3 次,观察数据变化
for i = 1, 3 do
sys.wait(2000) -- 每次读取间隔 2 秒
local d = exs_bme680.get_data()
if d then
local gas_kohm = d.gas_resistance / 1000
log.info("bme680_demo", string.format("第%d次读取: 温度=%.2f°C 气压=%.1fhPa 湿度=%.1f%%RH 气体=%.1fkΩ",
i, d.temperature, d.pressure, d.humidity, gas_kohm))
end
end
log.info("bme680_demo", "---- [1/6] 完成 ----")
return true
end
--------------------------------------------------------------
-- [2/6] IIR 滤波器切换演示
-- - set_filter(0~7) 设置 IIR 滤波器系数,数值越大数据越平滑
--------------------------------------------------------------
local function demo_filter_switch()
log.info("bme680_demo", "===== [2/6] IIR 滤波器切换演示 =====")
-- 依次切换 filter=0/1/2/3/4/5/6/7,观察数据变化
local filter_list = { 0, 1, 2, 3, 4, 5, 6, 7 }
for _, f in ipairs(filter_list) do
log.info("bme680_demo", string.format("设置滤波器 filter=%d", f))
exs_bme680.set_filter(f)
sys.wait(100) -- 等待滤波器生效,100ms
local data = exs_bme680.get_data()
if data then
log.info("bme680_demo", string.format("filter=%d: 温度=%.2f°C 气压=%.2fhPa 湿度=%.1f%%RH",
f, data.temperature, data.pressure, data.humidity))
end
sys.wait(1000) -- 每档滤波器显示间隔 1 秒
end
log.info("bme680_demo", "---- [2/6] 完成 ----")
return true
end
--------------------------------------------------------------
-- [3/6] 过采样率切换演示
-- - set_temp/press/hum_oversampling(0~5) 设置过采样率
-- - 低功耗(1X)与高精度(16X)对比
--------------------------------------------------------------
local function demo_oversampling_switch()
log.info("bme680_demo", "===== [3/6] 过采样率切换演示 =====")
-- 低功耗模式:全部 1X 过采样
log.info("bme680_demo", "切换到低功耗模式(1X过采样)")
exs_bme680.set_temp_oversampling(1)
exs_bme680.set_press_oversampling(1)
exs_bme680.set_hum_oversampling(1)
sys.wait(100) -- 等待配置生效,100ms
local data = exs_bme680.get_data()
if data then
log.info("bme680_demo", string.format("低功耗: 温度=%.2f°C 气压=%.2fhPa 湿度=%.1f%%RH",
data.temperature, data.pressure, data.humidity))
end
sys.wait(1000) -- 展示间隔 1 秒
-- 高精度模式:全部 16X 过采样
log.info("bme680_demo", "切换到高精度模式(16X过采样)")
exs_bme680.set_temp_oversampling(5)
exs_bme680.set_press_oversampling(5)
exs_bme680.set_hum_oversampling(5)
sys.wait(100) -- 等待配置生效,100ms
data = exs_bme680.get_data()
if data then
log.info("bme680_demo", string.format("高精度: 温度=%.2f°C 气压=%.2fhPa 湿度=%.1f%%RH",
data.temperature, data.pressure, data.humidity))
end
log.info("bme680_demo", "---- [3/6] 完成 ----")
return true
end
--------------------------------------------------------------
-- [4/6] 气体加热器切换演示
-- - set_gas_heater(temp, time) 设置加热器温度(200~400°C)与时长(1~4032ms)
-- - 不同温度下气体电阻值会变化
--------------------------------------------------------------
local function demo_gas_heater_switch()
log.info("bme680_demo", "===== [4/6] 气体加热器切换演示 =====")
-- 不同加热器温度组合
local heater_configs = {
{ temp = 250, time = 100, desc = "低温短时(250°C/100ms" },
{ temp = 320, time = 150, desc = "默认配置(320°C/150ms" },
{ temp = 350, time = 200, desc = "高温长时(350°C/200ms" },
}
for _, cfg in ipairs(heater_configs) do
log.info("bme680_demo", cfg.desc)
exs_bme680.set_gas_heater(cfg.temp, cfg.time)
sys.wait(200) -- 等待加热器参数生效,200ms
local data = exs_bme680.get_data()
if data then
local gas_kohm = data.gas_resistance / 1000
log.info("bme680_demo", string.format("气体=%.1fkΩ 温度=%.2f°C 湿度=%.1f%%RH",
gas_kohm, data.temperature, data.humidity))
end
sys.wait(1000) -- 展示间隔 1 秒
end
log.info("bme680_demo", "---- [4/6] 完成 ----")
return true
end
--------------------------------------------------------------
-- 空气质量判断辅助函数
-- 说明:不能直接看电阻绝对值判断空气好坏(不同芯片/环境基线差异大),
-- 必须以干净空气稳定基线 R0 为基准,看实时电阻 R 的相对下降幅度:
-- 污染度 = (1 - R/R0) * 100%,下降越多污染越高
-- 参数:R 实时气体电阻(Ω)
-- R0 干净空气稳定基线电阻(Ω)
-- 返回:等级字符串, 污染度百分比
--------------------------------------------------------------
local function calc_air_quality(R, R0)
if not R0 or R0 <= 0 or not R or R <= 0 then
return "未就绪", 0
end
local ratio = R / R0
local pollution = (1 - ratio) * 100
local level
if ratio >= 0.9 then
level = ""
elseif ratio >= 0.7 then
level = ""
elseif ratio >= 0.4 then
level = ""
else
level = ""
end
return level, pollution
end
--------------------------------------------------------------
-- [5/6] 空气质量判断演示
-- - 预热说明:MOX 传感器上电后电阻从低值爬升,新板需预热 20~30 分钟才稳定
-- - 判断方法:先记录干净空气稳定基线 R0,实时电阻相对 R0 下降越多空气越差
--------------------------------------------------------------
local function demo_air_quality()
log.info("bme680_demo", "===== [5/6] 空气质量判断演示 =====")
log.info("bme680_demo", "预热说明: 新板首次上电 MOX 气体传感器需预热 20~30 分钟")
log.info("bme680_demo", "电阻会从低值爬升直至稳定,稳定前气体电阻读值无参考意义")
log.info("bme680_demo", "判断方法: 以干净空气稳定电阻为基线R0,污染度=(1-R/R0)*100%")
local data = exs_bme680.get_data()
if not data then
log.error("bme680_demo", "读取数据失败,空气质量演示终止")
return true
end
-- 记录基线 R0:真实使用必须在干净空气中预热 20~30 分钟后记录稳定值,
-- 此处为便于演示,直接以当前读数为基线(若为 0 说明加热器未稳定)
local R0 = data.gas_resistance
if R0 <= 0 then
log.warn("bme680_demo", "当前气体电阻为 0(加热器未稳定),请先预热 20~30 分钟再演示")
log.warn("bme680_demo", "本次演示基线无效,后续空气等级将显示为未就绪")
else
log.info("bme680_demo", string.format("记录基线 R0=%.1fkΩ(应取干净空气预热稳定后的值)", R0 / 1000))
end
-- 连续读取 3 次,实时计算污染度与空气等级
for i = 1, 3 do
sys.wait(3000) -- 每次间隔 3 秒
local d = exs_bme680.get_data()
if d then
local level, pollution = calc_air_quality(d.gas_resistance, R0)
log.info("bme680_demo", string.format("第%d次: 气体=%.1fkΩ 污染度=%.1f%% 空气等级=%s",
i, d.gas_resistance / 1000, pollution, level))
end
end
log.info("bme680_demo", "提示: 空气等级阈值(优≥0.9R0/良≥0.7R0/中≥0.4R0/差<0.4R0)为经验值")
log.info("bme680_demo", "---- [5/6] 完成 ----")
return true
end
--------------------------------------------------------------
-- [6/6] 海拔高度测量与关闭
-- - get_altitude(pressure) 依据气压计算海拔高度
-- - close() 关闭传感器并释放 I2C 资源
--------------------------------------------------------------
local function demo_altitude_and_close()
log.info("bme680_demo", "===== [6/6] 海拔高度测量与关闭 =====")
local data = exs_bme680.get_data()
if data then
local alt = exs_bme680.get_altitude(data.pressure)
local gas_kohm = data.gas_resistance / 1000
log.info("bme680_demo", string.format("温度=%.2f°C 气压=%.1fhPa 湿度=%.1f%%RH 气体=%.1fkΩ 海拔=%.1f米",
data.temperature, data.pressure, data.humidity, gas_kohm, alt))
end
-- 关闭传感器
exs_bme680.close()
log.info("bme680_demo", "---- [6/6] 完成 ----")
return true
end
--------------------------------------------------------------
-- 主任务:按 [1/6]~[6/6] 顺序执行全部演示
--------------------------------------------------------------
local function bme680_demo_task_func()
log.info("bme680_demo", "HELLO")
sys.wait(1000) -- 等待系统启动稳定,1 秒
local ok = demo_init_and_read()
if not ok then
log.error("bme680_demo", "初始化失败,演示终止")
return
end
sys.wait(500) -- 演示间隔,500ms
demo_filter_switch()
sys.wait(500) -- 演示间隔,500ms
demo_oversampling_switch()
sys.wait(500) -- 演示间隔,500ms
demo_gas_heater_switch()
sys.wait(500) -- 演示间隔,500ms
demo_air_quality()
sys.wait(500) -- 演示间隔,500ms
demo_altitude_and_close()
sys.wait(500) -- 演示间隔,500ms
log.info("bme680_demo", "===== [演示完毕] =====")
log.info("bme680_demo", "End")
end
-- 启动演示任务协程
sys.taskInit(bme680_demo_task_func)
@@ -0,0 +1,70 @@
--[[
@module main
@summary BME680 四合一环境传感器 Demo 入口
@version 1.1
@date 2026.08.20
@author 江访
]]
--[[
=== 演示内容 ===
本 demo 演示 exs_bme680 扩展库的完整功能,顺序为:
HELLO→[1/6]→[2/6]→[3/6]→[4/6]→[5/6]→[6/6]→End
1、初始化和数据读取([1/6]
2、IIR 滤波器切换演示([2/6])
3、过采样率切换演示([3/6]
4、气体加热器切换演示([4/6]
5、空气质量判断演示([5/6],含气体预热说明)
6、海拔高度测量与关闭([6/6]
更多说明参考本目录下的 readme.md 文件
]]
--[[
VERSION:项目版本号,ascii string类型
如果使用合宙iot.openluat.com进行远程升级,必须按照"XXX.YYY.ZZZ"三段格式定义:
X、Y、Z各表示1位数字,三个X表示的数字可以相同,也可以不同,同理三个Y和三个Z表示的数字也是可以相同,可以不同
因为历史原因,YYY这三位数字必须存在,但是没有任何用处,可以一直写为000
如果不使用合宙iot.openluat.com进行远程升级,根据自己项目的需求,自定义格式即可
]]
PROJECT = "BME680_Demo" -- 项目命名
VERSION = "001.999.000" -- 项目版本号
-- 在日志中打印项目名和项目版本号
log.info("main", PROJECT, VERSION)
-- 设置日志输出风格为样式2(建议调试时开启)
-- log.style(2)
-- 如果内核固件支持errDump功能,此处进行配置,【强烈建议打开此处的注释】
-- 因为此功能模块可以记录并且上传脚本在运行过程中出现的语法错误或者其他自定义的错误信息
-- if errDump then
-- errDump.config(true, 600)
-- end
-- 使用LuatOS开发的任何一个项目,都强烈建议使用远程升级FOTA功能
-- 可以使用合宙的iot.openluat.com平台进行远程升级
-- 也可以使用客户自己搭建的平台进行远程升级
-- 启动一个循环定时器
-- 每隔3秒钟打印一次总内存,实时/已使用/历史最高内存情况
-- 方便分析内存使用是否有异常
-- local function mem_check_func()
-- log.info("mem.lua", rtos.meminfo())
-- log.info("mem.sys", rtos.meminfo("sys"))
-- end
-- sys.timerLoopStart(mem_check_func, 3000)
-- 加载 bme680_demo.lua 演示模块(完整功能演示)
require "bme680_demo"
-- 用户代码已结束
-- 结尾总是这一句
sys.run()
-- sys.run() 之后不要加任何语句!!!!!因为添加的任何语句都不会被执行
@@ -0,0 +1,282 @@
# BME680 四合一环境传感器演示
## 一、功能模块介绍
### 1.1 核心主程序模块
1. **main.lua** - 主程序入口
2. **bme680_demo.lua** - BME680 功能演示模块
### 1.2 扩展库模块
1. **exs_bme680** - BME680 扩展库,提供初始化、温度/气压/湿度/气体电阻读取、过采样率配置、IIR 滤波配置、气体加热器配置、海拔高度计算等 API
### 1.3 I2C 模式说明
**推荐使用软件 I2C 模式**BME680 使用标准 I2C 接口通信,软件 I2C 模式无需指定 I2C 控制器,任意 GPIO 均可模拟 I2C 时序,灵活性更高。本 demo 默认使用软件 I2C 模式演示,也可通过 `bme680_demo.lua` 中的 `MODE` 变量切换为硬件 I2C 模式。
## 二、演示流程介绍
本 demo 按顺序演示 exs_bme680 扩展库的 6 项功能:HELLO → [1/6] → [2/6] → [3/6] → [4/6] → [5/6] → [6/6] → End
### 2.1 功能演示项说明
1. **[1/6] 初始化与数据读取** - 初始化 BME680 传感器并读取温度(°C)、气压(hPa)、湿度(%RH)和气体电阻(Ω)数据,包含气体预热说明
2. **[2/6] IIR 滤波器切换演示** - 依次切换 filter=0~7,观察数据平滑效果
3. **[3/6] 过采样率切换演示** - 对比低功耗(1X)和高精度(16X)模式下的测量效果
4. **[4/6] 气体加热器切换演示** - 依次测试三种加热器温度/时间组合(250°C、320°C、350°C
5. **[5/6] 空气质量判断演示** - 演示如何判断空气好坏:先记录干净空气稳定基线 R0,实时电阻相对 R0 下降越多空气越差(污染度 = (1 - R/R0) × 100%
6. **[6/6] 海拔高度测量与关闭** - 通过气压值计算海拔高度后关闭传感器
> **关于气体传感器预热与空气好坏判断**(详见下文 5.4.5):
> - BME680 的 MOX 气体传感器上电后电阻会从低值(如几 kΩ)缓慢爬升至几十 kΩ,**新板首次上电需预热 20~30 分钟**电阻才稳定,这是正常现象(预热/烧机效应),稳定前读取的气体电阻没有参考意义
> - **不能直接看电阻绝对值判断空气好坏**,必须以干净空气中预热稳定后的电阻为基线 R0,实时电阻 R 相对 R0 **下降越多说明 VOC 浓度越高、空气越差**
> - 经验等级:污染度 ≤10% 优、10%~30% 良、30%~60% 中、>60% 差(阈值需结合场景标定)
## 三、演示硬件环境
### 3.1 硬件清单
- Air780EPM 核心板 × 1
- BME680 四合一环境传感器模块 × 1
demo所演示的 BME680 环境传感器模块[购买链接](https://item.taobao.com/item.htm?abbucket=12&id=585977696909&mi_id=00005GuQmhs21YgvmlIoT24gzgF3ZneshBSDiRStMyOfDd0&ns=1&priceTId=213e00d417839209172374576e1068&spm=a21n57.1.hoverItem.5&utparam=%7B%22aplus_abtest%22%3A%22e1d0645c1ad2540833bb794c3c13d5e1%22%7D&xxc=taobaoSearch)
- 母对母杜邦线 × 4
- TYPE-C 数据线 × 1
### 3.2 接线配置
#### 3.2.1 BME680 模块接线
| Air780EPM 核心板 | BME680 模块 |
|-----------------|------------|
| 32/GPIO31 | SCL |
| 31/GPIO30 | SDA |
| VDD_EXT | VCC |
| GND | GND |
> 说明:
> 1. 接线时注意杜邦线不宜过长,以免通信不稳定
> 2. SCL 和 SDA 需外接 4.7kΩ~10kΩ 上拉电阻到 VCC(部分模块已自带)
> 3. BME680 的 I2C 地址:SDO=GND 时 0x76SDO=VCC 时 0x77
![](https://docs.openluat.com/cdn/image/Air780EHM_BME680.png)
## 四、演示软件环境
### 4.1 开发工具
- [Luatools下载调试工具](https://docs.openluat.com/air780egh/luatos/common/download/) - 固件烧录和代码调试
### 4.2 内核固件
- [点击下载Air780EPM系列最新版本内核固件](https://docs.openluat.com/air780epm/luatos/firmware/780epm_version/)demo所使用的是 LuatOS-SoC_V2046_Air780EPM 1号固件
### 4.3 脚本文件
1. **main.lua** - 程序入口
2. **bme680_demo.lua** - BME680 功能演示模块
3. **exs_bme680** - BME680 扩展库
## 五、演示核心步骤
### 5.1 硬件准备
1. 按照接线表将 BME680 模块连接到核心板
2. 确保电源连接正确,通过 TYPE-C USB 口供电
3. 检查所有接线无误,避免短路
### 5.2 软件配置
`main.lua` 中加载对应的演示模块:
```lua
require "bme680_demo"
```
如需切换通信模式,修改 `bme680_demo.lua` 中的 `MODE` 变量(1=软件 I2C2=硬件 I2C)。
### 5.3 软件烧录
1. 使用 Luatools 选择最新内核固件
2. 下载本项目所有脚本文件
3. 将固件和脚本一起烧录到设备
4. 烧录成功后设备自动重启后开始运行
### 5.4 功能测试
#### 5.4.1 初始化与数据读取演示
1. 设备启动后打印 "HELLO",随后自动进入 [1/6] 初始化与数据读取
2. 观察日志输出,确认初始化成功(打印校准数据、预热提示)
3. 观察温度(°C)、气压(hPa)、湿度(%RH)和气体电阻(kΩ)的连续读取
4. 注意:首次上电气体电阻可能为 0,MOX 气体传感器需预热 20~30 分钟才稳定(详见 5.4.5
#### 5.4.2 IIR 滤波器切换演示
1. 自动进入 [2/6] IIR 滤波器切换演示
2. 依次观察 filter=0(关闭)~ filter=7128 次平均)下的数据
3. filter 越大数据跳动越小
#### 5.4.3 过采样率切换演示
1. 自动进入 [3/6] 过采样率切换演示
2. 先切换到低功耗模式(1X),观察数据
3. 再切换到高精度模式(16X),对比数据精度变化
#### 5.4.4 气体加热器切换演示
1. 自动进入 [4/6] 气体加热器切换演示
2. 依次测试 250°C/100ms、320°C/150ms、350°C/200ms 三种参数
3. 观察不同温度下气体电阻值的变化
#### 5.4.5 空气质量判断演示
> 这是理解 BME680 气体传感器最关键的一步,演示**预热时长**和**如何判断空气好坏**。
1. 自动进入 [5/6] 空气质量判断演示
2. 日志会先打印预热说明:**新板首次上电 MOX 气体传感器需预热 20~30 分钟**,电阻从低值缓慢爬升属正常,稳定前气体电阻读值无参考意义
3. 记录当前读数作为基线 R0(真实使用时必须在干净空气中预热 20~30 分钟、电阻稳定后再记录 R0)
4. 连续读取 3 次,每次计算污染度 `(1 - R/R0) × 100%` 并输出空气等级
**如何判断空气好坏(核心)**
- 不能直接看电阻**绝对值**(不同芯片、不同温湿度下基线差异大)
- 在**干净空气**中预热 20~30 分钟后,记录稳定电阻为基线 R0
- 运行时实时电阻 R 相对 R0 **下降越多,说明 VOC 浓度越高、空气越差**
- 判断指标:`ratio = R/R0`(越接近 1 越干净),`污染度 = (1 - R/R0) × 100%`
- 经验等级(阈值需结合场景标定):污染度 ≤10% **优**、10%~30% **良**、30%~60% **中**、>60% **差**
```lua
-- 判断空气质量等级,R 为实时气体电阻,R0 为干净空气稳定基线
local function judge_air(R, R0)
if R0 <= 0 or R <= 0 then return "未就绪" end
local pollution = (1 - R / R0) * 100
if pollution <= 10 then return "" end
if pollution <= 30 then return "" end
if pollution <= 60 then return "" end
return ""
end
```
#### 5.4.6 海拔高度测量与关闭
1. 自动进入 [6/6] 海拔高度测量与关闭
2. 显示温度、气压、湿度、气体电阻和海拔高度
3. 关闭传感器后打印 "End"
### 5.5 预期效果
- **初始化与数据读取**:BME680 初始化成功,四项环境数据正常输出
- **IIR 滤波器切换**:不同滤波器下数据平滑度不同
- **过采样率切换**:高精度模式数据更稳定
- **气体加热器切换**:不同温度下气体电阻值有变化
- **海拔高度测量**:根据气压计算出当前海拔高度
- **日志如下:**
```lua
[2026-08-20 21:30:06.039][000000000.246] I/user.main BME680_Demo 001.999.000
[2026-08-20 21:30:06.044][000000000.263] D/user.exs_bme680 version -> 202608080000
[2026-08-20 21:30:06.048][000000000.265] I/user.bme680_demo HELLO
[2026-08-20 21:30:06.172][000000001.265] I/user.bme680_demo ===== [1/5] =====
[2026-08-20 21:30:06.176][000000001.271] I/user.exs_bme680 I2C总线恢复完成
[2026-08-20 21:30:06.181][000000001.334] I/user.exs_bme680 BME680 @ I2C 0x77, CHIP_ID=0x61
[2026-08-20 21:30:06.194][000000001.347] I/user.exs_bme680 raw_T1=25923 raw_P1=36006 raw_T2=26603 raw_P2=-10347
[2026-08-20 21:30:06.215][000000001.347] I/user.exs_bme680 : T1=25923 T2=26603 T3=3 P1=36006 P2=-10347 H1=667 H2=1031 GH1=-34 GH2=-6023 GH3=18
[2026-08-20 21:30:06.233][000000001.355] I/user.exs_bme680 BME680 , os_temp=4 os_pres=3 os_hum=2 filter=3 heater_temp=320°C heater_dur=150ms
[2026-08-20 21:30:06.241][000000001.355] I/user.exs_bme680 : res_heat_range=1 res_heat_val=40 range_sw_err=1 heatr_res=0x76
[2026-08-20 21:30:06.250][000000001.355] I/user.exs_bme680 : MOX 20~30
[2026-08-20 21:30:06.258][000000001.355] I/user.exs_bme680 gas_resistance 0
[2026-08-20 21:30:06.270][000000001.355] I/user.bme680_demo BME680 : 202608080000
[2026-08-20 21:30:06.390][000000002.048] I/user.bme680_demo =24.12°C =1008.40hPa 湿=66.6%RH =2.4
[2026-08-20 21:30:09.534][000000005.241] I/user.bme680_demo 1: =24.12°C =1008.4hPa 湿=66.4%RH =3.4
[2026-08-20 21:30:11.735][000000007.434] I/user.bme680_demo 2: =24.14°C =1008.4hPa 湿=66.3%RH =4.6
[2026-08-20 21:30:13.922][000000009.627] I/user.bme680_demo 3: =24.16°C =1008.4hPa 湿=66.1%RH =5.9
[2026-08-20 21:30:13.929][000000009.628] I/user.bme680_demo ---- [1/5] 完成 ----
[2026-08-20 21:30:14.421][000000010.128] I/user.bme680_demo ===== [2/5] IIR =====
[2026-08-20 21:30:14.427][000000010.128] I/user.bme680_demo filter=0
[2026-08-20 21:30:14.437][000000010.136] I/user.exs_bme680 IIR 0 (0)
[2026-08-20 21:30:14.716][000000010.428] I/user.bme680_demo filter=0: =24.58°C =1008.42hPa 湿=66.1%RH
[2026-08-20 21:30:15.723][000000011.429] I/user.bme680_demo filter=1
[2026-08-20 21:30:15.729][000000011.436] I/user.exs_bme680 IIR 1 (1)
[2026-08-20 21:30:16.019][000000011.729] I/user.bme680_demo filter=1: =24.45°C =1008.44hPa 湿=65.8%RH
[2026-08-20 21:30:17.026][000000012.730] I/user.bme680_demo filter=2
[2026-08-20 21:30:17.033][000000012.737] I/user.exs_bme680 IIR 2 (3)
[2026-08-20 21:30:17.322][000000013.030] I/user.bme680_demo filter=2: =24.45°C =1008.40hPa 湿=65.5%RH
[2026-08-20 21:30:18.330][000000014.031] I/user.bme680_demo filter=3
[2026-08-20 21:30:18.336][000000014.038] I/user.exs_bme680 IIR 3 (7)
[2026-08-20 21:30:18.628][000000014.331] I/user.bme680_demo filter=3: =24.43°C =1008.40hPa 湿=65.3%RH
[2026-08-20 21:30:19.620][000000015.332] I/user.bme680_demo filter=4
[2026-08-20 21:30:19.634][000000015.339] I/user.exs_bme680 IIR 4 (15)
[2026-08-20 21:30:19.930][000000015.632] I/user.bme680_demo filter=4: =24.42°C =1008.36hPa 湿=65.0%RH
[2026-08-20 21:30:20.921][000000016.633] I/user.bme680_demo filter=5
[2026-08-20 21:30:20.937][000000016.640] I/user.exs_bme680 IIR 5 (31)
[2026-08-20 21:30:21.231][000000016.933] I/user.bme680_demo filter=5: =24.43°C =1008.40hPa 湿=64.9%RH
[2026-08-20 21:30:22.234][000000017.934] I/user.bme680_demo filter=6
[2026-08-20 21:30:22.240][000000017.941] I/user.exs_bme680 IIR 6 (63)
[2026-08-20 21:30:22.527][000000018.234] I/user.bme680_demo filter=6: =24.44°C =1008.42hPa 湿=64.7%RH
[2026-08-20 21:30:23.534][000000019.235] I/user.bme680_demo filter=7
[2026-08-20 21:30:23.540][000000019.242] I/user.exs_bme680 IIR 7 (127)
[2026-08-20 21:30:23.829][000000019.535] I/user.bme680_demo filter=7: =24.46°C =1008.40hPa 湿=64.7%RH
[2026-08-20 21:30:24.831][000000020.536] I/user.bme680_demo ---- [2/5] 完成 ----
[2026-08-20 21:30:25.326][000000021.036] I/user.bme680_demo ===== [3/5] =====
[2026-08-20 21:30:25.331][000000021.036] I/user.bme680_demo 1X过采样
[2026-08-20 21:30:25.342][000000021.043] I/user.exs_bme680 1
[2026-08-20 21:30:25.349][000000021.051] I/user.exs_bme680 1
[2026-08-20 21:30:25.357][000000021.058] I/user.exs_bme680 湿 1
[2026-08-20 21:30:25.621][000000021.326] I/user.bme680_demo : =24.46°C =1008.40hPa 湿=64.7%RH
[2026-08-20 21:30:26.621][000000022.327] I/user.bme680_demo 16X过采样
[2026-08-20 21:30:26.626][000000022.334] I/user.exs_bme680 5
[2026-08-20 21:30:26.636][000000022.342] I/user.exs_bme680 5
[2026-08-20 21:30:26.642][000000022.349] I/user.exs_bme680 湿 5
[2026-08-20 21:30:26.993][000000022.705] I/user.bme680_demo : =24.46°C =1008.40hPa 湿=64.7%RH
[2026-08-20 21:30:26.998][000000022.706] I/user.bme680_demo ---- [3/5] 完成 ----
[2026-08-20 21:30:27.504][000000023.206] I/user.bme680_demo ===== [4/5] =====
[2026-08-20 21:30:27.512][000000023.206] I/user.bme680_demo 250°C/100ms
[2026-08-20 21:30:27.518][000000023.214] I/user.exs_bme680 250°C, 100ms
[2026-08-20 21:30:27.919][000000023.620] I/user.bme680_demo =32.2 =24.46°C 湿=64.7%RH
[2026-08-20 21:30:28.909][000000024.621] I/user.bme680_demo 320°C/150ms
[2026-08-20 21:30:28.925][000000024.628] I/user.exs_bme680 320°C, 150ms
[2026-08-20 21:30:29.374][000000025.085] I/user.bme680_demo =16.6 =24.46°C 湿=64.6%RH
[2026-08-20 21:30:30.382][000000026.086] I/user.bme680_demo 350°C/200ms
[2026-08-20 21:30:30.389][000000026.093] I/user.exs_bme680 350°C, 200ms
[2026-08-20 21:30:30.894][000000026.600] I/user.bme680_demo =14.4 =24.46°C 湿=64.6%RH
[2026-08-20 21:30:31.888][000000027.601] I/user.bme680_demo ---- [4/5] 完成 ----
[2026-08-20 21:30:32.387][000000028.101] I/user.bme680_demo ===== [5/5] =====
[2026-08-20 21:30:32.700][000000028.409] I/user.bme680_demo =24.46°C =1008.4hPa 湿=64.6%RH =16.8 =40.5
[2026-08-20 21:30:32.706][000000028.409] I/user.exs_bme680
[2026-08-20 21:30:32.712][000000028.410] I/user.bme680_demo ---- [5/5] 完成 ----
[2026-08-20 21:30:33.210][000000028.910] I/user.bme680_demo ===== [] =====
[2026-08-20 21:30:33.215][000000028.910] I/user.bme680_demo End
```
### 5.6 故障排除
1. **传感器初始化失败**
- 检查 BME680 接线是否正确(SCL、SDA、VCC、GND
- 确认 GPIO 引脚配置与接线一致
- 检查电源电压是否稳定(3.3V
- 确认 SCL/SDA 上拉电阻是否连接
- 确认 exs_bme680 扩展库已正常加载
2. **读取数据异常**
- 检查传感器供电是否正常
- 自动地址检测会尝试 0x76 和 0x77,确认 SDO 引脚电平
- 检查接线无松动
3. **气体电阻一直为 0**
- 新板首次上电需要预热 20~30 分钟,MOX 加热器稳定前 gas_resistance 返回 0,属正常现象(详见 5.4.5)
- 预热期间电阻从低值缓慢爬升属正常,待电阻稳定后再记录基线 R0 判断空气质量
- 确认加热器温度和时间设置合理(默认 320°C/150ms),加热器未被禁用
- 若长时间预热后仍为 0,检查供电是否稳定、`set_gas_heater` 参数是否合法
4. **海拔高度显示异常**
- 海拔计算基于海平面标准气压 1013.25hPa,天气变化会影响计算精度
- 可通过 `exs_bme680.set_sea_level_pressure(pressure)` 传入实际海平面气压校正
### 5.7 扩展功能建议
exs_bme680 更多接口的使用可以查看 [exs_bme680 扩展库说明](https://docs.openluat.com/osapi/ext/sensor/exs_bme680/)