IsAssignableFrom与COM(IsAssignableFrom with COM)

2019-10-20 04:26发布

我有一个COM API,Autodesk Inventor的工作。

该测试通过了:

[Test]
public void CastTest()
{
    Inventor.Document document = _application.ActiveDocument;
    var assemblyDocument = (Inventor.AssemblyDocument)document;
    Assert.NotNull(assemblyDocument);
}

该测试失败:

[Test]
public void IsAssignableFromTest()
{
    Assert.IsTrue(typeof(Inventor.Document).IsAssignableFrom(typeof(Inventor.AssemblyDocument)));
}

我不知道很多有关COM可言,是有办法来检查,如果一个COM类“继承”另一个使用反射或某些COM巫术?

Answer 1:

COM类型系统是不是与.NET兼容。 相反,你是编程对包装(所谓的RCW的)。 为了测试,如果你可以将一个COM对象转换成另一个,COM提供QueryInterface -方法为成员IUnknown ,其中每一个COM对象必须实现。 但是.NET隐藏这些细节给你,让你可以编写COM代码,它的“感觉”像.NET代码。

如果你看一看的发明者互操作库的拆卸,你会认识到,有没有直接的关系, DocumentAssemblyDocument 。 两者都是那些只实现各自的组件类的默认界面,并与归因接口CoClassAttribute 。 但在他们的继承树,它们是没有直接关系的对方。 他们既可以实现相同的接口(我猜是这样IDocument ),但你不能转换一个WinForms按钮到一个图片框或者,即使他们都implment的Control -interface。

这是反射和IsAssignableFrom是测试:每个CLR型提供的元数据。 COM在这里工作不同。 每个COM对象可以在它自己的“决定”,如果它可以从另一个接口来调用。 为此它实现QueryInterface 。 为此和你必须创建源类型的实例,然后才能执行测试(COM不知道静态成员)。

传统投不调用QueryInterface ,让您的测试可能只是看起来像:

[Test]
public void IsAssignableFromTest()
{
    Assert.IsNotNull(_application.ActiveDocument as Inventor.AssemblyDocument);
}

否则,你可以调用QueryInterface通过直接Marshal -class。

然而,这是不可能通过与COM对象反射测试类型的元数据。



Answer 2:

如果你想使用Inventor的API,你可以强制转换为另一种类型之前检查的文件类型。

例:(VBA)

Dim oDoc As Document
Dim oAssyDoc As AssemblyDocument

Set oDoc = ThisApplication.ActiveDocument

If oDoc.DocumentType = DocumentTypeEnum.kAssemblyDocumentObject Then
    Set oAssyDoc = oDoc
End If

最好的祝福,



文章来源: IsAssignableFrom with COM