2017-05-07 66 views
0

所以我有一個接口(IInterface1)公開爲ComVisible(true),ClassInterfaceType(ClassInterfaceType.None)。如何通過COM Interop訪問複雜對象的屬性?

我有該接口,丙氨酸的對象:

public interface IInterface1 
{ 
    Object1 object {get; set;} 
} 

對象一個也被標記有ComVisible特性(真),是在一個單獨的組件,ClassInterfaceType(ClassInterfaceType.None),看起來像這樣:

public interface IObject1 
{ 
    string MyProperty {get;set;} 
} 

在C#的是,我有下面的類:

public class Interface1 : IInterface1 
{ 
    public IObject1 Object1 {get;set;} 
} 

從非託管C++,我將如何訪問Interface1.Object1.MyProperty?我正在導入TLH raw_interfaces_only,可以CreateInstance我的Interface1類,並訪問Object1。如果我嘗試訪問Object1上的MyProperty,則會得到「不允許的不完整類類型指針」。

C++代碼的樣子:

Assembly1::Interface1Ptr interface1ptr; 
HRESULT hrRetval = CoInitialize(NULL); 
hrRetval = interface1ptr.CreateInstance(__uuidof(Assembly1::Interface1)); 
Assembly1::Object1 *object1; 

hrRetval = interface1ptr.get_Object1(&object1); 

這是我堅持:

hrRetval = object1->get_MyProperty(varToStore); // This doesn't work. 

欣賞任何指針(HAR HAR)。

回答

0

你可以只導入這兩個組件,這應該是它:

Assembly1:

namespace ClassLibrary1 
{ 
    [ComVisible(true)] 
    public interface IObject1 
    { 
     string MyProperty { get; } 
    } 

    [ComVisible(true)] 
    [ClassInterface(ClassInterfaceType.None)] 
    public class Object1 : IObject1 
    { 
     public string MyProperty { get => "42"; } 
    } 
} 

// AssemblyInfo.cs 
[assembly: Guid("d1e7f7b4-3c3a-41e5-b0bf-5dec54050431")] 

Assembly2:

namespace ClassLibrary2 
{ 
    [ComVisible(true)] 
    public interface IInterface1 
    { 
     IObject1 Object1 {get;} 
    } 

    [ComVisible(true)] 
    [ClassInterface(ClassInterfaceType.None)] 
    public class Interface1 : IInterface1 
    { 
     public IObject1 Object1 { get => new Object1(); } 
    } 
} 

// AssemblyInfo.cs 
[assembly: Guid("a7a14989-71da-49d4-87be-85c4b87bcaf0")] 

C++:

#include "stdafx.h" 
#import "libid:d1e7f7b4-3c3a-41e5-b0bf-5dec54050431" raw_interfaces_only 
#import "libid:a7a14989-71da-49d4-87be-85c4b87bcaf0" raw_interfaces_only 

int main() 
{ 
    CoInitialize(nullptr); 

    ClassLibrary2::IInterface1Ptr i1; 
    i1.CreateInstance(__uuidof(ClassLibrary2::Interface1)); 

    ClassLibrary1::IObject1Ptr o1; 
    i1->get_Object1(&o1); 

    BSTR bstr; 
    o1->get_MyProperty(&bstr); 

    CoUninitialize(); 
    return 0; 
} 

BTW,是有一些s特別的原因你爲什麼要raw_interfaces_only?沒有它會更容易和更安全:

ClassLibrary2::IInterface1Ptr i1; 
i1.CreateInstance(__uuidof(ClassLibrary2::Interface1)); 

auto o1 = i1->Object1; 
auto bstr = o1->MyProperty;