【问题标题】:Binding DataContext to custom Control将 DataContext 绑定到自定义控件
【发布时间】:2015-06-01 12:46:32
【问题描述】:

我正在尝试在 DataGridTemplateColumn 内的自定义控件中绑定一个值,但绑定似乎不起作用。

我的 DataGridTemplateColumn :

<DataGridTemplateColumn Width="auto" SortMemberPath="Etat" CanUserReorder="False" CanUserResize="True" x:Name="colonneEtat">
                    <DataGridTemplateColumn.CellEditingTemplate>
                        <DataTemplate />
                    </DataGridTemplateColumn.CellEditingTemplate>
                    <DataGridTemplateColumn.CellTemplate>
                        <DataTemplate>
                            <widget:MyWidget MyObject="{Binding MyObjectVariable, Converter={StaticResource MyDebugConverter}}" Margin="5,0" VerticalAlignment="Center"/>
                        </DataTemplate>
                    </DataGridTemplateColumn.CellTemplate>
                </DataGridTemplateColumn>

我的自定义控件现在只包含一个 Grid,但它的属性定义如下:

public static readonly DependencyProperty MyObjectProperty=
            DependencyProperty.Register("MyObject",
            typeof(ObjectType),
            typeof(MyWidget),
            new PropertyMetadata(null));
public ObjectType MyObject
        {
            get { return (ObjectType)GetValue(MyObjectProperty); }
            set { 
                SetValue(MyObjectProperty, value);
                FillCustomControl();
            }
        }

Debug Converter 只是一个用于测试绑定的虚拟转换器:

public object Convert(object value, Type targetType,
               object parameter, CultureInfo culture)
        {
            System.Diagnostics.Debugger.Break();
            return value;
        }

我的自定义控件工作正常,我已经在我的应用程序的另一个地方尝试过。它的功能很简单:设置属性时,我根据属性中的内容填充自定义控件。如前所述,这种行为已经过测试。

但在此 DataGridTemplateColumn 的情况下,该属性永远不会设置。我在输出中没有任何绑定错误,并且调试器在转换器中停止 + 转换器中的值是预期的值。但由于某种原因,它没有在我的自定义控件中设置属性的值。

我错过了什么?

谢谢

【问题讨论】:

  • 我很困惑。您的MyObject 属性是在MyWidget 上定义的,但是您对MyWidget 的使用使用了一个名为ObjectProperty 的属性并尝试将其绑定到MyObjectObjectProperty 是什么?这个专栏在哪里?
  • 确实有两个同名对象……我已经改了,但还是不行。
  • 我并不是在暗示这就是它不起作用的原因,目前还不清楚您要做什么。我们仍然不知道MyObjectVariable 在哪里,您可能在内部使用MyWidget 中的DataContext' 等等。如果您可以提供minimal, complete, verifiable example 以便有人可以重现您的问题,这将很有帮助。答案最多只能是猜测。
  • 使用 snoop 我可以看到我的属性已设置,但我的属性的“设置”方法从未被调用,我想这就是问题所在。我将使用 Dependencyproperty 上的更改事件来解决此问题。

标签: c# wpf binding


【解决方案1】:

当数据绑定到它时,你应该省略DependencyPropertyProperty 部分,所以不要这样:

<widget:MyWidget ObjectProperty="{Binding MyObject ... }" />

你应该使用这个:

<widget:MyWidget MyObject="{Binding MyObject ...}" />

除非您实际上在您的 Widget 类中定义了另一个名为 ObjectPropertyPropertyDependencyProperty。另外,根据您的代码,为DataGrid 设置为DataContext 的对象也应该有一个名为MyObject 的属性。


更新>>>

好的,现在我了解您的问题了。也就是说,与DependencyProperty 相关的CLR 属性的设置器从不 被框架调用...该CLR 属性仅供您的 使用。如果您想在DependencyProperty 值更改时执行某些操作,则需要设置PropertyChangedCallback handler。您可以这样做(来自 MSDN 上的链接页面):

public static readonly DependencyProperty AquariumGraphicProperty = DependencyProperty.Register(
  "AquariumGraphic",
  typeof(Uri),
  typeof(AquariumObject),
  new FrameworkPropertyMetadata(null,
      FrameworkPropertyMetadataOptions.AffectsRender, 
      new PropertyChangedCallback(OnUriChanged)
  )
);

private static void OnUriChanged(DependencyObject d, DependencyPropertyChangedEventArgs e) {
  Shape sh = (Shape) d;
  sh.Fill = new ImageBrush(new BitmapImage((Uri)e.NewValue));
}

事实上,你甚至可以忽略 PropertyChangedCallback 构造函数并像这样声明它:

public static readonly DependencyProperty AquariumGraphicProperty = 
    DependencyProperty.Register("AquariumGraphic", typeof(Uri), typeof(AquariumObject), 
    new FrameworkPropertyMetadata(null, FrameworkPropertyMetadataOptions.AffectsRender, 
    OnUriChanged));

【讨论】:

  • 确实谢谢你,我粘贴代码时出错...已修复。该属性具有正确的名称,并且 MyObject 包含一个值(我可以在调试转换器中检查)。但是永远不会调用“集合”。我试图放置一个“对象”但同样的问题。
猜你喜欢
  • 2015-09-22
  • 2015-11-04
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-02-15
  • 2013-03-29
  • 2012-02-09
相关资源
最近更新 更多