obniz + TJBot で遊んでみた

![image.png](https://qiita-image-store.s3.amazonaws.com/0/193519/a4dc8241-0f4b-36d3-c134-9eafe01666fc.png)

[TJBot](https://www.ibm.com/developerworks/jp/code/open/projects/tjbot/index.html) という紙製のロボットに、[obniz](https://obniz.io/) を入れてコントロールしてみましたので、ご紹介します。手軽に遊べて楽しいですw

今回の TJBot 君がリモート操作でできることは以下です。

* 頭の フルカラーLED を光らせる
* 左手をサーボで動かす
* 圧電ブザーで音を鳴らす

# ハードウェアを準備する

## obniz を準備する

[obniz](https://obniz.io/) を購入し、自宅の Wifi 環境に接続します。obniz は小さいながらも表示画面と、入力用スイッチを装備していますので、Wifi 接続はとても簡単でした。

obniz がネットワークに接続したら [obniz 開発画面](http://obniz.io/program) からプログラム開発を開始できます。

## TJBot を組み立てる

[TJBotのページ](https://www.ibm.com/developerworks/jp/code/open/projects/tjbot/index.html) などで公開されている型紙をダウンロードし、TJBot を組み立ててください。以下のページも参考になります。

* [Node-REDで動く段ボール製の人工知能ロボットTJBotを作る](https://qiita.com/zuhito/items/ead9579a8676cb930556)

なお私は今回、ラズパイ2/3 など用の TJBot を使用しましたが、かなり内部に余裕があります。より小型の TJBot Zero でも obniz なら余裕で入りそうです。どなたか挑戦してみてくださいw

## 配線する

obniz は I/O 端子が汎用的なので、配線もあまり考えず順に刺していけば、たいてい大丈夫です。一応、どのピンに接続したか、なるべくは覚えておき、でもちゃんとした役割分けはソフトウェアのほうで設定します。
![image.png](https://qiita-image-store.s3.amazonaws.com/0/193519/6ae6f11d-15dd-3d00-83a8-8348c15d0292.png)
例えばフルカラーLEDは足が4本ありますので、obniz の 0～3 の端子にそのまま接続します。一番長い足が共通のカソードなので、それを 1 に接続したことだけは覚えておきます。

フルカラーLEDは抵抗を挟んだほうが良さそうなので、今回は一応、ブレッドボード経由で接続しておきました。それ以外は、左腕用のサーボを 4～6 端子に、音を鳴らす圧電ブザーは 7～8 の端子に、それぞれそのまま接続しています。

以下のような感じになりました。
![image.png](https://qiita-image-store.s3.amazonaws.com/0/193519/10c170a2-dd60-e63f-c660-f95bd4e2240b.png)

※ 左腕用のサーボモーターは、TJBot 組み立て時に既に組み込んであります

# ソフトウェアを準備する

## 基本ロジック

obniz の 開発画面を開き、以下のような初期化コードを用意します。

```javascript
var obniz = new Obniz("xxx-xxxx");
obniz.onconnect = async function () {
  obniz.display.clear();
  obniz.display.print("obniz + TJBot");

  // Main logic here...
}
```

## TJBot 画像を利用した Web UI を用意する

今回は使いやすさを考え、以下のように TJBot の画像上に UI 部品を並べたものを作成したいとおもいます。
![image.png](https://qiita-image-store.s3.amazonaws.com/0/193519/8089dfd9-a168-6763-ca0e-488f12ba60ae.png)

まあ obniz の標準的なサンプルの見た目を変えただけ、に近いんですけどw obniz の 開発画面へ、以下の Web 要素をコピペしてください。

```css:CSS
  div.button button.button {
    display: table-cell;
    width: 32px;
    height: 32px;
    position: absolute;
    text-align: center;
    vertical-align: middle;
    border: solid 1px #ccc;
  }
```

```html:html
  <h1>obniz + TJBot</h1>

  <div style="background-image:url(https://www.ibm.com/developerworks/jp/code/open/projects/tjbot/fig1.jpg); width:300px; height:300px; ">
    <div id="red" class="button" style="background-color:#ff0000; top:134px; left:140px; opacity: 0.4;">R</div>
    <div id="green" class="button" style="background-color:#00ff00; top:150px; left:100px; opacity: 0.4;">G</div>
    <div id="blue" class="button" style="background-color:#0000ff; top:150px; left:180px; opacity: 0.4;">B</div>
    <button id="s0" class="button" style="top:300px; left:250px;">→</button>
    <button id="s90" class="button" style="top:250px; left:220px;">↑</button>
    <button id="s180" class="button" style="top:300px; left:190px;">←</button>
    <button id="spC" class="button" style="top:320px; left:40px;">C</button>
    <button id="spD" class="button" style="top:320px; left:80px;">D</button>
    <button id="spA" class="button" style="top:320px; left:120px;">A</button>
  </div>
```

なお画像は [IBM Developer](https://developer.ibm.com/jp/) サイトにある、[TJBotのページ](https://www.ibm.com/developerworks/jp/code/open/projects/tjbot/index.html) のものをお借りしています。

## フルカラーLED を操作する

TJBot の頭に付いているLEDの操作UIのロジックを作成しましょう。
![image.png](https://qiita-image-store.s3.amazonaws.com/0/193519/797aa443-2e07-2455-2892-00037911d709.png)
色の取り違えはプログラム側でさくっと直せますので、覚えていた共通のピン 1 を設定して、残りのどの端子がどの色なのか確認していきます。各ボタンに対応するアクションを定義したのが以下のコードです。

```javascript
  var fc_led = obniz.wired("FullColorLED", {r: 0, g:2, b:3, common:1, commonType:'anode_common'}); 
  var fc_colors = [0,0,0];

  $('#red').click(function () {
    if (fc_colors[0] > 0) {
      fc_colors[0] = 0;
      $('#red').css('opacity', '0.4');
    } else {
      fc_colors[0] = 255;
      $('#red').css('opacity', '1');
    }
    fc_led.rgb(fc_colors[0], fc_colors[1], fc_colors[2]);
  });
  $('#green').click(function () {
    if (fc_colors[2] > 0) {
      fc_colors[2] = 0;
      $('#green').css('opacity', '0.4');
    } else {
      fc_colors[2] = 255;
      $('#green').css('opacity', '1');
    }
    fc_led.rgb(fc_colors[0], fc_colors[1], fc_colors[2]);
  });
  $('#blue').click(function () {
    if (fc_colors[1] > 0) {
      fc_colors[1] = 0;
      $('#blue').css('opacity', '0.4');
    } else {
      fc_colors[1] = 255;
      $('#blue').css('opacity', '1');
    }
    fc_led.rgb(fc_colors[0], fc_colors[1], fc_colors[2]);
  });
```

似たコードが3セット並び、ちょっと冗長ですがお許しください。

ここのコードでやっているのは、フルカラーLEDの各原色(赤、緑、青)の表示コントロールです。TJBot の LED 点灯にあわせ、UI のほうのボタンの色(実際には透明度)も変化させてみました。色の組み合わせなどを指定する際にわかりやすいのではないかとおもいます。

## サーボと圧電ブザーを操作する

以下の UI の下部にある、左腕のサーボの制御(←、↑、→)と、圧電ブザーで再生する音の種類(C、D、A)のそれぞれの操作ロジックもご紹介します。
![image.png](https://qiita-image-store.s3.amazonaws.com/0/193519/8089dfd9-a168-6763-ca0e-488f12ba60ae.png)

```javascript
  var servo = obniz.wired("ServoMotor", {signal:6, vcc:5, gnd:4});
  var speaker = obniz.wired("Speaker", {signal:8, gnd:7});
  
  $('#s0').click(function () {
      servo.angle(0);
  });
  $('#s90').click(function () {
      servo.angle(90.0);
  });
  $('#s180').click(function () {
      servo.angle(180.0);
  });
  $('#spC').click(async function () {
      speaker.play(1800); // C
      await obniz.wait(200);
      speaker.stop();
  });
  $('#spD').click(async function () {
      speaker.play(2300); // D
      await obniz.wait(200);
      speaker.stop();
  });
  $('#spA').click(async function () {
      speaker.play(2800); // A
      await obniz.wait(200);
      speaker.stop();
  });
```

こちらはサンプルにありがちな、ガッチガチに基本的なコードであることがわかります。今回の UI での特徴は、これらボタンを CSS で TJBot の画像上にうまく配置したこと、ぐらいです。

# 完成です

![image.png](https://qiita-image-store.s3.amazonaws.com/0/193519/e6fbb994-f2e8-ed90-6415-7ffdc98fcd88.png)
中身はわりとスカスカで、obniz は背中あたりに単に置いてあるだけです。
![image.png](https://qiita-image-store.s3.amazonaws.com/0/193519/f109c782-a4e3-5f4b-b49d-5cb20af4af00.png)
移動したとき、obniz を操作して Wifi 環境の設定をしなければいけないので、取り出しやすい位置に配置することにしました。

# というわけで

ラズパイ内蔵の TJBot のように自律的には動作せず、Wifi 経由で Web から操作する、まあリモコンみたいな実装なのですが。なにより簡単に実装できますし、Web 側のロジックを凝ることで、わりといろいろ実現できそうな気がしますので、ご紹介してみました。

なお今回の TJBot は私が初めて組み立てた初号機で、レーザーカッターの煤で薄汚れ、保全のためのスプレー跡も残り、見た感じかなり… ボロいです。ダサダサです。でも作者にとってみれば、やはり最初に作ったこの子が一番かわいい！んですよね。

それではまた。