我有一个ASP.NET MVC3网站,必须使用COM插件。为了做到这一点,我需要以某种方式定义一个接口。据我所知(我不是COM专家),这可以在.NET中完成,并使用tlbexp.exe或idl-> midl-> tlbimp导出。
我已经走了第一条路(用tlbexp)。我也尝试过IDL,但无济于事(由于某种原因,可以将实现COM对象强制转换回.NET中的tlbimp'ed接口。)
如果我的界面上没有事件,这种情况会很简单:
[ComVisible(true)]
[Guid("EFCFB783-0225-4D45-94CB-9A26B7CC19AF")]
public delegate void ItemStatusChanged(string itemGuid, string itemStatus);
[ComVisible(true)]
[Guid("35202AE5-392D-4015-993D-29966DA5DE31")]
[InterfaceType(ComInterfaceType.InterfaceIsDual)]
public interface ICOMOutputPlugin
{
void Method1(string arg);
void Method2(string arg);
event ItemStatusChanged ItemStatusChanged;
}
[ComVisible(true)]
[Guid("93862C43-503C-4C96-9BAE-944F1087AB77")]
[InterfaceType(ComInterfaceType.InterfaceIsIDispatch)]
public interface ICOMOutputPluginEvents
{
void ItemStatusChanged(string itemGuid, string itemStatus);
}
我使用tlbexp.exe将其导出到tlb并使用regtlibv12注册.tlb。 插件开发人员将仅使用此类型库来导入接口。
现在我有一个C ++项目,它将是一个插件,我在VS2010中添加了新的简单ATL对象并将IDL更改为:
importlib("stdole2.tlb");
importlib("MyExp.tlb");
[
uuid(E09BC67A-4192-4CA3-8FD0-5CBFC69B43AC)
]
coclass DumpToFileOutputPlugin
{
[default] interface ICOMOutputPlugin;
[default, source] dispinterface ICOMOutputPluginEvents;
};
我的第一个问题是,由于某种原因,我无法通过类向导将连接点添加到“正常方式”。当我将它指向MyExp.tlb时,它根本不显示任何源接口。所以我手动完成了(使用了另一个.tlb并重命名了所有内容)。
所以现在我有了这两种方法的COM对象:
STDMETHOD(add_ItemStatusChanged)(_ItemStatusChanged* value);
STDMETHOD(remove_ItemStatusChanged)(_ItemStatusChanged* value);
在.NET端,插件管理器实例化这样的插件:
Type type = Type.GetTypeFromProgID(progID);
comObject = Activator.CreateInstance(type) as ICOMOutputPlugin;
comObject.ItemStatusChanged += (guid, status) => ItemStatusChanged(guid, status);
最后一行奇迹般地在我的COM对象上调用add_ItemStatusChanged
方法。
在这里,我被困住了,这个方法我该怎么办?我目前的实施是:
HRESULT CDumpToFileOutputPlugin::add_ItemStatusChanged(_ItemStatusChanged* value)
{
DWORD cookie;
HRESULT ret = Advise(value, &cookie);
_com_error err(ret);
LPCTSTR errMsg = err.ErrorMessage();
return ret;
}
ret = CONNECT_E_CANNOTCONNECT(0x80040202),errMsg说“IDispatch错误#2”。
显然Advise期望传递的COM对象实现委托传递对象的连接点接口ICOMOutputPluginEvents
...我该怎么办?
我是否在.NET端订阅了错误的事件或添加处理程序?
任何帮助如何解决这个问题将不胜感激。
答案 0 :(得分:-1)
不要在ASP.Net的COM插件中使用“事件”,只需要调用方法即可。即一个名为OnEventName
的方法,而不是一个事件。
COM事件不是处理Web表单回发的正确方法。