一个MFC宏实现COM接口的问题

来源:百度文库 编辑:神马文学网 时间:2024/04/29 05:33:49

1.  问题提出:

《COM原理与应用》中的第五章的例子中的INIT_INTERFACE_PART(CDictionary, Dictionary)


DictionaryObj.h 文件中有以下宏定義:

BEGIN_INTERFACE_PART(Dictionary, IDictionary) 

INIT_INTERFACE_PART(CDictionary, Dictionary)

STDMETHOD_(BOOL, Initialize)();

STDMETHOD_(BOOL, LoadLibrary)(LPOLESTR);

STDMETHOD_(BOOL, InsertWord)(LPOLESTR, LPOLESTR); 

STDMETHOD_(void, DeleteWord)( LPOLESTR);

STDMETHOD_(BOOL, LookupWord)(LPOLESTR, LPOLESTR *);

STDMETHOD_(BOOL, RestoreLibrary)(LPOLESTR);

STDMETHOD_(void, FreeLibrary)();

END_INTERFACE_PART_STATIC(Dictionary)

2.候sir说过:“源码面前了无秘密”。看看这些宏定义的源代码:

#define BEGIN_INTERFACE_PART(localClass, baseClass) \    //这个宏在代码中插入如下代码一看就知道声明了IUnknown的三个方法

class X##localClass : public baseClass \

{ \

public: \

        STDMETHOD_(ULONG, AddRef)(); \

        STDMETHOD_(ULONG, Release)(); \

        STDMETHOD(QueryInterface)(REFIID iid, LPVOID* ppvObj); \

#ifndef _AFX_NO_NESTED_DERIVATION             //这里进行了判断,所以有时候不要也可以,最好要

#define INIT_INTERFACE_PART(theClass, localClass) \

        size_t m_nOffset; \                     //纪录指针偏移量

        INIT_INTERFACE_PART_DERIVE(theClass, localClass) \

#define INIT_INTERFACE_PART_DERIVE(theClass, localClass) \

        X##localClass() \

               { m_nOffset = offsetof(theClass, m_x##localClass); } \

#else

#define INIT_INTERFACE_PART(theClass, localClass)

#define INIT_INTERFACE_PART_DERIVE(theClass, localClass)

#endif

看了源码,其实我们已经可以清楚这些宏到底做了些什么。

1 首先你上面的问题:


就以原例说明:

baseClass:是指接口类IDictionary


localClass:是指实现当前接口IDictionary的嵌套类


theClass:这个才是真正实现接口的嵌套类!

好,再结合一个msdn的例子:

class CPrintEditObj : public CCmdTarget

{

public:

    // member data and member functions for CPrintEditObj go here

// Interface Maps

protected:

    DECLARE_INTERFACE_MAP()

    BEGIN_INTERFACE_PART(EditObj, IEditInterface)

        STDMETHOD_(void, EditObject)();

    END_INTERFACE_PART(EditObj)

    BEGIN_INTERFACE_PART(PrintObj, IPrintInterface)

        STDMETHOD_(void, PrintObject)();

    END_INTERFACE_PART(PrintObj)

};

在这个例子中CPrintEditObj是嵌套类,实现了两个接口IEditInterface和IPrintInterface,而:

BEGIN_INTERFACE_PART(EditObj,IEditInterface) 实现了IEditInterface接口

BEGIN_INTERFACE_PART(PrintObj, IPrintInterface) 实现了IPrintInterface接口

宏源码中的:

#define INIT_INTERFACE_PART_DERIVE(theClass, localClass) \

        X##localClass() \

               { m_nOffset = offsetof(theClass, m_x##localClass); } \

纪录下了m_x EditObj和m_x PrintObj与包容类CPrintEditObj的地址偏移。以便在通过CPrintEditObj嵌套类查询IEditInterface 和IPrintInterface接口的时候能返回正确的接口指针。

 


本文来自CSDN博客,转载请标明出处:http://blog.csdn.net/newcore/archive/2005/06/02/386714.aspx