具有自定义类型依赖属性的用户控件(绑定)
我目前编写了一个图像查看器控件,它封装了 WPF 图像控件和其他内容(用于应用过滤器和更改视图的控件)。以下是控件源代码的相关部分:
public partial class ImageViewPort : UserControl, INotifyPropertyChanged
{
private BitmapSource _source;
public static readonly DependencyProperty ImageDescriptorSourceProperty =
DependencyProperty.Register("ImageDescriptorSource",
typeof(ImageDescriptor),
typeof(ImageViewPort),
new UIPropertyMetadata(ImageDescriptorSourceChanged));
public ImageDescriptor ImageDescriptorSource
{
get { return (ImageDescriptor)GetValue(ImageDescriptorSourceProperty); }
set { SetValue(ImageDescriptorSourceProperty, value); }
}
public BitmapSource Source //the image control binds to this beauty!
{
get { return _source; }
set { _source = value; OnPropertyChanged("Source"); }
}
public ImageViewPort() { InitializeComponent(); }
private static void ImageDescriptorSourceChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
ImageViewPort viewPort = (ImageViewPort)d;
if (viewPort != null)
{
viewPort.TransformImage();
}
}
private BitmapSource TransformImage()
{
//do something that sets the "Source" property to a BitmapSource
}
}
用户控件的 XAML 代码(仅相关部分):
<UserControl x:Name="viewPort">
<Image Source="{Binding ElementName=viewPort,Path=Source}"/>
</UserControl>
最后是用法:
<WPF:ImageViewPort ImageDescriptorSource="{Binding Path=CurrentImage}"/>
在我的窗口中,我基本上迭代一个 Collection,并且在这样做时,为 CurrentImage 属性抛出 PropertyChanged 通知。这有效,每次都会调用 getter,因此绑定似乎有效。
我现在期望发生的是我的 UserControl 的 PropertyChanged-Callback 被触发,但没有发生这样的事情(它永远不会介入那里,我已经尝试使用断点)。我尝试过同样的方法来绑定原始类型(int),并且成功了。
您发现我的实施有任何缺陷吗?为什么用户控件不更新? 预先非常感谢您的帮助!
干杯
塞比
I currently write an image viewer control that encapsulates a WPF Image Control and further stuff (Controls for applying filters and changing views). Here's the relevant portion of control's source code:
public partial class ImageViewPort : UserControl, INotifyPropertyChanged
{
private BitmapSource _source;
public static readonly DependencyProperty ImageDescriptorSourceProperty =
DependencyProperty.Register("ImageDescriptorSource",
typeof(ImageDescriptor),
typeof(ImageViewPort),
new UIPropertyMetadata(ImageDescriptorSourceChanged));
public ImageDescriptor ImageDescriptorSource
{
get { return (ImageDescriptor)GetValue(ImageDescriptorSourceProperty); }
set { SetValue(ImageDescriptorSourceProperty, value); }
}
public BitmapSource Source //the image control binds to this beauty!
{
get { return _source; }
set { _source = value; OnPropertyChanged("Source"); }
}
public ImageViewPort() { InitializeComponent(); }
private static void ImageDescriptorSourceChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
ImageViewPort viewPort = (ImageViewPort)d;
if (viewPort != null)
{
viewPort.TransformImage();
}
}
private BitmapSource TransformImage()
{
//do something that sets the "Source" property to a BitmapSource
}
}
The XAML Code (only relevant parts) of the user control:
<UserControl x:Name="viewPort">
<Image Source="{Binding ElementName=viewPort,Path=Source}"/>
</UserControl>
And finally the usage:
<WPF:ImageViewPort ImageDescriptorSource="{Binding Path=CurrentImage}"/>
In my window, I basically iterate a Collection and, as I do so, throw PropertyChanged notification for the CurrentImage property. That works, the getter is called each time, so the binding seems to work.
What I would expect to happen now is that the PropertyChanged-Callback of my UserControl is fired, but no such thing happens (It never steps in there, I've tried using breakpoints). I've tried the same thing binding a primitive type (int), and that worked.
Do you see any flaw in my implementation? Why isn't the user control updating?
Thanks a lot in advance for any help!
Cheers
Sebi
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
检查输出...您收到任何绑定警告吗?您还设置新值吗? WPF 知道您何时尝试设置已设置的值并忽略它。我建议将元数据类型更改为 FrameworkPropertyMetadata 并提供适当的默认值。
要赋予此“注释”更多价值:在绑定上添加“PresentationTraceSources.TraceLevel=High”会提供有关绑定如何尝试获取其值的更多信息,这也有很大帮助,可以发现对 WPF 来说不是错误的问题。
Check the output ... do you get any binding warnings? Also are you setting a new value? WPF knows when you try to set a value that is already set and ignores it. I would suggest thange the Metadata type to FrameworkPropertyMetadata and supply a proper default value.
To give this "comment" more value: Adding "PresentationTraceSources.TraceLevel=High" on the binding gives alot more information about how the binding tries to get its value, which also helps alot, finding problems that are not errors for WPF.