【Arduino】手品の演技に合わせて光ってくれる衣装を作った【LED】

# はじめに

趣味で手品を嗜んでいる者です。
2020年のとある舞台にて、どうしても光る衣装を使って手品がしたい！となり、独学で情報をかき集め、無理矢理作りました。
手品の演技に合わせて、LEDの光をプログラムで制御します。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/620431/9f42be28-a9b8-64a6-9321-ee5815bfa18d.png)

私自身、オームの法則くらいしか知らないレベルの電飾ド素人であり、[led 光る 衣装 作り方]と検索しても、欲しい情報が全然ヒットしなかったこともあり、**かなり我流になっております。**

# 使用したもの

- Arduino uno
- [NeoPixel RGB/W テープLED](https://www.akiba-led.jp/product/1615)
- モバイルバッテリー(DC5V、2ポート)

# 作り方

## STEP1：衣装にLEDテープを縫い付ける

(手書きで分かりにくくすみません…)
![回路図.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/620431/d9aa8a2a-fecf-aca0-d75d-3c8b0221c8f8.jpeg)

モバイルバッテリーはDC5Vであることと、２ポートあるものが望ましいです。
２ポートのうち片方はArduinoへ、もう片方は衣装（LEDテープ）へ電流を流すためです。

LEDテープ向けのポートは途中で回路を分岐させ、上半身と下半身で並列に接続しています。

ここでの教訓としては、マジシャンがやたらと動くのに合わせてLEDテープのハンダや金属部分が割れてしまい、断線することがよくあったので、なるべくLEDテープが曲がらないように、LEDテープと同じサイズのプラスチック板を衣装に貼り付けてからその上にLEDテープを貼り付けるようにしています。

上記の通り、**衣装にLEDテープを貼り付ける際に最も意識するべき点は「断線させない」ことです。**

余談ですが、衣装の近くで半田付けを行っているとたまに半田が衣装に飛んでいってしまい、焦げて穴が開いた時はかなり凹みました。

## STEP2：プログラムを作成する

ArduinoでLEDテープを制御するのですが、ArduinoIDEというプログラムを書くためのツールがあります。
まずはこちらを自分のPCにインストールします。
https://www.arduino.cc/en/software

インストール後、IDEを立ち上げてLEDテープのプログラムに必要なライブラリ（Adafruit_NeoPixel.h)をインストールします。

参考サイト
https://kats-eye.net/info/2018/11/07/neopixel/

次に実際のコードの構成ですが下記のように作りました。

```c++:NeoPixel.ino
//ライブラリのインポート
#include <Adafruit_NeoPixel.h>
#ifdef __AVR__
  #include <avr/power.h>
#endif

#define PIN1 6 //Arduino6ピンから上半身へ出力
#define PIN2 7 //Arduino7ピンから下半身へ出力
#define BRIGHTNESS 50 //LEDの明るさ
#define NUM_LEDS1 222 //上半身のLEDの個数
#define NUM_LEDS2 106 //下半身のLEDの個数
・・・
#define その他細かいLEDの個数

Adafruit_NeoPixel strip1 = Adafruit_NeoPixel(NUM_LEDS1, PIN1, NEO_GRBW + NEO_KHZ800); //上半身用のLEDテープの定義
Adafruit_NeoPixel strip2 = Adafruit_NeoPixel(NUM_LEDS2, PIN2, NEO_GRBW + NEO_KHZ800); //下半身用のLEDテープの定義

void setup() {
  //上半身、下半身のLEDテープを初期化
  strip1.setBrightness(BRIGHTNESS);
  strip2.setBrightness(BRIGHTNESS);
  strip1.begin();
  strip2.begin();
  strip1.show();
  strip2.show(); 
}

void loop() {
  //delay関数と後述の特殊なLED関数を利用して、時間経過でLEDを制御するプログラムを書く
}

void ◯◯(){
  //特殊なLED制御を行う場合、関数として定義する
}


```

順に解説していきます。

### その他細かいLEDの個数について

```c++:NeoPixel.ino

#define NUM_LEDS1 222 //上半身のLEDの個数
#define NUM_LEDS2 106 //下半身のLEDの個数
・・・
#define その他細かいLEDの個数
```

