我正在尝试将插件库项目合并为一个(例如,Location + PhoneCallTask)。它与 wp7 完美配合,但我得到了一个未处理的 monodroid 异常:
无法加载文件或程序集“Cirrious.MvvmCross.Plugins.Location.Droid.dll”
当然,位置插件是在合并库“Cirrious.MvvmCross.Plugins.Droid.dll”中引用的。
有没有办法指向合并的库路径?
我正在尝试将插件库项目合并为一个(例如,Location + PhoneCallTask)。它与 wp7 完美配合,但我得到了一个未处理的 monodroid 异常:
无法加载文件或程序集“Cirrious.MvvmCross.Plugins.Location.Droid.dll”
当然,位置插件是在合并库“Cirrious.MvvmCross.Plugins.Droid.dll”中引用的。
有没有办法指向合并的库路径?
更全面地考虑了您的问题...
我仍然不完全确定什么是合并插件,但我认为您看到的问题必须归结为 MvvmCross-MonoDroid 使用文件约定加载插件而所有其他平台强制用户提供显式工厂方法的方式对于每个插件。
这种差异的原因是因为文件约定是(IMO)这样做的最佳方式......但是所有其他平台都将安全和/或编译问题置于意味着必须使用替代机制的方式......
对您来说最简单的事情可能是切换您的 MonoDroid 应用程序的设置以使用加载器约定。
去做这个:
在 Setup.cs 中覆盖CreatePluginManager()
为:
protected override IMvxPluginManager CreatePluginManager()
{
var toReturn = new MvxLoaderBasedPluginManager();
var registry = new MvxLoaderPluginRegistry(".Droid", toReturn.Loaders);
AddPluginsLoaders(registry);
return toReturn;
}
然后提供一个AddPluginsLoaders()
实现,如:
protected virtual void AddPluginsLoaders(Cirrious.MvvmCross.Platform.MvxLoaderPluginRegistry loaders)
{
loaders.AddConventionalPlugin<Cirrious.MvvmCross.Plugins.Visibility.Droid.Plugin>();
loaders.AddConventionalPlugin<Cirrious.MvvmCross.Plugins.Location.Droid.Plugin>();
loaders.AddConventionalPlugin<Cirrious.MvvmCross.Plugins.Phone.Droid.Plugin>();
loaders.AddConventionalPlugin<AlphaPage.MvvmCross.Plugins.Mega.Droid.Plugin>();
// etc
}
简短的回答:
我猜你需要:
更长的答案(基于我已经拥有的一些笔记 - 将很快发布):
如果您要构建一个全新的插件,那么您将:
这将是可移植类库 - 比如说AlphaPage.MvvmCross.Plugins.Mega
在该中央共享 PCL 中,您可以放置任何可用的可移植代码 - 通常这可能只是一些服务接口定义 - 例如
public interface IAlphaService { ... }
和
public interface IPageService { ... }
然后,您将为该插件添加 PluginManager,它只会添加以下样板:
public class PluginLoader
: IMvxPluginLoader
, IMvxServiceConsumer<IMvxPluginManager>
{
public static readonly PluginLoader Instance = new PluginLoader();
#region Implementation of IMvxPluginLoader
public void EnsureLoaded()
{
var manager = this.GetService<IMvxPluginManager>();
manager.EnsureLoaded<PluginLoader>();
}
#endregion
}
对于每个平台,您将实现插件 - 例如,您可以实现AlphaPage.MvvmCross.Plugins.Mega.WindowsPhone
和 AlphaPage.MvvmCross.Plugins.Mega.Droid
在其中的每一个中,您将实现提供服务的本机类:
public class MyAlphaService : IAlphaService { ... }
和
public class MyPageService : IPageService { ... }
最后,每个插件都将提供样板插件实现:
public class Plugin
: IMvxPlugin
, IMvxServiceProducer
{
#region Implementation of IMvxPlugin
public void Load()
{
// alpha registered as a singleton
this.RegisterServiceInstance<IAlphaService>(new MyAlphaService());
// page registered as a type
this.RegisterServiceType<IPageService, MyPageService>();
}
#endregion
}
每个 UI 客户端都必须初始化插件。
这是通过终端 UI 客户端添加库引用来完成的:
然后,对于WinRT、WindowsPhone 和 MonoTouch客户端,您还需要在 setup.cs 中提供一个 Loader 访问器 - 例如:
protected override void AddPluginsLoaders(Cirrious.MvvmCross.Platform.MvxLoaderPluginRegistry loaders)
{
loaders.AddConventionalPlugin<AlphaPage.MvvmCross.Plugins.Mega.WindowsPhone.Plugin>();
base.AddPluginsLoaders(loaders);
}
请注意,此处使用了约定 - 因此 AlphaPage.MvvmCross.Plugins.Mega.WindowsPhone.Plugin 为 AlphaPage.MvvmCross.Plugins.Mega.PluginLoader 实现 WindowsPhone 插件很重要
对于MonoDroid客户端,您不需要添加此设置步骤 - 因为 MonoDroid 的 Assembly.Load 限制比其他平台少 - 而且 ao 可以从文件加载插件。但要使其正常工作,程序集名称匹配很重要 - 如果 PluginLoader 是,AlphaPage.MvvmCross.Plugins.Mega.PluginLoader
那么约定将尝试从AlphaPage.MvvmCross.Plugins.Mega.Droid.dll
在此设置之后,应用程序最终应该能够通过以下方式访问插件:
AlphaPage.MvvmCross.Plugins.Mega.PluginLoader.Instance.EnsureLoaded()
this.GetService<IAlphaService>()
然后使用或访问个别服务this.GetService<IPageService>()
一些插件可以是“纯可移植的”
在这种情况下,他们不需要针对每个平台进行任何专业化,也不需要第 3 步。
有关这方面的示例,请参阅 Json 实现 - https://github.com/slodge/MvvmCross/tree/vnext/Cirrious/Plugins/Json