MVVM Execute command on ViewModel from another ViewModel

I tried for about 14 days with a simple task: in the database I have definitions for the hardware categories. For instance:

  • HDD
    • Interior
    • External
    • Flash

This list is in the database defined as follows:

[ID - ParrentID - Name] : 1 - 0 - HDD, 2 - 1 - Internal, 3 - 1 - External, 4 - 1 - Flash. 

Through the Entity Framework, I insert these lines into my application. From this flat data, I then create a structured object, which is my DataModel. This model is defined as follows:

 public class Category { private int _id = -1; private string _name = ""; private List<Category> _subCategories = null; // property getters and setters, constructors, and bool HasSubCategories } 

Now from these I create a ViewModel called SubCategoryViewModel, to which my TreeView is bound. That way I can browse my categories in treeview and with my specific and supported hierarchy. It works great. In the SubCategoryViewModel, the Command command is defined through the Attached Behavior for MouseDoubleClick, which is also bound to the TreeView. Thus, when the user double-clicks on an element, specific code will be executed in the SubViewCategoryModel method. The SubCategoryViewModel list is nested in the HWDocumentViewModel, which is the main ViewModel for my window. Now I need what I need: when the user double-clicks an element in the TreeView, I need to load the elements from the database and show them in the ListView. My opinion is that in HWDocumentViewModel I need to define a collection of elements and load them according to the selected category into the ListView. But I do not know how to execute the method in the HWDocumentViewModel of the SubCategoryViewModel. Because: TreeView is bound to a list of SubCategoryViewModel elements, so when DoubleClick happens, the method in SubCategoryViewModel is executed. I am looking for a way to execute a method on the main ViewModel (HWDocumentViewModel).

I tried this approach:
I created a property: public static SubCategoryViewModel SelectedCategory on HWDocumentViewModel . When a double click occurs, I set this property from SubCategoryViewModel to this . Thus, in this property there is an object that the delegate of the doubleclick event executes. Great, now I have an object in the HWDocumentView that is selected by the user.
So, I need to load items in a ListView. But will I load them from a method in a SubCategoryViewModel? I do not think so. Instead, I have to load them from the Main View Model by creating a ViewModel for them and linking it to the ListView, right? But how can I call a method from a SubCategoryViewModel in an HWDocumentViewModel? Should I write a static method on the HWDocumentViewModel that will be accessible from the SubCategoryViewModel?
Or is there a way to invoke the command defined in the HWDocumentViewModel from the SubCategoryViewModel?

Or, as a rule, I used the right approach to create an application in Warehouse in WPF?

Many thanks.

EDIT: The XAML for my TreeView is as follows:

 <TreeView x:Name="tvCategories" Background="White" ItemsSource="{Binding Categories}"> <TreeView.ItemContainerStyle> <Style TargetType="{x:Type TreeViewItem}"> <Setter Property="IsExpanded" Value="{Binding IsExpanded, Mode=TwoWay}" /> <Setter Property="IsSelected" Value="{Binding IsSelected, Mode=TwoWay}" /> <Setter Property="FontWeight" Value="Normal" /> <Setter Property="behaviors:MouseDoubleClick.Command" Value="{Binding MouseDoubleClickCommand}" /> <Setter Property="behaviors:MouseDoubleClick.CommandParameter" Value="{Binding}" /> <Style.Triggers> <Trigger Property="IsSelected" Value="True"> <Setter Property="FontWeight" Value="Bold" /> </Trigger> </Style.Triggers> </Style> </TreeView.ItemContainerStyle> <TreeView.Resources> <HierarchicalDataTemplate DataType="{x:Type localvm:SubCategoryViewModel}" ItemsSource="{Binding Children}"> <StackPanel Orientation="Horizontal"> <TextBlock Text="{Binding CategoryName}" /> </StackPanel> </HierarchicalDataTemplate> </TreeView.Resources> </TreeView> 
+6
source share
2 answers

I'm not sure I see the problem. You have a subcategory tree, and when it is selected, the corresponding SubCategoryViewModel sets itself as SelectedCategory in the main HWDocumentViewModel . This seems like a reasonable approach.

So why do you need to call a command? Why can't you just load the new list into the HWDocumentViewModel in response to changing its SelectedCategory property (i.e., in the installer)?

If you really have to use the command to call the load, just save the link to your main HWDocumentViewModel in each SubCategoryViewModel and call the command simple:

 _mainViewModel.LoadCategoryCommand.Execute(); 
+5
source

With MVVM and an attempt to communicate between View and ViewModel or between ViewModels, the publisher / subscriber setting works well or the messaging paradigm, for example, found in MVVMLight or Prism. I sent a response to the MVVM Light messaging setup here

In the message, you can send an object that contains any data that you want to send back and forth between view models.

I highly recommend using the framework when working with mvvm, which makes it a lot easier. Comparison The MVVM Framework is a link to an answer that goes through a comparison of some basic structures.

+3
source

Source: https://habr.com/ru/post/912676/


All Articles