I have a database catalog that is populated, and a cursor that can be used to retrieve objects. This catalog can obviously be very large, and what I'd like to do is use ReactiveUI to buffer the data in, while keeping the UI data-bound and responsive. I followed the steps here to translate my IEnumerable
into an IObservable
, as shown here:
public class CatalogService
{
...
public IObservable<DbObject> DataSource
{
get
{
return Observable.Create<DbObject>(obs =>
{
var cursor = Database.Instance.GetAllObjects();
var status = cursor.MoveToFirst();
while (status == DbStatus.OK)
{
var dbObject= Db.Create(cursor);
obs.OnNext(dbObject);
status = cursor.MoveToNext();
}
obs.OnCompleted();
return Disposable.Empty;
});
}
}
}
In my view class (specifically, the Loaded
event), I am subscribing to the data-source and using the buffer method in hopes of keeping the UI responsive.
public ObservableCollection<DbObject> DbObjects { get; set; }
private async void OnLoad(object sender, RoutedEventArgs e)
{
var observableData = CatalogService.Instance.DataSource.Publish();
var chunked = observableData.Buffer(TimeSpan.FromMilliseconds(100));
var dispatcherObs = chunked.ObserveOnDispatcher(DispatcherPriority.Background);
dispatcherObs.Subscribe(dbObjects =>
{
foreach (var dbObject in dbObjects)
{
DbObjects.Add(dbObject);
}
});
await Task.Run(() => observableData.Connect());
await dispatcherObs.ToTask();
}
The result is unfortunately quite the opposite. When my view control (which contains a simple ListBox
data-bound to the DbObjects
property) loads, it does not show any data until the entire catalog has been enumerated. Only then does the UI refresh.
I am new to ReactiveUI, but I am sure that it is capable for the task at hand. Does anyone have any suggestions or pointers if I am using it incorrectly?