Search code examples
xamarin.formsxamarin.android

Notify Activity of changes in viewModel


I try to exit 'lock task mode' in Xamarin Android app. Here is what I am trying to achieve:

  1. User taps on label (view in Xamarin.Forms) -> it cause change in ViewModel's boolean property to true
  2. MainActivity (Xamarin.Android) observe that property has changed to true -> it makes application exit 'lock task mode'

My viewModel is placed in Xamarin.Forms 'App.xaml' class so it is accessible in Forms and Android part.

How Can I notify my Activity that property has changed so it can exit locked mode? I know this is propably very poor workaround, I would love to hear any advices and tips to make it more professional.

Thank you in advance!

EDIT

So the point is that I have got ViewModel with boolean property exitLockMode which indicates if app should be in lock mode or not:

public class AdminViewModel : BaseViewModel
    {
        //Number of taps to touch at main banner in 'MainPage' to open Admin Window
        private int _tapsRequiredToAdmin = 5;
        //Number of tolerance in miliseconds between next taps
        private int _toleranceInMs = 1000;
        private bool _exitLockMode = false;

        
        public int ToleranceInMs { get => _toleranceInMs;  }
        public int TapsRequiredToAdmin { get => _tapsRequiredToAdmin; }

        public bool ExitLockMode
        {
            get => _exitLockMode;
            set => _exitLockMode=value;
        }
    }

AdminViewModel is created in 'App.xaml' class:

public partial class App : Application
    {
        private static AdminViewModel _adminViewModel;


        public App()
        {
            InitializeComponent();

            MainPage = new NavigationPage(new MainPage());
           
        }

        public static AdminViewModel AdminViewModel
        {
            get
            {
                if(_adminViewModel == null )
                    _adminViewModel = new AdminViewModel();
                return _adminViewModel;
            }
        }

        protected override void OnStart() { }

        protected override void OnSleep() { }

        protected override void OnResume() { }

        
        
    }

In my main view (Xamarin.Forms) I have got label where admin want to tap few times in order to exit lock mode:

private DateTime? LastTap = null;
        private byte NumberOfTaps = 0;
        AdminViewModel adminViewModel = App.AdminViewModel;

**********************************************
//This is method binded to Label in <TapGestureRecognizer Tapped="OnLabelTapped">

 private async void OnLabelTapped(object sender, EventArgs e)
        {
                if (LastTap == null || (DateTime.Now - LastTap.Value).TotalMilliseconds < adminViewModel.ToleranceInMs)
                {
                    if (NumberOfTaps == (adminViewModel.TapsRequiredToAdmin - 1))
                    {
                        NumberOfTaps = 0;
                        LastTap = null;
                        adminViewModel.ExitLockMode = true;

                        
                        return;
                    }
                    else
                    {
                        NumberOfTaps++;
                        LastTap = DateTime.Now;
                    }
                }
                else
                {
                    NumberOfTaps = 1;
                    LastTap = DateTime.Now;
                }
        }

Now I want to achieve that when I turn 'ExitLockMode' bool to true, it notify my 'MainActivity' (Xamarin.Android) to fire 'StopLockTask()' method. I know that in native Android it could be handled by observing bool property, but I don't know how to do it here.

I am newbie so it could be very messy, every help appreciated.


Solution

  • As Jason said, you can use messagecenter.The Xamarin.Forms MessagingCenter class implements the publish-subscribe pattern, allowing message-based communication between components that are inconvenient to link by object and type references.

    This mechanism allows publishers and subscribers to communicate without having a reference to each other, helping to reduce dependencies between them.

    You can follow this document and the sample in it https://learn.microsoft.com/en-us/xamarin/xamarin-forms/app-fundamentals/messaging-center