3.2.1实验内容
本实验为数字输入模块教学部分,以最基础的开关控制小灯泡实验为例。数字输入,即输入为数字信号。开关控制小灯泡实验中,开关有两种状态,“开”和“关”,分别对应输入“1”和“0”。之后用不同的输入控制LED的亮灭状态。
不同于现实生活中的开关与小灯泡或其他设备直接连接,用开关的通断来决定电路是否连接,这里的开关控制是用信号的输入输出来实现。简单的检测电压的高低,即检测数字信号,这里引入两个新的数字输入输出函数,digitalWrite()和digitalRead()。从英文的意思上也可以猜出来,digitalWrite函数为写入数字信号,digitalRead为读取数字信号,该函数的功能是检测引脚的状态,函数只需要一个参数,即所要检测的引脚,函数的返回值是引脚的两种状态(HIGH/LOW)。则代码的编写思路主要是,从开关模块读取数字信号(HIGH/LOW),之后将这个信号传入到继电器模块从而达到控制继电器开关状态的现象。
思路看似清晰简单,实践起来却有很多需要注意的细节。比如说开关的防抖动问题,默认的继电器初始时开关状态的问题等等。下面便用具体的代码来说明实现本实验的方法。
3.2.2实验器材介绍
实验所用开关为单刀单掷开关,为数字输入模块,一个管脚接5v电源以及数据输出,另一个管脚接地。 引进继电器模块,观察模块上的指示灯模拟小灯泡的实验现象。继电器模块有三个管脚,分别为IN、GND、VCC。IN接数据线,连接代码中设置的GPIO口,VCC接5v电源,GND接地。引入继电器模块目的在于让学习者对此模块的接线方法及模块产生的实验效果有个初步的了解。
3.2.3实验步骤
- 单刀单掷开关以及继电器的连线方式,如图所示:
- 打开Arduino IDE,新建项目,编写代码(以下为参考代码,实际可以实现本实验现象的方式有很多);
- 编译并上传到PcDuino开发板中,观察实验现象。
3.2.4代码及相关说明
代码一版:
/*
* Button test program
*/
#include <core.h>
int buttonPin = 2;
int ledPin = 0;
void setup(){
printf("Button Test Code!\n");
printf("Using I/O_0=Drive LED and I/O_2=Button input.\n");
pinMode(ledPin, OUTPUT); // 初始化ledPin为输出模式
pinMode(buttonPin, INPUT); // 初始化buttonPin为输入模式
}
void loop() {
int buttonIn = digitalRead(buttonPin);
// 定义int类型的buttonIn,来存储从开关传入的数据
digitalWrite(ledPin, buttonIn);
// 用传入的数据控制ledPin的状态
delay(50);
}
这一版的代码中,初始化部分设置ledPin和buttonPin的初始模式,循环模块将从button读取的数字信号直接传送到led模块。
实验现象为继电器上的灯的初始状态为亮,拨动单刀单掷开关则灯灭,不拨动则亮。可以说是实现了一个简单的开-灭,关-亮的对应。而且稳定性较差。2脚处于输入状态时,对外界环境非常敏感。当按键抬起时,2脚是处于悬空状态的,也就是说,它的状态是不确定的,很容易感应到其周围的电场而发生变化。所以,如果设备允许,最好加一个上拉电阻,也就是接一个1-10k的电阻到电源VCC。使其在按键松开后保证处于高电平的状态。也可以通过程序来实现上拉电阻的功能。即将pinMode(buttonPin,INPUT); 修改为pinMode(2,INPUT_PULLUP)。
对于防抖动问题,这个代码中也没有涉及。防抖动的思想为:如检测到按键状态发生改变时,再过10mS,再确认状态。
除增加以上两个修改以外,拓展单纯的开关两种状态对应灯泡的亮灭为按动完整的一次,灯的状态变化一次。
改动后的代码:
/*
* Button test program
*/
#include <core.h>
int buttonPin = 2;
int ledPin = 0;
void setup () {
printf("Button Test Code!\n");
printf("Using I/O_0=Drive LED and I/O_2=Button input.\n");
pinMode(ledPin, OUTPUT); // 初始化ledPin为输出模式
pinMode(buttonPin, INPUT); // 初始化buttonPin为输入模式 }
void loop () {
if (digitalRead(buttonPin)==HIGH && digitalRead(ledPin) == LOW)
//同时检测开关是否按下和led是否点亮(LOW为未点亮)
{ digitalWrite(ledPin,HIGH); //点亮led
while (digitalRead(buttonPin)==HIGH){
//消抖,检测按钮是否一直按下,如是测无限延迟,如不加此行代码按下按钮则会不停开关,
松开时led状态不可控
delay(1);
}
}
else if (digitalRead(buttonPin)==HIGH&&digitalRead(13)==HIGH){
//同时检测开关是否按下和led是否点亮(high为点亮)
digitalWrite(ledPin,LOW); //关灯
while (digitalRead(buttonPin)==HIGH){
delay(1); }
}
}
3.2.5 实验结果
第一版代码实验结果:
继电器上的灯的初始状态为亮,拨动开关到另一个状态时,灯熄灭。
更改后的实验结果:
图片表达的不是很清楚,实际效果为波动一次开关,灯变一次状态。