如何这是一个DataTemplate内部控制的(依赖)属性通过绑定? [英] How to programmatically bind a (dependency) property of a control that's inside a DataTemplate?

查看:478
本文介绍了如何这是一个DataTemplate内部控制的(依赖)属性通过绑定?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

的TextBlock 驻留在的DataTemplate ,所以我不能用它的名字引用它。那么,如何约束其(例如)文本属性编程?

The TextBlock resides in a DataTemplate, thus I can't refer to it by its name. So how do I bind its (e.g.) Text property programmatically?

XAML:

<UserControl x:Class="MyNameSpace.MyCustomControl" ... >
    ...
    <ListBox ItemsSource="{Binding Path=ItemsSource}">
        <ListBox.ItemTemplate>
            <DataTemplate>
                <StackPanel Orientation="Horizontal">
                    <TextBlock/>
                </StackPanel>
            </DataTemplate>
        </ListBox.ItemTemplate>
    </ListBox>
    ...
</UserControl>

code:

public partial class MyCustomControl : UserControl {
    ...

    public static readonly DependencyProperty DataSourceProperty =
        DependencyProperty.Register("DataSource", typeof (IEnumerable),
                                    typeof (MyCustomControl),
                                    new PropertyMetadata(default(IEnumerable)));

    public IEnumerable DataSource {
        get { return (IEnumerable) GetValue(DataSourceProperty); }
        set { SetValue(DataSourceProperty, value); }
    }

    public static readonly DependencyProperty MemberPathProperty =
        DependencyProperty.Register("MemberPath", typeof (string),
                                    typeof (MyCustomControl),
                                    new PropertyMetadata(default(string)));

    public string MemberPath {
        get { return (string) GetValue(MemberPathProperty); }
        set { SetValue(MemberPathProperty, value); }
    }
    ...
    public MyCustomControl() {
        InitializeComponent();

        var binding = new Binding(MemberPath);
        BindingOperations.SetBinding(/*how do I refer to the TextBlock here ???*/,
                                     TextBox.TextProperty, binding);
    }
    ...
}

预期用法示例:

<my:MyCustomControl DataSource="{Binding Path=SomeModelCollection}" MemberPath="Name"

其中, SomeModelCollection 一些数据模型属性如的ObservableCollection&LT; SomeModel&GT; SomeModel 有一个叫做物业名称

Where SomeModelCollection is some data-model property like ObservableCollection<SomeModel> (SomeModel has a property called Name)

推荐答案

您可以得到的TextBlock 使用 VisualTreeHelper 。这种方法将让你在ListBoxItem中的视觉树中的所有TextBlockes present:

You can get TextBlock using VisualTreeHelper. This method will get you all TextBlockes present in Visual tree of listBoxItem:

public IEnumerable<T> FindVisualChildren<T>(DependencyObject depObj)
            where T : DependencyObject
{
   if( depObj != null )
   {
       for( int i = 0; i < VisualTreeHelper.GetChildrenCount( depObj ); i++ )
       {
          DependencyObject child = VisualTreeHelper.GetChild( depObj, i );
          if( child != null && child is T )
          {
              yield return (T)child;
          }

          foreach( T childOfChild in FindVisualChildren<T>( child ) )
          {
             yield return childOfChild;
          }
       }
    }
}

用法:

TextBlock textBlock = FindVisualChildren<TextBlock>(listBoxItem)
                       .FirstOrDefault();

但是我还是建议做在code后面做,而不是在XAML的约束力。

在案件的ItemSource 的ObservableCollection&LT;为MyModel&GT; 为MyModel 包含属性名称,它可以在XAML中做过这样的:

In case ItemSource is ObservableCollection<MyModel> and MyModel contains property Name, it can be done in XAML like this:

<DataTemplate>
   <StackPanel Orientation="Horizontal">
      <TextBlock Text="{Binding Name}"/>
   </StackPanel>
 </DataTemplate>

由于的DataContext ListBoxItem的将是为MyModel ,因此你可以直接绑定到名称,如上面提到的属性。

Since DataContext of ListBoxItem will be MyModel, hence you can bind directly to Name property like mentioned above.

这篇关于如何这是一个DataTemplate内部控制的(依赖)属性通过绑定?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