gpt4 book ai didi

c# - 绑定(bind)ListBox中Usercontrol的DependencyProperty

转载 作者:太空宇宙 更新时间:2023-11-03 15:56:08 24 4
gpt4 key购买 nike

我需要列表框,其中列出了我的用户控件。我的 UserControl 有文本框。所以我想在用户控件的文本框中显示列表子项的属性。我用 DataContext 和 ElementName 尝试了很多选项 - 它只是不起作用。我只是坚持下去。使其工作的唯一方法是删除 UserControl 与其自身的 DataContext 绑定(bind)并更改 Item 属性名称,使其与 DependencyProperty 名称匹配 - 但我需要在具有不同实体的不同 View 模型中重用我的控件,因此几乎不可能使用方法。

有趣的是,如果我将我的 UserControl 更改为 Textbox 并绑定(bind)它的 Text 属性 - 一切正常。 Textbox 和我的 UserControl 有什么区别?

所以让我展示一下我的代码。我简化了代码以仅显示必要的内容:

控制 XAML:

<UserControl x:Class="TestControl.MyControl"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
mc:Ignorable="d"
d:DesignHeight="100" d:DesignWidth="200"
DataContext="{Binding RelativeSource={RelativeSource Self}}">
<Grid>
<TextBlock Text="{Binding Text}"/>
</Grid>
</UserControl>

控制CS:

    public partial class MyControl : UserControl
{
public MyControl()
{
InitializeComponent();
}
public string Text
{
get {
return (string)this.GetValue(TextProperty); }
set {
this.SetValue(TextProperty, value); }
}
public static DependencyProperty TextProperty = DependencyProperty.Register("Text", typeof(string), typeof(MyControl), new propertyMetadata(""));
}

窗口 XAML:

<Window x:Class="TestControl.MainWindow"
Name="_windows"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="clr-namespace:TestControl"
Title="MainWindow" Height="350" Width="525" >
<Grid Name="RootGrid">
<ListBox ItemsSource="{Binding ElementName=_windows, Path=MyList}">
<ItemsControl.ItemTemplate >
<DataTemplate >
<local:MyControl Text="{Binding Path=Name}"/>
</DataTemplate>
</ItemsControl.ItemTemplate>
</ListBox>
</Grid>
</Window>

窗口CS:

public partial class MainWindow : Window
{
public MainWindow()
{
_list = new ObservableCollection<Item>();
_list.Add(new Item("Sam"));
_list.Add(new Item("App"));
_list.Add(new Item("H**"));
InitializeComponent();

}
private ObservableCollection<Item> _list;

public ObservableCollection<Item> MyList
{
get { return _list;}
set {}
}
}
public class Item
{
public Item(string name)
{
_name = name;
}

private string _name;

public string Name
{
get { return _name; }
set { _name = value; }
}
}

最佳答案

这是 XAML 中一个相当大的陷阱。问题是当您在用户控件中执行此操作时:

DataContext="{Binding RelativeSource={RelativeSource Self}}"

您更改其数据上下文,以便在这一行中:

<local:MyControl Text="{Binding Path=Name}"/>

运行时现在将尝试在“MyControl”的实例上解析“Name”,而不是在继承的数据上下文(即 View 模型)上。 (通过检查“输出”窗口来确认这一点——您应该会看到与该效果相关的绑定(bind)错误。)

您可以通过使用 RelativeSource 绑定(bind)来解决此问题,而不是以这种方式设置用户控件的数据上下文:

<UserControl x:Class="TestControl.MyControl"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
mc:Ignorable="d"
d:DesignHeight="100" d:DesignWidth="200"
<Grid>
<TextBlock
Text="{Binding Text,RelativeSource={RelativeSource AncestorType=UserControl}}"
/>
</Grid>
</UserControl>

关于c# - 绑定(bind)ListBox中Usercontrol的DependencyProperty,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/23476751/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com