Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Inside a platform, Android or iOS, which Rx Scheduler should be used to ObserveOn the Main Thread?

When using Rx.NET in a platform specific project

  • Android
  • iOS

How do you ObserveOn the main thread? It doesn't look like ObserveOnDispatcher() is available under iOS or Android when using Xamarin.

This sample does work, as I know I am on the main thread when I subscribe. I just didn't know if there was a more formal way to deal with: "ALWAYS" use the main thread even if I am not on the main thread.

myObservable // assume this does work on an alternate thread
.ObserveOn(SynchronizationContext.Current)
.Subscribe(OnMyObservableNext);

Again, if I am on the main thread, say in a click event handler, I know that using SynchronizationContext.Current will put me back onto that thread. In testing this I have verified that as well.

What I am looking for though is the case where I may not be on the main thread and I want to get back there (from a PCL).

I can think of a solution where I store the SynchronizationContext.Current on a static class, in the case of iOS, in the FinishedLaunching method of the App Delegate. I don't know if this is advisable or not.

The solution mentioned above would be something like this:

PCL

namespace MyPCL
{

    public static class Settings
    {
        // obvioulsy probably don't want public setter, 
        // don't want anyone reaching in here and changiing it
        // from under us. But for the example this is fine.
        public static SynchronizationContext MainContext { get; set; }
    }
}

iOS

using MyPCL;

namespace MyApp.iOS
{
    [Register ("AppDelegate")]
    public class AppDelegate : UIApplicationDelegate
    {
        public override bool FinishedLaunching (UIApplication application, NSDictionary launchOptions)
        {
            // ...
            Settings.MainContext = SynchronizationContext.Current;
            // ^^^^ Save the Main SynchronizationContext 
            // ...
            return true;
        }
    }
}
like image 845
AJ Venturella Avatar asked Sep 11 '25 09:09

AJ Venturella


1 Answers

AFAIK there isn't an out of the box scheduler that you can use.

What you have paired with some injection http://www.introtorx.com/content/v1.0.10621.0/16_TestingRx.html#SchedulerDI

Is what I've seen in most recommendations Call method on UI thread from background in .net 2.0

That or if you're using Xamarin Forms just use this from the Subscribe

https://developer.xamarin.com/guides/xamarin-forms/platform-features/device/#Device.BeginInvokeOnMainThread

Which isn't the prettiest thing to do but it works

ReactiveUI does have some custom scheduler implementations that are used for getting to the Dispatcher thread

https://github.com/reactiveui/ReactiveUI/blob/b418df64918da0c78a378af1b846afbab0f4e5ae/src/ReactiveUI/Android/AndroidUIScheduler.cs

https://github.com/reactiveui/ReactiveUI/blob/b418df64918da0c78a378af1b846afbab0f4e5ae/src/ReactiveUI/Cocoa/NSRunloopScheduler.cs

So you can try those out as well but I'm not too sure the difference/advantages of using those over the SynchronizationContext

like image 58
Shane Neuville Avatar answered Sep 13 '25 22:09

Shane Neuville