かずきのBlog@hatena

すきな言語は C# + XAML の組み合わせ。Azure Functions も好き。最近は Go 言語勉強中。日本マイクロソフトで働いていますが、ここに書いていることは個人的なメモなので会社の公式見解ではありません。

InteractionRequestをRxに合流させる

こねたです。

こんなのを用意しておくと捗ります。

using Microsoft.Practices.Prism.Interactivity.InteractionRequest;
using System;
using System.Reactive.Disposables;
using System.Reactive.Linq;

namespace WpfApplication7
{
    public static class InteractionRequestExtensions
    {
        public static IObservable<T> RaiseAsObservable<T>(this InteractionRequest<T> self, T n)
            where T : INotification
        {
            return Observable.Create<T>(o =>
            {
                self.Raise(n, result => o.OnNext(result));
                return Disposable.Empty;
            });
        }

    }
}

例えば、RxCommandが実行されたら確認ダイアログが出てOKが押されたときのみ何かをするといった処理が以下のように書ける!

public class MainWindowViewModel
{
    public ReactiveCommand ConfirmCommand { get; private set; }

    public InteractionRequest<Confirmation> ConfirmRequest { get; private set; }

    public MainWindowViewModel()
    {
        this.ConfirmRequest = new InteractionRequest<Confirmation>();
        this.ConfirmCommand = new ReactiveCommand();

        this.ConfirmCommand
            .SelectMany(_ => this.ConfirmRequest.RaiseAsObservable(new Confirmation
            {
                Title = "確認",
                Content = "コンテンツ"
            }))
            .Where(c => c.Confirmed)
            .Subscribe(_ =>
            {
                Debug.WriteLine("モデルのコードの呼び出し");
            });
    }
}

割といいかも