iOS→UnityでOSC通信

最近UnityJapanのYoutubeチャンネルでビジュアルスクリプティングでOSCを使用するというネタの[動画](https://www.youtube.com/watch?v=aGwpV28EF94)が上がっていました。

そちらの動画を参考にiOSの加速度データをOSCでUnity(Windows)に飛ばすサンプルを実装しました。設定周りで少し躓いたりしたのでメモとして情報を残しておこうと思います。

Unityバージョンは2021.3.2f1です。使用しているライブラリが対応しているのがUnity 2021.3 or laterなのでそれ未満のバージョンでは上手く動かないかもしれません。

# 受信側の設定
まずはUnity側の設定からやっていきます。

## ライブラリのインポート

OSC通信を簡単に扱えるようにラップしてくれているライブラリがあるのでそちらを使用します。本記事で使用するバージョンは2.0.0です。

https://github.com/keijiro/OscJack

なお、冒頭で紹介したUnityJapanの動画では同じ作者さんのビジュアルスクリプティング用のライブラリを使用していますが、この記事では普通(?)にコードを書く用のライブラリを使用します。ビジュアルスクリプティング用のライブラリも裏ではこちらのライブラリを使用しているようなので機能的には変わらないと思います。

こちらのライブラリをインポートするためにUnity側の設定を変更します。

### Package Managerへのリポジトリの登録

まずはEdit→Project Settings→Package ManagerからPackage Managerの設定画面を開きます。
設定画面のScoped Registriesという所に以下のようにリポジトリ情報を登録します。
Name : Keijiro
URL : https://registry.npmjs.com
Scope(s) : jp.keijiro
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/526299/dbd873b0-2716-fde5-a972-910993c457d4.png)
これで作者のKeijiroさんが公開しているパッケージをPackage Managerからインポートできるようになりました。

### パッケージのインポート

続いてWindow→Package ManagerからPackage Managerを開きます。
ウインドウ左上のPackages:の項目をMy Registriesに変更します。 Assetstoreのアセットしか出てこない！となった人は"My Assets"になっているので"My Registries"にしましょう。
![無題.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/526299/d047e20d-3195-fd36-3957-c08947e1e3bb.png)

そうするとKeijiroさんが公開しているパッケージの一覧が表示される筈なので、そこから"OSC Jack"を選び、右下の"Install"からパッケージをインポートします。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/526299/38c6d393-1d6d-bf37-c5ff-05166565854a.png)

## 設定ファイルの作成

OSCの接続情報の設定ファイルを作成します。Assetsウインドウの適当なところで右クリック→Create→ScriptableObjects→OSC Jack→Connectionを押すと設定情報を持ったOSC ConnectionというScriptableObjectが作成されるので、適当な名前を付けます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/526299/f853fed5-3a7e-bad3-b895-9be5149da02c.png)

設定は以下のようにします。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/526299/e9f12b93-bef1-004f-c16f-155c5219d6c0.png)

設定が完了したらシーン中の適当なオブジェクトに `EventReceiver` というコンポーネントをアタッチします。Event ReceiverのプロパティのConnectionという所に先ほど作ったOSC Connectionファイルを設定します。OSC Addressという所も設定する必要があるのですがこちらは送信側に依存する値なので今は置いておきます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/526299/3a07a53e-0452-5ac9-6d93-82e006767e42.png)

# 送信側の設定

iOSからOSC通信が出来るアプリはいくつもAssetstoreで公開されています。どれを使っても問題ないと思いますが、本記事では無料で公開されている`ZIG SIM`というアプリを使用します。こちらのアプリは加速度やジャイロセンサ等のスマホのセンサ情報を色々とOSCで飛ばすことができます。

アプリをインストールしたら、SensorタブからUnity側に飛ばす情報を選びます。本記事では加速度センサの情報を取りたいので`ACCEL`を選びます。

![iOS の画像.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/526299/8f908833-d4f8-b8d5-9d40-24b8d60d5588.png)

続いてSettingsタブで送信側の接続情報を以下のように設定します。
DATA DESTINATION : OTHER APP
PROTOCOL : UDP
IP ADDRESS : Unityが動いているPCのローカルIP
PORT NUMBER : OSC Connectionで設定したポート番号(記事の場合は8000)
MESSAGE FORMAT : OSC
MESSAGE RATE : 必要に応じて(通信状況やセンサの性能次第では必ずしもこのレートが担保されるとは限りません)
![iOS の画像 (1).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/526299/8b0dc764-8df3-504f-7fce-ea882f5cbd9a.png)

