obs = Observable.interval(1, SECOND)
.replay(1)
.autoConnect(0)
obs
.observeOn(mainScheduler)
.subscribe() // here I'm losing one frame
obs2 = Observable.interval(1, SECOND)
.observeOn(mainScheduler)
.replay(1)
.autoConnect(0)
obs
.concatMapSingle { item ->
if (runningInMainThread())
Single.just(item)
else
Single.just(item)
.observeOn(mainThread)
}
.subscribe()
Single.just(item).observeOn(mainThread)
and Single.just(item).subscribeOn(mainThread)
in this case?In the terms of your example, are you sure that one second hasn't passed between the autoConnect and the subscribe.
Emissions aren't just dropped by observeOn. You are creating a hot observable that only caches one item. Because of this, it's possible to miss one or more emissions depending on when you subscribe.
The most common solution is to have your observable tell you whether it's loading or complete. Here is the common Android implementation.
So you would add a startWith before the replay(1) with Resource.loading(null). Then change your UI to start with the normal view instead of the loading view.
Another alternative, which I don't really advise, is to create your own scheduler that instantly runs whatever you schedule if you are already on the main thread. RxAndroid is open source so you can look at how they implemented the main thread scheduler and create a new implementation for your needs.
"Then change your UI to start with the normal view instead of the loading view."
So you would only show your loading view if the observable tells you it is loading with that Resource class I mentioned. You will still "miss" a frame, but you won't get the flickering.
If you truly want to avoid observeOn posting when it doesn't need to post, you should make your own scheduler. It's not standard behavior.