UniRx後継のR3を使ってみた-Operator編

Operatorとは

Observable から流れてくるデータを加工、変換、フィルタリングする処理のことです。以前の記事からの流れを例とすると
データの流れは Observable → Operator → Operator → Subscribe となり
ボタンクリックを例とすると
ボタンクリック+連打防止+回数制限+実行のような流れにすることができるようになります。
Operatorを使用して書くとObservable→Where→Take→Subscribeという形になります。

Operatorの例

Where

前回記載した通りで条件に合うデータだけを通すフィルタのような機能です。
以下は現在の得点が1000以上になったら、1度だけボーナススコアと表示する処理です。
private void BonusScore()
    {
        Observable.EveryUpdate()
        .Where(_ => currentScore >= 1000)
        .Take(1)
        .Subscribe(_ =>
        {
            Debug.Log("ボーナススコア");
        }).AddTo(this);
    }

Take

指定した回数まで処理を実行することができます。
以下の例は5回まで押すことのできるボタンを用意して、完了したら「収集完了」と表示するものです。
 
using UnityEngine;
using R3;
using UnityEngine.UI;
using TMPro;

public class R3Test2 : MonoBehaviour
{
    [SerializeField] private Button _collectbutton;
    [SerializeField] private TextMeshProUGUI itemCountText;
    [SerializeField] private TextMeshProUGUI statusText;

    private int _itemCount = 0;

    private void Start()
    {
        OnCollectButtonClick();
    }

    private void OnCollectButtonClick()
    {
        _collectbutton.OnClickAsObservable()
        .Take(5)
        .Subscribe(_ =>
        {
            _itemCount++;
            if (itemCountText != null)
            {
                itemCountText.text = $"アイテム:{_itemCount}/5";
            }
            Debug.Log($"アイテム収集:{_itemCount}/5");

            if (_itemCount >= 5)
            {
                if (_collectbutton != null)
                {
                    _collectbutton.interactable = false;
                }
                if (statusText != null)
                {
                    statusText.text = "収集完了";
                }
            }
        }).AddTo(this);
    }
}

Select

データの変換・加工を行うことができます。returnで次のオペレーターに処理を渡すことができる。
Subscribeは最終結果の処理を行うがSelectではデータの加工をする途中経過のイメージ。
以下はスコア加算をすると文字列としてスコアを表示する処理です。
using UnityEngine;
using R3;
using UnityEngine.UI;
using TMPro;

public class R3Test2 : MonoBehaviour
{
    [SerializeField] private Button scoreButton;
    [SerializeField] private TextMeshProUGUI scoreText;

    private int currentScore = 0;

    private void Start()
    {
        OnScoreDisplay();
    }

    //スコア表示
    private void OnScoreDisplay()
    {
        // ボタンクリック → スコア加算 → 文字列変換 → UI更新
        scoreButton.OnClickAsObservable()
            .Select(_ =>
            {
                currentScore += 100; // 100点加算
                return currentScore; //次のoperatorに渡す
            })
            .Select(score => $"Score: {score:D6}") // 6桁の文字列に変換
            .Subscribe(scoreString =>
            {
                scoreText.text = scoreString;
                Debug.Log($"現在のスコア: {scoreString}");
            })
            .AddTo(this);
    }
}

まとめ

ここまでで R3 の基本的な処理の流れとフィルタリングの処理ができるようになりました。ボタンの処理について多めに書きましたがInput Systemでも可能なので使い分けが大切ですね。
次回の記事で載せる予定の ReactiveProperty の方をよく使うので、今回は処理の流れを理解することに焦点を当てました。次回の項目をしっかり理解していきます。
最新情報をチェックしよう!
>
CTR IMG