• 智能家居入门DIY——【五、执行命令】


            前面几篇介绍了ESP8266使用AT命令来连接WIFI实现一系列功能。这一篇介绍一下使用Wemos D1 Wifi来进行开发,当然也可以用常见的8针ESP8266来完成(只是需要按网上的方法将Arduino作为烧写器,我是买了一个)。如果不用连接太多的传感器,那么ESP8266模块本身就够用了。

    一、工具选择

    1、VS2015社区版,安装FOR ARDUINO IDE。

    2、SOCKET调试工具NetAssist。

    二、过程

    1、安装ESP8266开发板到IDE

    2、选择NodeMCU1.0

    3、编写代码然后烧录

    这个不涉及到任何刷固件之类的软件,直接用IDE做就可以了。非常简单不是?

    作为例子,依然用lewei50的TCP连接,后面文章可能还会说一下OneNet的MQTT协议:

    此时,可以使用如下库:

    #include <ArduinoJson.h>
    #include <ESP8266WiFi.h>
    #include <WiFiClient.h>

    其中ESP8266WIFI是连接WIFI来的,而WIFICLIENT是用来做客户端和服务器通讯的:

    //连接WIFI
    bool ConnectWifi() {
        if (!WiFi.isConnected()) {
            WiFi.begin(ssid, password);
            while (!WiFi.isConnected())
            {
                delay(100);
            }
        }
        return WiFi.isConnected();// WiFi.status() == WL_CONNECTED;
    }
    
    //连接服务器
    bool ConnectServer() {
        if (wClient.status() != ESTABLISHED) {
            wClient.stop();
            wClient.connect(serverUrl, serverPort);
            delay(1000);
        }
        return wClient.status()==4;
    }

    这都非常简单,然后介绍一下ArduinoJson库,这个库就是用来编辑Json数据的,lewei50的TCP长连要求先发送识别码,相当于登录:

    //发送识别码
    bool UpDateToServer() {
        String info = "";
        StaticJsonDocument<200> doc;
        JsonObject root = doc.to<JsonObject>();
        root["method"] = "update";
        root["gatewayNo"] = "01";
        root["userkey"] = userKey;
        serializeJson(root, info);
        info += (String)"&^!";
        return wClient.print(info)== info.length();
    }

    这样就实现了这个登录格式要求(API参考文档为:http://www.lewei50.com/dev/doc/155)

    {
    
        "method": "update",
    
        "gatewayNo": "你的网关号",
    
        "userkey": "你的userkey"
    
    }&^!

    接下来来点干货,怎么实现这样的格式:

    {
    
        "method": "response",
    
        "result": {
    
            "successful": true,
    
            "message": "xxxx"
    
        }
    
    }&^!

    还有这样的格式:

    {
    
        "method": "upload",
    
        "data":[
    
        {
    
            "Name":"T1",
    
            "Value":"1"
    
        },
    
        {
    
            "Name":"01H1",
    
            "Value":"96.2"
    
        }
    
    ]
    
    }&^!

    这样的格式:

    {
    
        "method": "response",
    
        "result": {
    
            "successful": true,
    
            "message": "xxxx",
    
    
            "data":[
    
          {
             "id":"C1",
             "value":"1"
          },
          {
             "id":"C2",
             "value":"2"
          }] 
          
    
        }
    
    }&^!

    JsonObject是可以嵌套的,实现代码如下:

    //上传数据
    bool UpLoadToServer() {
        String info = "";
        //根节点
        StaticJsonDocument<500> doc;
        JsonObject root = doc.to<JsonObject>();
        //method节点
        root["method"] = "upload";
        //data节点
        JsonArray data= root.createNestedArray("data");
        //data数据
        data.add(CreateJsonObject("Name", "T1", "Value", (String)dht22.getTemperature()));
        data.add(CreateJsonObject("Name", "H1", "Value", (String)dht22.getHumidity()));
        serializeJson(root, info);
        info += (String)"&^!";
        return wClient.print(info) == info.length();
    }
    
    //创建data子json对象
    JsonObject CreateJsonObject(String key1,String val1,String key2 ,String val2) {
        StaticJsonDocument<100> buffer;
        JsonObject obj = buffer.to<JsonObject>();
        obj[key1] = val1;
        obj[key2] = val2;
        return obj;
    }

    至于执行命令,就是获取服务器发送来的消息,然后解析Json就可以了。

        String serverMessage = "";
        if (wClient.available()) {
            serverMessage = wClient.readString();
            Serial.println("read");
            //Serial.println(serverMessage);
        }
        if (serverMessage != "") {
            Serial.println("docommand");
             DoCommand(serverMessage);
        }
    //执行服务器的命令
    void DoCommand(String serverMessage) {
        String cmd = DumpServerMessage(serverMessage, "f");
        //回复服务器对控制器状态的查询
        if (cmd == "getAllSensors") {
            ResponseState();
        }
        //服务器更新控制器的命令
        else if (cmd == "updateSensor") {
            String id = DumpServerMessage(serverMessage, "p1");            //命令参数1,控制器ID
            int state = DumpServerMessage(serverMessage, "p2").toInt();    //命令参数2,控制器状态0=关,1=开
            if (!ResponseCommand((String)id + ":" + state)) {
                Serial.println("re command err");
            }
            else {
                if (id == "C1") {
                    digitalWrite(C1Pin, state);
                }
            }
        }
        //服务器的其他消息
        else {
            //Serial.println((String)"cmd:
    " + cmd);
        }
    }

    嗯,就到这里吧,剩下的可以自己去研究一下。下一篇介绍一下OneNet的MQTT,OnetNet比lewei50这个要灵活丰富很多,当然做起来也就需要更费劲一点。

  • 相关阅读:
    2017年3月10号课堂笔记
    2017年3月8号课堂笔记
    2017年3月6号课堂笔记
    2017年3月3号课堂笔记
    第7讲:设计PE型病毒2
    第6讲:设计PE型病毒1
    第5讲:HOOK 任务管理器 第2种方法注入
    第4讲:HOOK 任务管理器 无法结束进程
    第3讲:导入表的定位和读取操作
    第2讲:搜索PEB结构获取kernel32.dll的基址暴力搜索内存空间获得 Api 的线性地址
  • 原文地址:https://www.cnblogs.com/zcsor/p/9853324.html
Copyright © 2020-2023  润新知