Ошибка компиляции MvvmCross MvxWindowsPage

#c# #xaml #xamarin #uwp #mvvmcross

#c# #xaml #xamarin #uwp #mvvmcross

Вопрос:

Я пишу Xamarin.iOS , Xamarin.Android и UWP кроссплатформенное приложение с фреймворком MvvmCross.

Я создаю страницу входа, на которой есть LoginViewModel. В Xamarin.iOS , Xamarin.Android проектах привязка ViewModel и представления с нижеприведенным работает просто отлично

 public class LoginActivity : MvxAppCompatActivity<LoginViewModel> 
  
 public partial class LoginViewController : MvxViewController<LoginViewModel>  
  

Пытаясь сделать то же самое, что и выше, в UWP проекте, я получаю некоторую ошибку.

В XAML:

 <views:MvxWindowsPage
x:TypeArguments="viewModels:LoginViewModel" x:Class="MyApp.UWP.Views.LoginView"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:views="using:MvvmCross.WindowsUWP.Views"
xmlns:viewModels="using:MyApp.PresentationCore.ViewModels"
mc:Ignorable="d">
  

И мой код C #

 public sealed partial class LoginView : MvxWindowsPage<LoginViewModel>
  

Но я получаю ошибки компиляции. Как я могу их устранить?

  • `Неизвестный элемент’TypeArguments’ в элементе ‘MvxWindowsPage’
  • Имя «LoginViewModel» не существует в пространстве имен «using:MyApp.PresentationCore.ViewModels».
  • Общие аргументы[0], ‘Система.Объект’, на ‘MvvmCross.WindowsUWP.Views.MvxWindowsPage`1[TViewModel]’ нарушает ограничение типа ‘TViewModel’.

Я думаю, что ошибки немного неоднозначны, потому что при первой ошибке нет шаблонной версии, но третья ошибка связана с нарушением ограничения шаблона.

Я знаю, что есть опция, связывающая ViewModel и представление с соглашением об именовании или атрибутами, но я хотел бы использовать это строго типизированное решение.

Комментарии:

1. Не могли бы вы, пожалуйста, поделиться базовой демонстрацией, которая может воспроизвести эту проблему?

2. Я создал базовую демонстрационную версию, начиная с командной таблицы решения MvvmCross. Вы можете получить к нему доступ здесь Единственное, что я изменил, это базовый класс FirstView в проекте UWP.

Ответ №1:

К сожалению, я считаю, что UWP не поддерживает TypeArguments и, следовательно, параметры общих типов для базовых страниц. Вы можете проверить поток Prism GitHub, где они обсуждают это. Поэтому вам придется выбрать один из других вариантов регистрации.


Mvvmcross предлагает различные альтернативные подходы для регистрации вашего View в ViewModel . Во время инициализации Mvvmcross он попытается зарегистрировать ваш ViewModel для вашего View использования MvxViewModelViewTypeFinder в следующем порядке:

Регистрация на основе атрибутов:

Вы можете добавить MvxViewFor атрибут к своему классу страницы.

 [MvxViewFor(typeof(FirstViewModel))]
public sealed partial class FirstView : MvxWindowsPage
{
    public FirstView()
    {
        this.InitializeComponent();
    }
}
  

Регистрация на основе конкретного типа:

Вы можете зарегистрировать свой View на свой ViewModel , указав конкретный тип ViewModel.

 public sealed partial class FirstView : MvxWindowsPage
{
    public new FirstViewModel ViewModel => base.ViewModel as FirstViewModel;

    public FirstView()
    {
        this.InitializeComponent();
    }
}
  

Или в случае Android и iOS, где может использоваться общий базовый класс:

 // Android
public class FirstActivity : MvxAppCompatActivity<FirstViewModel>

// iOS
public class FirstViewController : MvxViewController<FirstViewModel>
  

Регистрация на основе соглашения:

Ваш view и ViewModel могут следовать одному и тому же соглашению об именовании, и Mvvmcross отобразит их для вас (xxxView и xxxViewModel)

Вид

 public sealed partial class FirstView : MvxWindowsPage
{
    public FirstView()
    {
        this.InitializeComponent();
    }
}
  

ViewModel

 public class FirstViewModel : MvxViewModel