1

The scenario is this:

I have an application developed in WPF, MVVM, Prism 6.3.0. This app considers

  • Shell.xaml (the shell)
  • UserControl1.xaml (inside a module, independient Class Library)

When I click on the Button defined in the Shell, I expect the command being executed and the condition defined in CanExecute be verified. But, this command is defined into the ViewModel class that's the view model of the module (in this application will be more than one module, loaded as Prism implements this traditionally).

To be called, I tried to define a localviewmodel into the resources collection of the Shell. This triggers the command, but doesn't triggers the condition CanExecute.

If I put the XAML code defined in the user control inside the module, (in other words, If I code a simple app with no use of Content region manager) a single-page XAML app, the command verifies the CanExecute without a problem. My best guess is a problem of binding the command defined in the module viewmodel, into a button in the Shell. Having read a lot about it, I just don't get the right way of declaring the binding.

Here's an example:

<Telerik:RadRibbonView x:Name="BarraHerramientas" Grid.Row="0"
                           DockPanel.Dock="Top" 
                           ContentHeight="130" 
                           Height="160" 
                           Template="{DynamicResource RadRibbonViewStyle}" 
                           MinimizeButtonVisibility="Visible" 
                           HelpButtonVisibility="Visible" Background="Red">
        <Telerik:RadRibbonTab Header="1" 
                              Style="{DynamicResource RadRibbonTabStyle}" 
                              IsSelected="True" 
                              TabIndex="0">
            <Telerik:RadRibbonGroup Header="RibbonGroup1" 
                                    DialogLauncherVisibility="Visible">
                <Telerik:RadRibbonButton CollapseToMedium="Never" 
                                         CollapseToSmall="WhenGroupIsMedium" 
                                         IsAutoSize="True" 
                                         LargeImage="Agregar.png" 
                                         Size="Large" 
                                         SmallImage="Agregar_16x16.png" 
                                         Text="Add..." 
                                         Command="{Binding AddRecordCommand, Source={StaticResource LocalViewModel}}" 
                                         CommandTarget="{Binding ElementName=MyRecords}"
                                         CommandParameter="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type Window}}}" " 
                                         Telerik:ScreenTip.Description="..." />
            </Telerik:RadRibbonGroup>
        </Telerik:RadRibbonTab>
</Telerik:RadRibbonView>

Where MyRecords is the name of the GridView that holds the data, and LocalViewModel is the key of the instance of the ViewModel defined in the loaded module. So, there's two instances in a point of time of LocalViewModel, the one defined as a resource in Shell.xaml, and the one defined into the loaded Module that holds the "MyRecords" GridView.

Using a one-page example, this works flawless, of course. And because I need to write a few modules, each one defines it's own ViewModel, or more than one. So, thats because I need to use commands defined into the different module's viewmodels, from the Shell. If I declare each ViewModel in the shell (a LOT of data coming in) probably will be a performance issue.

So, how can I call a command (from the shell) that is defined in a ViewModel as a resource in a module being loaded "on demand"?

Thanks everyone.

Gonza Romero
  • 81
  • 2
  • 6

1 Answers1

0

There are a number of ways to accomplish what you want. One approach would be to use a CompositeCommand. If your ShellViewModel will always contain the data you use as a parameter this will work for you. Each ViewModel can subscribe the the parent CompositeCommand and whenever the CompositeCommand is invoked all registered VM Commands will be invoked too. You can see a sample of CompositeCommands here:

https://github.com/PrismLibrary/Prism-Samples-Wpf/tree/master/12-UsingCompositeCommands

Another approach would be to have your ribbon buttons injected with each view you inject into the shell. So each view will know which tabs need to be added/removed to the ribbon as you add/remove the views in the shell region. You can see how to do that in my Pluralsight course Prism Problems & Solutions: Loading Dependent Views:

https://www.pluralsight.com/courses/prism-problems-solutions

  • Brian, thanks for your response...I am now reading that example to understand it. Adding more info, what I need to acomplish is let the ribbonview button to be active/inactive depending on a combobox value, that holds a SelectedItem property in a module's ViewModel. That's because I needed the ribbonview button to react to changes in that property, and the problem was that property is in a ViewModel inside a module, not the shell. I mean, the Shell is not aware of the model in the ViewModel. Am I seeing this correctly? regards, Charlie. – Gonza Romero May 04 '17 at 20:28
  • Application architecture is not something can be easily explained or solved in a SO comment :). I have no idea how you have your app structured, or your requirements. I suggest learning the approaches and applying the knowledge to your scenario. –  May 05 '17 at 01:11