Question

I am quite new in MvvmCross, so I might just be doing something wrong; or not.

Just in case, this is also a workaround and points to look out for other developers.

Using: Windows Phone 8

Issue: From a View page, subscribing with MvxPropertyChangedListener works for a while, and then stops.

Scenario: ViewModel has a property IsBusy, which for specific reason I need to access from View Page code behind (.xaml.cs). The way I figured it would work is...

public LoadingView()
{
    InitializeComponent();

    // until loaded, we can not access viewmodel
    Loaded += (sender, args) =>
    {
        var viewModel = (LoadingViewModel) ViewModel;

        // add listener
        new MvxPropertyChangedListener(viewModel).Listen(() => viewModel.IsBusy, () =>
        {
            // do something
        });
    };
}

Now, user clicks a command button, on which I call up an async Task rest method using jsonRestClient; once task is done, isBusy is set to false;

Note: I also have isBusy binding to an element in xaml file (to a progressBar visibility).

In WP Emulator, clicking the button does raise the listener event, but only for two to three times. After that, the code within the listener doesn't execute anymore. Funny thing is, xaml binding still updates;

I don't see how GC can come into play; as the property is in the ViewModel itself;

Work around: Didn't get much time to investigate this issue; instead I am now using IMvxMessenger, and subscribing from my View code behind; so far so good with no errors.

Rana

Was it helpful?

Solution

MvvmCross uses weak references a lot in its subscriptions - e.g. for things like ViewModel property subscriptions and for things like messenger subscriptions too.

The source for MvxPropertyChangedListener is in https://github.com/MvvmCross/MvvmCross/blob/v3.1/Cirrious/Cirrious.MvvmCross/ViewModels/MvxPropertyChangedListener.cs

This class subscribes to view model changes using:

_token = _notificationObject.WeakSubscribe(NotificationObjectOnPropertyChanged);

and the _token is stored in a private member variable.

Since your code creates the property listener as a temporary object, then this object will exist for a short while, but will then at some point determined by the system be garbage collected. When it is GC'd, so will the _token - and as a consequence the subscription itself will stop working.

To fix this, store the property listener in a field on your view:

 _isBusyListener = new MvxPropertyChangedListener //....

This will stop it from being GC'd

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top