0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

71歳の... ちょっと待って、時間(loop)よ止まれ!イベントドリブンにしたいんだ。

Last updated at Posted at 2025-06-12

 Arduinoスケッチで必須の「 loop() 」って、目的によっては使いづらいと感じたことないですか? VisualBasicでプログラミングを始めた私は、最初結構戸惑いました。マイコンでもイベントドリブン的な作りをずっと考えてましたが、今回それらしくなってきたので投稿します。(すでにWEBからの操作ではそれが実質上出来てました。)

tone_led.jpg
(余計なものを一杯くっつけたままの写真で醜くて申し訳ありません。外すの面倒で...)
 カギは以前の投稿でも載せていることで、loop()内に

while (Serial.available() == 0) { ; } 
// 見かけ上、シリアルからの入力があるまで停止
// 入力があったら、文字列を「line」で受け取る
String line = Serial.readString();

を挿入することです。そして、受け取った「line」を分割しコマンドを取り出します。あとはそれに応じた動作を定義しておけば良いわけです。文字列分割には次のサイト記事を参考にさせていただきました。有難うございます。

例1.ある周波数の音を2秒間鳴らす -> "tone 440 4"
例2.LEDを指定した明るさで1秒間光らせる -> "led 50 5"

 回路としては、使用するPin4からの出力を、圧電ブザーやLEDと、必要な抵抗を接続してGNDに落とします。

ArduinoIDE2.3.6でのスケッチです。普通のESP32で動作するはずです。


const int PWM_PIN = 4;

void setup() {
  Serial.begin(115200);
  Serial.println("\n\rSerial Console start...");

  ledcAttach(PWM_PIN, 24000, 8);
}

void loop() {
  Serial.println(">");
  while (Serial.available() == 0) { ; }
  String line = Serial.readString();
  line.trim();
  if (line.length() > 5 && line.substring(0, 4) == "tone") {
    int n = 2;  // "tone freq duration"
    String zs[n];
    int zi[n];
    bool flag = true;
    if (split(line.substring(5), ' ', zs, n) != n) flag = false;
    for (int i = 0; i < n; i++) {
      if (!(zi[i] = zs[i].toInt())) {
        flag = false;
        break;
      }
    }
    if (flag) {
      ledcWriteTone(PWM_PIN, zi[0]);  // freq
      delay(zi[1] * 500);             // duration
      ledcWriteTone(PWM_PIN, 0);
    }
  } else if (line.length() > 4 && line.substring(0, 3) == "led") {
    int n = 2;  // "led brightness duration"
    String zs[n];
    int zi[n];
    bool flag = true;
    if (split(line.substring(4), ' ', zs, n) != n) flag = false;
    for (int i = 0; i < n; i++) {
      if (!(zi[i] = zs[i].toInt())) {
        flag = false;
        break;
      }
    }
    if (flag) {
      analogWrite(PWM_PIN, zi[0]);
      delay(zi[1] * 200);
      analogWrite(PWM_PIN, 0);
    }
  } else {
    Serial.println("?");
  }
}

int split(String data, char delimiter, String* dst, int num) {
  int index = 0;
  int len = data.length();
  for (int i = 0; i < len; i++) {
    char tmp = data.charAt(i);
    if (tmp == delimiter) {
      index++;
      if (index > num - 1) return -1;
    } else {
      dst[index] += tmp;
    }
  }
  return index + 1;
}

 最後までご覧いただきありがとうございました。

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?