なつねこメモ

主にプログラミング関連のメモ帳 ♪(✿╹ヮ╹)ノ 書いてあるコードは自己責任でご自由にどうぞ。記事本文の無断転載は禁止です。

VRChat で自分にしか見えないオブジェクトを実装したい

自分にだけ見えると都合が良いもの (例: 表情確認カメラ) を実装したいとき、
そういったものを実装する為の方法のメモです。

実装する前に、まずセットアップが必要です。
私は VRC 始めてからの 1 年間やってなかったらしいのでやり方も書いておきます。

まず、新しいシーンを作成し、そこに VRCSDK の中にある VRCWorld を突っ込みます。
突っ込んだら、 VRChat SDK の Builder に「セットアップしてね!」みたいなボタンが出るので、
全部クリックしておきます。

セットアップはこれで終了です。
なんかレイヤーとか追加されたりします。

ということで本題へ。

自分にしか見えないオブジェクトを実装するには、以下の要素を使用します。

  • Camera
  • RenderTexture
  • Shader

まずは、 RenderTexture を作成します。
解像度だけ決めて、後はデフォルト設定のままで OK です。
私は 256x256 にしました。

次はカメラを設定します。
カメラはアバター内部に自分がうつるように設定し、以下の項目を設定します。

  • Clear Flags
  • Background
  • Culling Mask
  • Target Texture

他の項目は好きにいじってもらってもかまいません。
Clear Flags には Solid Color を設定します。
Background には Black (0,0,0,0) を設定します。
Culling Mask には MirrorReflection を設定します。
これは、先ほどセットアップしたときに追加されたレイヤーです。
このレイヤーには、自身のアバター全体が描画されているので、それのみを映す設定にしています。
最後に、 Target Texture には先ほど作成した RenderTexture を設定します。

Culling Plane とかを良い感じに狭く設定しておくとよりよいかもしれません。
(私は Near: 0.01, Far: 0.5 に設定しています。)

最後にシェーダーを書きます。
やってることとしては、先ほどの RenderTexture を入力として受け取り、
中心 (0.5, 0.5) が黒 (0, 0, 0, 0) であれば透過、それ以外なら描画します。

シェーダーとしてはこんな感じ (Fragment のみ)

// sampler2d _CameraMemoryTexture;
// sampler2d _Texture;

uint isPlayerSelf()
{
    float4 color = tex2D(_CameraMemoryTexture, float2(0.5, 0.5));

    return sign(color.r + color.g + color.b + color.a);
}

float4 fs(v2f i) : SV_TARGET
{
    float4 color = tex2D(_Texture, i.uv) * float4(1.0, 1.0, 1.0, 1.0);
    color.a = lerp(color.a, 0.0, abs(sign(1 - isPlayerSelf())));

    return color;
}

最後に、対象のオブジェクトにこのシェーダーを設定することで、
自分にしか見えないオブジェクトを作ることが出来ます。

ということで、メモでした。
ちなみに、必要なのは Fragment での上記のことのみなので、
既存のシェーダーにも組み込めます。