MVVMCross是否支持共享项目?嵌入Xamarin共享项目遇注册冲突
嘿,先给你明确答案:MVVMCross完全支持Shared Project!你遇到的这个重复注册报错,是因为视图被多次扫描并绑定到同一个ViewModel导致的,咱一步步来解决:
报错原因分析
Shared Project的特性是代码会被所有引用它的平台项目(比如Android、iOS)直接包含编译,如果你用了MVVMCross默认的约定式视图-ViewModel匹配(自动扫描程序集找对应关系),就会出现同一个HomePage被每个平台项目都扫描一次,进而重复注册HomeViewModel的情况,触发An item with the same key has already been...的错误。
具体解决步骤
1. 检查视图文件的编译配置
先确认Shared Project里的HomePage.xaml和HomePage.xaml.cs的编译操作:
HomePage.xaml:设置为Embedded ResourceHomePage.xaml.cs:设置为Compile
同时确保没有在任何平台项目里重复添加这些视图文件(比如不要把Shared Project的视图复制到Android项目里)。
2. 自定义视图扫描逻辑(解决约定式注册重复问题)
在每个平台项目的Setup.cs里重写GetViewAssemblies方法,确保只扫描一次Shared Project的程序集:
protected override IEnumerable<Assembly> GetViewAssemblies() { var baseAssemblies = base.GetViewAssemblies().ToList(); // 去重,避免同一个Shared Project程序集被多次扫描 return baseAssemblies.Distinct(); }
如果还是不行,可以直接指定要扫描的程序集,比如只包含Shared Project和当前平台项目的程序集:
protected override IEnumerable<Assembly> GetViewAssemblies() { return new[] { typeof(HomePage).Assembly, typeof(Setup).Assembly }; }
3. 改用手动注册视图-ViewModel(更稳妥的方式)
如果不想依赖自动扫描,直接在Setup.cs的InitializeLastChance方法里手动绑定:
protected override void InitializeLastChance() { base.InitializeLastChance(); // 手动注册ViewModel和View的对应关系 var lookup = new Dictionary<Type, Type> { { typeof(HomeViewModel), typeof(HomePage) } // 其他ViewModel-View绑定也可以加在这里 }; Mvx.RegisterSingleton<IMvxViewModelLocator>(new MvxViewModelLocator { ViewModelViewLookup = lookup }); }
4. 清理重建解决方案
有时候编译缓存会导致奇怪的重复问题,先删除所有项目的bin和obj文件夹,然后重新生成整个解决方案,很多时候能解决这类问题。
额外注意事项
如果你是用Xamarin.Forms结合MVVMCross,记得Shared Project只放Forms的视图和ViewModel,原生平台的视图(比如Android的.axml、iOS的.storyboard)要放在各自的平台项目里,不要混在Shared Project中。
内容的提问来源于stack exchange,提问作者Funcky

