# ReactiveUI.Uno **Repository Path**: mirrors_reactiveui/ReactiveUI.Uno ## Basic Information - **Project Name**: ReactiveUI.Uno - **Description**: No description available - **Primary Language**: Unknown - **License**: MIT - **Default Branch**: main - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2022-04-12 - **Last Updated**: 2026-07-26 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README [![Build](https://github.com/reactiveui/reactiveui.uno/actions/workflows/ci-build.yml/badge.svg)](https://github.com/reactiveui/reactiveui.uno/actions/workflows/ci-build.yml) [![Code Coverage](https://codecov.io/gh/reactiveui/reactiveui.uno/branch/main/graph/badge.svg)](https://codecov.io/gh/reactiveui/reactiveui.uno) [![#yourfirstpr](https://img.shields.io/badge/first--timers--only-friendly-blue.svg)](https://reactiveui.net/contribute) [![](https://img.shields.io/badge/chat-slack-blue.svg)](https://reactiveui.net/slack) [![ReactiveUI.Uno](https://img.shields.io/nuget/v/ReactiveUI.Uno.svg)](https://www.nuget.org/packages/ReactiveUI.Uno/) [![ReactiveUI.Uno.Reactive](https://img.shields.io/nuget/v/ReactiveUI.Uno.Reactive.svg)](https://www.nuget.org/packages/ReactiveUI.Uno.Reactive/)

