简体   繁体   中英

Pass selected item as command parameter vs. using a bound ViewModel Object (MVVM)

Hopefully this is a simple MVVM question, but I'm trying to grasp command parameters.

I have a user select an item from the ListBox, and click "Delete Selected". The ListBox binds SelectedItem to "SelectedTemplate". My button XAML looks like so:

<Button CommandParameter="{Binding SelectedTemplate}" Command="{Binding DeleteTemplateCommand}" Content="Delete Selected"/>

When i get to my execute command, I'm reading the parameter from the Command. However, I also can access "SelectedTemplate". If i use the passed parameter, I'd then have to convert it to the correct objecttype before removing the object, versus just going ahead and removing "selectedTemplate"

public void DeleteTemplate(object template)
{
    Convert.ChangeType(template, typeof(Template));
    if (template == SelectedTemplate )
    {
        _ESTContext.Templates.Remove(SelectedTemplate);
    }     
}

My question here is that to me it seems both satisfy the MVVM philosophy, is there a benefit/detriment to using one or the other?

The only real difference is readability (and potentially one extra binding for the engine to have to evaluate, but that isn't going to really hurt you in this case).

You are using SelectedTemplate either way so I wouldn't bother with binding it to the parameter and use it directly.

Unless that is the only thing you are using SelectedTemplate for, in which case I would toss it as a variable, and bind directly to the selection:

<Button CommandParameter="{Binding ElementName=MyListBox, Path=SelectedItem}" Command="{Binding DeleteTemplateCommand}" Content="Delete Selected"/>

The primary benefit of using a command parameter is that you can execute the same command against different inputs, as opposed to one hard-coded input. Being able to delete any item is arguably more flexible than being able to delete just SelectedTemplate . In practice, I tend to favor using parameters.

You can avoid the cast in your "execute" callback by using a generic command implementation (ie, something like RelayCommand<TParameter> ).

My question here is that to me it seems both satisfy the MVVM philosophy, is there a benefit/detriment to using one or the other?

@MikeStrobel gave you a good argument for using parameters, so I guess you need someone arguing for using the VM property!

You are correct in that both satisfy MVVM, so really it just comes down to how you want your app to work.

In our apps that have this kind of functionality, our SelectedTemplate concept is key to how the UI works. There will be NullToVisibility/Boolean converters bound to that property that dictate whether certain controls are enabled or visible. Detail sections, command buttons and all sorts of other workflow hang off whether you have selected a thing. With this workflow in mind, having a valid SelectedTemplate would make the DeleteTemplate button active. So for us it makes sense that our commands, such as DeleteTemplateCommand would all operate on the SelectedTemplate object. This means we don't need to pass command parameters around.

For us, performing operations (such as a delete) on something that isn't the SelectedTemplate doesn't make sense. For your app, and UI, it might.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM