multiple command parameters from WPF context menu

Yanıt multiple command parameters from WPF context menu

  • 13 Temmuz 2011 Çarşamba 13:46
     
     
    Hi,
    Is there any way to pass multiple command parameter from a context menu of a xaml grid?
    Can we pass filed names of selected grid row as parameters?
    regards
    Vivek

Tüm Yanıtlar

  • 13 Temmuz 2011 Çarşamba 13:56
     
     Yanıt

    Command parameters are passed into commands as objects.  This means they can be anything you want them to be.  For example you can have a command helper class that passes in a zillion things.  Trick is to determine how you want to bind it all up. 

    If you do it in XAML then you have to (easiest way) either bind to something within the View (Some element value) OR you can bind to a Property for the view.  For example you have a property that contains a list of employess.  You have a button to Process the list.  You point the command binding to the command and you pass in the property (of the list of employees).  If you use MVVM this is pretty simple to do, because that property is already defined in the view model.  You can either bind direct to the property or you can bind to the UIElement's source which is bound to that property.

    OR...

    You can use code behind in the view to new up the command and pass in args via code.


    JP
  • 15 Temmuz 2011 Cuma 05:12
     
      Kod İçerir

    Hi,

    Thanks for your reply.

     

    Am trying to pass two items in a context menu click,

    I got a  sample but I am not getting all the values passed values in class which is implementing IMultiValueConverter.

     

    My XAML is

    <Window x:Class="WPF4._0_DataGrid_Rows_Management.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="MainWindow" Height="350" Width="525" xmlns:data="clr-namespace:WPF4._0_DataGrid_Rows_Management" >
      <Window.Resources>
        <data:ViewModel x:Key="EmpVM"></data:ViewModel>
      </Window.Resources>
      <Grid DataContext="{Binding Source={StaticResource EmpVM}}">
        <DataGrid AutoGenerateColumns="False" Height="287"
             HorizontalAlignment="Left" Margin="23,12,0,0"
             Name="dgEmp" VerticalAlignment="Top" Width="657"
              ItemsSource="{Binding Path=Employees}" ColumnWidth="*"
             SelectedIndex="{Binding Path=RecordIndex,Mode=TwoWay}" SelectedItem="{Binding Path=EmpName,Mode=OneWay}">
          <DataGrid.Columns>
            <DataGridTextColumn Header="EmpNo" Binding="{Binding EmpNo}" />
            <DataGridTextColumn Header="EmpName" Binding="{Binding EmpName}" />
            <DataGridTextColumn Header="Salary" Binding="{Binding Salary}" />
            <DataGridTextColumn Header="Designation" Binding="{Binding Designation}" />
          </DataGrid.Columns>
    
          <DataGrid.ContextMenu>
            <ContextMenu>
              <MenuItem Command="{Binding InsertCommand}" 
          Header="Insert">
                <MenuItem.Resources>
                  <data:FindCommandParametersConverter x:Key="findCommandParametersConverter"></data:FindCommandParametersConverter>
                </MenuItem.Resources>
                <MenuItem.CommandParameter>
                  <MultiBinding Converter="{StaticResource findCommandParametersConverter}">
                    <MultiBinding.Bindings>
                      <Binding Path="RecordIndex"/>
                      <Binding Path="EmpName" />
    
                    </MultiBinding.Bindings>
                  </MultiBinding>
                </MenuItem.CommandParameter>
              </MenuItem>
              <MenuItem Command="{Binding DeleteCommand}"
          CommandParameter="{Binding RecordIndex}" Header="Delete"/>
            </ContextMenu>
          </DataGrid.ContextMenu>
        </DataGrid>
      </Grid>
    </Window>
    

    Convertor Class is
     public class FindCommandParametersConverter : IMultiValueConverter
      {
        public object Convert(object[] values, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
          FindCommandParameters parameters = new FindCommandParameters();
          foreach (var obj in values)
          {
            if (obj is string) parameters.EmployeeName = (string)obj;
            else if (obj is int) parameters.IndexOfRec = (int)obj;
          }
          return parameters;
        }
        public object[] ConvertBack(object value, Type[] targetTypes, object parameter, System.Globalization.CultureInfo culture)
        {
          throw new NotImplementedException();
        }
      }

     

    In the above class the Second parameter of the object collection is coming as null,Do we need to define all the binding parameter in a class which is implementing INotifyPropertyChanged?

     

    Please guide.

     

    Thanks

     

    Vivek

  • 15 Temmuz 2011 Cuma 13:23
     
     

    I like how you set up your command parameters as Bindings.  The INPC does inform WPF of changes.  How it applies specifically to a multibinding is unknown to me.  My understanding of INPC is that it does indeed hook into the WPF binding, but typically that event allows for WPF to update GUI bindings.  I guess it needs it as well for command bindings. 

    You can also try something that is a bit easier by doing the same thing as above in code.  If you do it in code you can new-up the command parameter class and actually see the results prior to calling the command.  This can help you debug this issue because we all know debugging Binding errors is a deficit in VS2010. 


    JP
  • 19 Temmuz 2011 Salı 05:35
    Moderatör
     
     Yanıt Kod İçerir

    Hi Vivek,

    Have you resolve the problem?

    Binding a DataGrid's SelectedItem and SelectedIndex at the same time doesn't make sense. The binding path of the SelectedItem and the second column are the same. So I think the SelectedItem binding is incorrect which causes the problem.

    Try making the following changes to resolve the problem.

     

     <DataGrid AutoGenerateColumns="False" Height="287"
       HorizontalAlignment="Left" Margin="23,12,0,0"
       Name="dgEmp" VerticalAlignment="Top" Width="657"
       ItemsSource="{Binding Path=Employees}" ColumnWidth="*"
       SelectedIndex="{Binding Path=RecordIndex,Mode=TwoWay}" >
    

      <MultiBinding Converter="{StaticResource findCommandParametersConverter}">
       <MultiBinding.Bindings>
        <Binding Path="RecordIndex"/>
        <Binding Path="PlacementTarget.SelectedItem.EmpName" RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType=ContextMenu}"/>
       </MultiBinding.Bindings>
      </MultiBinding>
    

    Hope this helps.

     

    Best regards,


    Min Zhu [MSFT]
    MSDN Community Support | Feedback to us
    Get or Request Code Sample from Microsoft
    Please remember to mark the replies as answers if they help and unmark them if they provide no help.


  • 03 Ağustos 2011 Çarşamba 02:03
    Moderatör
     
     

    Hi Vivek,

    I am marking this issue as "Answered". If you have any new questions or concerns about this issue, please feel free to let me know.

    Thank you and have a nice day!


    Min Zhu [MSFT]
    MSDN Community Support | Feedback to us
    Get or Request Code Sample from Microsoft
    Please remember to mark the replies as answers if they help and unmark them if they provide no help.

  • 16 Nisan 2012 Pazartesi 15:01
     
     

    Hey,

    Actually I have similar problem in some extent. I have treeview inside that say there are three concanated fields named ID, Name and Status (as a part of controltemplate). I have one context menu item outside of treeview. there are thrre menu items (Name, ID and Status) with respective submenus (ASC, DESC) that can sort all treeview columns. For example, If I click on Name > ASC (on context menu) it should sort Name column as Ascending. Similarly if I click on Name > DESC (on context menu), it should sort datagrid's Name column in descending order.

    As I am new in WPF, I intended to provide SortColumn, SortOrder from XAML. For example, if I click on Name > ASC (on context menu), I wanted to provide Name and ASC to SortCommand in ViewModel.

     SortCommand(string sortcol, string sortorder) method which in in ViewModel, my RelayCOmmand cannot invoke a parametrised method.

    Could you please help me to implement this logic or suggest the best you have?

    Thanks


    P :)