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,72 @@
--[[
@module main
@summary VL53L1X 飞行时间测距传感器 Demo 入口
@version 1.0
@date 2026.07.20
@author 江访
]]
--[[
=== 演示内容 ===
本 demo 演示 exs_vl53l1x 扩展库的完整功能,顺序为:
HELLO→[1/5]→[2/5]→[3/5]→[4/5]→[5/5]→End
1、标准测距演示([1/5]
2、测距模式切换([2/5]
3、中断读取演示([3/5]
4、休眠与唤醒([4/5]
5、持续测距演示([5/5]
]]
--[[
VERSION:项目版本号,ascii string类型
如果使用合宙iot.openluat.com进行远程升级,必须按照"XXX.YYY.ZZZ"三段格式定义:
X、Y、Z各表示1位数字,三个X表示的数字可以相同,也可以不同,同理三个Y和三个Z表示的数字也是可以相同,可以不同
因为历史原因,YYY这三位数字必须存在,但是没有任何用处,可以一直写为000
如果不使用合宙iot.openluat.com进行远程升级,根据自己项目的需求,自定义格式即可
]]
-- main.lua - 程序入口文件
PROJECT = "VL53L1X_Demo" -- 项目命名
VERSION = "001.999.000" -- 项目版本号
-- 在日志中打印项目名和项目版本号
log.info("main", PROJECT, VERSION)
-- 设置日志输出风格为样式2(建议调试时开启)
-- log.style(2)
-- 如果内核固件支持errDump功能,此处进行配置,【强烈建议打开此处的注释】
-- 因为此功能模块可以记录并且上传脚本在运行过程中出现的语法错误或者其他自定义的错误信息,可以初步分析一些设备运行异常的问题
-- 以下代码是最基本的用法,更复杂的用法可以详细阅读API说明文档
-- 启动errDump日志存储并且上传功能,600秒上传一次
-- if errDump then
-- errDump.config(true, 600)
-- end
-- 使用LuatOS开发的任何一个项目,都强烈建议使用远程升级FOTA功能
-- 可以使用合宙的iot.openluat.com平台进行远程升级
-- 也可以使用客户自己搭建的平台进行远程升级
-- 远程升级的详细用法,可以参考fota的demo进行使用
-- 启动一个循环定时器
-- 每隔3秒钟打印一次总内存,实时的已使用内存,历史最高的已使用内存情况
-- 方便分析内存使用是否有异常
-- sys.timerLoopStart(function()
-- log.info("mem.lua", rtos.meminfo())
-- log.info("mem.sys", rtos.meminfo("sys"))
-- end, 3000)
-- 加载 vl53l1x_demo.lua 演示模块
require "vl53l1x_demo"
-- 用户代码已结束
-- 结尾总是这一句
sys.run()
-- sys.run()之后不要加任何语句!!!!!因为添加的任何语句都不会被执行
@@ -0,0 +1,224 @@
# VL53L1X 激光红外测距传感器演示
## 一、功能模块介绍
### 1.1 核心主程序模块
1. **main.lua** - 主程序入口,负责项目初始化、版本定义和任务调度
2. **vl53l1x_demo.lua** - VL53L1X 功能演示模块,包含标准测距、模式切换、休眠唤醒、持续测距等所有功能的演示用例
### 1.2 扩展库模块
1. **exs_vl53l1x** - VL53L1X 扩展库,提供初始化、测距数据读取、模式切换、睡眠/唤醒、关闭等 API
### 1.3 诊断工具模块(按需使用)
1. **vl53l1x_scan.lua** - 基础扫描:I2C 地址检测、软件复位、固件状态、Model ID 读取
2. **vl53l1x_deep_scan.lua** - 深度扫描:扫描全寄存器,判断芯片响应是否正常
3. **vl53l1x_xshut_test.lua** - XSHUT 硬件复位测试
> 注:诊断工具模块需要在 main.lua 中通过 `require` 切换加载,不参与演示流程。
## 二、演示流程介绍
本 demo 按顺序演示 exs_vl53l1x 扩展库的 4 项功能:HELLO → [1/4] → [2/4] → [3/4] → [4/4] → End
### 2.1 功能演示项说明
1. **[1/5] 标准测距** - 初始化传感器,连续读取 5 次距离数据(默认 standard 模式)
2. **[2/4] 测距模式切换** - 演示 short(抗强光)和 long(远距离)两种模式切换
3. **[3/4] 休眠与唤醒** - 演示 sleep() 进入软件待机、wakeup() 唤醒恢复测距
4. **[4/4] 持续测距** - 演示 sleep() 进入软件待机、wakeup() 唤醒恢复测距
** - 每隔 1 秒读取一次距离数据,共 5 次
## 三、演示硬件环境
### 3.1 硬件清单
- Air780EPM 核心板 × 1
- VL53L1X 激光红外测距传感器模块(如 GY-VL53L1X 等) × 1
demo所演示的VL53L1X 激光红外测距传感器模块[购买链接](https://item.taobao.com/item.htm?app=chrome&bxsign=scd0Y1aCFssu5WNBf4zgfL9PHTC771hSBaYQhJANVSUUTh2awzexyQyuQSg4mN6Pbloj55y5X5F66iW6hytMgKrQauVMZK_2eg_EVTNPrAckp1M2aoTVhEBdqhZFkPdhK0r&cpp=1&h5_spm=a-tb-item.b-tb-item&id=597981154375&share_crt_v=1&shareurl=true&short_name=h.8XEIWwnTbGSsdlI&sp_tk=MGdwOGd0NWtvME0%3D&spm=a2159r.13376460.0.0&tbSocialPopKey=shareItem&tk=0gp8gt5ko0M&un=33e3e4902f14a2acade3a8129ff9a52d&un_site=0&ut_sk=1.aHcpu1x%2F2XQDACU%2ByKbrGPzO_21646297_1784598506860.TaoPassword-WeiXin.1&wxsign=tbwRNA5Uhd58zJzNm2egOHG_-dy1Cgfx7h_MWqBNsxfXGOARu2O3Fc6t-RivRx0dfSe2M0HcrjjRwaVMelu4sxeZQ-Sg6ckAT9CCpBMe0GKHQ-1vgswN6QAK7KQCMvOfph_&x-ssr=true)
- 母对母杜邦线 × 4
- TYPE-C 数据线 × 1
### 3.2 接线配置
#### 3.2.1 I2C 模式接线
<table>
<tr>
<td>Air780EPM 核心板<br/></td><td>VL53L1X 模块<br/></td></tr>
<tr>
<td>32/GPIO31<br/></td><td>SCL<br/></td></tr>
<tr>
<td>31/GPIO30<br/></td><td>SDA<br/></td></tr>
<tr>
<td>VDD_EXT<br/></td><td>VCC3.3V<br/></td></tr>
<tr>
<td>GND<br/></td><td>GND<br/></td></tr>
</table>
> 说明:接线时注意杜邦线不宜过长,以免通信不稳定。VL53L1X 模块上的 SCL/SDA 通常已集成上拉电阻,无需额外配置。XSHUT 引脚不接时传感器会自动启动。
![](https://docs.openluat.com/cdn/image/Air780EHM_exs_vl53l1x.png)
## 四、演示软件环境
### 4.1 开发工具
- [Luatools下载调试工具](https://docs.openluat.com/air780epm/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. **vl53l1x_demo.lua** - VL53L1X 功能演示模块
3. **exs_vl53l1x** - VL53L1X 扩展库
## 五、演示核心步骤
### 5.1 硬件准备
1. 按照接线表将 VL53L1X 模块连接到核心板
2. 确保电源连接正确,通过 TYPE-C USB 口供电
3. 检查所有接线无误,避免短路
### 5.2 软件配置
`main.lua` 中加载对应的演示模块:
```lua
-- 加载 vl53l1x_demo.lua 演示模块
require "vl53l1x_demo"
```
### 5.3 软件烧录
1. 使用 Luatools 选择最新内核固件
2. 下载本项目所有脚本文件
3. 将固件和脚本一起烧录到设备
4. 烧录成功后设备自动重启后开始运行
### 5.4 功能测试
#### 5.4.1 标准测距演示
1. 设备启动后打印 "HELLO",随后自动进入 [1/5] 标准测距
2. 观察日志输出,确认初始化成功(应看到 `MID=0xEA MT=0xCC`
3. 观察距离数据(单位 mm)的连续读取,共 5 次
#### 5.4.2 测距模式切换演示
1. 自动进入 [2/4] 测距模式切换
2. short 模式:抗环境光干扰最强,适合窗口附近等强光环境
3. long 模式:最远可测约 3.6m,适合室内暗光远距离场景
#### 5.4.3 休眠与唤醒演示
1. 自动进入 [3/4] 休眠与唤醒演示
2. 读一次当前距离作为参考
3. sleep() 进入软件待机(约 6μA),3 秒后 wakeup() 唤醒恢复测距
4. 观察唤醒后测距是否正常恢复
#### 5.4.4 持续测距演示
1. 自动进入 [4/4] 持续测距演示
2. 每隔 1 秒读取一次距离数据,共 5 次
3. 观察数据稳定性与状态码
### 5.5 预期效果
- **标准测距**:初始化成功,距离数据正常输出
- **模式切换**short/long 模式均能正常读取距离
- **休眠唤醒**sleep 后停止测距,wakeup 后测距恢复正常
- **持续测距**:每秒一帧数据,状态码 0(测距成功)
- **日志如下:**
```lua
[2026-07-21 20:17:13.093][000000000.246] I/user.main VL53L1X_Demo 001.999.000
[2026-07-21 20:17:13.099][000000000.263] I/user.vl53l1x_demo HELLO
[2026-07-21 20:17:13.228][000000001.264] I/user.vl53l1x_demo ===== [1/5] =====
[2026-07-21 20:17:13.232][000000001.275] I/user.exs_vl53l1x 0x00E5=0x03
[2026-07-21 20:17:13.238][000000001.385] I/user.exs_vl53l1x (mode=standard)
[2026-07-21 20:17:13.243][000000001.388] I/user.exs_vl53l1x MID=0xEA MT=0xCC
[2026-07-21 20:17:13.377][000000001.591] I/user.exs_vl53l1x Standard Ranging
[2026-07-21 20:17:13.382][000000001.591] I/user.vl53l1x_demo VL53L1X : 202607201200
[2026-07-21 20:17:13.400][000000001.845] I/user.vl53l1x_demo 1: =201mm = stream=1
[2026-07-21 20:17:13.820][000000002.354] I/user.vl53l1x_demo 2: =200mm = stream=2
[2026-07-21 20:17:14.325][000000002.863] I/user.vl53l1x_demo 3: =200mm = stream=3
[2026-07-21 20:17:14.827][000000003.372] I/user.vl53l1x_demo 4: =196mm = stream=4
[2026-07-21 20:17:15.339][000000003.881] I/user.vl53l1x_demo 5: =197mm = stream=5
[2026-07-21 20:17:15.837][000000004.385] I/user.exs_vl53l1x
[2026-07-21 20:17:15.845][000000004.385] I/user.vl53l1x_demo ---- [1/5] 完成 ----
[2026-07-21 20:17:16.343][000000004.886] I/user.vl53l1x_demo ===== [2/5] =====
[2026-07-21 20:17:16.348][000000004.886] I/user.vl53l1x_demo short
[2026-07-21 20:17:16.358][000000004.898] I/user.exs_vl53l1x 0x00E5=0x03
[2026-07-21 20:17:16.466][000000005.008] I/user.exs_vl53l1x (mode=short)
[2026-07-21 20:17:16.471][000000005.011] I/user.exs_vl53l1x MID=0xEA MT=0xCC
[2026-07-21 20:17:16.668][000000005.215] I/user.exs_vl53l1x Standard Ranging
[2026-07-21 20:17:16.916][000000005.461] I/user.vl53l1x_demo short : =24mm =
[2026-07-21 20:17:16.923][000000005.465] I/user.exs_vl53l1x
[2026-07-21 20:17:16.928][000000005.465] I/user.vl53l1x_demo long
[2026-07-21 20:17:16.934][000000005.477] I/user.exs_vl53l1x 0x00E5=0x03
[2026-07-21 20:17:17.040][000000005.587] I/user.exs_vl53l1x (mode=long)
[2026-07-21 20:17:17.056][000000005.590] I/user.exs_vl53l1x MID=0xEA MT=0xCC
[2026-07-21 20:17:17.258][000000005.794] I/user.exs_vl53l1x Standard Ranging
[2026-07-21 20:17:17.524][000000006.058] I/user.vl53l1x_demo long : =199mm =
[2026-07-21 20:17:17.530][000000006.062] I/user.exs_vl53l1x
[2026-07-21 20:17:17.534][000000006.062] I/user.vl53l1x_demo ---- [2/5] 完成 ----
[2026-07-21 20:17:18.021][000000006.563] I/user.vl53l1x_demo ===== [4/5] =====
[2026-07-21 20:17:18.036][000000006.574] I/user.exs_vl53l1x 0x00E5=0x03
[2026-07-21 20:17:18.144][000000006.684] I/user.exs_vl53l1x (mode=standard)
[2026-07-21 20:17:18.151][000000006.688] I/user.exs_vl53l1x MID=0xEA MT=0xCC
[2026-07-21 20:17:18.345][000000006.891] I/user.exs_vl53l1x Standard Ranging
[2026-07-21 20:17:18.609][000000007.144] I/user.vl53l1x_demo : =201mm =
[2026-07-21 20:17:18.614][000000007.144] I/user.vl53l1x_demo
[2026-07-21 20:17:18.620][000000007.149] I/user.exs_vl53l1x
[2026-07-21 20:17:21.610][000000010.149] I/user.vl53l1x_demo
[2026-07-21 20:17:21.626][000000010.162] I/user.exs_vl53l1x
[2026-07-21 20:17:21.875][000000010.415] I/user.vl53l1x_demo : =199mm =
[2026-07-21 20:17:21.882][000000010.419] I/user.exs_vl53l1x
[2026-07-21 20:17:21.887][000000010.419] I/user.vl53l1x_demo ---- [4/5] 完成 ----
[2026-07-21 20:17:22.385][000000010.920] I/user.vl53l1x_demo ===== [5/5] =====
[2026-07-21 20:17:22.391][000000010.931] I/user.exs_vl53l1x 0x00E5=0x03
[2026-07-21 20:17:22.508][000000011.041] I/user.exs_vl53l1x (mode=standard)
[2026-07-21 20:17:22.514][000000011.044] I/user.exs_vl53l1x MID=0xEA MT=0xCC
[2026-07-21 20:17:22.711][000000011.248] I/user.exs_vl53l1x Standard Ranging
[2026-07-21 20:17:22.721][000000011.248] I/user.vl53l1x_demo 1 5
[2026-07-21 20:17:23.764][000000012.302] I/user.vl53l1x_demo [1]: =201mm =
[2026-07-21 20:17:24.771][000000013.311] I/user.vl53l1x_demo [2]: =199mm =
[2026-07-21 20:17:25.779][000000014.320] I/user.vl53l1x_demo [3]: =197mm =
[2026-07-21 20:17:26.788][000000015.329] I/user.vl53l1x_demo [4]: =198mm =
[2026-07-21 20:17:27.803][000000016.338] I/user.vl53l1x_demo [5]: =197mm =
[2026-07-21 20:17:27.808][000000016.342] I/user.exs_vl53l1x
[2026-07-21 20:17:27.813][000000016.342] I/user.vl53l1x_demo ---- [5/5] 完成 ----
[2026-07-21 20:17:28.299][000000016.843] I/user.vl53l1x_demo ===== [] =====
```
### 5.6 故障排除
1. **传感器初始化失败**
- 检查 VL53L1X 接线是否正确(SCL、SDA、VCC、GND
- 确认 GPIO 引脚配置与接线一致
- 检查电源电压是否稳定(3.3V
- 确认 exs_vl53l1x 扩展库已正常加载
2. **读取数据始终为 0 或异常**
- 检查传感器供电是否正常
- 确认 I2C 地址是否正确(默认 0x29)
- 确认接线无松动
3. **测距状态码异常**
- 状态码 1(Sigma 失效):测量波动太大,目标反射率过低
- 状态码 2(信号失效):信号太弱,目标距离过远或反射率低
- 状态码 9(串扰信号):有保护玻璃串扰,可运行串扰校准
- 状态码 14(范围无效):通常对应第一帧无效数据,会自动跳过
### 5.7 扩展功能建议
exs_vl53l1x 更多接口的使用可以查看 [exs_vl53l1x 扩展库说明](https://docs.openluat.com/osapi/ext/sensor/exs_vl53l1x/)
@@ -0,0 +1,151 @@
--[[
@module vl53l1x_demo
@summary VL53L1X 飞行时间测距传感器演示模块,包含所有功能的演示用例
@version 1.0
@date 2026.07.20
@author 江访
@usage
本文件包含 VL53L1X 的逐项功能演示。
通过 exs_vl53l1x 扩展库的 API 逐一演示标准测距、模式切换、中断读取、休眠唤醒、持续测距等功能。
]]
-- 加载 exs_vl53l1x 扩展库
local exs_vl53l1x = require "exs_vl53l1x"
-- [1/5] 标准测距演示
local function demo_standard_ranging()
log.info("vl53l1x_demo", "===== [1/5] 标准测距 =====")
-- 软件 I2C 模式:SCL=GPIO31, SDA=GPIO30Air780EPM 接线)
local result = exs_vl53l1x.setup({scl = 31, sda = 30})
if not result then
log.error("vl53l1x_demo", "初始化失败,请检查接线")
return false
end
log.info("vl53l1x_demo", "VL53L1X 初始化成功,版本:", exs_vl53l1x.version())
sys.wait(200)
for i = 1, 5 do
local data = exs_vl53l1x.get_data()
if data then
log.info("vl53l1x_demo", string.format("第%d次: 距离=%dmm 状态=%s stream=%d",
i, data.distance, data.status_str, data.stream_count or 0))
else
log.error("vl53l1x_demo", "读取数据失败")
end
sys.wait(500)
end
exs_vl53l1x.close()
log.info("vl53l1x_demo", "---- [1/5] 完成 ----")
return true
end
-- [2/5] 测距模式切换
local function demo_range_mode()
log.info("vl53l1x_demo", "===== [2/5] 测距模式切换 =====")
-- short 模式(抗强光,约 1.36m
log.info("vl53l1x_demo", "切换 short 模式(抗强光)")
local ok = exs_vl53l1x.setup({scl = 31, sda = 30, range_mode = "short"})
if not ok then return end
sys.wait(200)
local data = exs_vl53l1x.get_data()
if data then
log.info("vl53l1x_demo", string.format("short 模式: 距离=%dmm 状态=%s", data.distance, data.status_str))
end
exs_vl53l1x.close()
-- long 模式(远距离,约 3.6m)
log.info("vl53l1x_demo", "切换 long 模式(远距离)")
ok = exs_vl53l1x.setup({scl = 31, sda = 30, range_mode = "long"})
if not ok then return end
sys.wait(200)
data = exs_vl53l1x.get_data()
if data then
log.info("vl53l1x_demo", string.format("long 模式: 距离=%dmm 状态=%s", data.distance, data.status_str))
end
exs_vl53l1x.close()
log.info("vl53l1x_demo", "---- [2/5] 完成 ----")
end
-- [3/5] 休眠与唤醒
local function demo_sleep_wakeup()
log.info("vl53l1x_demo", "===== [4/5] 休眠与唤醒演示 =====")
local result = exs_vl53l1x.setup({scl = 31, sda = 30})
if not result then return end
sys.wait(200)
-- 读一次数据作为参考
local data = exs_vl53l1x.get_data()
if data then
log.info("vl53l1x_demo", string.format("休眠前: 距离=%dmm 状态=%s", data.distance, data.status_str))
end
-- 进入软件待机(约 6μA
log.info("vl53l1x_demo", "进入软件待机模式")
exs_vl53l1x.sleep()
sys.wait(3000)
-- 唤醒(自动恢复测距)
log.info("vl53l1x_demo", "从软件待机模式唤醒")
exs_vl53l1x.wakeup()
sys.wait(200)
data = exs_vl53l1x.get_data()
if data then
log.info("vl53l1x_demo", string.format("唤醒后: 距离=%dmm 状态=%s", data.distance, data.status_str))
end
exs_vl53l1x.close()
log.info("vl53l1x_demo", "---- [4/5] 完成 ----")
end
-- [5/5] 持续测距演示
local function demo_continuous_ranging()
log.info("vl53l1x_demo", "===== [5/5] 持续测距演示 =====")
local result = exs_vl53l1x.setup({scl = 31, sda = 30})
if not result then return end
log.info("vl53l1x_demo", "每隔 1 秒读取一次距离数据,共 5 次")
for i = 1, 5 do
sys.wait(1000)
local data = exs_vl53l1x.get_data()
if data then
log.info("vl53l1x_demo", string.format("持续测距[%d]: 距离=%dmm 状态=%s",
i, data.distance, data.status_str))
else
log.warn("vl53l1x_demo", string.format("持续测距[%d] 读取失败", i))
end
end
exs_vl53l1x.close()
log.info("vl53l1x_demo", "---- [5/5] 完成 ----")
end
-- 演示主函数(运行在协程中)
local function vl53l1x_demo_task_func()
log.info("vl53l1x_demo", "HELLO")
sys.wait(1000)
-- HELLO 开始 → [1/5] → [2/5] → [3/5] → [4/5] → End
local ok = demo_standard_ranging()
if not ok then return end
sys.wait(500)
demo_range_mode()
sys.wait(500)
demo_sleep_wakeup()
sys.wait(500)
demo_continuous_ranging()
sys.wait(500)
log.info("vl53l1x_demo", "===== [演示完毕] =====")
end
sys.taskInit(vl53l1x_demo_task_func)