
Godot4でQuestパススルーするWebXRプロジェクトを作った記録
概要
Meta Quest3を買ったのでpass throughするWebXRを作ってみた時の記録です。書いてないところはチュートリアルに従いました。書き忘れもありそうです。間違いや不要な設定もありそうです。
初めにXRチュートリアルに書いてある内容を実施しました。
XR — Godot Engine (4.x)の日本語のドキュメント
次にWebXRチュートリアルに書いてある内容を実施しました。
How to make a VR game for WebXR with Godot 4 | Snopek Games
下記も参考にしました。
Godot 4 VR開発メモ - フレームシンセシス (framesynthesis.co.jp)
WebXR in "immersive-ar" session mode shows opaque artifacts overshadowing the background · Issue #75581 · godotengine/godot (github.com)
Setting up XR
Setting up XR — Godot Engine (4.x)の日本語のドキュメント
上記を参考にプロジェクトを作りました。プロジェクトを作るときはモバイルと書いてありました。(Forward+を選んだら上手く動かなかった。HTML5もしくはWebXRもしくはWebGLだと互換性にするようです。)

プロジェクト設定のXRの下のOpenXRとシェーダーを有効にしました。

WebXRには関係ない、WebXRでは使えないフルトラについて。GodotのOpenXR(SteamVRを使ったPCVR)だとTracker名が/user/vive_tracker_htcx/role/left_footとなっています。いっけんVive専用に見えますがUni-motionでも動きました。

話題がそれましたがプロジェクト作成だけ"Setting up XR"に従いました。シーンとノードの追加は、次の"How to make a VR game for WebXR with Godot 4"に従いました。
How to make a VR game for WebXR with Godot 4
How to make a VR game for WebXR with Godot 4 | Snopek Games
に従い、WebXR(HTML5)に対応しました。
Node3Dでルートノードを作成し名前をMainに変えました。その子ノードにXROrigin3Dを付けます。
XROrigin3Dの子供にXRCameraとXRController3Dを2個付けます。
XRController3Dは、LeftControllerとRightControllerに名前を変えました。
LeftControllerとRightControllerの子供にMeshInstance3Dを付け0.1mの立方体BoxMeshにしました。
XRCamera3DとLeftControllerとRightControllerは良い感じの位置に配置しました。インスペクターからTrackerは、left_handとright_handに割り当てています。
CanvusLayerとButtonも記載の通りに追加しました。
DirectionalLight3Dも書いてなかったのですが足しました。

プロジェクト->エクスポートでビルド先の設定をします。Windows DesktopとWebを追加しました。
Webで"Header Include"に参考にしたサイトのヘッダーを記載しました。
もしHeader Includeを忘れているとエラーでした。"Failed to initialize: Unable to make WebGL context compatible with WebXR: TypeError: Failded to construct 'XRWebGLBinding': parameter 1is not of type 'XRSession'."

また、"モバイル向け"をオンにするとETC2/ASTCテクスチャ圧縮が必要と表示されました。

プロジェクト->プロジェクト設定->レンダリング でAdvanced SettingsをONにしVRAM圧縮 Import ETC2 ASTCをオンにしました。

エディタ->エディタ設定で、Webの"HTTPホスト"をIPに"Use TLS"をオンにしました。

これで右上の実行ボタンを押すとブラウザで確認することができました。

ブラウザからの確認はメタ社のimmersive-web-emulatorが便利でした。
meta-quest/immersive-web-emulator: Browser extension that emulates Meta Quest devices for WebXR development. Lead: Felix Zhang (fe1ix@meta.com) (github.com)
よくわかりませんが、画面に何も表示されない場合immersive-web-emulatorの右上のStereoボタンを押すと表示されました。

Web Launchも便利でした。
#WebXR 対応ウェブサイトに Web Launch 機能がついたら Oculus Meta Browser での閲覧が捗るお話 (zenn.dev)
WebXR in "immersive-ar"でAR化
WebXR in "immersive-ar" session mode shows opaque artifacts overshadowing the background · Issue #75581 · godotengine/godot (github.com)
上記のminimal exampleを参考にimmersive-arに対応させました。
具体的には"How to make a VR game for WebXR with Godot 4 | Snopek Games"に書かれていたスクリプト下記部分を変更しました。
_ready()関数内のxr_interface.is_session_supported("immersive-vr")をxr_interface.is_session_supported("immersive-ar")へ
_webxr_session_supported関数の"immersive-vr"を"immersive-ar"へ
_on_button_pressed関数の先頭get_viewport().transparent_bg = trueを追加
_on_button_pressed関数のxr_interface.session_mode = 'immersive-vr'をimmersive-arへ変更
_webxr_session_ended関数にget_viewport().transparent_bg = falseを追加
これで、Quest3のブラウザでpass throughができました。(部屋が汚すぎて画像を公開できない)
エクスポートしたHTML5をサーバに置く場合
エクスポートして生成したWebXR(HTML5)をサーバに置く場合は、httpsでしか動かず下記のhttpヘッダーが必要でした。
Cross-Origin-Embedder-Policy: "require-corp"
Cross-Origin-Opener-Policy: "same-origin"
文字を表示する場合
ゲーム中で文字を表示する場合、Label3DのBillboardをEnabledにすると便利でした。文字が常にカメラのほうを向くようになります。

出来たゲームの公開
クソゲーですがitch.ioで公開しました。