天天看點

了解 UWP 視圖的概念,讓 UWP 應用顯示多個視窗(多視圖)

原文 了解 UWP 視圖的概念,讓 UWP 應用顯示多個視窗(多視圖) UWP 應用多是一個視窗完成所有業務的,事實上我也推薦使用這種單一視窗的方式。不過,總有一些特别的情況下我們需要用到不止一個視窗,那麼 UWP 中如何使用多視窗呢?

本文内容

多視窗在傳統 Win32 的開發當中是司空見慣的事兒了,不過我個人非常不喜歡,因為 Windows 系統上的多視窗太多坑。以下是我以前寫的關于傳統多視窗開發中的一些坑(除此之外還有更多):

使用多視窗的原因很簡單 —— 允許使用者多任務處理。從這個角度來說,傳統 Win32 使用“模态”多視窗的方式簡直是低效的同時還帶來 Bug!

微軟官方文檔中列舉了一些例子:例如一邊寫郵件一邊參考以往的郵件;一邊看正在播放的音樂一邊浏覽播放清單;一次性打開多份文章然後稍後一起閱讀等。

在學習如何編寫 UWP 多視窗之前,我們需要了解一些 UWP 視圖(View)的概念。

在 

CoreApplication/Application、CoreWindow/Window 之間的差別

 一文中,我描述了 UWP 視圖的一些概念:

CoreApplication

 管理一個 UWP 應用中的所有視圖(View),而 

CoreApplication

直接管理的視圖是 

CoreApplicationView

;也就是說,UWP 應用 

CoreApplication

管理所有的應用視圖 

CoreApplicationView

。而一個 

CoreApplicationView

 包含一個視窗和一個線程排程模型,即 

CoreWindow

 和 

CoreDispatcher

CoreWindow

 就是我們所了解的視窗。為了友善使用,

Windows.UI.XAML.Window

 類型封裝了這個 

CoreWindow

CoreDispatcher

 是基于消息循環的線程排程模型,正是因為有了消息循環,是以此視窗才能一直顯示而不被銷毀。
為了了解 UWP 的啟動流程,我從零開始建立了一個 UWP 程式

 一文中,我們也能體會到 

CoreApplication

CoreWindow

 之間的關系,了解消息循環在應用中的作用。

在了解到 UWP 視圖的概念之後,嚴格意義上說,這一節的标題應該叫做 “UWP 多視圖”。

我畫了一個思維導圖來描述它們之間的關系。

CoreApplication

 有靜态方法 

CreateNewView

,調用後能夠建立新的 

CoreApplicationView

,這包含一個完整的 

CoreWindow

CoreDispatcher

建立并顯示一個新 

CoreApplicationView

 的代碼如下:

private async void OnLoaded(object sender, RoutedEventArgs e)
{
    // 建立一個 CoreApplicationView,即新的應用視圖。
    var applicationView = CoreApplication.CreateNewView();

    // 一個應用視圖有自己的 Id,稍後我們建立應用視圖的時候,需要記錄這個 Id。
    int newViewId = 0;

    // 使用新應用視圖的 CoreDispatcher 線程排程模型來執行新視圖中的操作。
    await applicationView.Dispatcher.RunAsync(CoreDispatcherPriority.Normal, () =>
    {
        // 在新的應用視圖中,我們将新的視窗内容設定為 ThePageInNewView 頁面。
        Frame frame = new Frame();
        frame.Navigate(typeof(ThePageInNewView), null);
        Window.Current.Content = frame;
        Window.Current.Activate();

        // 記錄新應用視圖的 Id,這樣才能稍後切換。
        newViewId = ApplicationView.GetForCurrentView().Id;
    });

    // 使用剛剛記錄的新應用視圖 Id 顯示新的應用視圖。
    var viewShown = await ApplicationViewSwitcher.TryShowAsStandaloneAsync(newViewId);
}
           

建立完後的效果如下圖:

我們平時開發 UWP 應用的時候很少去關心 

CoreApplicationView

,因為預設情況下 UWP 能為我們做很多管理應用視圖的工作。

CoreApplication

 有一個 

MainView

 屬性,即我們一開始運作 UWP 應用時的那個應用視圖。如果我們有不止一個應用視圖顯示出來,那麼這時點選主視窗的關閉按鈕将不再是關閉,而是隐藏。如果要關閉,需要調用 

Application.Exit

CoreApplication

 有 

Views

 屬性儲存所有的 

CoreApplicationView

,我們可以使用此集合來管理多個視圖。使用 

ApplicationViewSwitcher.SwitchAsync

 并傳入視圖 Id 可以切換視圖的顯示。

await ApplicationViewSwitcher.SwitchAsync(viewIdToShow);
           

本文會經常更新,請閱讀原文: 

https://walterlv.com/post/show-multiple-views-for-an-uwp-app.html

,以避免陳舊錯誤知識的誤導,同時有更好的閱讀體驗。

繼續閱讀