Help us understand the problem. What is going on with this article?

Prism入門 その2 - NavigationService

はじめに

Prism入門2回目です。

今回は画面遷移を行うためのNavigationServiceについて説明します。

Xamarin.Formsでは画面遷移にNavigation.PushAsyncを使用します。
ただ、このメソッドはContentPageクラスのメソッドであり、MVVMの層でいうとViewに存在します。
Viewは画面を描画する機能しか持たないのに画面遷移の機能をViewで行うのはおかしいです。

そこで、XamarinにはNavigationServiceという機能が存在します。
これはViewModelで画面遷移を行えるようにする機能です。

一旦、画面遷移はViewModelでやるべきか、という話は置いておきましょう。

今回はNavigationServiceについて説明します。

NavigationServiceの生成と使用

NavigationServiceはコンストラクタの引数に
INavigationService navigationService と記述すると
自動的にクラスが生成された時にNavigationServiceも生成されます。

コンストラクタ内で画面遷移を行うことはまずないので、メンバー変数に保存しておきます。

public class MainPageViewModel : BindableBase, INavigationAware
{
    INavigationService navigationService = null;

    public MainPageViewModel(INavigationService navigationService)
    {
        this.navigationService = navigationService;
    }
}

画面遷移する時は引数に遷移する先のViewのクラス名を指定します。
今回はNextPageに遷移するとします。

navigationService.NavigateAsync("NextPage");

これだけでは動きません。NextPageを遷移先として登録する必要があります。
登録はAppのRegisterTypes(IContainerRegistry containerRegistry)で行います。

public partial class App : PrismApplication
    {
        public App(IPlatformInitializer initializer = null) : base(initializer) { }

        protected override void OnInitialized()
        {
            InitializeComponent();

            NavigationService.NavigateAsync("MainPage");
        }

        protected override void RegisterTypes(IContainerRegistry containerRegistry)
        {
            containerRegistry.RegisterForNavigation<MainPage>();
            containerRegistry.RegisterForNavigation<NextPage>();
        }
    }

登録すると、NavigationServiceで画面遷移を行えるようになります。
文字列で画面遷移を行なっているため、画面同士は疎であると言えます。
(実際のところ文字列で指定しているので完璧に疎かと言われると微妙ですが)

遷移イベントとデータの受け渡し

画面遷移する時に下記のメソッドが呼び出されます。
画面Aから画面Bに移動しようとすると、
AのOnNavigatedFrom、BのOnNavigatingTo、Bの画面表示、BのOnNavigatedToの
順番に呼び出されます。
遷移するときの初期化や終了処理をここに書くと便利でしょう。
ただ、特定の条件(物理バックキー等)で遷移した時は呼び出されないので注意してください。
それらの条件については、OnNavigatingTo等のキーワードで検索すると見つかります。

public void OnNavigatedFrom(NavigationParameters parameters) {}

public void OnNavigatedTo(NavigationParameters parameters) {}

public void OnNavigatingTo(NavigationParameters parameters) {}

これらのメソッドはINavigationAwareのインターフェースで定義されています。
テンプレートでは最初からインターフェースが適用されてますが、自分でゼロから
書くときは、INavigationAwareを書き忘れないようにしましょう。

画面遷移するときに画面間でパラメーターを渡すこともできます。

遷移元ではnavigationParametersに値を加えます。

var navigationParameters = new NavigationParameters();
navigationParameters.Add("Key", "Value");
navigationService.NavigateAsync("NextPage", navigationParameters);

遷移先のOnNavigatedToやOnNavigatingToで受け取ります。

if (parameters.ContainsKey("Key")) {
    // なんらかの処理
}

遷移するときのアドレスの文字列に値を指定することもできます。

最後に

今回は機能の一部のみを紹介しました。
紹介してない機能として戻るの実装や画面遷移のキャンセルといった機能もあります。
興味あったら他の資料を探してみてください。

swd
Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
Comments
No comments
Sign up for free and join this conversation.
If you already have a Qiita account
Why do not you register as a user and use Qiita more conveniently?
You need to log in to use this function. Qiita can be used more conveniently after logging in.
You seem to be reading articles frequently this month. Qiita can be used more conveniently after logging in.
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
ユーザーは見つかりませんでした