反应力游戏:计时器
本课属于 Coddy Arduino 学习旅程的“项目”单元。第 6 课,共 24 课。
现在,游戏会测量你的反应时间。反应时间是从 LED 点亮到你按下按钮所经过的时间,因此草图需要记住一个时刻:LED 点亮的时刻。
digitalWrite(ledPin, HIGH);
litAt = millis();
state = LIT;在 LIT 状态下检测到按键时,两者的时间差就是答案:
unsigned long reaction = millis() - litAt;
Serial.print("Reaction: ");
Serial.print(reaction);
Serial.println(" ms");这只有在草图从不使用 delay() 停下来时才有效:loop() 每毫秒检查按钮数千次,因此按键发生后不到 1 毫秒就会被检测到。大多数人需要 200 到 300 ms。
挑战
中等记录玩家的反应时间:
- LED 亮起时,将
millis()保存到litAt中 - 在
LIT状态下按下按钮时,计算millis() - litAt - 将结果打印为
Reaction: 250 ms
点击运行,进行游戏,查看 Serial 监视器,然后点击检查。
亲手试试
const int ledPin = 12;
const int buttonPin = 2;
// 一轮中的三种状态
enum State { READY, WAITING, LIT };
State state = READY;
int lastButton = HIGH; // 上一次读取到的按钮状态
unsigned long waitStart = 0; // 等待开始的时间
unsigned long waitTime = 0; // 这次等待的时长
void setup() {
pinMode(ledPin, OUTPUT);
pinMode(buttonPin, INPUT_PULLUP);
Serial.begin(9600);
Serial.println("Press the button to start");
}
void loop() {
int button = digitalRead(buttonPin);
bool pressed = (button == LOW && lastButton == HIGH); // 刚刚按下
lastButton = button;
unsigned long now = millis();
switch (state) {
case READY:
if (pressed) {
randomSeed(micros()); // 每次按下按钮的时间都不同
waitTime = random(1000, 3001);
waitStart = now;
state = WAITING;
}
break;
case WAITING:
if (now - waitStart >= waitTime) {
digitalWrite(ledPin, HIGH);
state = LIT;
}
break;
case LIT:
if (pressed) {
digitalWrite(ledPin, LOW);
state = READY;
}
break;
}
}
这节课包含一个小测验。开始学习即可作答,并记录你的进度。
项目中的所有课
自己练习: Arduino 在线编辑器