11
10

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

シリアル通信でデジタル出力

Last updated at Posted at 2020-10-02

はじめに

ここでは、Arduino UNOでシリアル通信とデジタル出力を組み合わせた実験をします。

目次へ戻るには ここ をクリック

※本ページは実験のテキストです。

デジタル出力とシリアル通信

Lチカ(デジタル出力)の解説 では、デジタル出力の機能を説明しました。
Arduinoの特定のピンを5VにしたりGNDにしたりすることで、LEDを点灯/消灯できました。

シリアル通信をしてみよう(Serial) では、パソコンとマイコンとの間をシリアル通信でデータ送受信しました。

今回は、両者を組み合わせてみます。
シリアル通信でキーを入力し、キーに応じてLEDを点灯/消灯する、というプログラムを作成します。

具体的には、

  • シリアル通信で q を送信したらLEDを点灯
  • シリアル通信で a を送信したらLEDを消灯

の様に動作させます。
具体的には、以下のようなイメージです。
serial_led.png

スケッチを書き込む

それでは、プログラミングしてみます。
メニューバーから[ファイル]-[新規ファイル]をクリックし、新しいプログラムを書く準備をしてください。

以下のプログラムを打ち込み、コンパイル/実行してみましょう。
ファイル名は Serial_led.ino としました。

Serial_led.ino
void setup() {
  // LED_BUILTINのデジタルピンを出力モードに設定
  pinMode(LED_BUILTIN, OUTPUT);

  Serial.begin( 9600 );     // シリアル通信を初期化する。通信速度は9600bps

  Serial.println( "Hello Arduino!" );   // 最初に1回だけメッセージを表示する
}

void loop() {
  char key;     // 受信データを格納するchar型の変数

  // 受信データがあった時だけ、処理を行う
  if ( Serial.available() ) {       // 受信データがあるか?
    key = Serial.read();            // 1文字だけ読み込む
    Serial.write( key );            // 1文字送信。受信データをそのまま送り返す。

    // keyの文字に応じて、行う処理を切り替える
    switch( key ) {
      // qキーが押された時の処理
      case 'q':
        digitalWrite(LED_BUILTIN, HIGH);   // LED点灯(HIGHは電圧を5Vにする)
        break;

      // aキーが押された時の処理
      case 'a':
        digitalWrite(LED_BUILTIN, LOW);    // LED消灯(LOWは電圧を0Vにする)
        break;

      // 上記以外の場合の処理(何もしない)
      default:
        break;
    } //switch文の末尾

  } // if文の末尾

} // loop関数の末尾

動作テスト

Arduinoに書き込み終わったら、シリアルモニタを開いて文字を送信し、動作を確認しましょう。
serial_led.png

きちんと図のように動いていますか?

このプログラムで 「パソコンからの指令でArduinoマイコンを操作した」 ことになります。
この手法を応用すれば、

・キーボード入力でモータを回す/停止させる
・複数のモータを1つのキーで同時に操作する
・キーボードをゲームコントローラの十字キーの様に使うことで、前後移動や旋回をさせる

といった使い方もできるので、ロボットの遠隔操作なども可能になります。

プログラム解説

以降は,スケッチの内容を解説していきます。

setup関数

電源投入またはリセット後に一度だけ実行されるのがsetup関数でした。
いわゆる「初期化」の作業です。

setup関数
void setup() {
  // LED_BUILTINのデジタルピンを出力モードに設定
  pinMode(LED_BUILTIN, OUTPUT);

  Serial.begin( 9600 );     // シリアル通信を初期化する。通信速度は9600bps

  Serial.println( "Hello Arduino!" );   // 最初に1回だけメッセージを表示する
}

setup関数では、大別して2つの作業をしています。

  • デジタル出力の初期化:pinMode()
  • シリアル通信の初期化:Serial.begin()

両者を連携させるので、それぞれきちんと初期化しておく必要がありますね。

Serial.printで "Hello Arduino!" を出力しているのは、
プログラムがきちんと動作していることを確認するためのメッセージです。

パソコンも、電源投入直後にはメーカーのロゴマークなどが表示されますが、
あれと同様に「ちゃんと動いてるよ~」というアピールです。

loop関数

何度も繰り返して呼び出されるのがloop関数です。

loop関数(1)
void loop() {
  char key;     // 受信データを格納するchar型の変数

  // 受信データがあった時だけ、処理を行う
  if ( Serial.available() ) {       // 受信データがあるか?
    key = Serial.read();            // 1文字だけ読み込む
    Serial.write( key );            // 1文字送信。受信データをそのまま送り返す。

loop関数の冒頭では、シリアル通信をしてみよう(Serial) と同じ記述をしています。

  • パソコンからデータが来たかどうかを、Serial.available関数でチェック
  • データがあったら、Serial.read関数で取り出す
  • パソコン側に何も表示されないのは寂しいので、Serial.write関数で送り返す

ブロッキング関数であるSerial.readをいきなり呼び出すのではなく、
まずはSerial.availableで様子見/偵察するのが重要な作法です。

loop関数(2)
    // keyの文字に応じて、行う処理を切り替える
    switch( key ) {
      // qキーが押された時の処理
      case 'q':
        digitalWrite(LED_BUILTIN, HIGH);   // LED点灯(HIGHは電圧を5Vにする)
        break;

      // aキーが押された時の処理
      case 'a':
        digitalWrite(LED_BUILTIN, LOW);    // LED消灯(LOWは電圧を0Vにする)
        break;

      // 上記以外の場合の処理(何もしない)
      default:
        break;
    } //switch文の末尾

  } // if文の末尾

} // loop関数の末尾

次は、switch文でkeyの中身に応じて処理を選択しています。
'q'のときには、digitalWrite関数でHIGHを出力することで、LEDが点灯します。
'a'のときには、digitalWrite関数でLOWを出力することで、LEDが消灯します。
'q''a'以外が入っているときは、default:に流れていきますが、特に何もすることなく無反応になります。
switch文は、defaultをきちんと書くのがマナーです。
「デフォルトの処理」、すなわち特別なケースに当てはまらなかった「失敗時の処理」という意味が本質です。
しかし日本では、特別ではない時=通常時 という意味合いで浸透したのが、ネットスラングの「デフォ」です。
switch文的には「デフォルトで何をさせる?」「デフォで何をする?」という使い方だったのが、
「~するのがデフォ」のような「定番」という意味にまで派生しています。

 参考:「デフォ」は若者言葉?死語?

key変数と比較したいキーボードの文字は,'q' 'a'の様にシングルクォーテーション'で囲みます。
q aと何も付けずに書くと、コンパイラは変数q・変数aがいると勘違いしてしまいます。
'q'と書けば「ああ、ASCIIコードでのq、すなわち16進数の0x71ね」と解釈してくれます。

 参考:ASCIIコード表

つまり、

if( key == 'q' )

こう書くことは、

if( key == 0x71 )

これと同じ意味になります。
'a'に関しても同様に,実際の値は16進数で0x61です。

まとめ

  • key にはキーボードの文字が入っている
  • switch( key ) と書けば、文字に応じて違う処理をさせることができる

おわりに

これでシリアル通信によってLEDを操作することができました。

次はブレッドボードの使い方を解説します。

目次 へ戻って次の作業を行ってください。

11
10
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
11
10

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?