# ReactiveUI for Uno Platform ReactiveUI.Uno integrates [ReactiveUI](https://reactiveui.net/) with the [Uno Platform](https://platform.uno/) so the same MVVM code can run on Windows, desktop, WebAssembly, Android, and Apple targets. It provides Uno-aware view bases, activation, routing hosts, dependency-property observation, binding hooks, boolean visibility conversion, scheduler integration, resource dictionaries, and suspension storage. The package family has two variants: | Package | Use when | Reactive foundation | | --- | --- | --- | | `ReactiveUI.Uno` | New Uno applications or libraries that should use ReactiveUI 24 with `ReactiveUI.Primitives` and avoid a direct `System.Reactive` dependency. | `ReactiveUI`, `ReactiveUI.Primitives`, `ReactiveUI.Primitives.Blazor` on browser WebAssembly targets. | | `ReactiveUI.Uno.Reactive` | Existing ReactiveUI/System.Reactive applications that need Rx-compatible `Unit`, `IScheduler`, and Rx operators while sharing the same Uno integration code. | `ReactiveUI.Reactive`, `ReactiveUI.Primitives.Reactive`, `ReactiveUI.Primitives.Blazor.Reactive` on browser WebAssembly targets. | Both packages use the same source code. `ReactiveUI.Uno.Reactive` compiles it with the `REACTIVE_SHIM` symbol and publishes the public types under `ReactiveUI.Uno.Reactive`. ## Supported Targets The packages are built as Uno single-project libraries. The solution currently targets: | Target family | Target frameworks | | --- | --- | | Cross-platform .NET | `net9.0`, `net9.0-desktop`, `net10.0`, `net10.0-desktop`, `net10.0-browserwasm`, `net11.0`, `net11.0-desktop`, `net11.0-browserwasm` | | Windows desktop | `net9.0-windows10.0.19041.0`, `net10.0-windows10.0.19041.0`, `net11.0-windows10.0.19041.0` | | Android | `net10.0-android`, `net11.0-android` | | iOS | `net10.0-ios`, `net11.0-ios` | Windows targets are added only when building on Windows. Apple mobile targets are added when building on macOS or Windows. ## Install Install one package, not both, into the Uno project that owns your application startup and views. ```powershell dotnet add package ReactiveUI.Uno ``` Use the Rx-compatible variant for existing System.Reactive-facing code: ```powershell dotnet add package ReactiveUI.Uno.Reactive ``` The repository uses central package management. At the time of this branch, the core package references are: | Package | Version | | --- | --- | | `ReactiveUI` | `24.0.0-beta.3` | | `ReactiveUI.Reactive` | `24.0.0-beta.3` | | `ReactiveUI.Primitives` | `6.0.0` | | `ReactiveUI.Primitives.Reactive` | `6.0.0` | | `ReactiveUI.Primitives.Blazor` | `6.0.0` | | `ReactiveUI.Primitives.Blazor.Reactive` | `6.0.0` | ## Namespace Map | Scenario | Main namespaces | | --- | --- | | Lean package | `ReactiveUI`, `ReactiveUI.Builder`, `ReactiveUI.Primitives`, `ReactiveUI.Primitives.Concurrency`, `ReactiveUI.Uno` | | Rx-compatible package | `ReactiveUI.Reactive`, `ReactiveUI.Builder`, `ReactiveUI.Reactive.Builder`, `ReactiveUI.Primitives.Reactive`, `ReactiveUI.Primitives.Reactive.Concurrency`, `ReactiveUI.Uno.Reactive` | | XAML namespace | `http://reactiveui.net` on non-Windows targets, or `using:ReactiveUI.Uno` / `using:ReactiveUI.Uno.Reactive` | `ReactiveUI.Uno` uses `ReactiveUI.Primitives.RxVoid` for command completion values and `ReactiveUI.Primitives.Concurrency.ISequencer` for scheduling. `ReactiveUI.Uno.Reactive` uses `System.Reactive.Unit` and `System.Reactive.Concurrency.IScheduler` through the `.Reactive` packages. ## Application Startup Call `WithUno(Window)` during application startup. It registers Uno services, configures the main-thread scheduler, configures the task-pool scheduler, registers binding converters and hooks, and adds the ReactiveUI Uno resource dictionary after the startup window activates. ```csharp using ReactiveUI.Builder; using ReactiveUI.Uno; public partial class App : Application { private Window? _window; protected override void OnLaunched(LaunchActivatedEventArgs args) { _window ??= new Window(); _ = RxAppBuilder.CreateReactiveUIBuilder() .WithUno(_window) .WithDefaultIScreen() .BuildApp(); _window.Content = new MainView { ViewModel = new MainViewModel() }; _window.Activate(); } } ``` The `.Reactive` startup shape is the same, but the view and library types come from `ReactiveUI.Uno.Reactive`. ```csharp using ReactiveUI.Builder; using ReactiveUI.Uno.Reactive; _ = RxAppBuilder.CreateReactiveUIBuilder() .WithUno(window) .WithRegistration(mutable => mutable.RegisterConstant(new AppBootstrapper())) .BuildApp(); ``` ## API Reference ### Builder and Registration | API | Package namespace | Purpose | | --- | --- | --- | | `UnoReactiveUIBuilderExtensions.WithUno(Window startupWindow)` | `ReactiveUI.Builder` | Registers Uno services, the platform scheduler, task-pool scheduler, resource dictionary, binding converters, binding hooks, activation, dependency-property observation, and suspension storage. | | `UnoReactiveUIBuilderExtensions.WithUnoScheduler()` | `ReactiveUI.Builder` | Registers only the current Uno main-thread scheduler. Use this for advanced hosts that manage services and resources separately. | | `UnoReactiveUIBuilderExtensions.WithDefaultIScreen()` | `ReactiveUI.Builder` | Registers a default `IScreen` backed by `AppBootstrapper`. | | `UnoReactiveUIBuilderExtensions.UnoMainThreadScheduler` | `ReactiveUI.Builder` | Non-Windows scheduler facade that resolves `UnoDispatcherScheduler.Current` lazily. | | `UnoReactiveUIBuilderExtensions.UnoWinUIMainThreadScheduler` | `ReactiveUI.Builder` | Windows scheduler facade that resolves `UnoWinUIDispatcherScheduler.Current` lazily. | | `Registrations` | `ReactiveUI.Uno` or `ReactiveUI.Uno.Reactive` | Implements `IWantsToRegisterStuff`; registers platform services, converters, hooks, and `WinRTAppDataDriver`. Usually used through `WithUno`. | | `AppBootstrapper` | `ReactiveUI.Uno` or `ReactiveUI.Uno.Reactive` | `ReactiveObject` and `IScreen` implementation with a `RoutingState Router`. | ### Views and Host Controls | API | Members | Purpose | | --- | --- | --- | | `ReactivePage` | `ViewModelProperty`, `ViewModel`, `BindingRoot`, `IViewFor.ViewModel` | Uno `Page` base class that implements `IViewFor` and wires an empty activation block so `WhenActivated` is available. | | `ReactiveUserControl` | `ViewModelProperty`, `ViewModel`, `BindingRoot`, `IViewFor.ViewModel` | Uno `UserControl` base class that implements `IViewFor`. | | `RoutedViewHost` | `Router`, `DefaultContent`, `ViewContract`, `ViewContractObservable`, `ViewLocator` | `TransitioningContentControl` that displays the view for `Router.CurrentViewModel`. | | `ViewModelViewHost` | `ViewModel`, `DefaultContent`, `ViewContract`, `ViewContractObservable`, `ViewLocator` | `TransitioningContentControl` that displays the view for a single view model object, useful inside data templates. | | `TransitioningContentControl` | Inherits `ContentControl` | Base content host used by `RoutedViewHost` and `ViewModelViewHost`. | | `ReactiveUIUnoDictionary` | `Source` is set to the embedded package dictionary | Loads the package resource dictionary. `WithUno(Window)` adds it automatically. | ### Activation, Binding, and Platform Services | API | Members | Purpose | | --- | --- | --- | | `ActivationForViewFetcher` | `GetAffinityForView(Type)`, `GetActivationForView(IActivatableView)` | Activates `FrameworkElement` views when they are loading, visible to hit testing, and not unloaded. | | `DependencyObjectObservableForProperty` | `GetAffinityForObject(...)`, `GetNotificationForProperty(...)` | Observes Uno dependency-property changes for `WhenAnyValue`, bindings, and property observation. Falls back to POCO observation when needed. | | `AutoDataTemplateBindingHook` | `DefaultItemTemplate`, `ExecuteHook(...)` | Automatically assigns a `DataTemplate` containing `ViewModelViewHost` when an `ItemsControl.ItemsSource` binding has no template or display member path. | | `BooleanToVisibilityTypeConverter` | `GetAffinityForObjects()`, `TryConvert(bool, object?, out Visibility)` | Converts `bool` values to `Visibility.Visible` or `Visibility.Collapsed`. | | `BooleanToVisibilityHint` | `None`, `Inverse` | Optional conversion hint for inverted boolean visibility conversion. | | `PlatformOperations` | `GetOrientation()` | Supplies the current display orientation for view contract selection where platform APIs are available. | ### Schedulers | API | Platform | Lean package behavior | `.Reactive` package behavior | | --- | --- | --- | --- | | `UnoDispatcherScheduler` | Non-Windows Uno targets using `Windows.UI.Core.CoreDispatcher` | Implements `ISequencer`, exposes `Current`, `Dispatcher`, `Priority`, `Now`, `Timestamp`, `Schedule(IWorkItem)`, `Schedule(IWorkItem, long)`, and `SchedulePeriodic(...)`. | Implements the Rx scheduler surface through the `IScheduler` alias, exposing `Current`, `Dispatcher`, `Priority`, `Now`, `Schedule(...)`, due-time overloads, and `SchedulePeriodic(...)`. | | `UnoWinUIDispatcherScheduler` | Windows targets using `Microsoft.UI.Dispatching.DispatcherQueue` | Implements `ISequencer`, exposes `Current`, `DispatcherQueue`, `Priority`, `Now`, `Timestamp`, `Schedule(IWorkItem)`, `Schedule(IWorkItem, long)`, and `SchedulePeriodic(...)`. | Implements the Rx scheduler surface through the `IScheduler` alias, exposing `Current`, `DispatcherQueue`, `Priority`, `Now`, `Schedule(...)`, due-time overloads, and `SchedulePeriodic(...)`. | On browser WebAssembly targets, `WithUno(Window)` uses `ReactiveUI.Primitives.Blazor.Concurrency.BlazorRendererSequencer` in the lean package and `ReactiveUI.Primitives.Blazor.Reactive.Concurrency.BlazorRendererSequencer` in the `.Reactive` package. ### Suspension Storage | API | Return type in `ReactiveUI.Uno` | Return type in `ReactiveUI.Uno.Reactive` | Purpose | | --- | --- | --- | --- | | `WinRTAppDataDriver.LoadState()` | `IObservable` | `IObservable` | Loads DataContract XML state from `ApplicationData.Current.RoamingFolder/appData.xmlish`. This path is marked `RequiresDynamicCode` and `RequiresUnreferencedCode`. | | `WinRTAppDataDriver.SaveState(T state)` | `IObservable` | `IObservable` | Saves DataContract XML state to `appData.xmlish`. This path is marked `RequiresDynamicCode` and `RequiresUnreferencedCode`. | | `WinRTAppDataDriver.LoadState(JsonTypeInfo typeInfo)` | `IObservable` | `IObservable` | Loads JSON state from `appData.json` using source-generated `JsonTypeInfo`. Prefer this for AOT/trimming. | | `WinRTAppDataDriver.SaveState(T state, JsonTypeInfo typeInfo)` | `IObservable` | `IObservable` | Saves JSON state using source-generated `JsonTypeInfo`. Prefer this for AOT/trimming. | | `WinRTAppDataDriver.InvalidateState()` | `IObservable` | `IObservable` | Deletes both XML and JSON persisted state files when present. | ## Feature Examples ### Reactive View Models Use `ReactiveObject`, `RaiseAndSetIfChanged`, `WhenAnyValue`, `ObservableAsPropertyHelper`, and `ReactiveCommand` from ReactiveUI. In the lean package, use `ReactiveUI.Primitives.RxVoid` for command completion values. ```csharp using ReactiveUI; using ReactiveUI.Primitives; public sealed class DeviceViewModel : ReactiveObject, IDisposable { private readonly ObservableAsPropertyHelper _isCritical; private string _name = "Pump A17"; private double _pressure; public DeviceViewModel() { _isCritical = this.WhenAnyValue(x => x.Pressure) .Select(static pressure => pressure > 56) .ToProperty(this, static x => x.IsCritical); Refresh = ReactiveCommand.CreateFromTask(RefreshAsync); } public string Name { get => _name; set => this.RaiseAndSetIfChanged(ref _name, value); } public double Pressure { get => _pressure; set => this.RaiseAndSetIfChanged(ref _pressure, value); } public bool IsCritical => _isCritical.Value; public ReactiveCommand Refresh { get; } public void Dispose() { _isCritical.Dispose(); Refresh.Dispose(); } private Task RefreshAsync() { Pressure = 42.5; return Task.CompletedTask; } } ``` The `.Reactive` package uses the same ReactiveUI concepts with `System.Reactive.Unit`. ```csharp using ReactiveUI.Reactive; using System.Reactive; public ReactiveCommand Refresh { get; } = ReactiveCommand.Create(() => Unit.Default); ``` ### ReactivePage `ReactivePage` is the recommended base for page-level views. For Uno XAML, create a non-generic base class and use that base in XAML. ```csharp using ReactiveUI; using ReactiveUI.Uno; public sealed class MainPageBase : ReactivePage { } public sealed partial class MainPage : MainPageBase { public MainPage() { InitializeComponent(); ViewModel = new MainViewModel(); this.WhenActivated(disposables => { disposables(this.OneWayBind(ViewModel, vm => vm.Title, view => view.TitleText.Text)); disposables(this.BindCommand(ViewModel, vm => vm.Refresh, view => view.RefreshButton)); }); } } ``` ```xml