问题:ESP8266的GPIO16身份特殊,如何检测输入呢?
开始:
1)头文件 #include "driver/gpio16.h"
2)ESP8266的GPIO16属于RTC模块,不能触发中断,与其他GPIO的配置方式不同,配置函数如下
void gpio16_output_conf(void); //初始化为输出模式
void gpio16_output_set(uint8 value); //输出指定电平
void gpio16InputConf(void); //配置为输入模式
uint8 gpio16InputGet(void); //获取管脚输入
3)因为不能中断,无法监控其状态,通过循环或定时器回调检查
//检查输入的回调
Pin16_NewState=SWITCH_Pin16_State;//gpio16_input_get()读取输入的电平状态!!
if(Pin16_NewState==0x0)
{//按下时是0,不按是1
Pin16_OldState=!Pin16_OldState;//取反(全局变量!!)
GPIO_OUTPUT_SET(GPIO_ID_PIN(RELAY_PIN1), Pin16_OldState);//继电器1
if(Pin16_OldState==1)
{
//状态发布
}else{
//状态发布
}
if(Pin16_NewState==Pin16_OldState)
{
os_delay_us(500);//解决防抖(debounce)
}
}
//================================================================
//在user_init()里初始化
void ICACHE_FLASH_ATTR
GPIO16_Timer_init(){
os_timer_disarm(&timer);
os_timer_setfn(&timer,(os_timer_func_t *)gpio16_timer_cb,NULL); //set callback func
os_timer_arm(&timer,500,1); //set timer interval 1000ms
}
扩展知识:正常的中断如何调用?干货!
static void GPIO_INTR_Handler(void* arg){
//读取GPIO中断状态;寄存器,获取中断信息
u32 GPIOStatus = GPIO_REG_READ(GPIO_STATUS_ADDRESS);
//全局关闭GPIO中断
ETS_GPIO_INTR_DISABLE();
//清除中断状态信息
GPIO_REG_WRITE( GPIO_STATUS_W1TC_ADDRESS, GPIOStatus);//clear interrupt status
if ( GPIOStatus & BIT(14)){ //中断源来自
RelayStatus = !RelayStatus;//状态取反
GPIO_OUTPUT_SET(GPIO_ID_PIN(13), RelayStatus);//开或关(高电平触发)
//按键同步状态到客户端
if(RelayStatus)
{
//状态发布
}else{
//状态发布
}
}
os_delay_us(50);//防抖 debounce
//开启GPIO中断
ETS_GPIO_INTR_ENABLE();
}
//初始化中断
void ICACHE_FLASH_ATTR
Touch_INTR_init(){
ETS_GPIO_INTR_DISABLE(); //全局关闭GPIO中断
ETS_GPIO_INTR_ATTACH(&GPIO_INTR_Handler, NULL ); //设置中断函数
gpio_pin_intr_state_set(GPIO_ID_PIN(TOUCH_PIN1),1); //上升沿触发中断 按键14,gpio.h;;;DISABLE\POSEDGE\NEGEDGE\LOLEVEL\HILEVEL
GPIO_REG_WRITE( GPIO_STATUS_W1TC_ADDRESS, BIT(TOUCH_PIN1)); //remove the GPIO interrupt mark of this pin
ETS_GPIO_INTR_ENABLE(); //启用中断
}