Anas
Anas

Reputation: 5727

Why the ViewModel doesn't implement ICommand in MVVM

I'm trying to understand MVVM for WPF applications

In the example below, we use a delegate that inherits from ICommand, then in our ViewModel, we instantiate the delegate and provide the appropriate implementation

My Question is why can't we just make the ViewModel implement ICommand?

ViewModel :

public class ViewModel : INotifyPropertyChanged
{
    public ViewModel()
    {
        InitializeViewModel();
    }

    protected void InitializeViewModel()
    {
        DelegateCommand MyCommand = new DelegateCommand<SomeClass>(
            SomeCommand_Execute, SomeCommand_CanExecute);    
    }

    void SomeCommand_Execute(SomeClass arg)
    {
        // Implementation
    }

    bool SomeCommand_CanExecute(SomeClass arg)
    {
        // Implementation
    }
}

DelegateCommand :

public class DelegateCommand<T> : ICommand
{
    public DelegateCommand(Action<T> execute) : this(execute, null) { }

    public DelegateCommand(Action<T> execute, Predicate<T> canExecute) : this(execute, canExecute, "") { }

    public DelegateCommand(Action<T> execute, Predicate<T> canExecute, string label)
    {
        _Execute = execute;
        _CanExecute = canExecute;
    }
.
.
.
}

Upvotes: 2

Views: 309

Answers (3)

Joao
Joao

Reputation: 7486

Short answer: because your ViewModel isn't a command.

Moreover, your ViewModel can hold multiple commands.

public class ViewModel : INotifyPropertyChanged
{
    public ViewModel()
    {
        InitializeViewModel();

        OpenCommand = new DelegateCommand<SomeClass>(
            param => { ... },
            param => { return true; }); 

        SaveCommand = new DelegateCommand<SomeClass>(
            param => { ... },
            param => { return true; });

        SaveAsCommand = new DelegateCommand<SomeClass>(
            param => { ... },
            param => { return true; });
    }

    public ICommand OpenCommand { get; private set; }

    public ICommand SaveCommand { get; private set; }

    public ICommand SaveAsCommand { get; private set; }
}

Now you can binding those commands to your view, because they are a property.

Upvotes: 3

Khan
Khan

Reputation: 18162

The reason would be having a one to many relationship between your view and your number of commands.

You typically will have one ViewModel for every View. But you may want to have many Commands for a single view. If you were to use your ViewModel as a Command, you would have to have multiple instances of your ViewModel.

The typical implementation would be that your ViewModel would contain instances of all of the Commands your View needs.

Upvotes: 3

Reed Copsey
Reed Copsey

Reputation: 564771

You can implement ICommand this way - and this is a very common way of implementing ICommand. That being said, you still need to make MyCommand a property on the ViewModel in order to bind to it.

Upvotes: 0

Related Questions