我在文本框上有一个上下文菜单,我试图将isChecked属性绑定到该文本框的datacontext中的一个属性,并带有一个值转换器 .
我遇到的问题非常相似,我相信这篇文章...... WPF MenuItem.Command binding to ElementName results to System.Windows.Data Error: 4 : Cannot find source for binding with reference
在那里,Aran Mulholland提出了3种不同的解决方案 . 我一直在努力工作,并且还没有看到一个实际工作的例子,是#2 . 我认为这是MVVM最友好的方法,为此最优雅...再说一次,我对此很新 .
这是我的xaml
<DataTemplate x:Key="SFTemplateWithContextMenu">
<TextBlock x:Name="Field" Text="{Binding Path=FieldName}" >
<TextBlock.ContextMenu>
<!--<ContextMenu PlacementTarget="{Binding ElementName=Field}" > -->
<ContextMenu DataContext="{Binding RelativeSource={RelativeSource Mode=Self}, Path=PlacementTarget.DataContext}">
<MenuItem Header="Rename..." />
<MenuItem Header="Field Type">
<MenuItem.Resources>
<Configurator:EnumToBooleanConverter x:Key="EnumToBooleanConverter" />
</MenuItem.Resources>
<!--<MenuItem Header="String" IsCheckable="True" IsChecked="{Binding Path=PlacementTarget.DataContext.FieldType, RelativeSource={RelativeSource AncestorType={x:Type ContextMenu}}, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged, Converter={StaticResource EnumToBooleanConverter}, ConverterParameter={x:Static Configurator:TypeDesc.String}, PresentationTraceSources.TraceLevel=High}"/>-->
<MenuItem Header="String" IsCheckable="True" IsChecked="{Binding Path=FieldType, RelativeSource={RelativeSource AncestorType={x:Type ContextMenu}}, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged, Converter={StaticResource EnumToBooleanConverter}, ConverterParameter={x:Static Configurator:TypeDesc.String}, PresentationTraceSources.TraceLevel=High}"/>
</MenuItem>
</ContextMenu>
</TextBlock.ContextMenu>
</TextBlock>
</DataTemplate>
我正在使用DataTemplate填充以下ListBox ...
<ListBox DnD:DragDropHelper.IsDragSource="True" Name="sourceFieldsLB" Height="238" HorizontalAlignment="Left" Margin="20,286,0,0" VerticalAlignment="Top" Width="150" ItemTemplate="{StaticResource SFTemplateWithContextMenu}" ItemsSource="{Binding Selection.SourceFields, Mode=TwoWay}" AllowDrop="True" >
我下载了Snoop来查看内部情况,看看发生了什么 . 我尝试了几种不同程度的失败方法 .
评论出来的作品是我试图实现目标的先前方式 . 问题在于我得到了错误......“无法找到与引用'elementname = Field'绑定的源代码”但TextBlock使用Snoop显示其名称为IS Field .
按照目前的方式,我正在这样做,我可以看到textblock有一个本地名称范围,它的名字是Field - 这是我期望和想要的 . ContextMenu值显示它有一个ContextMenu有2个项目......这是正确的 . 所以我点击ContextMenu来查看事物的外观和低级,看看ContextMenu没有DataContext .
任何帮助和方向都会很棒 . 我不确定我到底错过了什么 . 我环顾四周,每当有人似乎接近完成这项工作时,他们就会提到他们找到了一些“解决方法”或其他方式来做到这一点并且永远不会让它发挥作用 . 这个有能力工作...我只是太新了,看不到丢失的一块 .
我知道可以做一个真正的MVVM方式......对吗?
1 回答
Bryce,主要问题是ContextMenus不是标准可视化树的一部分,它们唯一真正的连接是通过PlacementTarget属性 . 因此,通常最好尽快将其连接起来 . 所以...
给定一个ViewModel
还有一个MainWindow
还有一个app.xaml.cs
您可以看到ContextMenu的DataContext被该行正确连接
你应该得到一个表现良好的ContextMenu,与底层的VieWModel对话 .