Hinweis
Für den Zugriff auf diese Seite ist eine Autorisierung erforderlich. Sie können versuchen, sich anzumelden oder das Verzeichnis zu wechseln.
Für den Zugriff auf diese Seite ist eine Autorisierung erforderlich. Sie können versuchen, das Verzeichnis zu wechseln.
Sie können Windows Runtime C++ Template Library (WRL) können Sie grundlegende klassische COM-Komponenten für die Desktop-Apps, zusätzlich zur Verwendung für Windows Store-App zu erstellen.Für die Erstellung von COM-Komponenten, erfordert WRL möglicherweise weniger Code als das ATL.Informationen über die Teilmenge von COM, der die WRL Unterstützung, Windows Runtime C++ Template Library (WRL) sieht.
Dieses Dokument, wie WRL verwendet, um eine grundlegende COM-Komponente zu erstellen.Obwohl Sie den Bereitstellungsmechanismus verwenden können, den auch am besten erfüllt die Anforderungen, dieses Dokument einer grundlegenden Methode, die von einer COM-Komponente Desktop-App zu registrieren und verarbeiten anzeigt.
So WRL verwenden, um eine grundlegende klassische COM-Komponente zu erstellen
In Visual Studio erstellen Sie ein Projekt Leere Projektmappe.Nennen Sie das Projekt beispielsweise WRLClassicCOM.
Fügen Sie Win32-Projekt der Projektmappe hinzu.Nennen Sie das Projekt beispielsweise CalculatorComponent.Klicken Sie auf der Registerkarte Anwendungseinstellungen ausgewähltes DLL.
Fügen Sie eine Datei Midl-Datei (.idl) dem Projekt hinzu.Nennen Sie die Datei beispielsweise CalculatorComponent.idl.
Fügen Sie diesen Code CalculatorComponent.idl hinzu:
import "ocidl.idl"; [uuid(0DBABB94-CE99-42F7-ACBD-E698B2332C60), version(1.0)] interface ICalculatorComponent : IUnknown { HRESULT Add([in] int a, [in] int b, [out, retval] int* value); } [uuid(9D3E6826-CB8E-4D86-8B14-89F0D7EFCD01), version(1.0)] library CalculatorComponentLib { [uuid(E68F5EDD-6257-4E72-A10B-4067ED8E85F2), version(1.0)] coclass CalculatorComponent { [default] interface ICalculatorComponent; } };In CalculatorComponent.cpp definieren Sie die CalculatorComponent-Klasse.Die CalculatorComponent-Klasse erbt von Microsoft::WRL::RuntimeClass.Microsoft::WRL::RuntimeClassFlags<ClassicCom> gibt an, dass die Klasse von IUnknown und nicht IInspectable berechnet.(IInspectable ist nur auf Store-App-Komponenten verfügbar.), CoCreatableClass stellt eine Factory für die Klasse, der mit Funktionen wie CoCreateInstance.
#include "stdafx.h" #include "CalculatorComponent_h.h" #include <wrl.h> using namespace Microsoft::WRL; class CalculatorComponent: public RuntimeClass<RuntimeClassFlags<ClassicCom>, ICalculatorComponent> { public: CalculatorComponent() { } STDMETHODIMP Add(_In_ int a, _In_ int b, _Out_ int* value) { if (value == nullptr) { return E_POINTER; } *value = a + b; return S_OK; } }; CoCreatableClass(CalculatorComponent);Verwenden Sie folgenden Code, um den Code in dllmain.cpp zu ersetzen.Diese Datei definiert die DLL-Exportfunktionen.Diese Funktionen verwenden die Microsoft::WRL::Module-Klasse, um die Class Factory für das Modul zu verwalten.
#include "stdafx.h" #include <wrl\module.h> using namespace Microsoft::WRL; #if !defined(__WRL_CLASSIC_COM__) STDAPI DllGetActivationFactory(_In_ HSTRING activatibleClassId, _COM_Outptr_ IActivationFactory** factory) { return Module<InProc>::GetModule().GetActivationFactory(activatibleClassId, factory); } #endif #if !defined(__WRL_WINRT_STRICT__) STDAPI DllGetClassObject(REFCLSID rclsid, REFIID riid, _COM_Outptr_ void** ppv) { return Module<InProc>::GetModule().GetClassObject(rclsid, riid, ppv); } #endif STDAPI DllCanUnloadNow() { return Module<InProc>::GetModule().Terminate() ? S_OK : S_FALSE; } STDAPI_(BOOL) DllMain(_In_opt_ HINSTANCE hinst, DWORD reason, _In_opt_ void*) { if (reason == DLL_PROCESS_ATTACH) { DisableThreadLibraryCalls(hinst); } return TRUE; }Fügen Sie eine Datei DEF-Datei (.def) dem Projekt hinzu.Nennen Sie die Datei beispielsweise CalculatorComponent.def.Diese Datei gibt dem Linker die Namen der exportiert werden Funktionen.
Fügen Sie diesen Code CalculatorComponent.def hinzu:
LIBRARY EXPORTS DllGetActivationFactory PRIVATE DllGetClassObject PRIVATE DllCanUnloadNow PRIVATEFügen Sie runtimeobject.lib der Linkerzeile hinzu.So erfahren, wie, .LIB-Dateien als Linkereingabe finden Sie unter.
Um die COM-Komponente von einer Desktop-App nutzen
Registrieren Sie die COM-Komponente mit der Windows-Registrierung.Sie hierzu, eine Registrierungseintragsdatei erstellen, diese benennen RegScript.reg und den folgenden Text hinzufügen.Ersetzen Sie <dll-path> durch den Pfad aus dem DLL – z. B. C:\\temp\\WRLClassicCOM\\Debug\\CalculatorComponent.dll.
Windows Registry Editor Version 5.00 [HKEY_CLASSES_ROOT\Wow6432Node\CLSID\{E68F5EDD-6257-4E72-A10B-4067ED8E85F2}] @="CalculatorComponent Class" [HKEY_CLASSES_ROOT\Wow6432Node\CLSID\{E68F5EDD-6257-4E72-A10B-4067ED8E85F2}\InprocServer32] @="<dll-path>" "ThreadingModel"="Apartment" [HKEY_CLASSES_ROOT\Wow6432Node\CLSID\{E68F5EDD-6257-4E72-A10B-4067ED8E85F2}\Programmable] [HKEY_CLASSES_ROOT\Wow6432Node\CLSID\{E68F5EDD-6257-4E72-A10B-4067ED8E85F2}\TypeLib] @="{9D3E6826-CB8E-4D86-8B14-89F0D7EFCD01}" [HKEY_CLASSES_ROOT\Wow6432Node\CLSID\{E68F5EDD-6257-4E72-A10B-4067ED8E85F2}\Version] @="1.0"Führen Sie RegScript.reg aus oder fügen Sie es Postbuildereignis des Projekts hinzu.Weitere Informationen finden Sie unter Dialogfeld "Befehlszeile für Präbuildereignis"/"Befehlszeile für Postbuildereignis".
Fügen Sie ein Win32-Konsolenanwendung Projekt der Projektmappe hinzu.Nennen Sie das Projekt beispielsweise Computer.
Verwenden Sie diesen Code, um den Inhalt von Calculator.cpp zu ersetzen:
#include "stdafx.h" #include "..\CalculatorComponent\CalculatorComponent_h.h" const IID IID_ICalculatorComponent = {0x0DBABB94,0xCE99,0x42F7,0xAC,0xBD,0xE6,0x98,0xB2,0x33,0x2C,0x60}; const CLSID CLSID_CalculatorComponent = {0xE68F5EDD,0x6257,0x4E72,0xA1,0x0B,0x40,0x67,0xED,0x8E,0x85,0xF2}; // Prints an error string for the provided source code line and HRESULT // value and returns the HRESULT value as an int. int PrintError(unsigned int line, HRESULT hr) { wprintf_s(L"ERROR: Line:%d HRESULT: 0x%X\n", line, hr); return hr; } int wmain() { HRESULT hr; // Initialize the COM library. hr = CoInitializeEx(nullptr, COINIT_APARTMENTTHREADED); if (FAILED(hr)) { return PrintError(__LINE__, hr); } ICalculatorComponent* calc = nullptr; // Interface to COM component. // Create the CalculatorComponent object. hr = CoCreateInstance(CLSID_CalculatorComponent, nullptr, CLSCTX_INPROC_SERVER, IID_ICalculatorComponent, reinterpret_cast<void**>(&calc)); if (SUCCEEDED(hr)) { // Test the component by adding two numbers. int result; hr = calc->Add(4, 5, &result); if (FAILED(hr)) { PrintError(__LINE__, hr); } else { wprintf_s(L"result = %d\n", result); } // Free the CalculatorComponent object. calc->Release(); } else { // Object creation failed. Print a message. PrintError(__LINE__, hr); } // Free the COM library. CoUninitialize(); return hr; } /* Output: result = 9 */
Robuste Programmierung
In diesem Dokument werden Standard-COM-Funktionen, um zu zeigen, dass Sie WRL verwenden können, um eine COM-Komponente zu erstellen und sie zu machen für jede COM-aktivierte Technologie.Sie können WRL-Typen wie Microsoft::WRL::ComPtr in der Desktop-App auch verwenden, um die Lebensdauer von COM und anderen Objekten zu verwalten.Im folgenden Code wird WRL, um die Lebensdauer des ICalculatorComponent Zeigers zu verwalten.Die CoInitializeWrapper-Klasse ist ein RAII-Wrapper, mit dem sichergestellt wird, dass die COM-Bibliothek und auch Garantien freigegeben wird, dass die Lebensdauer der COM-Bibliothek das Objekt ComPtr intelligenten Zeigermechanismus Noch vorhanden.
#include "stdafx.h"
#include <wrl.h>
#include "..\CalculatorComponent\CalculatorComponent_h.h"
using namespace Microsoft::WRL;
const IID IID_ICalculatorComponent = {0x0DBABB94,0xCE99,0x42F7,0xAC,0xBD,0xE6,0x98,0xB2,0x33,0x2C,0x60};
const CLSID CLSID_CalculatorComponent = {0xE68F5EDD,0x6257,0x4E72,0xA1,0x0B,0x40,0x67,0xED,0x8E,0x85,0xF2};
// Prints an error string for the provided source code line and HRESULT
// value and returns the HRESULT value as an int.
int PrintError(unsigned int line, HRESULT hr)
{
wprintf_s(L"ERROR: Line:%d HRESULT: 0x%X\n", line, hr);
return hr;
}
int wmain()
{
HRESULT hr;
// RAII wrapper for managing the lifetime of the COM library.
class CoInitializeWrapper
{
HRESULT _hr;
public:
CoInitializeWrapper(DWORD flags)
{
_hr = CoInitializeEx(nullptr, flags);
}
~CoInitializeWrapper()
{
if (SUCCEEDED(_hr))
{
CoUninitialize();
}
}
operator HRESULT()
{
return _hr;
}
};
// Initialize the COM library.
CoInitializeWrapper initialize(COINIT_APARTMENTTHREADED);
if (FAILED(initialize))
{
return PrintError(__LINE__, initialize);
}
ComPtr<ICalculatorComponent> calc; // Interface to COM component.
// Create the CalculatorComponent object.
hr = CoCreateInstance(CLSID_CalculatorComponent, nullptr, CLSCTX_INPROC_SERVER, IID_ICalculatorComponent, reinterpret_cast<void**>(calc.GetAddressOf()));
if (SUCCEEDED(hr))
{
// Test the component by adding two numbers.
int result;
hr = calc->Add(4, 5, &result);
if (FAILED(hr))
{
return PrintError(__LINE__, hr);
}
wprintf_s(L"result = %d\n", result);
}
else
{
// Object creation failed. Print a message.
return PrintError(__LINE__, hr);
}
return 0;
}