如何:直接实例化 WRL 组件

了解如何使用 Windows 运行时 C++ 模板库 (WRL)Microsoft::WRL::MakeMicrosoft::WRL::Details::MakeAndInitialize函数去实例化定义的模块组件。

当您不需要类工厂或其他机制时,通过直接实例化组件可以降低开销。 可以直接在Windows 应用商店应用程序和在桌面应用程序中实例化一个组件。

若要了解如何使用 WRL 创建一个基本的 Windows 运行时 组件并将其从外部 Windows 应用商店 应用程序实例化,请参见 演练:使用 WRL 创建基本 Windows 运行时组件。 若要了解如何使用 WRL 创建一个基本的COM组件并将其从外部桌面应用程序实例化,请参见如何:使用 WRL 创建传统型 COM 组件

此文档显示两个示例。 第一个示例使用 Make 函数实例化组件。 第二个示例使用 MakeAndInitialize 函数实例化构造失败的组件。(由于 COM 通常使用 HRESULT 值,而不是异常,为了指示错误,COM 类型通常不从其构造函数抛出。 MakeAndInitialize 通过 RuntimeClassInitialize 方法使组件验证其构造实参。)两个示例定义一个基本的记录器接口并通过定义写消息到控制台的类来实现该接口。

重要

不能使用 new 运算符实例化 WRL组件。因此,建议您始终使用 MakeMakeAndInitialize 直接实例化组件。

创建和实例化一个基本的记录器组件

  1. 在 Visual Studio 中,创建一个Win32控制台应用程序项目。 例如,将项目命名为WRLLogger。

  2. 添加一个**Midl File (.idl)**文件到项目,将文件命名为 ILogger.idl,然后添加以下代码:

    import "ocidl.idl";
    
    // Prints text to the console.
    [uuid(AFDB9683-F18A-4B85-90D1-B6158DAFA46C)]
    interface ILogger : IUnknown
    {
        HRESULT Log([in] LPCWSTR text);
    }
    
  3. 使用以下代码替换“WRLLogger.cpp”的内容:

    #include "stdafx.h"
    #include <wrl\implements.h>
    #include <comutil.h>
    
    #include "ILogger_h.h" 
    
    using namespace Microsoft::WRL;
    
    // Writes logging messages to the console. 
    class CConsoleWriter : public RuntimeClass<RuntimeClassFlags<ClassicCom>, ILogger>
    {
    public:
        STDMETHODIMP Log(_In_ PCWSTR text)
        {
            wprintf_s(L"%s\n", text);
            return S_OK;
        }
    
    private:
        // Make destroyable only through Release.
        ~CConsoleWriter()
        {
        }
    };
    
    int wmain()
    {
        ComPtr<CConsoleWriter> writer = Make<CConsoleWriter>();
        HRESULT hr = writer->Log(L"Logger ready.");
        return hr;
    }
    
    /* Output:
    Logger ready.
    */
    

处理基本的记录器组件的构造失败事件

  1. 用下面的代码替换 CConsoleWriter 类的定义。 此版本包含一个私有字符串成员变量并重写 RuntimeClass::RuntimeClassInitialize 方法。 如果对 SHStrDup 的调用失败,则RuntimeClassInitialize 失败。

    // Writes logging messages to the console. 
    class CConsoleWriter : public RuntimeClass<RuntimeClassFlags<ClassicCom>, ILogger>
    {
    public:
        // Initializes the CConsoleWriter object. 
        // Failure here causes your object to fail construction with the HRESULT you choose.
        HRESULT RuntimeClassInitialize(_In_ PCWSTR category)
        {
            return SHStrDup(category, &m_category);
        }
    
        STDMETHODIMP Log(_In_ PCWSTR text)
        {
            wprintf_s(L"%s: %s\n", m_category, text);
            return S_OK;
        }
    
    private:
        PWSTR m_category;
    
        // Make destroyable only through Release.
        ~CConsoleWriter()
        {
            CoTaskMemFree(m_category);
        }
    };
    
  2. 用下面的代码替换方法wmain的定义。 此版本使用 MakeAndInitialize 实例化 CConsoleWriter 对象和检查 HRESULT 结果。

    int wmain()
    {
        ComPtr<CConsoleWriter> writer;
        HRESULT hr = MakeAndInitialize<CConsoleWriter>(&writer, L"INFO");
        if (FAILED(hr))
        {
            wprintf_s(L"Object creation failed. Result = 0x%x", hr);
            return hr;
        }
        hr = writer->Log(L"Logger ready.");
        return hr;
    }
    
    /* Output:
    INFO: Logger ready.
    */
    

请参见

参考

Microsoft::WRL::Make

Microsoft::WRL::Details::MakeAndInitialize

概念

Windows 运行时 C++ 模板库 (WRL)