ProtoFluxの基本操作

# はじめに
![スクリーンショット 2023-11-12 150554.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/4ddf3dcf-1942-42dc-59ab-b2a3779c2b54.png)

Resoniteではノードプログラミングの「ProtoFlux」でツールを開発したりすることができます。
またワールド内の要素だけでなくクラウド上に値を保持したり、レンダリングエンジンの変更が終わった後にはProtoFluxでシェーダー周りを制御できるようにする計画も検討されており、Resoniteのあらゆる要素を制御できるシステムとなっています。

この記事では、ProtoFluxを使うにあたっての最低限の基本操作について解説します。
開発に便利なツールやMODの紹介もしていますので、ぜひ参考にしてください。

＊情報不足や誤植については都度修正します。

# ノード操作
ProtoFluxではノードを接続してあらゆる制御や動作を実装している。
厳密には多種多様なコンポーネントを組み合わせることで細かな実装を可能にしているのだが中上級者向けの話なのでここでは省略。
基本的に説明はデスクトップモード用に書いてありますが、VRモードの場合は以下の通りに読み替えてください。

| デスクトップモード | VRモード |
|:-:|:-:|
|クリック|プライマリ（トリガー）|
|右クリック|グラブ|
|Rキー|セカンダリ（スティック押し込み等）|
|貼り付け(Ctrl＋V)|ダッシュメニューの「ホーム」タブ内、「クリップボードから貼り付け」ボタン|

## ProtoFluxツールチップの装備
デスクトップモードは2キーでツールを直接装備。0キーで装備解除。

VRモードの場合はインベントリの以下の場所にある「Proto Flux Tool」を取り出して装備。
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/7a01912d-033c-beed-e314-fb23a0a14140.png">
```html:
Resonite Essentials/Tools
```
頻繁に使う場合はインベントリの直下に保存しておくと素早く取り出せて便利になる。

<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/7c60b8fe-c883-aacb-9072-961db07449c4.jpeg">


## ノードの取り出し
ツールチップを装備した状態でコンテキストメニューを開き「ノードブラウザ」を選択。
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/c35a1be8-b1c1-4bdb-042c-ce1aeb83caed.png">

ダブルクリックで階層を降りて、最後に目的のノードの項目をダブルクリックで取得。
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/cba3dc4c-8fba-e679-370e-8f0729f2b960.png">

そのあと何もない箇所をダブルクリックするとノードが出現する。
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/855ebc66-fdce-7b7d-c60c-6600c2d5e7c8.jpeg">

:::note info
2023-11-12 現在ノードブラウザに検索機能がないため、「CherryPick」のMODを導入して検索できるようにすると非常に便利。
現状は自己責任扱いになってしまいますが、PC操作に慣れている方なら導入推奨。
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/d15e5f2f-dff6-189b-800f-2daabd8c2731.png">

MODの導入方法については下記を参照
https://sharedx.notion.site/ce8a842d2e67465aa4f8ca9452d27b2d?v=91506a6b5e9146d6969513798d7005ab
:::

### UIカメラモード(デスクトップ限定)
デフォルトの状態でノードを並べていくと、奥行きがずれたり角度がずれたりと整理されていない状態になりやすく操作や管理が難しくなる。
この問題を解決するために、デスクトップモード用にはUIカメラモードが用意されている。
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/18f54930-46ba-a4e5-ac80-58daf5f46cad.png">

#### UIカメラモードの操作方法
| 操作 | 説明 |
|:-:|:-:|
|UIカメラモード有効化|Ctrlキーを押しながら基準にしたいオブジェクト(ノードなど)をクリック。|
|UIカメラモード解除|Ctrlキーを押しながら何もない場所をクリック。|
|ズームイン/アウト|Ctrlキーを押しながらホイール上下|
|視点のパン(上下左右移動)|Ctrlキー＋マウスの右ボタンを押しながらドラッグ|

UIカメラモードが有効な状態でノードを追加したりインスペクタを開くと、基準となったオブジェクトに沿って平らに設置される。
これによって3D空間にいながら2Dのような平坦な操作が可能になる。
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/b2fcd1cf-f79e-c2de-499e-2b9edd19873b.png">

:::note info
VRモードの場合は、「RedPrint」というユーザー制のツールの利用がおすすめ
詳細は下端の「あると便利なツールなど」参照。
:::

## ノードの接続
繋ぎたい始点を左クリックで掴み、そのまま接続先までドラッグすることでつなげられる。
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/653c1205-b528-4674-0477-3b23671793e0.png">

## ノードの切断
何もない空間を左クリックでドラッグすると、図のように赤線を引くことができる。
この赤線を切断したい場所と交差させてクリックを解除することでノードの接続を切ることができる。
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/1c8b3295-53b6-cb6b-613d-08273a836fa5.png">

