菜单上的 WPF selectedItem 或在 viewmodel 中获取命令参数

WPF selectedItem on Menu or get commandparameter in viewmodel

我正在寻找几个小时来解决一个简单的问题。我想在我的 menuItems 上使用 "SelectedItem",但在使用 Whosebug 数小时后,我发现这是不可能的。我发现了很多关于 "CommandParameter" 的信息,但我不明白它是如何工作的。 这就是我想要做的:我有一个带有 "background1, background2,..." 的菜单。如果您 select 菜单中的背景,我想将那个 select 编辑的背景设置为背景。

这是一个学校项目,所以我们必须使用 MVVM,并且不允许代码隐藏。 我如何 "use" 我的 ViewModel 中的命令参数?

这是我的 mainWindow.xaml:

                <Toolbar>
                  <Menu>
                    <MenuItem Header="Background" ItemsSource="{Binding Backgrounds}">
                        <MenuItem.ItemTemplate>
                            <DataTemplate>
                                <MenuItem Header="{Binding Name}" Command="{Binding ChangeBackgroundCommand}" CommandParameter="{Binding Name}"/>
                            </DataTemplate>
                        </MenuItem.ItemTemplate>
                    </MenuItem>
                  </Menu>
                </Toolbar>

这是我的 mainWindowViewModel 的一部分:

public MainWindowViewModel()
    {
        //load data
        BackgroundDataService bds = new BackgroundDataService();
        Backgrounds = bds.GetBackgrounds();

        //connect command
        WijzigBackgroundCommand = new BaseCommand(WijzigBackground);
    }
private void ChangeBackground()
    {
        //I want here the name of the selected menuItem (by parameter?)
    }

}

我们使用一个 baseCommand class(我不想改变这个 class 因为我认为它是标准的):

class BaseCommand : ICommand
{
    Action actie;

    public BaseCommand(Action Actie)
    {
        actie = Actie;
    }

    public event EventHandler CanExecuteChanged;

    public bool CanExecute(object parameter)
    {
        return true;
    }

    public void Execute(object parameter)
    {
        actie.Invoke();
    }
}

我经常使用 Whosebug :-) 这是我的第一次 post/question,我希望它是清楚的

试试这个:

class BaseCommand<T> : ICommand
{
    private readonly Action<T> _executeMethod = null;
    private readonly Func<T, bool> _canExecuteMethod = null;

    public BaseCommand(Action<T> executeMethod)
        : this(executeMethod, null)
    {
    }

    public BaseCommand(Action<T> executeMethod, Func<T, bool> canExecuteMethod)
    {
        _executeMethod = executeMethod;
        _canExecuteMethod = canExecuteMethod;
    }

    public bool CanExecute(T parameter)
    {
        if (_canExecuteMethod != null)
        {
            return _canExecuteMethod(parameter);
        }
        return true;
    }

    public void Execute(T parameter)
    {
        if (_executeMethod != null)
        {
            _executeMethod(parameter);
        }
    }

    public event EventHandler CanExecuteChanged;

    bool ICommand.CanExecute(object parameter)
    {
        if (parameter == null &&
            typeof(T).IsValueType)
        {
            return (_canExecuteMethod == null);
        }
        return CanExecute((T)parameter);
    }

    void ICommand.Execute(object parameter)
    {
        Execute((T)parameter);
     }
}

这样使用:

public MainWindowViewModel()
{
    // ...

    // connect command
    WijzigBackgroundCommand = new BaseCommand<YourBackgroundClass>(
         (commandParam) => WijzigBackground(commandParam), 
         (commandParam) => CanWijzigBackground(commandParam));
}

private void WijzigBackground(YourBackgroundClass param)
{
    // Use 'param'
}

private bool CanWijzigBackground(YourBackgroundClass param)
{
    // Use 'param'
}