6

ContextMenu 内の UserControl の元の DataContext を取得するにはどうすればよいですか。

以下のコードでは、DataTemplate に Button があり、正しくバインドされていることがわかります。ただし、コンテキスト メニューのデータ ソースをバインドしようとすると、次のエラーが表示されます。

System.Windows.Data エラー: 4 : 参照 'RelativeSource FindAncestor、AncestorType='System.Windows.Controls.TreeView'、AncestorLevel='1'' でバインディングのソースが見つかりません。BindingExpression:Path=DataContext; DataItem=null; ターゲット要素は 'ContextMenu' (Name='') です。ターゲット プロパティは 'DataContext' (タイプ 'Object') です

ContextMenu を ViewModel にバインドできるようにするにはどうすればよいですか?

================================================== =============================

ViewModel は分離コードでビューのデータ コンテキストに割り当てられます。

意見:

<TreeView ItemsSource="{Binding Clients}"
          cmd:TreeViewSelect.Command="{Binding SelectionChangedCommand}"
          cmd:TreeViewSelect.CommandParameter="{Binding RelativeSource={RelativeSource Self},Path=SelectedItem}">
    <TreeView.ItemTemplate>
        <DataTemplate>
            <StackPanel>
                <TextBlock Text="{Binding Name}">
                    <TextBlock.ContextMenu>
                        <ContextMenu DataContext="{Binding DataContext, 
                            RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type TreeView}}}">
                            <MenuItem Header="{Binding TestString}" />
                        </ContextMenu>
                    </TextBlock.ContextMenu>
                </TextBlock>

                <Button  DataContext="{Binding DataContext, 
                            RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type TreeView}}}"
                         Content="{Binding TestString}" Command="{Binding EditSelectedClientCommand}" />
             </StackPanel>
        </DataTemplate>
    </TreeView.ItemTemplate>
</TreeView>

ビューモデル:

public class ClientListViewModel : ViewModelBase
{
    public String TestString { 
        get {
            return "TESTING";  
        }
    }

    private ClientList _clients = null;
    private readonly IClientService _clientService = null;
    private readonly IEventAggregator _eventAggregator = null;
    private Client _selectedClient = null;
    private ICommand _selectionChangedCommand = null;
    private ICommand _editSelectedClientCommand = null;
    ....
}
4

1 に答える 1

10

ContextMenusRelativeSourceバインディングが失敗する原因となるビジュアルツリーに表示されませんが、何らかのDataContext方法で取得できます。たとえば、これを試すことができます:

<TextBlock Text="{Binding Name}"
           Tag="{Binding DataContext, RelativeSource={RelativeSource AncestorType=TreeView}}">
    <TextBlock.ContextMenu>
        <ContextMenu DataContext="{Binding PlacementTarget.Tag, RelativeSource={RelativeSource Self}}">
            <MenuItem Header="{Binding TestString}" />
            <!-- ... --->

PlacementTargetTextBlock であり、DataContextは を介し​​てトンネリングされますTag。これを行う1つの方法(少なくともうまくいくことを願っています)、このギャップを別の方法で橋渡しするライブラリもいくつか見ましたが、それらの起源を思い出せません...

于 2011-07-26T01:04:05.717 に答える