## ノードのパッキング(格納)
①パッキングしたいノードにカーソルを当てて「R」キーを長押し。選択されると色が変わる。パックしたい対象が複数ある場合は必要な分だけ繰り返す。選択解除したい場合は、コンテキストメニューを開き「選択解除」。

<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/7ca2ca2d-62b5-3fcb-ed7c-8c3aa06d4cce.png">

②パッキングしたいSlot(格納先のSlot)をインスペクタから右クリックドラッグして、掴んだままコンテキストメニューを開く。(画像の場合は、Boxオブジェクトの子にFluxという空のSlotを作成しそれをドラッグしている。)
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/81323fdb-fb15-dad4-afe1-095f627a3481.png">

③「〇〇にパッキング」を選択する。

これでパッキング完了。
Fluxの下にSlotが追加されていることが確認できる。
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/773a7641-fd8d-5a80-e3ff-49b0edb51cc4.png">

## ノードのアンパック(取り出し)
①インスペクタからノードを取り出したいSlotを右クリックドラッグして、掴んだままコンテキストメニューを開く。
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/5cd6a462-b663-75d6-b130-daa2ab0c8f1d.png">

②「〇〇をアンパック」を選択する。


これでパックしたノードが展開される。
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/39888a7c-e01c-5fb6-89ee-9ba8299c8a51.png">

:::note alert
アンパック時の注意
アンパックの際、複数のパックしたSlotが子にあるとそれらもすべて展開されてしまいます。

下図は誤ってBoxをドラッグしてアンパックしてしまった失敗例です。
FluxとFlux2の中身が同時に展開されてしまっています。ノード数が増えて複雑になると元に戻すことが困難になるため十分に注意してください。
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/08eec90e-e3e2-6b70-819a-2be369356822.png">
:::

# 各要素の取り出しと読み書きの操作
Resoniteでワールド内の要素に干渉する場合、インスペクタから必要な値を取り出してアクセスする方法が基本になります。条件を指定して検索するようなノードもありますが、ここでは省略します。

## 値の取り出し
インスペクタを開き、取り出したい値の名前の部分(scaleなど)を右クリックでドラッグしそのままコンテキストメニューを開く。
(図の場合はBoxのScaleを取り出している)
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/c55086a4-ab30-cee2-5d99-33a499a5b30a.png">

ReferenceやSourceで取り出したノードをほかのノードに繋げることであらゆる計算や制御をおこなうことが可能になる。
また、出てきたノードの右端の四角をドラッグしてRキーを押すと、Displayノードが出現して値を参照することができる。
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/c77e8641-0754-dc9f-6b2b-30fb1bbcb890.png">

:::note info
取り出せる要素の違いについては下記の通り。
対応していないものはコンテキストメニューに出てこない。
例えばインスペクタ左側のSlotをドラッグして取り出した場合はReferenceのみ選択可能。
|名称|説明|
|:-:|:-:|
|Reference|プログラミングでいうポインタに近い要素。アドレスの参照先を変えることで柔軟に取得元を変えられる。(筆者注：理解に自身がないため間違ってる可能性あり)|
|Source|主に値を読み取る目的のノードとして取り出す|
|Drive|主に値を書き込む目的のノードとして取り出す|
:::

## 値の書き込み
BoxのScaleをDriveで取り出してこのようにノードをつなげると、時間経過に応じてBoxが大きくなったり小さくなったりする制御が可能になる。
(ノードのつなぎ方は、上記の「ノードの接続」を参照)
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/3c6de955-3e63-7d0c-a941-ba539b2f9cbc.png">

:::note warn
Driveで書き込まれていると、背景が紫色になり他からの値の書き込みができなくなるので注意。
![スクリーンショット 2023-11-12 165408.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/a1a1f6da-143c-e914-e442-bd7249676fa4.png)
:::

:::note info
値の書き込む方法としてDrive以外にWriteなどで書き込む方法もあるが大まかな違いは以下の通り。
|名称|説明|
|:-:|:-:|
|Wtire|都度ネットワーク上で結果が同期される。基本的に値は全ユーザーで同じ。実装によるが他からWriteなどで自由に書き込める。|
|Drive|各ユーザーごとでローカル上で計算される。値はユーザーによって異なることがある。基本的にDriveの接続を切り替えられるように実装しないかぎり、他から値を書き込めない。|

詳細についてはこちらを参照。
NeosVR時代のものだが、考え方はまだ変わってないと思われる。
https://qiita.com/Rabbuttz_/items/a30f8992b836a663baff
:::


