はじめに
私が作るアプリケーションはメイン画面と設定画面など複数の画面で構成されるのがほとんどです。
以前記事にしたIDialogServiceを使って設定ダイアログを出してもいいですが、手段は複数持っておき状況に合わせて使い分けしたいと思い、WinFormsでやった事のあるメインとなる部分の表示を切り替える手法をやってみます。
ソースファイルはこちら
新しいユーザーコントロールの追加
まずは新しいユーザーコントロールを2つ追加してみます。
理由は分かりませんが、Viewsフォルダで行わないとViewとViewModelのファイルがが正しく生成されませんので注意が必要です。
ソリューションエクスプローラーのViewsフォルダで右クリック-「追加」-「新しい項目」で表示されたダイアログより「Prism」-「WPF」のツリーを辿って行き、「Prism UserControl(WPF)」を選択し、分かりやすい名前でユーザーコントロールを作成します。
今回は「Page1」と「Page2」のユーザーコントロールを作成てみます。
DIコンテナの登録
App.xaml.csを開いてください。
そこにあるRegisterTypesメソッドに下記2行を追加しDIコンテナに表示するユーザーコントロールを登録します。
「Page1」と「Page2」が作ったユーザーコントロールです。
特に面倒な記述はありません。
これで終了です。
表示させる
メインウィンドウにページを切り替えるボタン2つと表示するページの領域を確保します。
コメント「登録されたページを表示」の下にある1行がDIコンテナに登録されたページを表示する部分です。
制御する
上記xamlではボタンが2つ配置されてますが、これを使ってページを切り替えてみます。
まずはボタンのCommandにBindingするReactiveCommandです。
ついでにボタン表示を抑制するための情報を持たせておきます。
もう1つ、MainWindowViewModel内で使用するIRegionManagerも準備しましょう。
コンストラクタで引数IRegionManagerを取得し上記で作成したMainWindowViewModel内で使用するIRegionManagerに入れときます。
コンストラクタは下記のようになります。
引数で得たregionManagerをprivate変数RegionManagerに入れておきます。
そして以下はコンストラクタ内で初期表示を行ったりボタンが押された時の表示制御を記述します。
RequestNavigateの引数にxamlのContentControlにあるRegionNameで示した名称と表示するページ名を渡します。
これで無事表示の切り替えは成功します。
各ページにある破棄しなければいけない変数の処理
各ページのViewModelクラスはIDisposableを継承すればアプリを閉じる時Disposeメソッドが呼ばれるかと期待してたのですが甘かったです。
ViewModelに終了処理を記述したメソッドを置いてMainWindowViewModelが終了する時(Closedイベント等をキャッチ)にそのメソッドを呼べば解決しますが、イマイチスマートではありません。
そこで各ページのViewModelはIDestructibleを継承しDestroyメソッドを置いて対処します。
これで各ページが破棄される時Destroyメソッドが呼び出され自分で破棄する動作を別で作る必要がなくなります。
但し各ページが破棄されるタイミングは自分で処理する必要があります。
ReactivePropertyを使ってれば終了時の破棄処理は必須?だと思うので同じ所で良いです。
RemoveAllが実行されると各ページのViewModelにあるDestroyメソッドが実行されます。
RemoveAllするのも破棄するメソッドを呼ぶのも手間は同じじゃない?といったツッコミはご遠慮くださいw
滅多に表示しないページは閉じたら破棄したい
各ページは一度開くとメモリ上に存在し続けます。
しかし設定画面などがそうですが、一度設定が決まれば二度と開かないページもあります。
そんなページは閉じたら破棄する事で無駄なメモリ消費を抑制できます。
そんな場合ViewModelはIRegionMemberLifetimeを継承し、下記の1行を追加してください。
これでページを閉じた(他のページが表示された)タイミングで破棄されます。
これで終わりですが,xamlに「ContentControl」を複数置いて必要なページだけを切り替えれば柔軟な表示ができるアプリが作れるかと思います。
0 件のコメント:
コメントを投稿