GPIO6 ~ 11一般不推荐使用,因为这几个口接了存储程序用的Flash,不当使用可能引起程序崩溃)
闪烁灯
#include int pin_num = 15;
//输出的引脚为15
void setup()
{
pinMode(pin_num,OUTPUT);
//设置引脚模式为输出模式
}void loop()
{
digitalWrite(pin_num, HIGH);
//数字输出为高电平
delay(10);
//延时10ms
digitalWrite(pin_num, LOW);
//数字输出为低电平
delay(10);
}
串口输出
#include void setup()
{
Serial.begin(115200);
//设置的波特率
}void loop()
{
Serial.println("hello esp32");
}
按键检测
#include int pin_num = 35;
//按键的引脚号
void setup()
{
pinMode(pin_num, INPUT);
//按键设置为输入模式
Serial.begin(115200);
//波特率设置
}void loop()
{
if (digitalRead(pin_num) == LOW)//读取按键的状态,如果是低则串口发送
{
Serial.println("You push the botton!");
}}
PS:汉堡推荐了一个按键库button2(需要自己手动安装)
基于button2的按键检测
#include
#include "Button2.h"int pin_num = 35;
//按键的引脚号
Button2 button = Button2(pin_num);
void handler(Button2 &btn);
void setup()
{
//pinMode(pin_num, INPUT);
//按键设置为输入模式
Serial.begin(115200);
//波特率设置
button.setClickHandler(handler);
//设置四种按法的回调函数
button.setLongClickHandler(handler);
button.setDoubleClickHandler(handler);
button.setTripleClickHandler(handler);
}void loop()
{
button.loop();
//button的loop,参照官方例程}
void handler(Button2& btn) {//回调函数,官方例程写法,代码很通俗不过多注释了
switch (btn.getClickType()) {
case SINGLE_CLICK://判断按键方式,在里面编辑自己的命令
Serial.print("single ");
//串口发送
break;
case DOUBLE_CLICK:
Serial.print("double ");
break;
case TRIPLE_CLICK:
Serial.print("triple ");
break;
case LONG_CLICK:
Serial.print("long");
break;
}
Serial.print("click");
Serial.print(" (");
Serial.print(btn.getNumberOfClicks());
Serial.println(")");
}
pwm波输出
#include int channel_PWM = 3;
// 舵机频率,那么周期也就是1/50,也就是20ms ,PWM一共有16个通道,0-7位高速通道由80Mhz时钟驱动,后面8个为低速通道由1Mhz时钟驱动
int freq_PWM = 1000;
// PWM分辨率,取值为 0-20 之间,这里填写为10,那么后面的ledcWrite 这个里面填写的pwm值就在 0 - 2的10次方 之间 也就是 0-1024 ,如果是要求不高的东西你可以直接拿1000去算了
int resolution_PWM = 8;
// 绑定的IO,在下面的绑定函数里面会用到,绑定之后这个IO就会变成我们PWM的输出口
const int PWM_Pin = 15;
//指定pwm绑定到这个io上输出void setup()
{
Serial.begin(115200);
ledcSetup(channel_PWM, freq_PWM, resolution_PWM);
// 设置舵机通道
ledcAttachPin(PWM_Pin, channel_PWM);
//将 LEDC 通道绑定到指定 IO 口上以实现输出
}void get_pwm_info()
{
Serial.println("*******************************************************************");
Serial.print("读取指定通道占空比的值为:");
Serial.println(ledcRead(channel_PWM));
//读取指定通道占空比的值
Serial.print("读取指定通道频率的值为:");
Serial.println(ledcReadFreq(channel_PWM));
//返回指定通道当前频率(如果当前占空比为0 则该方法返回0)
}void loop()
{
ledcWrite(channel_PWM, 100);
//20ms高电平为1ms左右 ,也就是1/20*1024,此时360度舵机正传最快
get_pwm_info();
//打印信息,点击IDE右上角的串口查看器就可以看到打印的内容了
delay(500);
//ledcDetachPin(PWM_Pin);
//这个是解除IO口的pwm输出功能模式
}
【esp8266|arduino ESP32各外设例程 esp32外设代码查询】外部中断
#include int pin_num = 25;
//按键的引脚号
int interruptCounter = 0;
portMUX_TYPE mux = portMUX_INITIALIZER_UNLOCKED;
//声明一个portMUX_TYPE类型的变量,利用其对主代码和中断之间的同步进行处理void handleInterrupt()
{
portENTER_CRITICAL_ISR(&mux);
//个人理解这个包括下一句是保证中断不被打断,有点原子操作的意思
delay(20);
//延时20ms作为消抖,如果是很稳定的中断可以不加或者加很少的消抖时间
if (digitalRead(pin_num) == 0) //因为是下拉触发,所以在消抖时间完后读取引脚高低电平,如果还是为低那么就代表出现了一次稳定的中断
{
interruptCounter++;
Serial.println("interrupt!");
Serial.print("interrupt times:");
Serial.println(interruptCounter);
}
portEXIT_CRITICAL_ISR(&mux);
}void setup()
{
//pinMode(pin_num, INPUT);
//按键设置为输入模式
Serial.begin(115200);
//波特率设置
pinMode(pin_num, INPUT_PULLUP);
attachInterrupt(digitalPinToInterrupt(pin_num), handleInterrupt, FALLING);
/*接下来,我们通过调用attachInterrupt函数将中断附加到引脚。作为首个参数,
我们将调用结果传递给digitalPinToInterrupt函数,该函数将使用的引脚编号转换为相应的内部中断编号。
接下来,我们传递中断处理函数,换而言之,当指定引脚上出现中断时,该函数将予以执行。
我们将其称为handleInterruptand,稍后再指定其代码。
falling是下拉触发*/
}
void loop()
{
}
定时器中断
#include
//对于TTGO来说主频测试为80mhz
hw_timer_t * timer = NULL;
portMUX_TYPE timerMux = portMUX_INITIALIZER_UNLOCKED;
void IRAM_ATTR onTimer() {
portENTER_CRITICAL_ISR(&timerMux);
Serial.println("interrupt");
portEXIT_CRITICAL_ISR(&timerMux);
}
void setup() {
Serial.begin(115200);
timer = timerBegin(0, 80, true);
//0为定时器编号(0到3,对应全部4个硬件定时器),80为分频的数量,esp32主频80Mhz
timerAttachInterrupt(timer, &onTimer, true);
//该函数的第一个参数是定时器指针,第二个参数是触发中断的计数器值,第三个参数是一个表示定时器在产生中断时是否重新加载的标志。
timerAlarmWrite(timer, 1000, true);
/*定时器全局变量作为第一个输入参数,第三个参数设置为真(表示计数器将自动重新加载),这样就能周期性地产生中断。
关于第二个参数,不要忘了我们之前对预分频器的设置,中断应在数微秒后产生。
因此,对本例而言,假如我们想要每秒产生一个中断,那么该值就是1 000 000微秒(等于1秒)。*/
timerAlarmEnable(timer);
//使能定时器
}
void loop() {}
ADC
ADC2通道在ESP32开启WIFI后,功能会受到限制!!
#include #define ANALOG_PIN_0 36 //adc引脚
//esp32的adc是12位的分辨率4096,可以设置位数,参考esp32-hal-adc.h文件
void setup()
{
Serial.begin(115200);
pinMode(ANALOG_PIN_0, INPUT);
//设置为输入模式
}void loop()
{
int analog_value = https://www.it610.com/article/0;
analog_value = analogRead(ANALOG_PIN_0);
//读取adc的值
delay(1000);
Serial.printf("Current Reading on Pin(%d)=%d\n", ANALOG_PIN_0, analog_value);
}
DAC
//DAC输出电压由VDD3P3_RTC引脚输入电压和value决定,使用常用的模块时VDD3P3_RTC上电压为3.3V;
//DAC_OUT = VDD3P3_RTC * value / 256 ;
#include //DAC引脚只能是25 26个引脚
#define LED1 25void setup()
{
//DAC的IO口也可以不进行初始化
pinMode(LED1, OUTPUT);
}void loop()
{
dacWrite(LED1, 100);
//第一个参数为引脚号,第二个参数为输出的adc值,范围0-255,对应电压值参照前注释
}
推荐阅读
- C语言学习|第十一届蓝桥杯省赛 大学B组 C/C++ 第一场
- 【C】题目|【C语言】题集 of ⑥
- 单片机|单片机初学者做项目为什么这么难(单片机初学者心得有哪些)
- 单片机|自学单片机好找工作吗(会单片机能找什么工作?)
- 单片机|keil把源代码生成lib的方法
- c语言|一文搞懂栈(stack)、堆(heap)、单片机裸机内存管理malloc
- 单片机|Arduino、arm、树莓派、单片机四者有什么不同()
- c语言|C语言初期学习遇到的特殊点 【三子棋详解】【初学者福音,详细总结,复习能手】
- 笔记|C语言数据结构——二叉树的顺序存储和二叉树的遍历
- 个人理解|【C语言基础之类型转换】