如何在 WPF 中使用命令






4.61/5 (36投票s)
本文档展示了如何在 WPF 中使用命令。
引言
在本文中,我们将讨论 WPF 命令。当我使用 WPF 开发新应用程序时,我尝试遵循 MVVM 模式(模型-视图-ViewModel)。为了帮助我实现这一点,我使用了 Laurent Bugnion 分享的工具包:MVVM Light Toolkit (Galasoft)。无论有或没有工具包,其思想都是相同的。
使用代码
为了向您展示如何使用命令,我们将创建一个简单的应用程序,用于保存有关人员的一些信息。
因此,可以使用以下字段来描述一个人
- LastName
- FirstName
- 地址
- 邮政编码
- 城市
“保存”按钮将调用 SaveCommand
,“取消”按钮将调用 CancelCommand
。我们首先创建我们的模型,在 Model 目录中添加一个 Person
类。保持简单:
public class Person
{
public string LastName { get; set; }
public string FirstName { get; set; }
public string Address { get; set; }
public string ZipCode { get; set; }
public string City { get; set; }
}
然后我们创建我们的 ViewModel:我将简单地修改为 MainWindow
创建的模板。我只是编辑它以添加所需的属性
public class MainViewModel : ViewModelBase
{
private readonly Person _newPerson;
private const string LastNamePropertyName = "LastName";
public string LastName
{
get { return _newPerson.LastName; }
set
{
_newPerson.LastName = value;
RaisePropertyChanged(LastNamePropertyName);
}
}
private const string FirstNamePropertyName = "FirstName";
public string FirstName
{
get
{
return _newPerson.FirstName;
}
set
{
_newPerson.FirstName = value;
RaisePropertyChanged(FirstNamePropertyName);
}
}
private const string AddressPropertyName = "Address";
public string Address
{
get
{
return _newPerson.Address;
}
set
{
_newPerson.Address = value;
RaisePropertyChanged(AddressPropertyName);
}
}
private const string ZipCodePropertyName = "ZipCode";
public string ZipCode
{
get
{
return _newPerson.ZipCode;
}
set
{
_newPerson.ZipCode = value;
RaisePropertyChanged(ZipCodePropertyName);
}
}
private const string CityPropertyName = "City";
public string City
{
get
{
return _newPerson.City;
}
set
{
_newPerson.City = value;
RaisePropertyChanged(CityPropertyName);
}
}
///
/// Initializes a new instance of the MainViewModel class.
///
public MainViewModel()
{
_newPerson = new Person();
}
}
让我们创建 UI。 我们将在 MainWindow.xaml 中创建一个简单的表单
<Grid Height="195">
<Grid.RowDefinitions>
<RowDefinition Height="30" />
<RowDefinition Height="30" />
<RowDefinition Height="30" />
<RowDefinition Height="30" />
<RowDefinition Height="30" />
<RowDefinition Height="Auto" />
<RowDefinition Height="42*" />
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="122*" />
<ColumnDefinition Width="296*" />
</Grid.ColumnDefinitions>
<Label Content="LastName" Grid.RowSpan="2" Height="28" HorizontalAlignment="Left"
Margin="40,5,0,0" Name="label1" VerticalAlignment="Top" />
<Label Content="FirstName" Grid.Row="1" Grid.RowSpan="2" Height="28"
HorizontalAlignment="Left" Margin="40,5,0,0" Name="label2"
VerticalAlignment="Top" />
<Label Content="Address" Grid.Row="2" Grid.RowSpan="2" Height="28"
HorizontalAlignment="Left" Margin="40,5,0,0"
Name="label3" VerticalAlignment="Top" />
<Label Content="Code Postal" Grid.Row="3" Grid.RowSpan="2"
Height="28" HorizontalAlignment="Left" Margin="40,5,0,0"
Name="label4" VerticalAlignment="Top" />
<Label Content="City" Grid.Row="4" Grid.RowSpan="3" Height="28"
HorizontalAlignment="Left" Margin="40,5,0,0"
Name="label5" VerticalAlignment="Top" />
<TextBox Grid.Column="1" Grid.RowSpan="2" Height="23" HorizontalAlignment="Left"
Margin="20,5,0,0" Name="textBox1" VerticalAlignment="Top"
Width="120" Text="{Binding Path=LastName}" />
<TextBox Grid.Column="1" Grid.Row="1" Grid.RowSpan="2" Height="23"
HorizontalAlignment="Left" Margin="20,5,0,0" Name="textBox2"
VerticalAlignment="Top" Width="120" Text="{Binding Path=FirstName}" />
<TextBox Grid.Column="1" Grid.Row="2" Grid.RowSpan="2" Height="23"
HorizontalAlignment="Left" Margin="20,5,0,0" Name="textBox3"
VerticalAlignment="Top" Width="120" Text="{Binding Path=Address}" />
<TextBox Grid.Column="1" Grid.Row="4" Height="23" HorizontalAlignment="Left"
Margin="20,5,0,0" Name="textBox4" VerticalAlignment="Top"
Width="120" Text="{Binding Path=City}" />
<TextBox Grid.Column="1" Grid.Row="3" Grid.RowSpan="2" Height="23"
HorizontalAlignment="Left" Margin="20,5,0,0" Name="textBox5"
VerticalAlignment="Top" Width="120" Text="{Binding Path=ZipCode}" />
<Button Content="Save" Grid.Column="1" Grid.Row="6" Height="23"
HorizontalAlignment="Left" Margin="25,10,0,0" Name="button1"
VerticalAlignment="Top" Width="75" />
<Button Content="Cancel" Grid.Column="1" Grid.Row="6" Height="23"
HorizontalAlignment="Left" Margin="120,10,0,0" Name="button2"
VerticalAlignment="Top" Width="75" />
</Grid>
它应该如下所示
现在,本文档的主要原因:命令。我们将创建两个命令,然后将它们绑定到我们的按钮。我们如何定义一个命令?首先,该命令应实现 ICommand
接口。然后,一个 Create
方法将创建该命令,以便我们可以使用它。然后,我们找到两种方法:第一种,CanExecute
,将检查是否可以执行该命令,第二种,Execute
,将执行该命令。
保存命令
public ICommand SaveCommand
{
get;
internal set;
}
private bool CanExecuteSaveCommand()
{
return !string.IsNullOrEmpty(LastName);
}
private void CreateSaveCommand()
{
SaveCommand = new RelayCommand(SaveExecute, CanExecuteSaveCommand);
}
public void SaveExecute()
{
Person.Save(_newPerson);
}
如果我们查看 CanExecute
方法,我们可以看到只有在存在姓氏时才允许执行。
现在,我们在 ViewModel 的构造函数中添加方法的创建
public MainViewModel()
{
_newPerson = new Person();
CreateSaveCommand();
}
并将我们的命令绑定到“保存”按钮
<Button Content="Save" Grid.Column="1" Grid.Row="6" Height="23"
HorizontalAlignment="Left" Margin="25,10,0,0"
Name="button1" VerticalAlignment="Top"
Width="75" Command="{Binding Path=SaveCommand}" />
让我们启动应用程序并测试此命令。
当应用程序启动时,当然,LastName 是空的。 您可以看到“保存”按钮已禁用,我们无法保存
我们添加一个姓氏并将焦点设置在以下文本框上,我们可以观察到“保存”按钮现在已启用。 CanExecute
中的条件返回 true
!
如果我们删除姓氏并更改焦点,按钮将再次禁用。
现在,我们添加“取消”命令。它的工作方式与“保存”命令相同,但没有要求允许该操作。因此,我们将不使用 CanExecute
方法
public ICommand CancelCommand
{
get;
internal set;
}
private void CreateCancelCommand()
{
CancelCommand = new RelayCommand(CancelExecute);
}
public void CancelExecute()
{
LastName = string.Empty;
FirstName = string.Empty;
Address = string.Empty;
ZipCode = string.Empty;
City = string.Empty;
}
在 Execute
方法中,我们清空所有文本框。填写信息并单击“取消”按钮,所有文本框都将被清除。不要忘记在构造函数中调用 CreateCancelCommand
方法并将命令绑定到“取消”命令。构造函数
public MainViewModel()
{
_newPerson = new Person();
CreateSaveCommand();
CreateCancelCommand();
}
取消按钮绑定
<Button Content="Cancel" Grid.Column="1" Grid.Row="6" Height="23"
HorizontalAlignment="Left" Margin="120,10,0,0" Name="button2" VerticalAlignment="Top"
Width="75" Command="{Binding Path=CancelCommand}" />
这是一个在 WPF 中使用命令的非常简单的示例。 让我们试试!
关注点
WPF 命令在多种方式上都非常有用。 在这里您看到了如何使用它,现在您可以尝试发现可以使用它们做什么。
历史
- 2011 年 8 月 9 日:首次发布。