PUNRpcでの状態の同期のサンプル

設計なんもわからん

流れ

送信側
UIがイベントを発火(UseCaseのメソッドを呼ぶ)

UseCaseは自分側のNetWork GameObjectにイベント送信

NetWork Object はイベントを購読しRpc実行

受信側
NetWork ObjectはRpcが実行される

NetWork ObjectからUseCaseなりにイベント送信

イベントを購読しているUIがイベントを受け取り情報を更新

    // 送信側
    public class NotifyUpdateHogeEvent {
        public static NotifyUpdateHogeEvent Default = new NotifyUpdateHogeEvent();
    }
    
    // 受信側
    public class HogeUpdatedEvent {
        public static HogeUpdatedEvent Default = new HogeUpdatedEvent();
    }

NetWork Object

NetWork Objectはイベントのやり取りをするだけ

public class HogePUNObject: MonoBehaviourPunCallbacks {
    [PunRPC]
    void OnHogeUpdatedEvent() {
        MessageBroker.Default.Publish(Event.HogeUpdatedEvent.Default);
    }
    
    private void Awake() {
        MessageBroker.Default
            .Receive<Event.NotifyHogeUpdateEvent>()
            .Subscribe(_ => {
                photonView.RPC(nameof(OnHogeUpdatedEvent), RpcTarget.All);
            });
    }
}

UseCase

UniRx の MessageBroker を使っているがなんでもいい
(Repositoryを通じてNetWork Objectとやりとりすべき?)

    public interface IHogeUseCase { ... }
    
    public class HogeUseCase: IHogeUseCase {
         [Inject]
         private IHogeRepository _repo;
    	 ...
    	
    	 public IObservable<Event.HogeUpdatedEvent> OnHogeUpdated() {
             return MessageBroker.Default.Receive<Event.HogeUpdatedEvent>();
         }
         
         public void NotifyHogeUpdate() {
             MessageBroker.Default.Publish(Event.NotifyHogeUpdateEvent.Default);
         }
    }

UI

例ではUIWidgetsを使っているがuGUIでも同じ,
Start()
でリスナーを書く
(補足: UIWidget + Zenject

)

	class HogePage : ZenjectStatefulWidget<HogePage, HogePageState> {
        [Inject]
        public IHogeUseCase HogeUseCase;
	}
 
    class HogePageState : State<HogePage> {
        [Inject]
        public HogePage HogePage { get; }
        
        ...
        
        private OnHogeButtonClicked() {
            widget.HogeUseCase.NotifyHogeUpdate();
        }
        
        private UpdateHoge() {}
        
        public override void initState() {
              base.initState();
                    
              widget.MatchingUseCase
              	.OnHogeUpdated()
              	.Subscribe(_ => UpdateHoge());
        }
  }

参考文献

2019年をふわっとまとめる 〜Unityにおけるアーキテクチャの自分なりの解〜
usecase層より下層でのやりとりでObservableを扱うことについて
ここらへんも参考にしたい