最初版的构思是通过ESP32板子连接学校的校园网,进而访问学校一个协会的服务器(仅在校园网或者协会WiFi能够连接上协会的服务器),使用服务器的Broker,以MQTT协议为基础,通过ArduinoIDE用C++对ESP32板子烧录程序,以达到物联网的效果(这里仅仅是想让这个东西可以开门就行)。
实际操作过程中遇到了两大问题:一、校园网的认证破解难度太高,学习周期偏长(需要从1700多行的JS语言中找到正确的JOSN数据包,并且加重了ESP32本身需要烧录的程序);二、MQTTX在手机端操作麻烦。
经过查阅,了解到了Blinker这款应用,于是有了以下构思:
用ESP32直接连接互联网,并访问Blinker的MQTT Broker,同样以MQTT协议为基础,通过ArduinoIDE用C++给ESP32烧录程序,以实现物联网。
此方案解决问题的途径:一、对于访问MQTT Broker的问题,因为Blinker的服务器是公开的,可以用任何网络去访问。二、对于手机版运用复杂问题,BlinkerAPP提供了一款手机版的APP(适用于安卓、苹果),让手机版界面更便于操作和个性化。
此外,Blinker有许多可以现用的库函数,让项目内容得到了提升(给加入温湿度测量的提供了基础)。
一、ArduinoIDE环境搭建
①ESP32开发板
关于Arduino的下载就不多赘述了,这里主要是想要分享一下关于在开发板管理器中添加ESP32时,在首选项里面关于网址的填写。
相信大多数人在首选项中用的Github上面的网址,下载的速度实在是太慢了,本人之前在开发ESP8266时也遇到过这样的问题。也在网上去寻找过许多方法,其实最简单的就是用这个网址:
https://arduino.me/packages/esp32.json
https://arduino.me/packages/esp8266.json(esp8266的也奉上)
当然,想要了解更多的可以自己去Arduino社区里看看,网址:
②Blinker库、DHT库和ServoESP32库
我用的是这三个,当然你也可以用自己的。(这里需要注意的是ServoESP32库可能会和Servo库有冲突,后面代码大家可以自己看看想用哪一个,第一个完整的代码是没有用ServoESP32库的代码,里面关于pwm信号的计算在本文中不做介绍,第二个完整代码是用了ServoESP32库的)
二、手机下载Blinker
直接在手机浏览器上面搜索Blinker官网上面直接下载就行。
Blinker官网:https://diandeng.tech/home
三、硬件设施
主要包括:1个ESP32的板子、1个拓展板(注意和你手上板子的兼容性)、1个MG995舵机、1个DHT11温湿度传感器模块,3D打印配件(这个东西根据你们自己的需要去打印就行,这里就不过多介绍了),1个电源(来个充电宝就行)。
四、代码
完整代码:
直接给想要copy后,自己理解的UU们奉上。
未运用ESP32Servo库的代码:
运用了ESP32Servo库的代码:
代码讲解:
这里是头文件,其他的没什么好讲的,需要注意的就是如果你的DHT和我的不一样的话,宏定义的部分可能也有不同,根据你自己的硬件的介绍去改就行。
这是Blinker的初始化。(我看Blinker文档的时候看见只有这种格式,如果有其他的大家可以在评论区说一下)
这里是Blinker库里面的类,用类创建了两个数据对象和一个按键对象。里面的参数是Blinker手机板APP里面我们创建的对应数据和按键的组件键名。
这里的heartbeat()函数名可以自定,在这个函数里面是运用了Blinker数据对象的print()函数,将DHT11读取到的数据上传给手机的BlinkerAPP ,而上传的触发是由Blinker.arrachHeartbeat()函数来实现的,这个函数是网络连接的一个心跳包(这里涉及到了MQTT协议),ESP32会每59s给Blinker的MQTT服务器发一个消息。所以我们将数据上传函数的触发与心跳函数结合起来,就可以让寝室温湿度及时的上传给手机端(如果直接将heartbeat()函数直接写在loop()函数里面可能会影响ESP32和Blinker的服务器连接的稳定性,具体原因和MQTT协议的通讯模式有关)。同时,我们需要注意到的是我们将DHT11的数据读取放在了loop()函数中,并将其设定为2s读取一次,这样可以确保ESP32在向服务器传输的数据都是及时更新的,这样并不会影响开门的功能。(也许有UU要问,为什么不把这个读取放在heartbeat()函数中呢?其实是可以的,这样的好处是减少了ESP32的工作量,但是会存在数据更新延迟太长的现象大概是90s-120s,并且读取到的数据准确性下降。两种方案各有弊益,各位自己选择。)
而Button1.attch()函数则是Button对象里面的一个成员函数,它将Button1触发后的动作设定为button_callback(),于是就实现了我们按下开关就开门。需要注意的是不同的舵机,这里的代码不同,我的舵机是360°的,所以在这里用myservo.write(0或180)是舵机会分别向两个相反的方向一直旋转,而myservo.write(90)是舵机会停止旋转。如果你手上的是180°的舵机,那么就可以把myservo.write(90)这部分给省略掉。
五、手机APP操作
那些copy完就直接上传的都是失败了的,看到这里他们才明白原因。当然,恭喜认真看完的你,离成功就差最后一步了。这里我直接上图,照着操作就行。
点入你自己的设备后自己设计自己的界面的一定要将组件键名和你代码里面的设置成一样的,这样才能够实现最后一个界面。
关于DHT模块的运用其实可以不止于显示在手机上面,还可以与寝室里面的一些其他硬件结合起来,比如:空调、加湿器等。可以做到自己调节开关,当然也可以像开门一样,做一个按钮。(这两者结合当然是最好的)其次关于开门方面的提升,可以再加一个指纹识别模块,做到不需要任何其他的工具来开门。(想法是让一块ESP8266的板子处于混合模式,这样让指纹识别模块和ESP32连接在一个局域网内进行通讯,进而实现开门。这样还解决了一个问题, 就是关于ESP32配网的问题。由于ESP32在blinker架构下没有像esp8266wifimulti库这样的库函数来配置网络连接,当我们用ESP32来联网时,只能连接预设好的WiFi。但我们学校校园网覆盖广,所以寝室就没有专门安装固定的路由器,而让ESP32连接校园网需要认证通过,太麻烦能力不够,所以我们的WiFi就只是寝室里某一个人的手机热点,就有局限性了。而用ESP8266来当中间人,就可以解决这一问题,同时还可以通过ESP8266的WiFi的一些库函数来识别连接的WiFi信息,从而向其他成员汇报谁回寝、或者谁开了门之类的功能,当然这里的前提是你手机的热点连接了互联网。)