该方案可以实现物理按键KEY和远程APP同步控制四路LED,其中KEY1长按进入SOFTAP模式,KEY1短按控制LED1,KEY2长按进入AIRLINK模式,KEY2短按控制LED2,KEY3短按控制LED3,KEY4短按控制LED4。GPIO5端口用于读取DHT11温湿度传感器的值(这里有个坑需要跟大家讲下)。(原计划通过长按KEY3控制LED全开,长按KEY4控制LED全关,尝试了很多办法会出错,如果找到比较稳定的好办法会给大家分享。LED本来是4路继电器,还没到所以就凑合下,反正原理都一样,哈哈)
数据点1 LED_1
数据点2 LED_2
数据点3 LED_3
数据点4 LED_4
数据点5 temperature
数据点6 humidity
下面是大家喜闻乐见的干货部分,哈哈。
首先是把DHT11的驱动配置好
hal_temp_hum.h放到/app/include/driver文件夹内
hal_temp_hum.c放到/app/driver文件夹内
没有这个驱动文件可以到机智云下载中心,找到GoKit MCU示例工程,在对应的文件夹内有相应的驱动文件。
如果有朋友懒得改程序,想直接看到效果,最简单的办法就是数据点和我上面的设置的一样,然后直接改上面覆盖的两个地方,我的程序会给大家链接,可供参考。但是不建议这么做,这不利于理解程序的功能,运行机制。
下面红框中的值最好改成100或者50,不改的话控制延时有1s,我感觉延时太大挺别扭的。
定义一个数组用于储存4个LED的状态
extern bool statu[4];
首先加入DHT11的头文件(userhand()需要调用),然后是定义的数组statu[4]初始化
#include “driver/hal_temp_hum.h”
bool statu[4] = {0};
LED状态扫描、DHT11数值读取 定义扫描、读取时间间隔
#define USER_TIME_MS 100
#define LED_TIMEOUT (100/USER_TIME_MS 100) // LED状态扫描,100ms扫描一次
#define DHT_TIMEOUT (1000/USER_TIME_MS 100) // DHT11数值读取,1s扫描一次
(扫描、读取其实是一个意思,可能用词不准,见谅)
改gizwitsEventProcess()程序
先说下数组statu[ ]和LED数据点的对应关系
statu[0]=LED_1
statu[1]=LED_2
statu[2]=LED_3
statu[3]=LED_4
也就是说statu[0]=1是LED_1就开
以下面gizwitsEventProcess()里的程序为例
case EVENT_LED_1 : //LED_1为数据点
currentDataPoint.valueLED_1 = dataPointPtr->valueLED_1;
GIZWITS_LOG(“Evt: EVENT_LED_1 %d \n”, currentDataPoint.valueLED_1);
if(0x01 == currentDataPoint.valueLED_1)
{
statu[0]=1;// 开灯
}
else
{
statu[0]=0;//关灯
}
break;
以此类推
数据点LED_1
数据点LED_4
由于程序太长,数据点LED_2、LED_3就不截图了。
最后改userHandle()程序
首先添加以下代码,这里的代码是将软件世界和硬件世界连接的桥梁,将ESP8266的引脚和数组statu[ ]关联,数组statu[ ]就是这个桥。个人理解,不喜勿喷,哈哈。
GPIO_OUTPUT_SET(GPIO_ID_PIN(14),!statu[0]);
GPIO_OUTPUT_SET(GPIO_ID_PIN(12),!statu[1]);
GPIO_OUTPUT_SET(GPIO_ID_PIN(13),!statu[2]);
GPIO_OUTPUT_SET(GPIO_ID_PIN(15),!statu[3]);
实现定时LED状态扫描、DHT11数值读取
下面的是C语言基础,应该比较容易看懂
uint8_t ret=0;
uint8_t curTemperature=0;
uint8_t curHumidity=0;
static uint8_t dhttime=0;
static uint8_t ledtime=0;
dhttime++;
ledtime++;
if(DHT_TIMEOUT
dhttime=0;
ret=dh11Read(&curTemperature,&curHumidity);
if(0==ret)
{
currentDataPoint.valuetemperature=curTemperature;
currentDataPoint.valuehumidity=curHumidity;
}
else
{
os_printf("@@@ dh11Read error! \n");
}
}
if(LED_TIMEOUT
ledtime=0;
currentDataPoint.valueLED_1=statu[0];
currentDataPoint.valueLED_2=statu[1];
currentDataPoint.valueLED_3=statu[2];
currentDataPoint.valueLED_4=statu[3];
}
最后就是数据点的初始化程序userInit()
这个会自动生成,把注释去掉,把值都改为0
currentDataPoint.valueLED_1 = 0;
currentDataPoint.valueLED_2 = 0;
currentDataPoint.valueLED_3 = 0;
currentDataPoint.valueLED_4 = 0;
currentDataPoint.valuetemperature = 0;
currentDataPoint.valuehumidity = 0;
首先填DHT11的头文件
#include “driver/hal_temp_hum.h”
接下来是4个按键的定义
#define GPIO_KEY_NUM 4 ///< Defines the total number of key members
#define KEY_0_IO_MUX PERIPHS_IO_MUX_GPIO0_U ///< ESP8266 GPIO function
#define KEY_0_IO_NUM 0 ///< ESP8266 GPIO number
#define KEY_0_IO_FUNC FUNC_GPIO0 ///< ESP8266 GPIO name
#define KEY_1_IO_MUX PERIPHS_IO_MUX_GPIO2_U ///< ESP8266 GPIO function
#define KEY_1_IO_NUM 2 ///< ESP8266 GPIO number
#define KEY_1_IO_FUNC FUNC_GPIO2 ///< ESP8266 GPIO name
#define KEY_2_IO_MUX PERIPHS_IO_MUX_U0RXD_U ///< ESP8266 GPIO function
#define KEY_2_IO_NUM 3 ///< ESP8266 GPIO number
#define KEY_2_IO_FUNC FUNC_GPIO3 ///< ESP8266 GPIO name
#define KEY_3_IO_MUX PERIPHS_IO_MUX_U0TXD_U ///< ESP8266 GPIO function
#define KEY_3_IO_NUM 1 ///< ESP8266 GPIO number
#define KEY_3_IO_FUNC FUNC_GPIO1 ///< ESP8266 GPIO name
定义按键的功能(长按、短按)
/**
LOCAL void ICACHE_FLASH_ATTR key1ShortPress(void)
{
if(statu[0]=!statu[0])
GIZWITS_LOG("#### KEY1 short press ,LED_1 ON/OFF \n");
}
/**
Key1 key presses a long press
@param none
@return none
*/
LOCAL void ICACHE_FLASH_ATTR key1LongPress(void)
{
GIZWITS_LOG("#### key1 long press, SOFTAP MODE\n");
gizwitsSetMode(WIFI_SOFTAP_MODE);
}
/**
}
/**
Key2 button long press
@param none
@return none
*/
LOCAL void ICACHE_FLASH_ATTR key2LongPress(void)
{
GIZWITS_LOG("#### key2 long press, AIRLINK MODE\n");
gizwitsSetMode(WIFI_AIRLINK_MODE);
}
/**
LOCAL void ICACHE_FLASH_ATTR key3ShortPress(void)
{
if(statu[2]=!statu[2])
GIZWITS_LOG("#### key3 short press, LED_3 ON/OFF \n");
}
/**
}
/**
LOCAL void ICACHE_FLASH_ATTR key4ShortPress(void)
{
if(statu[3]=!statu[3])
GIZWITS_LOG("#### key4 short press, LED_4 ON/OFF \n");
}
/**
}
由于程序太长,且全部代码都给出,就只做一个截图
再就是按键初始化keyInit(void)
LOCAL void ICACHE_FLASH_ATTR keyInit(void)
{
singleKey[0] = keyInitOne(KEY_0_IO_NUM, KEY_0_IO_MUX, KEY_0_IO_FUNC,
key1LongPress, key1ShortPress);
singleKey[1] = keyInitOne(KEY_1_IO_NUM, KEY_1_IO_MUX, KEY_1_IO_FUNC,
key2LongPress, key2ShortPress);
singleKey[2] = keyInitOne(KEY_2_IO_NUM, KEY_2_IO_MUX, KEY_2_IO_FUNC,
key3LongPress, key3ShortPress);
singleKey[3] = keyInitOne(KEY_3_IO_NUM, KEY_3_IO_MUX, KEY_3_IO_FUNC,
key4LongPress, key4ShortPress);
keys.singleKey = singleKey;
keyParaInit(&keys);
PIN_FUNC_SELECT(PERIPHS_IO_MUX_MTMS_U,FUNC_GPIO14);// 配置lED_1引脚输出
GPIO_DIS_OUTPUT(GPIO_ID_PIN(14));
PIN_FUNC_SELECT(PERIPHS_IO_MUX_MTDI_U,FUNC_GPIO12);// 配置LED_2引脚输出
GPIO_DIS_OUTPUT(GPIO_ID_PIN(12));
PIN_FUNC_SELECT(PERIPHS_IO_MUX_MTCK_U,FUNC_GPIO13);// 配置lED_1引脚输出
GPIO_DIS_OUTPUT(GPIO_ID_PIN(13));
PIN_FUNC_SELECT(PERIPHS_IO_MUX_MTDO_U,FUNC_GPIO15);// 配置lED_1引脚输出
GPIO_DIS_OUTPUT(GPIO_ID_PIN(15));
GPIO_OUTPUT_SET(GPIO_ID_PIN(14), 0);//输出高电平 LED_1 OFF
GPIO_OUTPUT_SET(GPIO_ID_PIN(12), 0);//输出高电平 LED_2 OFF
GPIO_OUTPUT_SET(GPIO_ID_PIN(13), 0);//输出高电平 LED_3 OFF
GPIO_OUTPUT_SET(GPIO_ID_PIN(15), 0);//输出高电平 LED_4 OFF
}
完整的程序都给出,所以不做截图了
最后在user_init(void)里添加DHT11初始化程序
dh11Init( );
接下来的操作就不用说了吧!如果不会请看我的第一篇稿子,第一次总是潦草的,见谅。地址:esp8266 NodeMcu机智云SOC方案开发经验分享
大功告成!并没有完,哈哈。
那个DHT11的坑没有讲,现在补充下
右击dh11Init( );选择下图红框
发现了没有,当你要定义其他引脚作为DHT11的数据接口时,改头文件是不够的,红框里也要改
需要代码的话可以回复我
That’all .thans for your reading.