我有一个带有元素集合的简单控件。我想在 xaml 中添加元素并绑定到元素。
但是,当我在 xaml 中绑定到 Bar.Value 时,它永远不会起作用。最小的例子:
[ContentProperty("Bars")]
public class FooControl : Control
{
private ObservableCollection<IBar> _bars = new ObservableCollection<IBar>();
public ObservableCollection<IBar> Bars { get { return _bars; } }
}
public interface IBar
{
string Value { get; }
}
public class Bar : DependencyObject, IBar
{
public static readonly DependencyProperty ValueProperty = DependencyProperty.Register("Value", typeof(string), typeof(Bar), new PropertyMetadata("<not set>"));
public string Value
{
get { return (string)GetValue(ValueProperty); }
set { SetValue(ValueProperty, value); }
}
}
<Window x:Class="WpfTestApplication.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:this="clr-namespace:WpfTestApplication"
xmlns:sys="clr-namespace:System;assembly=mscorlib"
Title="MainWindow" Height="200" Width="1000">
<Window.Resources>
<Style TargetType="this:FooControl">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="this:FooControl">
<ItemsControl ItemsSource="{Binding Bars, RelativeSource={RelativeSource TemplatedParent}}">
<ItemsControl.ItemTemplate>
<DataTemplate>
<TextBlock Text="{Binding Value}"/>
</DataTemplate>
</ItemsControl.ItemTemplate>
</ItemsControl>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</Window.Resources>
<Window.DataContext>
<sys:String>from DataContext</sys:String>
</Window.DataContext>
<Grid>
<this:FooControl>
<this:Bar Value="directly set"/>
<this:Bar Value="{Binding Source=from_binding_source}"/>
<this:Bar Value="{Binding}"/>
<this:Bar Value="{Binding Text, ElementName=SomeTextBlock}"/>
</this:FooControl>
<TextBlock Text="from TextBox" Name="SomeTextBlock" Visibility="Collapsed"/>
</Grid>
</Window>
输出
directly set
from_binding_source
"<not set>"
"<not set>"
调试输出
System.Windows.Data 错误:2:找不到目标元素的管理 FrameworkElement 或 FrameworkContentElement。绑定表达式:路径=文本;数据项=空;目标元素是'Bar'(HashCode=26568931);目标属性是“值”(类型“字符串”)
任何建议如何让它工作?
我目前的解决方法是在代码中定义绑定,但这是更多代码,并且查看 xaml 并不明显存在哪些绑定。(请参阅我的解决方法代码的答案)