- 机器人等级考试
ESP32 for Arduino 学习笔记(外部中断 + 数码管显示)
- 2025-7-12 22:16:12 @
ESP32 for Arduino 学习笔记(外部中断 + 数码管显示)
一、外部中断
(一)基础知识
控制系统工作流程是感受变化→分析判断→做出反应 。感受变化就是读传感器数值,分析判断依据数值和程序处理,做出反应是把结果给执行器。为随时响应传感器变化,程序不断重复这一过程叫轮询 ,但轮询有缺点,比如按钮按下时主程序在忙其他事,可能就检测不到,用外部中断能解决。
外部中断由外部设备(像按钮)发起请求。每个中断对应一个中断程序(也叫中断回调函数 ),中断触发时,控制器暂停主程序,去运行中断程序,运行完再回到主程序暂停处接着执行,这样就能实时响应事件啦。
还有 5 种触发模式: |序号|触发模式|说明| | ---- | ---- | ---- | |1|RISING|低电平变高电平时触发| |2|FALLING|高电平变低电平时触发| |3|CHANGE|电平变化(高变低或低变高)时触发| |4|ONLOW|当前是低电平就触发| |5|ONHIGH|当前是高电平就触发|
(二)代码示例(按钮外部中断)
// 定义按钮引脚和LED引脚
const int keyPin = 2;
const int ledPin = 4;
int num = 0;
// 中断回调函数,按钮触发中断时执行
void numadd() {
num++; // 变量num加1
Serial.println(num); // 串口打印num的值,方便我们看变化
}
void setup() {
pinMode(keyPin, INPUT); // 设置keyPin为输入模式,接收按钮信号
pinMode(ledPin, OUTPUT); // 设置ledPin为输出模式,控制LED
Serial.begin(9600); // 打开串口,波特率9600,用来打印信息
// 配置外部中断,keyPin引脚触发,触发模式是RISING(上升沿),触发时执行numadd函数
attachInterrupt(keyPin, numadd, RISING);
}
void loop() {
digitalWrite(ledPin, HIGH); // 点亮LED
delay(3000); // 亮3秒
digitalWrite(ledPin, LOW); // 熄灭LED
delay(3000); // 灭3秒
}
代码解释 :
const int keyPin = 2;
const int ledPin = 4;
:定义按钮接在引脚 2,LED 接在引脚 4 。void numadd() { ... }
:中断触发时执行的函数,让num
增加并串口打印。setup
里:pinMode
配置引脚模式,Serial.begin
打开串口,attachInterrupt
配置中断,指定引脚、回调函数和触发模式 。loop
里:让 LED 亮灭循环,中断触发时会暂停这个循环去执行numadd
,执行完再回来继续循环。
二、数码管显示
(一)基础知识
数码管就像多个 LED 组成的,一般 7 个 LED 排成“8”字,再加 1 个当小数点。控制特定 LED 亮就能显示数字。数码管分共阳(公共引脚是阳极)和共阴(公共引脚是阴极) 。比如共阴数码管,“1”表示对应 LED 亮,“0”表示熄灭,不同数字对应不同 LED 亮灭组合(看下面表格,以共阴为例) : |显示内容|a|b|c|d|e|f|g|dp| | ---- | ---- | ---- | ---- | ---- | ---- | ---- | ---- | ---- | |0|1|1|1|1|1|1|0|0| |1|0|1|1|0|0|0|0|0| |2|1|1|0|1|1|0|1|0| |3|1|1|1|1|0|0|1|0| |4|0|1|1|0|0|1|1|0| |5|1|0|1|1|0|1|1|0| |6|1|0|1|1|1|1|1|0| |7|1|1|1|0|0|0|0|0| |8|1|1|1|1|1|1|1|0| |9|1|1|1|1|0|1|1|0| |.|0|0|0|0|0|0|0|1|
要是用的是共阳数码管,代码里控制 LED 亮灭得取反(在 digitalWrite
第二个参数前加 !
),因为共阳是公共引脚接高电平,要让某个段灭,就得给低电平 。
(二)代码示例(数码管显示数字)
假设数码管引脚和编程引脚对应如下(共阳数码管示例 ,如果是共阴,去掉 !
就行 ):
|数码管引脚|a|b|c|d|e|f|g|dp|
| ---- | ---- | ---- | ---- | ---- | ---- | ---- | ---- | ---- |
|编程引脚|13|14|15|16|17|25|26|27|
// 定义数码管各段对应的引脚
const int aPin = 13;
const int bPin = 14;
const int cPin = 15;
const int dPin = 16;
const int ePin = 17;
const int fPin = 25;
const int gPin = 26;
const int dpPin = 27;
// 显示数字0的函数(共阳数码管,所以用!取反)
void disNum0() {
digitalWrite(aPin, !1); // 控制a段,!1是0,共阳时给0熄灭?不,共阳是公共端接VCC,要让段亮,得给低电平。这里可能得结合实际电路理解,简单说就是按共阳逻辑控制亮灭
digitalWrite(bPin, !1);
digitalWrite(cPin, !1);
digitalWrite(dPin, !1);
digitalWrite(ePin, !1);
digitalWrite(fPin, !1);
digitalWrite(gPin, !0);
digitalWrite(dpPin, !0);
}
void setup() {
// 把所有数码管引脚设置为输出模式
pinMode(aPin, OUTPUT);
pinMode(bPin, OUTPUT);
pinMode(cPin, OUTPUT);
pinMode(dPin, OUTPUT);
pinMode(ePin, OUTPUT);
pinMode(fPin, OUTPUT);
pinMode(gPin, OUTPUT);
pinMode(dpPin, OUTPUT);
}
void loop() {
disNum0(); // 调用显示数字0的函数
// 这里可以接着写显示其他数字的函数调用,比如disNum1()等,做数字切换显示
}
代码解释 :
- 先定义数码管各段对应的 ESP32 引脚 。
disNum0
函数里,用digitalWrite
结合!
(因为是共阳)控制各段亮灭,按照共阴数码管显示 0 的逻辑取反,让共阳数码管显示 0 。setup
里把所有数码管引脚设为输出模式,好控制电平 。loop
里调用disNum0
显示数字 0 ,也能扩展显示其他数字,让数码管变化起来 。
这样,通过外部中断能及时响应按钮等外部信号,数码管能显示数字,把这些知识结合起来,就能做更有趣的小项目啦,比如按钮按下计数,数码管显示计数值 ,慢慢玩起来吧!