WPF(1) – 將 WinForm 改成 WPF

使用 WinForm 寫一個字串反轉的範例 :

新增 WPF 專案,在畫面建立三個控制項 :

  • TextBox
  • Button
  • TextBlock

使用 ViewModel

建立 ViewModel

WPF 使用 Window.DataContext 將 ViewModel 繫結到 View

  • 因為 ReverseStringViewModel 的 namespace 在 WpfApp1.ViewModels 底下, 所以創建了一個 xmlns:vm 指向該 namespace
  • Window.DataContext 設定 DataContext 的 ViewModel
  • 在 TextBox 使用 Binding 繫結 ViewModel 的屬性

為了方便識別,在 TextBlock 也使用 {{Binding InutString}}

測試的時候可以發現,只有觸發按鈕的時候,才會呼叫寫回資料到 ViewModel

INotifyPropertyChanged

為了讓資料可以即時更新,需要讓 ViewModel 繼承實作 INotifyPropertyChanged

完成之後,回到 Binding 的地方,增加一個屬性 UpdateSourceTrigger=PropertyChanged

此時畫面輸入值的時候,底下的 TextBlock 也會跟著更新

ICommand

在 WPF 可以使用 WinForm 的 Click 事件,但為了可以讓他與介面分離,實作到 ViewModel ,提供了 ICommand 介面

先修正 ViewModel 的 ReverseString 與畫面的 TextBlock 改 Binding ReverseString

ICommand 需要兩個方法,但如果只為了這功能,每個 ICommand 都要繼承並實作一個 xxxComand 其實很費工,所以通常會建立一個 RelayCommand

RelayCommand 有各種版本

來源 : https://www.c-sharpcorner.com/UploadFile/20c06b/icommand-and-relaycommand-in-wpf/

    public class RelayCommand : ICommand
    {
        private Action<object> execute;
        private Func<object, bool> canExecute;

        public event EventHandler CanExecuteChanged
        {
            add { CommandManager.RequerySuggested += value; }
            remove { CommandManager.RequerySuggested -= value; }
        }

        public RelayCommand(Action<object> execute, Func<object, bool> canExecute = null)
        {
            this.execute = execute;
            this.canExecute = canExecute;
        }

        public bool CanExecute(object parameter)
        {
            return this.canExecute == null || this.canExecute(parameter);
        }

        public void Execute(object parameter)
        {
            this.execute(parameter);
        }
    }

使用 Command

執行結果 :

參考 :

https://www.c-sharpcorner.com/UploadFile/20c06b/icommand-and-relaycommand-in-wpf/

http://blog.sanc.idv.tw/2011/12/wpf-mvvm.html

http://blog.sanc.idv.tw/2011/12/wpf-mvvm_29.html

http://blog.sanc.idv.tw/2011/12/wpf-mvvm_31.html

print

發佈留言

發佈留言必須填寫的電子郵件地址不會公開。 必填欄位標示為 *