## ドライブ制御・値のリセット等
![スクリーンショット 2023-11-12 165609.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/649f37c1-f535-63e9-1269-a6cb831dc3f4.png)
インスペクターの名前のさらに左側の部分をクリックすると、
下記のようにコンテキストメニューが出現する。
(参照する値によってコンテキストメニューの内容は異なる)
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/e0ea22a4-b696-f9a6-1b51-676e201e4dd9.png">


|名称|説明|
|:-:|:-:|
|Open Link/Drive Source|Driveで書き込んでる元へアクセスする|
|Reset to default|デフォルト値へのリセット|
|Set all to average|すべての値を平均値に置き換える|
|Set all to X|すべての値をXの値に置き換える|
|Set all to Y|すべての値をXの値に置き換える|
|Set all to Z|すべての値をXの値に置き換える|
|Break Link/Drive|Driveで書き込まれている場合、その状態を切断/解除する。ノードで書き込んでいる場合、書き込み元や書き込み先のノード自体が削除されたりノード同士の接続が切断されることはない。|



# あると便利なツールなど
ProtoFlux開発に便利なツールを載せています。
新たなものを見つけ次第随時追加します。
## 各種MOD
上記でも紹介した各種MODを導入するとProtoFluxの開発が便利になります。
現状自己責任になってしまいますが、PC操作が苦でなければ導入推奨。
https://sharedx.notion.site/ce8a842d2e67465aa4f8ca9452d27b2d?v=91506a6b5e9146d6969513798d7005ab

個人的おすすめMOD
CherryPick、TypePicker(中上級者向)

## RedPrint
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/ef67dc68-c3c5-0882-6946-2f30150e54be.png">

ユーザーによって制作されたProtoFluxのノード管理ツール。
パネルにノードを並べることでVRモードでもきれいに管理できる。
また、ノードのパッキング管理も簡単になるためデスクトップモードでも恩恵があり高度な制御を行いたい場合は導入を推奨。
#### 取得方法
下記のURLをコピーしてResonite内で張り付け(Ctrl＋V)
```html:
resrec:///U-ukilop/R-a1a25903-2046-4ed1-8f0a-335f338e2f7e
```
#### 使い方
NeosVR時代の記事だが、内容はResonite用の現行バージョンとほぼ同じなので参考にしてください。
https://qiita.com/e1ght3/items/e1eefb98f041779c6283


## 日本語対応キーボード
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/ed875c79-4f05-d64f-7498-d20a8ba24d3a.png">

VRモードの場合、デフォルトのキーボードが使いにくいため、気になるようであれば導入推奨。
逆にデスクトップモードの場合は手元のキーボードから直接入力するため特に必要ありません。

#### 取得方法
下記のURLをコピーしてResonite内で張り付け(Ctrl＋V)
```html:
resdb:///5c0dce4cde489fcd5fdd0a89c33e8b9c9949a0cbd97cb35b38100054970946bf.brson
```
もしくは
```html:
resrec:///U-amaguri765/R-9baa3cc6-b639-4305-b6e9-e397a7093cec
```

#### 導入方法
アイテムを保存して「キーボードに設定」ボタンを押下。Resoniteを再起動すれば完了。

## SmaerInventoryCreator
<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2308792/c6512b4b-bcd3-144e-a643-5983a5eafe51.png">

インベントリの特定のフォルダ内のアイテムをコンテキストメニューから素早く取り出せるようにするツール。

#### 取得方法
下記のURLをコピーしてResonite内で張り付け(Ctrl＋V)し、その中のSmaerInventoryCreatorを取り出す。
```html:
resrec:///U-rhenium/R-32338edd-bd95-4e38-a1ea-a0f24e4ecda6
```

#### 導入方法
基本的に画面に従えば問題ない。
①CreateNewを押す
②対象にしたいパブリックフォルダを取り出して真ん中の箇所にドラッグ(フォルダ内にはあらかじめ取り出したいアイテムを入れておく。)
③上の文字列を下にドラッグ
④出てきたアクセサリをアバターに装備させる
⑤アクセサリを装備した状態のアバターをインベントリに保存し、次回からはそちらを使用する。
で完了。

中級者以上である程度慣れてる方は、アクセサリ内にある必要なSlotのみアバター内に放りこんでインストールでも問題なし。

# その他チュートリアル情報

## ゲーミングキューブの作成チュートリアル
基本操作の確認後におすすめのチュートリアル。
虹色に光るBOX、いわゆるゲーミングキューブの作り方を学べます。

https://note.com/tatikawa_yuzuki/n/n76f1e966a542

## ゲーム内チュートリアルワールド
英語に抵抗がなければ、下記のワールドでクエスト形式で基本操作を学べます。
The Fortress of Flux - An Adventure Tutorial for Protoflux
https://api.resonite.com/open/world/U-SoftPoint/R-b33509a0-3d80-43fc-b4c1-35eac6462d89