我有一些需要創建多個實例的部分導入。通過搜索我決定我需要使用ExportFactory類。不幸的是,默認情況下,ExportFactory類在WPF中不可用,但幸運的是Glenn Block有ported the code。MEF - [ImportMany]在WPF中使用ExportFactory <T> - .NET 4.0
原來,在導入時我指定類型:
[ImportMany(typeof(IMyModule))]
public IEnumerable<Lazy<IMyModule, IMyModuleMetadata>> Modules { get; set; }
我還創建了一個出口屬性:
[MetadataAttribute]
[AttributeUsage(AttributeTargets.Class, AllowMultiple=false)]
public class ExportMyModuleMetadata : ExportAttribute, IMyModuleMetadata
{
public ExportMyModuleMetadata(string category, string name)
: base(typeof(IMyModuleData))
{
Category = category;
Name = name;
}
public string Category { get; set; }
public string Name { get; set; }
}
我出口是這樣的:
[ExportMyModuleMetadata("Standard","Post Processor")]
[PartCreationPolicy(CreationPolicy.NonShared)]
public class Module1 : IMyModuleData
以上導入工作正常。但是,一旦我將Lazy<T,T>
更改爲ExportFactory<T,T>
,我在組合過程中開始出現錯誤。
[ImportMany(typeof(IMyModule))]
public IEnumerable<ExportFactory<IMyModule, IMyModuleMetadata>> Modules { get; set; }
我得到的錯誤信息是:
The export 'Module1 (ContractName="IMyModule")' is not assignable to type
'System.ComponentModel.Composition.ExportFactory`
我看到的地方(我找不到鏈接現在),在ImportMany
屬性指定Type
的問題。我想我可以沒有它,所以我從ImportMany
刪除類型。使用Lazy<T,T>
當
[ImportMany()]
public IEnumerable<Lazy<IMyModule, IMyModuleMetadata>> Modules { get; set; }
該進口仍然工作,但一旦我把它改爲ExportFactory<T,T>
,我不再進口任何東西。我再也沒有遇到錯誤,但沒有任何東西被導入。
有誰知道如何正確使用ImportMany
與ExportFactory<T,T>
的WPF?
更新:
隨着韋斯的關於添加ExportFactoryProvider()
技巧中,我得到了ExportFactory<T,T>
.NET 4的工作!以下是更新後的合成代碼。
var ep = new ExportFactoryProvider();
//Looks for modules in main assembly and scans folder of DLLs for modules.
var moduleCatalog = new AggregateCatalog(
new AssemblyCatalog(runningApp),
new DirectoryCatalog(".", "*.dll"));
var container = new CompositionContainer(moduleCatalog, ep);
ep.SourceProvider = container;
var Modules = new Modules();
container.ComposeParts(Modules);
我也發現了這個討論在MEF Codeplex site,討論多一點關於這一點。
記住申請讓 - 菲利普·勒孔特的修復在天空驅動器文件中的註釋中提到: 在ExportFactoryInstantiationProvider在行115: 如果(CBID == NULL || cbid.RequiredTypeIdentity.StartsWith(PartCreatorContractPrefix)!) 應是: 如果(CBID == NULL || cbid.RequiredTypeIdentity == NULL || cbid.RequiredTypeIdentity.StartsWith(PartCreatorContractPrefix)!) 因爲RequiredTypeIdentity(cbid.RequiredTypeIdentity)爲空時,不存在必要型(進口按名稱),從而在空字符串上調用StartsWith。 – Sly