2011-03-27 53 views
2

我在Silverlight中使用MVVM Light Toolkit。Silverlight MVVM Light列表框項目Click事件

在我的UserControl上我有一個顯示文件列表的ListBox。每個文件在文件名旁邊都有一個刪除圖像。在列表框的DataTemplate中,我有一個圖像(或可以使用按鈕)和一個TextBlock。

所以我想捕捉使用事件時,用戶將點擊圖像(或帶圖像的按鈕)從文件列表中刪除文件。

但我似乎無法捕捉到事件。也許這是由於在列表框上有SelectedItem事件?

public class MainViewModel : ViewModelBase 
{ 
    #region Properties 

    public const string SelectedListBoxFilePropertyName = "SelectedUploadFile"; 
    private UploadFile _selectedUploadFile = null; 
    public UploadFile SelectedUploadFile 
    { 
     get 
     { 
      return _selectedUploadFile; 
     } 
     set 
     { 
      if (_selectedUploadFile == value) 
       return; 

      _selectedUploadFile = value; 

      RaisePropertyChanged(SelectedListBoxFilePropertyName); 
     } 
    } 

    public const string UploadFilesPropertyName = "UploadFiles"; 
    private ObservableCollection<UploadFile> _uploadFiles = new ObservableCollection<UploadFile>(); 
    public ObservableCollection<UploadFile> UploadFiles 
    { 
     get 
     { 
      return _uploadFiles; 
     } 
     set 
     { 
      if (_uploadFiles == value) 
       return; 

      _uploadFiles = value; 

      RaisePropertyChanged(UploadFilesPropertyName); 
     } 
    } 
    #endregion 

    public static ICommand BrowseCommand { get; private set; } 
    public static ICommand DragDropFileCommand { get; private set; } 
    public static ICommand RemoveCommand { get; private set; } 

    #region Constructor 
    public MainViewModel() 
    {    
     if (IsInDesignMode) 
     { 
      // Code runs in Blend --> create design time data. 
      UploadFiles = new UploadFileContainer().UploadFiles; 
     } 
     else 
     { 
      // Code runs "for real" 
     } 

     WireUpCommands(); 
    } 
    #endregion 

    #region Event Handlers 
    private void OnBrowseFileCommand() 
    { 
     var dialog = new OpenFileDialog(); 
     dialog.ShowDialog(); 

     if (dialog.Files != null) 
      AddFiles(dialog.Files); 
    } 

    private void OnDropFileCommand(DragEventArgs e) 
    { 
     var files = e.Data.GetData(DataFormats.FileDrop) as FileInfo[]; 

     AddFiles(files); 
    } 

    private void OnRemoveFileCommand() 
    { 
     UploadFiles.Remove(_selectedUploadFile); 
    } 
    #endregion 

    #region Private Methods 

    private void WireUpCommands() 
    { 
     BrowseCommand = new RelayCommand(OnBrowseFileCommand); 
     DragDropFileCommand = new RelayCommand<DragEventArgs>(e => OnDropFileCommand(e)); 
     RemoveCommand = new RelayCommand(OnRemoveFileCommand); 
     UploadCommand = new RelayCommand(OnClickUploadCommand); 
    } 
    #endregion 
} 
<ListBox Grid.Row="1" Height="214" HorizontalAlignment="Left" AllowDrop="True" Margin="6,26,0,0" Name="UploadFilesListBox" VerticalAlignment="Top" Width="415" ItemsSource="{Binding Path=UploadFiles}" SelectedItem="{Binding Path=SelectedListBoxFile, Mode=TwoWay}" ScrollViewer.VerticalScrollBarVisibility="Auto"> 
    <i:Interaction.Triggers> 
     <i:EventTrigger EventName="Drop"> 
      <cmd:EventToCommand Command="{Binding DragDropFileCommand}" PassEventArgsToCommand="True"/> 
     </i:EventTrigger> 
    </i:Interaction.Triggers> 
    <ListBox.Background> 
     <ImageBrush ImageSource="/FileUploadApplication;component/Resources/dragdrophere.png" Stretch="None" /> 
    </ListBox.Background> 
    <ListBox.ItemTemplate> 
     <DataTemplate> 
      <StackPanel Orientation="Horizontal"> 
       <Button Command="{Binding RemoveCommand}">         
           <Image Source="/FileUploadApplication;component/Resources/delete.png"/> 
          </Button> 
          <Image Source="/FileUploadApplication;component/Resources/delete.png"> 
           <i:Interaction.Triggers> 
            <i:EventTrigger EventName="Click"> 
             <cmd:EventToCommand Command="{Binding RemoveCommand}"/> 
            </i:EventTrigger> 
           </i:Interaction.Triggers> 
          </Image> <TextBlock Text=" " /> 
       <TextBlock Text="{Binding Name}" /> 
      </StackPanel> 
     </DataTemplate> 
    </ListBox.ItemTemplate> 
</ListBox> 
+0

您不要使用EventToCommand作爲按鈕。你可以發佈你的viewmodel(s)嗎? – 2011-03-27 01:50:29

+0

對於mvvm和silverlight來說很新,所以推測你不能將一個列表框上的重複控件綁定到一個命令上,而是我想我可以使用eventtocommand。我理想上會喜歡它只是X的圖像而不是使用按鈕,但不知道如何實現點擊圖像。事件指令是否正確? – BBurke 2011-03-27 11:01:34

+0

您可以擺脫按鈕並使用EventToCommand來捕獲圖像上的單擊事件,所以是的,它是正確的模式。如果您想使用按鈕,您可以將命令屬性設置爲RemoveCommand。 – 2011-03-27 14:08:48

回答

0

由於您的ItemsSource是UploadFiles它可能發送事件UploadFile而不是用戶控件綁定到視圖模型。

+0

啊我想我明白你的意思了。所以我可以在主視圖模型中創建另一個視圖模型,該視圖模型將包含文件列表,然後爲removefile創建一個命令?然後設置這個視圖模型作爲itemssource – BBurke 2011-03-27 11:05:55

+0

如果我去這條路線我使用列表框或itemource的datacontext設置爲childViewModel? – BBurke 2011-03-27 11:30:55

+0

您可以在UploadLoadFile類中粘貼RemoveFile並設置斷點以查看它是否正在觸發。有很多方法可以處理你想要做的事情。看看這個:http://weblogs.asp.net/dwahlin/archive/2009/08/20/creating-a-silverlight-datacontext-proxy-to-simplify-data-binding-in-nested-controls.aspx – 2011-03-27 14:26:59

0

您的按鈕是ItemTemplate中的元素。你將列表框ItemsSource綁定到ObservableCollection。每個Itemtemplate DataContext不是MainViewModel,而是UploadFile,它沒有RemoveCommand。 我解決這個問題的方法是使用構造函數向每個項目添加父對象。 RemoveCommand在項目的ViewModel中,並且刪除了我調用父項的方法刪除項目的remove函數。 不知道這是否是最好的解決方案,但它對我有用。