wpf 如何从 XAML 访问代码中的对象
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/15211829/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How to access objects in code from XAML
提问by JNygren
I am new to WPF and am trying to understand how to use data binding to bind the controls on my window to objects in my code behind. I see several questions about accessing XAML objects from the codebehind, but that's not what I'm looking for. I already know how to do that.
我是 WPF 的新手,正在尝试了解如何使用数据绑定将窗口上的控件绑定到我后面代码中的对象。我看到几个关于从代码隐藏访问 XAML 对象的问题,但这不是我要找的。我已经知道该怎么做了。
label1.Content = LabelText;
listbox1.ItemsSource = ListItems;
I have also seen answers about how to access a class in the codebehind from XAML.
我还看到了有关如何从 XAML 访问代码隐藏中的类的答案。
<local:MyClass x:Key="myClass" />
But I don't see how to apply that to a specific instance of the class. Here is an example of what I'm trying to do. The 'Bindings' are obviously incorrect. That is what I need help with.
但我不知道如何将其应用于类的特定实例。这是我正在尝试做的一个例子。“绑定”显然是不正确的。这就是我需要帮助的。
public partial class MainWindow : Window
{
private string _labelText;
private List<string> _listItems = new List<string>();
public MainWindow()
{
InitializeComponent();
_labelText = "Binding";
_listItems.Add("To");
_listItems.Add("An");
_listItems.Add("Object");
}
public string LabelText
{
get { return _labelText; }
set { _labelText = value; }
}
public List<string> ListItems
{
get { return _listItems; }
set { _listItems = value; }
}
}
<Window x:Class="SO_Demo.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="SO Demo" Height="160" Width="225">
<Grid DataContext="MainWindow">
<Label x:Name="label1" Width="80" Height="25" Margin="12,12,0,0"
Content="{Binding Path=LabelText}"
HorizontalAlignment="Left" VerticalAlignment="Top" />
<ListBox x:Name="listbox1" Width="100" Height="60" Margin="12,44,0,0"
ItemsSource="{Binding Path=ListItems}" DisplayMemberPath="ListItems"
HorizontalAlignment="Left" VerticalAlignment="Top" />
</Grid>
</Window>
The books and tutorials I have read make it sound like this should be very simple. What am I missing?
我读过的书籍和教程听起来应该很简单。我错过了什么?
回答by Brian S
While you can DataBinddirectly to the class in the manner you're attempting, it is not how this is commonly done. The recommended approach is to create an object (ViewModel) that aggregates all the model data you want displayed in your UI, and then set that ViewModel as the DataContextof your View (Window in this case). I would recommend reading about MVVM, which is how most WPF application are built. But the example below can get you started.
虽然您可以DataBind按照您尝试的方式直接进入课程,但这并不是通常的做法。推荐的方法是创建一个对象 (ViewModel) 来聚合您希望在 UI 中显示的所有模型数据,然后将该 ViewModel 设置DataContext为您的视图(在本例中为窗口)的。我建议阅读有关 MVVM 的内容,这是大多数 WPF 应用程序的构建方式。但是下面的示例可以帮助您入门。
Here is a simple example based on your sample above:
这是一个基于上述示例的简单示例:
ViewModel
视图模型
public class MyViewModel : INotifyPropertyChanged
{
private string _title;
private ObservableCollection<string> _items;
public string LabelText
{
get { return _title; }
set
{
_title = value;
this.RaisePropertyChanged("Title");
}
}
public ObservableCollection<string> ListItems {
get { return _items; }
set
{
_items = value; //Not the best way to populate your "items", but this is just for demonstration purposes.
this.RaisePropertyChanged("ListItems");
}
}
//Implementation of INotifyPropertyChanged
public event PropertyChangedEventHandler PropertyChanged;
protected void RaisePropertyChanged(string propertyName)
{
if (PropertyChanged != null)
PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
}
}
CodeBehind
代码隐藏
public partial class MainWindow : Window
{
private MyViewModel _viewModel;
public MainWindow()
{
InitializeComponent();
_viewModel = new MyViewModel();
//Initialize view model with data...
this.DataContext = _viewModel;
}
}
View (Window)
视图(窗口)
<Window x:Class="SO_Demo.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="SO Demo" Height="160" Width="225">
<Grid>
<Label x:Name="label1" Width="80" Height="25" Margin="12,12,0,0" Content="{Binding Path=LabelText}"
HorizontalAlignment="Left" VerticalAlignment="Top" />
<ListBox x:Name="listbox1" Width="100" Height="60" Margin="12,44,0,0"
ItemsSource="{Binding Path=ListItems}"
HorizontalAlignment="Left" VerticalAlignment="Top" />
</Grid>
</Window>
回答by Federico Berasategui
<Grid DataContext="MainWindow">is invalid.
<Grid DataContext="MainWindow">是无效的。
If you want to reference the window you must either:
如果要引用该窗口,则必须:
<Window x:Name="MyWindow">
<Grid DataContext="{Binding ElementName=MyWindow}"/>
</Window>
or
或者
<Grid DataContext="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type Window}}}"/>

