MRが楽しい

MRやVRについて学習したことを書き残す

UniRxを使ってTransformの変化をIObservableで監視する

本日は UniRx の小ネタ枠です。
UniRxを使ってTransformの変化をIObservableで監視する方法について記事にします。

ObserveEveryValueChanged

ObserveEveryValueChangedはUniRxで定義されている全クラスの拡張メソッドです。
この関数を利用することで、様々なクラスのフレーム間での値変化の監視が行えるようになります。

例えば以下のように利用することでTransformの変化を監視することができます。

IObservable<Vector3> CurrentMove => transform.ObserveEveryValueChanged(transform => transform.localPosition);
IObservable<Quaternion> CurrentRotate => transform.ObserveEveryValueChanged(transform => transform.localRotation);
IObservable<float> CurrentScale => transform.ObserveEveryValueChanged(transform => transform.localScale.x);

Transformの変化をIObservableで監視する

ObserveEveryValueChangedを使ってTransformの変化をIObservableで監視するサンプルクラスと、実際に参照してログ出力を行うサンプルクラスを作成しました。
・TransformObserveTest.cs

using System;
using UniRx;
using UnityEngine;

public class TransformObserveTest : MonoBehaviour
{
    /// <summary>
    /// Positionの変更を監視する
    /// </summary>
    public IObservable<Vector3> CurrentMove =>
        transform.ObserveEveryValueChanged(transform => transform.localPosition);

    /// <summary>
    /// Rotationの変更を監視する
    /// </summary>
    public IObservable<Quaternion> CurrentRotate =>
        transform.ObserveEveryValueChanged(transform => transform.localRotation);

    /// <summary>
    /// Scaleの変更を監視する
    /// </summary>
    public IObservable<float> CurrentScale =>
        transform.ObserveEveryValueChanged(transform => transform.localScale.x);
}

・TransformSubscribeTest.cs

using UniRx;
using UnityEngine;

public class TransformSubscribeTest : MonoBehaviour
{
    [SerializeField]
    private TransformObserveTest _transformObserveTest;
    
    // Start is called before the first frame update
    void Start()
    {
        // Subscribeを使ってトランスフォームの各種変更を監視する
        _transformObserveTest.CurrentMove.Subscribe(move => Debug.Log($"Move: {move}"));
        _transformObserveTest.CurrentRotate.Subscribe(rotate => Debug.Log($"Rotate: {rotate}"));
        _transformObserveTest.CurrentScale.Subscribe(scale => Debug.Log($"Scale: {scale}"));
    }
}


動作確認

シーンを再生して動作を確認します。

ObserveEveryValueChangedを設定したオブジェクトのトランスフォームを変更するとデバッグログが更新されれば成功です。