I try to open a page in a new window in my UWP app. Is this possible with the IMvxNavigationService
provided by MvvmCross? Right now it only replaces the page in the current window.
ViewModel
public class MyViewModel: MvxViewModel
{
private readonly IMvxNavigationService _navigationService;
public MyViewModel(IMvxNavigationService navigationService)
{
_navigationService = navigationService;
}
public MvxCommand MyCommand { get; set; }
public override void Prepare()
{
base.Prepare();
MyCommand = new MvxCommand<>(MyEvent);
}
private void MyEvent()
{
_navigationService.Navigate<OtherViewModel>();
}
}
I now realized that I could implement a custom presenter and use the new AppWindow.
MvxWindowPresentationAttribute.cs
public class MvxWindowPresentationAttribute : MvxBasePresentationAttribute
{
}
CustomMvxWindowsViewPresenter.cs
public class CustomMvxWindowsViewPresenter : MvxWindowsViewPresenter
{
public CustomMvxWindowsViewPresenter(IMvxWindowsFrame rootFrame) : base(rootFrame)
{
}
public override void RegisterAttributeTypes()
{
base.RegisterAttributeTypes();
AttributeTypesToActionsDictionary.Register<MvxWindowPresentationAttribute>(ShowWindow, CloseWindow);
}
private Task<bool> CloseWindow(IMvxViewModel viewModel, MvxWindowPresentationAttribute attribute)
{
return base.ClosePage(viewModel, attribute);
}
private Task<bool> ShowWindow(Type viewType, MvxWindowPresentationAttribute attribute,
MvxViewModelRequest request)
{
try
{
return Task.Run(async () =>
{
var requestText = GetRequestText(request);
var viewsContainer = Mvx.IoCProvider.Resolve<IMvxViewsContainer>();
await CoreApplication.MainView.CoreWindow.Dispatcher.RunAsync(CoreDispatcherPriority.High,
async () => {
var appWindow = await AppWindow.TryCreateAsync();
var appWindowContentFrame = new Frame();
appWindowContentFrame.Navigate(viewType, requestText);
ElementCompositionPreview.SetAppWindowContent(appWindow, appWindowContentFrame);
await appWindow.TryShowAsync();
HandleBackButtonVisibility();
});
return true;
});
}
catch (Exception exception)
{
return Task.FromResult(false);
}
}
}
Setup.cs
protected override IMvxWindowsViewPresenter CreateViewPresenter(IMvxWindowsFrame rootFrame)
{
return new CustomMvxWindowsViewPresenter(rootFrame);
}
The only thing left to do is to annotate your views with the created attribute MvxWindowPresentation
.
OtherView.xaml.cs
[MvxWindowPresentation]
public sealed partial class OtherView : MvxWindowsPage
{
// ...
}