ikn*_*now 2 data-binding wpf xaml
ToolTip我尝试以这种方式绑定文本UserControl:
<Grid.ToolTip>
<TextBlock
Text="{
Binding Path=InfoTT,
RelativeSource={
RelativeSource Mode=FindAncestor,
AncestorType={x:Type UserControl}
}
}" />
</Grid.ToolTip>
Run Code Online (Sandbox Code Playgroud)
它不起作用,Tooltip是空的,在日志中,我看到:
System.Windows.Data 错误:4:无法找到引用“RelativeSource FindAncestor,AncestorType='System.Windows.Controls.UserControl”,AncestorLevel='1'' 进行绑定的源。BindingExpression:Path=InfoTT; 数据项=空;目标元素是“TextBlock”(名称=“”);目标属性是“文本”(类型“字符串”)*
但是当我这样做时:
<Grid
ToolTip="{
Binding Path=InfoTT,
RelativeSource={
RelativeSource Mode=FindAncestor,
AncestorType={x:Type UserControl}
}
}">
</Grid>
Run Code Online (Sandbox Code Playgroud)
有效。谁能解释为什么第一种方法不起作用?
当Binding.RelativeSource无法解决时,您始终可以确定它Binding.Target不是可视化树的一部分。
在您的第一个示例中,您显式定义了ToolTip. 您正在显式创建内容,例如通过添加TextBlock. 的内容ToolTip不是视觉树的一部分,因此Binding.RelativeSource无法解析。
在第二个示例中,您让FrameworkElement隐式创建ToolTip内容。
现在FrameWorkElement将首先解析Binding,它会解析,因为FrameworkElement仍然是可视化树的一部分。解析的值被获取、ToString调用、TextBlock创建并将字符串值分配给TextBlock.Text。
为了解决绑定问题,在ToolTip显式实现时,您可以按照 @Mark Feldman 的评论中的建议实现绑定代理,它利用标记为不属于可视化树的元素StaticResource提供 a 。
它基本上是一个可绑定的.Binding.SourceObjectDataProvider
与绑定代理类似的解决方案是将内容定义为 的资源Grid,然后通过DynamicResource使用引用它ContentPresnter:
<UserControl>
<Grid>
<Grid.Resources>
<!-- The proxy -->
<TextBlock x:Key="ToolTipText"
Text="{Binding RelativeSource={RelativeSource AncestorType=UserControl}, Path=InfoTT}" />
<Grid.ToolTip>
<ToolTip>
<ContentPresenter Content="{DynamicResource ToolTipText}" />
</ToolTip>
</Grid.ToolTip>
</Grid>
</UserControl>
Run Code Online (Sandbox Code Playgroud)
但您也可以利用DataContext仍然继承的事实。对遗嘱的绑定DataContext仍会解析。
在您的场景中,如果您想要将 的内容绑定ToolTip到父级的属性UserControl,则可以将此属性绑定到视图模型的属性,该属性是 的当前属性DataContext(Grid因此也是其当前的属性ToolTip)。我仅在绑定到业务数据而不是布局数据时建议这样做:
<UserControl InfoTT="{Binding ViewModelInfoTT}">
<UserControl.DataContext>
<ViewModel />
</UserControl.DataContext>
<Grid>
<Grid.ToolTip>
<ToolTip>
<TextBlock Text="{Binding ViewModelInfoTT}" />
</ToolTip>
</Grid.ToolTip>
</Grid>
</UserControl>
Run Code Online (Sandbox Code Playgroud)
如果您不使用视图模型并将数据直接托管在控件中,您可能希望将 设为DataContext控件本身。通过这种方式,您可以简化所有绑定,当然现在可以绑定到UserControl以下内容ToolTip:
// Constructor
public MyUserControl()
{
InitializeComponent();
// Set the UserControl's DataContext to the control itself
this.DataContext = this;
}
<UserControl>
<Grid>
<Grid.ToolTip>
<ToolTip>
<TextBlock Text="{Binding InfoTT}" />
</ToolTip>
</Grid.ToolTip>
</Grid>
</UserControl>
Run Code Online (Sandbox Code Playgroud)
或者覆盖DataContext. 当然,您将无法访问当前上下文:
<UserControl>
<Grid DataContext="{Binding RelativeSource={RelativeSource AncestoType=UserControl}>
<Grid.ToolTip>
<ToolTip>
<TextBlock Text="{Binding InfoTT}" />
</ToolTip>
</Grid.ToolTip>
</Grid>
</UserControl>
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
527 次 |
| 最近记录: |