我需要将一些东西绑定到我的VisualTree中一个元素的子元素。
在UserControl中:
<StackPanel>
<DataGrid x:Name="dataGrid" />
<Control Tag="{Binding ElementName=dataGrid}" />
</StackPanel>
在DataGrid的模板中:
<Template TargetType=DataGrid>
......
<Control x:Name="FindMe" />
......
</Template>
我想要做的是遍历VisualTree of DataGrid,为此目的iv'e创建了一个自定义标记扩展:
public class TemplatePartBinding : MarkupExtension
{
public override object ProvideValue(IServiceProvider serviceProvider)
{
Binding binding = new Binding();
binding.ElementName = ElementName;
// HOW DO I GET THE SOURCE OBJECT FROM THE BINDING ?
DataGrid dataGrid = // Extract the DataGrid from the binding.
Control _findMe = VisualTreeHelperExtentions.FindVisualChild<Control>(dataGrid,"FindMe");
binding.Target = _findMe;
binding.Path = new PropertyPath("Tag");
return binding;
}
[ConstructorArgument("ElementName")]
public string ElementName
{
get;
set;
}
[ConstructorArgument("TemplatePartName")]
public string TemplatePartName
{
get;
set;
}
}
在ProvideValue中,在给出绑定的ElementName值(它的名称)之后,我不会定位DataGrid (绑定的源对象),
如何从刚刚创建的绑定iv'e中提取DependencyObject (我的DataGrid)?
发布于 2014-02-02 04:41:01
您可以在标记扩展中获取DataGrid
实例,提供值方法,但是您将无法使用VisualTree扩展方法获得DataGrid
实例,因为当调用该方法时,没有创建用于dataGrid的VisualTree。
此外,逻辑树也不会有任何帮助,因为Control是dataGrid的视觉子而不是逻辑子。
但是,要想找到dataGrid,您可以这样做:
public override object ProvideValue(IServiceProvider serviceProvider)
{
IRootObjectProvider provider = (IRootObjectProvider)serviceProvider
.GetService(typeof(IRootObjectProvider));
DataGrid dataGrid =
LogicalTreeHelper.FindLogicalNode((DependencyObject)provider.RootObject,
ElementName) as DataGrid;
....
}
IRootObjectProvider
将为您提供RootObject which will be UserControl
,并最终可以通过遍历LogicalTree而不是VisualTree获得DataGrid,因为它将返回null。(尚未创建可视树)。
https://stackoverflow.com/questions/21509716
复制相似问题