树莓派3B+通过I2C连接三个TSL2561并同步获取数据的方法
树莓派3B+同时读取三个TSL2561光感模块的解决方案
问题背景
我有一台树莓派3B+和三个TSL2561光感模块,已实现单个模块的Python读取,但无法同时获取三个模块的数据。使用的库为adafruit-circuitpython-tsl2561(安装命令:sudo pip3 install adafruit-circuitpython-tsl2561)。
TSL2561引脚定义:
- 1: GND
- 2: VCC(接3.3V)
- 3: SDA
- 4: SCL
- 5: INT(可选,暂不用)
传感器参数说明:
lux: 计算得出的光照勒克斯值(可能返回None,代表量程超限)broadband: 宽带通道原始数值infrared: 红外通道原始数值luminosity: 包含宽带和红外数值的二元组
问题根源
TSL2561默认I2C地址为0x39,多个模块直接接同一I2C总线会触发地址冲突,导致无法同时通信。必须先为每个模块设置唯一的I2C地址。
解决步骤
1. 硬件调整:设置不同的I2C地址
TSL2561的地址由ADDR引脚电平决定(部分模块通过板载焊盘设置,需查看模块说明书):
- 模块1:ADDR接GND → 地址
0x39(默认) - 模块2:ADDR接VCC → 地址
0x38 - 模块3:ADDR接SDA → 地址
0x3A(或接SCL得到0x3B,确保三个地址唯一即可)
所有模块的GND、SDA、SCL分别并联到树莓派对应引脚:
- 树莓派SDA对应引脚3,SCL对应引脚5,GND对应任意GND引脚,VCC接3.3V引脚(引脚1)。
2. 验证I2C地址
在树莓派终端执行以下命令,扫描I2C总线确认三个地址存在:
i2cdetect -y 1
输出中应能看到0x38、0x39、0x3A(或你设置的其他地址)。
3. Python多模块读取代码
修改原代码,为每个传感器创建独立实例并指定地址:
import time import board import busio import adafruit_tsl2561 # 初始化I2C总线 i2c = busio.I2C(board.SCL, board.SDA) # 创建三个传感器实例,分别指定不同地址 tsl1 = adafruit_tsl2561.TSL2561(i2c, address=0x39) # 模块1地址 tsl2 = adafruit_tsl2561.TSL2561(i2c, address=0x38) # 模块2地址 tsl3 = adafruit_tsl2561.TSL2561(i2c, address=0x3A) # 模块3地址 # 统一配置传感器参数(可根据需求单独调整每个模块) def configure_sensor(sensor): sensor.enabled = True time.sleep(1) sensor.gain = 0 # 0=1x增益,1=16x增益 sensor.integration_time = 1 # 0=13.7ms,1=101ms,2=402ms,3=手动 # 配置所有传感器 configure_sensor(tsl1) configure_sensor(tsl2) configure_sensor(tsl3) def read_sensor(sensor, name): """读取单个传感器数据并打印""" broadband = sensor.broadband infrared = sensor.infrared lux = sensor.lux print(f"\n[{name}] 读取数据:") print(f"增益:{sensor.gain}") print(f"积分时间:{sensor.integration_time}") print(f"宽带通道:{broadband}") print(f"红外通道:{infrared}") if lux is not None: print(f"光照值(Lux):{lux:.2f}") else: print("光照值:None(传感器量程超限)") try: while True: read_sensor(tsl1, "模块1") read_sensor(tsl2, "模块2") read_sensor(tsl3, "模块3") time.sleep(2) # 间隔2秒读取一次 except KeyboardInterrupt: # 退出时关闭传感器 tsl1.enabled = False tsl2.enabled = False tsl3.enabled = False print("\n程序已退出")
注意事项
- 所有TSL2561的VCC必须接树莓派的3.3V,接5V会烧毁传感器。
- 如果某个模块无法读取,检查接线是否牢固、地址设置是否正确。
- 若
lux返回None,可尝试调整gain(改为16x)或integration_time(延长到402ms)。
内容的提问来源于stack exchange,提问作者Abbas Taheri
相关产品推荐
相关产品推荐

