如何注册Sink事件的接收器对象 [英] How to Register Sink Object for SENS Events
问题描述
我在看MSDN文档,说我可以 CoCreateInstance使用其CLSID的SENS对象。但是,不清楚是否__uuidof(SENS)意味着任何东西 - 因为它只是Sensevts.h文件中的向前声明。此外,SENS类仅提供输出接口,并标记为不可创建(通过MS Com Viewer查看),这使我不知道如何引用SENS对象本身的实例。
这与获取 IShellLink 的实例的示例代码形成对比, a>:
HRESULT hr;
IShellLink * pISL;
hr = CoCreateInstance(CLSID_ShellLink,// coclass的CLSID
NULL,//未使用 - 聚合
CLSCTX_INPROC_SERVER,//服务器类型
IID_IShellLink,//接口的IID
(void **)& pISL); //指向我们的接口指针
这里ShellLink被称为IShellLink。很公平。但是我应该使用什么类型(除了void *)来接收SENS的实例?除了CLSID问题,关于IID我打算用于SENS呢?最终我想使用SENS的IID_ISensLogon接口,但是因为它是一个传出接口,我不能想象在这里使用它是有意义的。大概我需要和SENS的 IConnectionPointContainer
接口交谈(确实它实现了,是吗?),以便我可以到ISensLogon。
简而言之,有人可以告诉我示例代码的样子,以便我可以调用Advise(),并开始接收SENS的事件?
UPDATE 我正在取得一些进展,现在我的代码看起来像这样:
#import< es.dll>
#include< EventSys.h>
使用命名空间EventSystemLib;
// ...
:: CoInitializeEx(NULL,COINIT_APARTMENTTHREADED);
do {
IEventSystemPtr evSystem;
HRESULT hr = evSystem.CreateInstance(CLSID_CEventSystem);
if(!SUCCEEDED(hr)){
break;
}
IEventSubscriptionPtr evSubscriber;
hr = evSystem.CreateInstance(CLSID_CEventSubscription);
if(!SUCCEEDED(hr)){
break;
}
} while(false);问题是创建CLSID_CEventSubscription失败,并且HRESULT代码 E_NOINTERFACE code>。 该错误的在线文档表明我使用错误的线程模型。但我已尝试过 COINIT_MULTITHREADED
和 COINIT_APARTMENTTHREADED
,也不会更改错误。任何想法?
解决方案根据 MSDN ,则不创建SENS对象。如果我正在读这个权限,你创建一个IEventSystem(CLSID_CEventSystem)的实例,查询它感兴趣的SENS发布者/事件类,并注册你的订阅。
编辑:
对于你的新问题,我不确定根本原因,但我发现,切换使用IEventSubscriptionPtr似乎工作:
// Works
CComPtr< :: IEventSubscription> pSub2;
hr = pSub2.CoCreateInstance(CLSID_CEventSubscription);
//不工作
IEventSubscriptionPtr evSubscriber;
hr = evSystem.CreateInstance(CLSID_CEventSubscription);
I'm looking at MSDN documentation that says I can CoCreateInstance a SENS object using its CLSID. However, it is not clear if __uuidof(SENS) means anything - since it is just a forward declaration in the Sensevts.h file. Furthermore, the SENS class only offers "outgoing" interfaces, and is labeled "noncreateable" (as viewed through MS Com Viewer) which leaves me not knowing how to refer to an instance of the SENS object itself.
This contrasts with sample code for getting an instance of IShellLink:
HRESULT hr;
IShellLink* pISL;
hr = CoCreateInstance ( CLSID_ShellLink, // CLSID of coclass
NULL, // not used - aggregation
CLSCTX_INPROC_SERVER, // type of server
IID_IShellLink, // IID of interface
(void**) &pISL ); // Pointer to our interface pointer
Here ShellLink was referred to as "IShellLink." Fair enough. But what type (besides void*) should I use to to receive the instance of SENS? And besides the CLSID problem, what about the IID I'm meant to use for SENS? Ultimately I want to work with the IID_ISensLogon interface of SENS, but because it is an outgoing interface, I can't imagine it makes sense to use that here. Presumably I need to talk to the IConnectionPointContainer
interface of SENS (assuredly it implements that, right?) so that I can get to ISensLogon.
In short, could someone show me what the sample code would look like so that I can get to the point where I can call "Advise()" and start receiving events from SENS?
UPDATE I'm making some progress, so that my code now looks like this:
#import <es.dll>
#include <EventSys.h>
using namespace EventSystemLib;
//...
::CoInitializeEx(NULL, COINIT_APARTMENTTHREADED);
do {
IEventSystemPtr evSystem;
HRESULT hr = evSystem.CreateInstance(CLSID_CEventSystem);
if (!SUCCEEDED(hr)){
break;
}
IEventSubscriptionPtr evSubscriber;
hr = evSystem.CreateInstance(CLSID_CEventSubscription);
if (!SUCCEEDED(hr)){
break;
}
}while (false);
The problem is that the creation of CLSID_CEventSubscription fails with HRESULT code E_NOINTERFACE
. Online docs for that error suggest I'm using the wrong threading model. But I've tried both COINIT_MULTITHREADED
and COINIT_APARTMENTTHREADED
and neither changes the error. Any thoughts?
Incidentally, the closest thing I've seen to a working example is given in this link.
解决方案 According to other parts of MSDN, you don't create a SENS object. If I'm reading this right, you create an instance of IEventSystem (CLSID_CEventSystem), query it for the SENS publisher / event classes of interest, and register your subscription with them.
Edit:
For your new problem, I'm unsure of the root cause, however I've found that switching away from using IEventSubscriptionPtr seems to work:
// Works
CComPtr<::IEventSubscription> pSub2;
hr = pSub2.CoCreateInstance(CLSID_CEventSubscription);
// Doesn't work
IEventSubscriptionPtr evSubscriber;
hr = evSystem.CreateInstance(CLSID_CEventSubscription);
这篇关于如何注册Sink事件的接收器对象的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!