简体   繁体   中英

How to handle multiple ViewModels with MVVM Light ViewModelLocator

How can I register and unregister multiple ViewModels in my application when using MVVMLight ViewModelLocator?

The problem is that I want to be able to tell the app which ViewModel should be registered and which Unregistered. I have 14 ViewModels in my app (few of them are working in the background like SessionViewModel, which is determining current session status for all views)

EDIT

Part of my ViewModelLocator:

public New()
{
    ServiceLocator.SetLocatorProvider(() => SimpleIoc.Default);
    SimpleIoc.Default.Register<AdministratorViewModel>();
    SimpleIoc.Default.Register<CallViewModel>();
    SimpleIoc.Default.Register<EmployeeViewModel>();
    SimpleIoc.Default.Register<LoginViewModel>();
    SimpleIoc.Default.Register<MessengerViewModel>();
    SimpleIoc.Default.Register<QualityViewModel>();
}

To be able to access ViewModels from a View in XAML I've used:

DataContext="{Binding Source={StaticResource Locator}}"

LoginViewModel should be available for all Views. And as an example: Employee View will use only CallViewModel , EmployeeViewModel and MessengerViewModel , so I don't need for Employee View AdministratorViewModel and QualityViewModel . Then, how can I register only needed ViewModels for Employee View?

I think you need to take some time to clearly plan your goals for this app.

Those register functions are called during your viewmodel locator construction/app load. They don't consume resources until your create one - which is what happens when your view binds to a view model. So the other view models that are not "open" do not exist yet.

If you "close" your view/window/usercontrol the viewmodel still exists. This can be a benefit because it allows you to keep the "state" of the VM so that when you open the view again the data etc is preserved. You will have to figure out a way to refresh any record-sets you have.

You can use the unregister function for viewmodels and it will be removed from the cache:

SimpleIoc.Default.Unregister(AdministratorViewModel);

But if you do that you will have to register it before it can be used again. So why are you looking to do this, is it to clear up memory? Most VM's are meant to be singletons and its normal to have them exist for the lifetime of the application.

Your statement that the LoginViewModle should be available for all views raises an alarm. View models are meant to be contained "units of work" and VM's should not really be communicating with other VM's (but there are some exceptions - hence the messenger functions in mvvmLight). Have you considered using services to hold the functions/business logic that needs to be available to each view model. The dependency injection of SImpleIOC is designed to enable this. I have a UserService that logs the user in and tracks the users settings and permissions. Then this service is injected into the constructor of each VM that needs it. for example :

public interface IUserService
{
    employee LoggedEmployee { get; set; }
    List<int> UserRoles { get; set; }
    bool LoggedIn { get; set; }
    void UpdatePassword(int idEmployee, string password);
    ...
}

Public Class UserService :  IUserService
{
    Public void UpdatePassword(int idEmployee, String password) {   }
        }

You define a service and then implement it (which allows for testing) but then you can inject it into your WM constructor:

Public Class AdministratorViewModel
{

    Private IUserService _UserService;

    Public New(IUserService UserService)
    {

        Try {
            _UserService = UserService;

        } catch (Exception ex) {

        }
    }
}

And because this user service is a singleton all viewmodels that have it injected can access its functions and data and this keep the separation of concerns for your application.

Hopefully this helps you make sure you are going in the right direction

JK

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