ここでは体のパーツごとのLEDの番号を定義します。
例えば右腕だけを光らせたい！という時は、右腕に該当するLEDが何個目から何個目までであるかを定義します。
下記例ではLEDテープのスタート時点から34個目が右腕の開始時点で、71個目が終了時点ということになります。

```c++:NeoPixel.ino

#define RightArmStart 34 //右腕の開始番号
#define RightArmEnd 71 //右腕の終了番号
```

このように定数として定義しておくことで、右腕を光らせるためにはloop関数内で下記のように書けば光ります。

```c++:NeoPixel.ino

void loop() {
  //右腕に白色の光をセットする
  for(uint16_t i=RightArmStart; i<=RightArmEnd; i++) {
    strip1.setPixelColor(i, strip1.Color(255, 255, 255));
  }
  
  //セットした光を光らせる
  strip1.show();
  〜省略〜
}
```

定数として定義するメリットとしては、断線などが原因でLEDの個数が増減した場合に、定数部分のみのメンテナンスで済むことです。

### 時間経過でLEDを制御するプログラムを書く

Arduinoの電源が入った瞬間に、loop関数の中が上から実行されます。
そのため、例えばArduinoの電源が入って5秒後に右腕を光らせて、さらに10秒後に光を消す処理を書く場合は下記にように書きます。

```c++:NeoPixel.ino

void loop() {

  //5秒間
  delay(5000); 

  //右腕に白色の光をセットする
  for(uint16_t i=RightArmStart; i<=RightArmEnd; i++) {
    strip1.setPixelColor(i, strip1.Color(255, 255, 255));
  }
  //セットした光を光らせる
  strip1.show();

  //10秒間
  delay(10000); 

  //右腕に黒色の光をセットする(光を消す)
  for(uint16_t i=RightArmStart; i<=RightArmEnd; i++) {
    strip1.setPixelColor(i, strip1.Color(0, 0, 0));
  }
  //セットした光を光らせる(光を消す)
  strip1.show();

  〜省略〜
}
```

上記のように、delay関数を上手く活用して時間操作を行い、適切なタイミングで衣装を光らせるといった内容をloop関数に書きます。


### 特殊なLED制御関数

LEDテープに光をセットして、光らせる部分の処理は関数化しておき、使い回せるようにします。
上記の「右腕を光らせる」という処理はもう少し汎用的に捉えると、「特定の始点〜終点のLEDを光らせる」という処理として関数化しておくと、多くの場面で使い回すことができます。

仮に「特定の始点〜終点のLEDを光らせる」を関数化すると下記のように書けます。

```c++:NeoPixel.ino
void colorWipeRange(uint32_t color, uint32_t wait, uint32_t startLED, uint32_t endLED) {
  for(uint16_t i=startLED; i<=endLED; i++) {
    strip1.setPixelColor(i, color);
  }
    strip1.show();
    delay(wait);
}
```

上記の関数を使うと、先ほどのloop関数の中の「Arduinoの電源が入って5秒後に右腕を光らせて、さらに10秒後に光を消す処理」はこのように書くことができます。

```c++:NeoPixel.ino

void loop() {

  //5秒間
  delay(5000); 
  
  //右腕を１０秒間光らせる
  colorWipeRange(strip1.Color(255, 255, 255), 10000, RightArmStart, RightArmEnd);

  //右腕の光を消す
  colorWipeRange(strip1.Color(0, 0, 0), 0, RightArmStart, RightArmEnd);

  〜省略〜
}
```

大分スッキリしたと思います。

こういった形で、色んな光り方（流れるように光る、じわじわ光るなど）に合わせて関数を作成し、loop関数内で呼び出す、といった書き方をしています。


## STEP3：Arduinoにプログラムを書き込む

一通り書き終わったら、ArduinoIDEの [スケッチ] > [検証・コンパイル] をクリックします。
エラーも無くコンパイルが終わったら、USBケーブルでPCとArduinoを接続した上で、ArduinoIDEの [スケッチ] > [マイコンボードに書き込む] をクリックします。
これでArduinoにプログラムが書き込まれます。

この後、モバイルバッテリー、Arduino、衣装を接続し、モバイルバッテリーの電源をONにすると衣装が光ります。