Go实现树莓派I2C读取SHT30温度湿度传感器

简介

树莓派其实本身包含很多资源引脚, 合理利用其实可以自制智能家居的一部分,本身硬件和Linux系统等高级语言支持加生态, 不说了,
做就好了…

I2C 功能开启

参考之前的文章就可以了 Go实现树莓派读取bh1750光照强度

查看I2C总线上SHT30的设备地址

树莓派上两路i2c总线, 我们连接的是第一路,指令也是 -y 1, 如下
i2cdetect -y 1
在这里插入图片描述
为什么是0x44, 接着向下看, SHT3x默认地址就是0x44, 当Addr引脚接地则地址是0x44, 接VCC则是0x45, 电路图如下, 所以地址是0x44
在这里插入图片描述

在这里插入图片描述

代码

sht30.go

package sensorimport ("context""periph.io/x/conn/v3/gpio""periph.io/x/conn/v3/gpio/gpioreg""time"
)type SHT3xOption struct {I2COptionOnAlerted   func()AlertPinNum PinNum
}type SHT30TemperatureValue struct {value int64
}func (v SHT30TemperatureValue) Fahrenheit() float32 {return -49.0 + (315.0 * float32(v.value) / 65535.0)
}func (v SHT30TemperatureValue) Celsius() float32 {return -49.0 + (175.0 * float32(v.value) / 65535.0)
}type SHT30Value struct {temperature SHT30TemperatureValuehumidity    float32
}func (s *SHT30Value) setValues(temp int64, hum int64) {s.temperature.value = temps.humidity = 100.0 * (float32(hum) / 65535.0)
}func (s *SHT30Value) Humidity() float32 {return s.humidity
}func (s *SHT30Value) Temperature() SHT30TemperatureValue {return s.temperature
}type SHT30Sensor struct {opt      SHT3xOptionalertPin gpio.PinIni2cDevicecancalFunc context.CancelFunc
}func NewSHT30Sensor(opt SHT3xOption) (*SHT30Sensor, error) {var (sensor = &SHT30Sensor{opt: opt,})if opt.AlertPinNum > 0 {sensor.alertPin = gpioreg.ByName(opt.AlertPinNum.String())if nil == sensor.alertPin {return nil, CantFindPinError}}sensor.setDeviceInfo(opt.I2COption)return sensor, nil
}func (sensor *SHT30Sensor) Init() (err error) {if err = sensor.init(); nil != err {return err}if nil != sensor.opt.OnAlerted && nil != sensor.alertPin {err = sensor.alertPin.In(gpio.PullNoChange, gpio.NoEdge)if nil != err {return err}var ctx context.Contextctx, sensor.cancalFunc = context.WithCancel(context.Background())go sensor.monitorAlertPin(ctx)}//if err = sensor.reset(); nil != err {//	return err//}return
}func (sensor *SHT30Sensor) Destroy() error {if nil != sensor.cancalFunc {sensor.cancalFunc()sensor.cancalFunc = nil}return nil
}func (sensor *SHT30Sensor) GetValue() (v SHT30Value, err error) {var (sendBytes = []byte{0xE0, 0x00} // read commandrecvBytes = make([]byte, 6)temp, hum int64)err = sensor.dev.Tx(sendBytes, recvBytes)if nil != err {return}if !sensor.checksumCompare(recvBytes[:2], recvBytes[2]) {err = CRCCheckFailedErrorreturn}if !sensor.checksumCompare(recvBytes[3:5], recvBytes[5]) {err = CRCCheckFailedErrorreturn}temp = int64(recvBytes[0])<<8 | int64(recvBytes[1])v.temperature.value = temphum = int64(recvBytes[3])<<8 | int64(recvBytes[4])v.setValues(temp, hum)return
}/*
同硬件上nReset相同, 但这里是软件发送指令, 硬件是引脚触发, 不再响应指令
目前调用就会报错,所以直接返回
*/
func (sensor *SHT30Sensor) reset() error {var (sendBytes = []byte{0x30, 0xA2} // 软重置)_, err := sensor.dev.Write(sendBytes)if nil != err {return err}time.Sleep(time.Millisecond * (15 + 1)) // 软重置最长时间 1ms, 可能后续需要考虑指令取消,  最长15ms,目前先跟数据手册单个指令时间来return err
}/*
设置测量周期mps 0.5, 指令 0x20, 0x32/0x24/0x2F(High/Medium/Low)mps 1  , 指令 0x21, 0x30/0x26/0x2D(High/Medium/Low)mps 2  , 指令 0x22, 0x36/0x20/0x2B(High/Medium/Low)mps 4  , 指令 0x23, 0x34/0x22/0x29(High/Medium/Low)mps 10 , 指令 0x27, 0x37/0x21/0x2A(High/Medium/Low)
*/
func (sensor *SHT30Sensor) init() error {var (sendBytes = []byte{0x22, 0x36})_, err := sensor.dev.Write(sendBytes)if nil != err {return err}time.Sleep(time.Millisecond * 15)return err
}func (sensor *SHT30Sensor) checksumCompare(dat []byte, checksum byte) bool {var crc = sensor.crc8(dat)return crc == checksum
}func (sensor *SHT30Sensor) crc8(dat []byte) byte {var polynomial = byte(0x31) // 多项式值var crc byte = 0xFF         // 初始化值for _, v := range dat {crc ^= vfor i := 0; i < 8; i++ {if (crc & 0x80) != 0 {crc = (crc << 1) ^ polynomial} else {crc <<= 1}crc &= 0xFF // 保持 crc 为 8 位}}return crc
}func (sensor *SHT30Sensor) monitorAlertPin(ctx context.Context) {var (triggered bool // 用于确保不会反复提醒...)for {if gpio.Low == sensor.alertPin.Read() {if !triggered {go sensor.opt.OnAlerted()triggered = true}} else {if triggered {triggered = false}}select {case <-ctx.Done():returncase <-time.After(time.Millisecond * 10):}}
}

使用代码
main.go

package mainimport ("IntelligentAgriculture/sensor""fmt""periph.io/x/conn/v3/i2c/i2creg""time"
)const (AlertPinNum = 27MotorPinNum = 17LEDPinNum   = 22I2CSHT30Addr   = 0x44I2CAt24C02Addr = 0x50I2CBH1750Addr  = 0x23
)func main() {i2cBus, err := i2creg.Open("")if nil != err {fmt.Println("i2creg.Open:", err)return}defer i2cBus.Close()s, err := sensor.NewSHT30Sensor(sensor.SHT3xOption{OnAlerted: func() {fmt.Println("alerted!!!")},AlertPinNum: AlertPinNum,I2COption: sensor.I2COption{I2CBus:        i2cBus,DeviceAddress: I2CSHT30Addr,},})if nil != err {fmt.Println("sensor.NewSHT30Sensor:", err)return}defer s.Destroy()err = s.Init()if nil != err {fmt.Println("sensor.Init:", err)return}for {v, err := s.GetValue()if nil != err {fmt.Println("sensor.GetValue: ", err)continue}fmt.Printf("%0.2f℃, %0.2f℉, %0.2f(RH)\n", v.Temperature().Celsius(), v.Temperature().Fahrenheit(), v.Humidity())time.Sleep(time.Second)}
}

其他文章

Go实现树莓派读取bh1750光照强度
Go实现树莓派读取at24c02 eeprom读写数据
Go实现树莓派控制舵机
Go实现树莓派超声波测距

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://xiahunao.cn/news/3030734.html

如若内容造成侵权/违法违规/事实不符,请联系瞎胡闹网进行投诉反馈,一经查实,立即删除!

相关文章

(Java)心得:LeetCode——5.最长回文子串

一、原题 给你一个字符串 s&#xff0c;找到 s 中最长的回文子串。 如果字符串的反序与原始字符串相同&#xff0c;则该字符串称为回文字符串。 示例 1&#xff1a; 输入&#xff1a;s "babad" 输出&#xff1a;"bab" 解释&#xff1a;"aba"…

网页版Figma汉化

最近学习Figma&#xff0c;简单介绍一下网页版Figma的汉化方法 1.打开网址&#xff1a;Figma软件汉化-Figma中文版下载-Figma中文社区 2.下载汉化插件离线包 解压汉化包 3.点开谷歌的管理扩展程序 4.点击加载已解压的扩展程序&#xff0c;选择刚刚解压的包 这样就安装好了汉化…

厚德提问大佬答4:AI绘画生成的心得

遇到难题不要怕&#xff01;厚德提问大佬答&#xff01; 厚德提问大佬答 你是否对AI绘画感兴趣却无从下手&#xff1f;是否有很多疑问却苦于没有大佬解答带你飞&#xff1f;从此刻开始这些问题都将迎刃而解&#xff01;你感兴趣的话题&#xff0c;厚德云替你问&#xff0c;你解…

2019年计算机真题

2019年计算机真题 离散数学 一、用逻辑符号表达下列语句(论域为包含一切事物的集合) 1&#xff09;过平面上的两个点&#xff0c;有且仅有一条直线通过。 解: (1) P ( x , y ) : x , y \mathrm{P}_{(\mathrm{x}, \mathrm{y})}: \mathrm{x}, \mathrm{y} P(x,y)​:x,y 是平面上的…

Git泄露(续)

接上一篇补充 git config --global user.name " " git config --global user.email 邮箱地址 配置用户名和邮箱 git commit 使其处于交互区&#xff0c;没有使用 -m&#xff0c;默认用vim 来编辑和提交信息 输入要提交的内容&#xff0c;然后按ESC建回到命令…

智慧仓储可视化大屏,以最直观的形式展示海量数据。

智慧仓储可视化大屏是一种通过数据可视化技术&#xff0c;将仓储管理系统中的海量数据以图表、地图、仪表盘等形式直观展示在大屏上的解决方案。它可以帮助仓储管理人员更清晰地了解仓库的运营情况&#xff0c;从而做出更明智的决策。 智慧仓储可视化大屏通常包括以下功能和特点…

github删除自己的仓库

测试Github的时候新建了很多仓库&#xff0c;但是后来想删除&#xff0c;找了半天居然没有找到按钮。 我就推测这个删除的功能肯定藏起来了&#xff0c;后来度娘了一下&#xff0c;发现果然在一个比较隐蔽的位置&#xff0c;不知道以后这个功能会不会改到一个比较明显的位置吧…

高效工作之软件系统——数据结构登记表

数据结构模板 开发完软件系统后&#xff0c;往往需要进行一些登记——《软件系统数据结构登记表》 然后软件项目有60个表左右&#xff0c;难道需要手动录入&#xff0c;那肯定不可能 工欲善其事必先利其器&#xff01;go。。。同事给的模板是下图 效果图 于是想到 之前使用…

Java代理Ⅱ

目录 静态代理的内存结构图 测试demo 内存图 关于为什么不能直接修改原方法&#xff0c;而是要用代理 参考文章 关于代理我之前写过一篇博客&#xff0c;基本已经讲的差不多了&#xff0c;有兴趣的读者可以去看看 Java代理 最近有了新的感悟&#xff0c;所以记录一下 静…

基于springboot实现毕业设计系统项目【项目源码+论文说明】

基于springboot实现毕业设计系统演示 摘要 在如今社会上&#xff0c;关于信息上面的处理&#xff0c;没有任何一个企业或者个人会忽视&#xff0c;如何让信息急速传递&#xff0c;并且归档储存查询&#xff0c;采用之前的纸张记录模式已经不符合当前使用要求了。所以&#xff…

文本三剑客grep与正则表达式、元字符

正则表达式 正则表达式又称为正规表达式、常规表达式、在代码中常简写为regex、regex或RE。正则表达式是使用单个字符串来描述、匹配一系列符合某个句法规则的字符串&#xff0c;简单来说&#xff0c;是一种匹配字符串的方法&#xff0c;通过一些特殊符号&#xff0c;实现快速查…

cocos中的meta文件有什么用?如何生成?

cocos中的.meta文件有什么用&#xff1f;如何生成&#xff1f; 1. .meta文件有什么用&#xff1f; Cocos Creator 会为 assets 目录下的每一个文件和目录生成一个同名的 meta 文件 示例 {"ver": "4.0.23", // 版本"importer": "typescr…

Mybatis入门之在基于Springboot的框架下拿到MySQL中数据

介绍 Java技术操作数据库 MyBatis是一款优秀的持久层框架 用于简化JDBC的开发 优秀的持久层框架 我们要基于Springboot整合Mybatis 实操 学习 基于Mybatis是如何操作数据库的 通过MyBatis书写SQL语句 SQL语句执行完毕后 会将查询结果返回给Java程序 表中数据会自动封装…

Mongodb中的索引

目录 索引的类型 单字段索引 符合索引 其他索引 索引的管理操作 查看索引 创建索引 移除索引 索引的使用 执行计划 覆盖的索引查询 索引支持在MongoDB中高效地执行查询。 如果没有索引&#xff0c;MongoDB必须执行全集合扫描&#xff0c;即扫描集合中的每个文档&a…

Java入门基础学习笔记1——初识java

1、为什么学习java&#xff1f; 几乎统治了服务端的开发&#xff1b;几乎所有的互联网企业都使用&#xff1b;100%国内大中型企业都用&#xff1b;全球100亿的设备运行java。开发岗位薪资高。 Java的流行度很高&#xff0c;商用占有率很高。 可移植性。 2、Java的背景知识 …

QT C++ widget layout 嵌套 例子2

在上篇文章中描述了实中套虚&#xff08;用setLayout&#xff09;&#xff0c;虚中套实&#xff08;用addWidget&#xff09;。 本文再加1条&#xff0c;虚中套虚&#xff08;用addLayout&#xff09;。 所谓虚中套虚&#xff0c;是layout 套 layout 。 另外用循环代码生成从…

怎么用照片制作gif动图?一个网站在线做

在数字图像处理中&#xff0c;动态图片是我们日常生活中不可缺少的一部分。Gif动图以为器画面展示的形式&#xff0c;文件的体积以及兼容性而备受喜爱。通过使用多张照片制作gif动画的操作&#xff0c;可以让我们制作出生地有趣的gif动态效果&#xff0c;能够更好更快的传达信息…

太阳能无人机的多元化应用

随着新能源技术的不断发展和成熟&#xff0c;太阳能在无人机的应用技术已经成熟。太阳能无人机得到了量产和广泛的应用。传统无人机相比&#xff0c;太阳能无人机无需燃油&#xff0c;运行费用低廉&#xff0c;搭载多种高科技设备&#xff0c;能够高效、多元化地采集和分析各类…

【算法】Dijkstra求最短路算法

TOP提示&#xff1a;Dijkstra算法只适用于不含负权边的情况 Dijkstra算法是一个基于贪心&#xff0c;广搜和动态规划 求图中某点到其他所有点的最短路径的算法 一、步骤 首先我们先总结Dijkstra算法的完整步骤 我们需要一个dis数组存储从起点到达其他节点的最短距离&…

无列名注入

在进行sql注入时&#xff0c;一般都是使用 information_schema 库来获取表名与列名&#xff0c;因此有一种场景是传入参数时会将 information_schema 过滤 在这种情况下&#xff0c;由于 information_schema 无法使用&#xff0c;我们无法获取表名与列名。 表名获取方式 Inn…