2017-10-07 32 views
1

我有一个失败的DisplayMemberPath值。WPF DisplayMemberPath只在嵌套视图/虚拟机时启动

我的项目的设置是,我有一个ParentView,其中包含一个ChildView(这个子视图,我简化到单个控件失败的这个问题)。父视图的DataContext在虚拟机中设置为父虚拟机,并使用DataTemplate设置ChildView的上下文。该DataTemplate在父视图中设置。

问题:我需要显示FileName,而不是我的ListBox中的FileInfo对象的FullFileName属性值。我设置了DisplayMemberName,它在ChildView/UserControl中设置为绑定时部分起作用。这只是在启动应用程序时才起作用。如果我将一个FileInfo对象添加到我的ChildVM中 - 它将显示在ListBox中,但不会显示为FileName。相反,我只是得到FullFileName。

原因是我错过了一个触发绑定的事件,但我并不完全确定我应该首先绑定这种方式。

这是功能代码。请注意我为了这个问题已经简化了它。您可以忽略命名约定等。

这里是usercontrol。它是一个包含FileInfo对象的列表框,我要将DisplayMemberName设置为FileInfo.FileName值。

<UserControl x:Class="CatalogInterface.ctlDirFilesListBox" 
      xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
      xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
      xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
      xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
      xmlns:local="clr-namespace:CatalogInterface" 
      xmlns:vm="clr-namespace:CatalogInterface.ViewModels" 
      mc:Ignorable="d" 
      d:DesignHeight="300" d:DesignWidth="300"> 

    <Grid x:Name="MainControlGrid"> 
     <ListBox x:Name="FileListBox" 
       DisplayMemberPath="{Binding ElementName=Files, Path=Files.FileName}" 
       <!-- Also tried DisplayMemberPath="FileName" --> 
       ItemsSource="{Binding Files}" 
       SelectedItem="{Binding Path=SelectedFiles}" 
       SelectionChanged="ListBoxItem_SelectionChanged" 
       HorizontalAlignment="Stretch" 
       VerticalAlignment="Stretch" 
       Background="#FFFFFF" 
       Grid.Row="2" 
       Grid.Column="1" 
       Grid.ColumnSpan="3" 
       BorderThickness="0"> 
      <ListBox.ItemContainerStyle> 
       <Style TargetType="{x:Type ListBoxItem}" BasedOn="{StaticResource {x:Type ListBoxItem}}"> 
        <EventSetter Event="MouseDoubleClick" Handler="ListBoxItem_MouseDoubleClick"/> 
        <EventSetter Event="KeyDown" Handler="ListBoxItem_KeyDown"/> 
       </Style> 
      </ListBox.ItemContainerStyle> 
     </ListBox> 
    </Grid> 
</UserControl> 

这是我MainWindo查看这需要在用户控件:

<Window x:Name="FCTWindow" x:Class="CatalogInterface.MainWindow" 
     xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
     xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
     xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
     xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
     xmlns:local="clr-namespace:CatalogInterface" 
     xmlns:vm="clr-namespace:CatalogInterface.ViewModels" 
     mc:Ignorable="d" 
     Title="MainWindow" Height="350" Width="532"> 

    <Window.DataContext> 
     <vm:MainWindowViewModel /> 
    </Window.DataContext> 

    <!--#region Body Left Side Grid--> 
    <Grid x:Name="BodyGridLeft" Grid.Row="0" Grid.Column="0"> 
     <UserControl Content="{Binding DirFilesViewModel}"> 
      <UserControl.ContentTemplate> 
       <DataTemplate> 
        <local:ctlDirFilesListBox /> 
       </DataTemplate> 
      </UserControl.ContentTemplate> 
     </UserControl> 
    </Grid> 
    <!--#endregion Body Left Side--> 
</Window> 

这是虚拟机的用户控件(用户控件实际上是我简化了这个quesiton更复杂的子视图的一部分

using System; 
using System.Collections.Generic; 
using System.Collections.ObjectModel; 
using System.IO; 

namespace CatalogInterface.ViewModels 
{ 
    public class DirFilesViewModel : ViewModelBase<DirFilesModel> 
    { 
     private object _selectedFiles; 
     private Messenger _messenger; 

     public object SelectedFiles 
     { 
      get { return _selectedFiles; } 
      set { 
       SetProperty<object>(ref _selectedFiles, value); 
       _messenger.SendMessage(this, "DirFilesListBox_SelectedDocumentChanged", _selectedFiles); 
      } 
     } 

     public ObservableCollection<FileInfo> Files { get; set; } 
     private DirFilesModel _model; 

     public DirFilesViewModel() 
     { 
      _model = new DirFilesModel(); 
      Files = new ObservableCollection<FileInfo>(); 
      this.OnPublishDirFiles(this, new MessageEventArgs("s", "o")); 
      _messenger = Messenger.Set_Messenger(); 
      _messenger.Register(OnPublishDirFiles, "PublishDirFiles"); 
     } 
     protected virtual void OnPublishDirFiles(object source, MessageEventArgs e) 
     { 
      PublishDirFiles(); 
     } 
     private void PublishDirFiles() 
     { 
      if (Files == null) { } //raise NullArgumentException 
      Files.Clear(); 
      foreach (FileInfo f in _model.Files) Files.Add(f); 
      OnPropertyChanged("Files.FileName"); 
     } 
    } 
} 

回答

2

岂不是DisplayMemberPath="Name":)在虚拟机中,当OnPublishDirFiles()被调用列表框更新?我没有看到实际的“FileName”属性。有NameFullName

+1

我怎么会这么愚蠢...... :( –

+0

我知道这种感觉,盯着代码足够长,开始看东西。 – Laith