如何创建一个从基类派生的ATL COM类?

时间:2008-11-17 17:39:56

标签: c++ visual-studio com atl classwizard

“ATL简单对象”向导未提供指定从现有coclass及其接口派生新类的方法。在Visual Studio 2008中,如何创建从现有的ATL COM类派生的新ATL COM类(即Base实现IBase,并且我想创建一个从{{Derived派生的新Base类1}}实现IDerived,其中IDerived派生自IBase。)

更新:听起来很简单,但向导生成的ATL类最多有六个基类,一个COM映射和一个连接点映射。应该在派生类中重复哪些基类和映射?如果映射在派生类中重复,它们是否应包含基类映射的内容或仅包含其他项?基类的顺序是否重要?那么FinalConstruct()FinalRelease()怎么样?应该在派生类中重复DECLARE_PROTECT_FINAL_CONSTRUCTDECLARE_REGISTRY_RESOURCEID吗?

这是一个示例基类,除了所有样板文件外都是空的。现在派生类应该是什么样的?

class ATL_NO_VTABLE CBase :
    public CComObjectRootEx<CComSingleThreadModel>,
    public CComCoClass<CBase, &CLSID_Base>,
    public ISupportErrorInfo,
    public IConnectionPointContainerImpl<CBase>,
    public CProxy_IBaseEvents<CBase>,
    public IDispatchImpl<IBase, &IID_IBase, &LIBID_ExampleLib, /*wMajor =*/ 1, /*wMinor =*/ 0>
{
public:
    CBase()
    {
    }

DECLARE_REGISTRY_RESOURCEID(IDR_Base)


BEGIN_COM_MAP(CBase)
    COM_INTERFACE_ENTRY(IBase)
    COM_INTERFACE_ENTRY(IDispatch)
    COM_INTERFACE_ENTRY(ISupportErrorInfo)
    COM_INTERFACE_ENTRY(IConnectionPointContainer)
END_COM_MAP()

BEGIN_CONNECTION_POINT_MAP(CBase)
    CONNECTION_POINT_ENTRY(__uuidof(_IBaseEvents))
END_CONNECTION_POINT_MAP()
// ISupportsErrorInfo
    STDMETHOD(InterfaceSupportsErrorInfo)(REFIID riid);


    DECLARE_PROTECT_FINAL_CONSTRUCT()

    HRESULT FinalConstruct()
    {
        return S_OK;
    }

    void FinalRelease()
    {
    }
};

OBJECT_ENTRY_AUTO(__uuidof(Base), CBase)

2 个答案:

答案 0 :(得分:1)

只是一个建议 - 如果你的COM对象不需要对COM相关的东西做任何特殊的事情,那么你可以实现代码,使你的基类COM类所做的真正逻辑被封装在另一个普通的旧C ++类中,比如说CBaseLogic。

CBaseLogic : IBase

class ATL_NO_VTABLE CBase :
    public CComObjectRootEx<CComSingleThreadModel>,
    public CComCoClass<CBase, &CLSID_Base>,
    public ISupportErrorInfo,
    public IConnectionPointContainerImpl<CBase>,
    public CProxy_IBaseEvents<CBase>,
    public IDispatchImpl<IBase, &IID_IBase, &LIBID_ExampleLib
{
CBaseLogic m_LogicObj; /* Method calls are simply forwarded to this member */
};


CDerivedLogic : public CBaseLogic

class ATL_NO_VTABLE CDerived :
    public CComObjectRootEx<CComSingleThreadModel>,
    public CComCoClass<CDerived, &CLSID_Base>,
    public ISupportErrorInfo,
    public IConnectionPointContainerImpl<CDerived>,
    public CProxy_IBaseEvents<CDerived>,
    public IDispatchImpl<IBase, &IID_IBase, &LIBID_ExampleLib
{
CDerivedLogic m_LogicObj;
};

通过

的附加优势,您可以实现目标
  1. 将您的真实程序逻辑与基础架构/打包(COM)分开
  2. 使真正的逻辑平台独立。
  3. 未来的维护者无需了解您的聪明COM黑客
  4. 保持程序逻辑清洁,远离COM语法,提高可读性
  5. 在其他形式的包装中更容易重用真实逻辑,例如作为C DLL

答案 1 :(得分:0)

编辑向导生成的代码。如果希望对象从其他接口派生,请将这些基类添加到生成的类声明中。