これで送受信双方の設定が出来ました。が、Unityが動いているPCのファイアウォールの設定次第ではOSCがブロックされる場合があります。Windowsの初期設定ではブロックされるので許可しましょう。iOS→Windowsに向かってpingが通れば大丈夫だと思います。

# ファイアウォールの設定
この設定はウイルス対策ソフトを使用している場合はそちらで設定する必要があるかもしれません。ここで紹介しているのはWindows Defenderのみを使用している場合の設定です。また当然ですがファイアウォールの設定を緩めることはセキュリティリスクを高めることになるので気を付けましょう。
右下のネットワークアイコンからネットワークとインターネットの設定を開きます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/526299/ece2d492-6f9e-6918-69c2-9a478589244c.png)

ネットワークの状態から、今接続しているネットワークがパブリックネットワーク、プライベートネットワーク、ドメインネットワークのどれかを調べます。下の画像の場合はプライベートネットワークです。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/526299/ddad4fa8-03f6-2ad0-13d5-089034421cb0.png)

そうしたら次は設定の検索に「Windowsセキュリティ」と打ち込んでセキュリティ設定を開き、ファイアウォールとネットワーク保護を開きます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/526299/e381a8ca-48ef-00ed-9d07-bf02a5297e86.png)

詳細設定を選びます。
![無題1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/526299/32bc06e3-c8cb-1054-d6c5-39334a071b0d.png)

ファイアウォールの設定画面が開くので、左側のビューから`受信の規則`を選びます
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/526299/4b292a0a-6d05-4c1c-68af-cf3428b72ac7.png)

そうすると、ウインドウ中央のビューに様々な規則が表示されるので、そこから`ファイルとプリンターの共有(エコー共有 - ICMPv4 受信)`を探します。2つあると思いますが、プロファイルの列の値を見て、接続しているネットワークの方を右クリックして`規則の有効化`をします。
![image (1).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/526299/5ef387f7-a440-cbef-60b3-e21872a9c35a.png)

これでファイアウォールの設定が完了しました。

# 送受信の接続

これでOSCの疎通が出来るようになったはずです。UnityのWindow→OSC MonitorからOSC Monitorを開きましょう。最初は何も表示されていませんが、OSCのパケットが来たらその情報がここに表示されます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/526299/fead10d3-bdfd-2c56-c512-36a5dee72d1e.png)

Unityのプレイボタンを押した後iOS側からOSCを送ってみましょう。ZIG SIMの場合Startボタンを押したら設定に応じてセンサ情報が送られます。以下のように接続情報と送られてきた値が表示されればOKです。スマホを振ったらaccelの行の値が大きくなるはずです。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/526299/cdc0672d-b1b5-e6f8-5e26-7708db81f2a1.png)

この値を自前のスクリプトで受け取るためには送信側のOSC Addressを知る必要があります。OSC Monitorでデータの前にコロン区切りで表示されている文字列がアドレスになります。上の画像の場合だと加速度の値を取得するためには`Event Receiver`のOSC Addressの欄に`/ZIGSIM/FGlaY4GSu3UJToRZ/accel`を入れます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/526299/d326a102-60de-f200-fabd-40e43e187809.png)

続いて、受け取ったデータを処理するスクリプトを書きます。今回はシンプルにDebug.Logで加速度の値を吐くだけのものにします。

```c#
using UnityEngine;

public class OSCReceiveSample : MonoBehaviour
{
    // 必ずpublicにし、引数はVector3が1つ
    public void Receive(Vector3 accel)
    {
        Debug.Log(accel);
    }
}
```

このスクリプトを適当なGameObjectにアタッチします。加速度の情報は3つの実数の組なので、Event Receiverの`Data Type`は`Vector3`とします。その後、先ほど作ったスクリプトのReceive関数を呼び出すように設定します。最終的に以下のようになるはずです。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/526299/0bfa8cf4-f787-0710-d52b-26044c95517c.png)

コンソールに以下のように加速度情報が表示されれば成功です。もしもEvent Receiverがエラーを吐いたりした場合はUnityエディタを再起動してみてください。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/526299/5551a6b4-ac9e-4a05-0b36-9b46d1676f8e.png)

# まとめ

非常に簡単にスマホのセンサ情報をOSCでUnityに飛ばすことが出来ました。スマートフォンをコントローラにする、といった使い道が出来そうです。