1. Journal 的使用
Journal 用于在 XAML 瀏覽器應用程序(XBAP)中維護歷史訪問頁。刪除前一訪問頁只需調當前 NavigationService 對象的 RemoveBackEntry() 即可;而增加一個訪問頁則復雜得多:
1) 實現一個 CustomContentState 的派生類,每個對象對應一個要保存的訪問頁,其中數據結構用于維護這個歷史訪問頁的數據,在構造的時候通過適當的參數傳入。它必須標上 Serializable() 屬性。在這個類里要重載一個 Replay 方法和一個 JournalEntryName。Replay 一般通過向構造時傳入的頁面回調提供數據,恢復出歷史頁面。JournalEntryName 就是這個項目顯示在訪問歷史下拉列表中的名稱。
2) 相關頁面需要實現 IProvideCustomContentState 接口。這個接口必須實現 GetContentState 函數,這個函數用于在當前頁面上發生瀏覽切換時對瀏覽服務 NavigationService 提供一個 CustomContentState。
3) 在需要保存的狀況下(如用戶對頁面進行變動時)對頁面調用 NavigationService.AddBackEntry 手動進行快照。
2. NavigationService 的事件
?
頁面瀏覽事件不是接力事件(Routed Events),且在一切的瀏覽過程中(如通過 NavigationService 調用或超鏈接訪問)均會發生。以下依次羅列一次頁面瀏覽發生的事件:
Navigating | 開始轉向指定的頁面 |
Navigated | 瀏覽啟動后但最終頁面送達之前發送的一個事件 |
NavigationProgress | 在頁面加載過程中每傳送1KB數據發生的一個事件 |
LoadCompleted | 頁面送達后發送的第一個事件 |
FragmentNavigation | 如果訪問指向目標頁面的某個單元,則在轉向該單元時發送這個事件 |
此外 NavigationStopped 和 NavigationFailed 分別表示 StopLoading 導致瀏覽取消(不包括在 Navigating 事件響應中 Cancel)和瀏覽目標頁面失敗的事件。
3. WPF的后臺任務
msdn 上有個例子值得一看,它同時詳細說明了 BackgroundWorker 和 Monitor 的使用:
http://msdn.microsoft.com/library/system.threading.monitor.pulse(VS.95).aspx
注意其中多個 m_worker 通過 ProgressChanged 回調對 outputBlock.Text 可以做到直接且互斥的訪問,說明 WPF 的后臺任務是一種不同于一般線程的特殊的機制(小范蛙注:很有可能是通過 Windows API 中的 SendMessage 或類似的機制,這種機制在 .NET Framework 中也有應用,即控件的 Invoke 方法,它通過在控件所在的窗口線程上 [而非調用它的線程上] 執行方法來避免非串行的調用)。如果不使用這個方法,就需要在線程中調 m_worker.ReportProgress 的地方改用調 outputBlock.Dispatcher.BeginInvoke 的方法更新 outputBlock 內容。
4. 工程中的Settings
在工程屬性中的 Settings 可以作為 Properties.Settings.Default 的同名屬性(由開發環境即時生成)直接訪問,并且類型一致。調用 Properties.Settings.Default.Save 方法即可保存。這和基于 XML 保存的 Application Settings 不同。(小范蛙補充:這個是自動生成的類,是強類型的,有助于避免程序引用不存在的設置項。)
5. 命令
命令相對事件來說比較獨立。命令的組成:
1) 命令定義:定義一個命令。類型為 RoutedUICommand,通常作為靜態屬性封裝在一個類中。
2) 命令綁定:連接命令和(多個)處理函數的橋梁。有代碼綁定(UIElement 的 CommandBindings 集合)和 XAML 直接綁定兩種方法。通過各層單元的命令綁定,實現命令上浮式(Bubbling)搜索。(注意,命令不同于事件接力,其傳遞過程中一旦遇到處理方法,就不再繼續傳遞,參考資料 2 似乎也報告了這個問題)
3) 命令激發:觸發命令的條件。主要有控件直接觸發(實現 ICommandSource 控件的 Command 屬性)、手勢觸發(命令的 InputGestures 集合,可在構造時添加)和代碼觸發(命令的 Execute 方法)三種方法。
6. 事件
接力事件(或路由事件,Routed Events)完全奉行下沉式(Tunneling)和上浮式(Bubbling)接力過程。事件處理方法可以通過 XAML 直接靜態綁定,或用 AddHandler(或 += 操作)動態綁定(小范蛙注:此處 AddHandler 不是指 VB.NET 的關鍵詞 AddHandler)。
參考資料
1. http://msdn.microsoft.com/magazine/cc785480.aspx#id0190070
2. http://social.msdn.microsoft.com/forums/wpf/thread/1fb817dc-4f6f-4d2c-8bdf-624b26a0ed45/
3. http://joshsmithonwpf.wordpress.com/2008/03/18/understanding-routed-commands/?(這則會導引至 CodeProject 和 MSDN 的幾篇比較深入的文章)