我尝试环顾四周,但无法说服自己,因为COM / ActiveX的世界似乎非常令人困惑。
基本上,我想知道的是,给定GUID,有没有办法知道ActiveX控件公开的所有接口,属性和方法?我在某处读到,您只需要询问是否存在特定属性即可。但是,在知道房产之前,我该如何询问房产?
我猜想IDispatch可以做类似的事情,但是我无法确定如何使用它。如果这是可行的,那么最好使用C#的一小段代码将帮助我更好地理解。
谢谢
我正在针对C++ COM服务器实现ac#COM客户端.当我将COM接口标记为"Dual"时,COM客户端正常运行,但是当我删除"Dual"属性时,它会抛出InvalidCastException.
因此,对我来说简单的方法是将其标记为Dual.但是从在线阅读来看,它似乎不是推荐的COM服务器使用方法.任何人都可以向我解释将界面标记为双重以及为什么不推荐它的重要性(以外行的术语)?
我只需要它用于测试目的,我正在使用C#客户端(不要以为我会使用VB)
或者,任何人都可以指出我为非双接口创建C#COM客户端的良好演练(MSDN上的示例都是双接口)谢谢!
我在WMI/WBEM接口上调用返回HRESULTS的方法.我想向用户显示这些错误代码的有意义的错误消息.但是,当我查找HRESULT的错误消息时,我只得到类似"IDispatch错误#3598"的字符串.
我可以找到这些IDispatch错误代码的列表来解释它们的含义吗?
可能发生错误的示例代码:
IWbemLocator *pLocator = NULL;
IWbemServices *pNamespace = NULL;
hr = CoCreateInstance(CLSID_WbemLocator, 0, CLSCTX_INPROC_SERVER, IID_IWbemLocator, (LPVOID *) &pLocator);
if (FAILED(hr))
return hr;
hr = pLocator->ConnectServer(wPath, NULL, NULL, NULL, 0, NULL, NULL, &pNamespace);
if(FAILED(hr))
return hr;
Run Code Online (Sandbox Code Playgroud)
错误查找:
CString sMessage = _com_error(nError).ErrorMessage();
// sMessage now contains a string like "IDispatch error #3598"
Run Code Online (Sandbox Code Playgroud)
注意:这没有帮助 - 它不包含我得到的HRESULTS.它们都不包含在winerror.h中.
我们正在使用一些旧代码(由Binh Ly创建的ComLib.pas),因此我们可以在(OleVariant)对象上使用枚举接口:
type
TDispNewEnum = dispinterface
['{97079E31-6957-11D2-9154-0000B4552A26}'] // dummy
property _NewEnum: IUnknown readonly dispid -4; // DISPID_NEWENUM
function _NewEnumFunc: IUnknown; dispid -4; // DISPID_NEWENUM
end;
procedure TEnumVariant.AttachUnknown (const Unk: IUnknown);
var
pDisp: IDispatch;
_NewEnumPropFailed: boolean;
Unknown: IUnknown;
begin
Detach;
Unknown := Unk;
{ extract IEnumVariant }
if (Unknown <> nil) then
begin
{ try IEnumVariant }
if not (Succeeded (Unknown.QueryInterface (IEnumVariant, FEnumVariant))) then
begin
FEnumVariant := nil; // safety!
{ test _NewEnum prop and _NewEnum func }
if (Succeeded (Unknown.QueryInterface …Run Code Online (Sandbox Code Playgroud) 我想构建一个COM可见的 C#类,比如说DynamicComponent,它将通过COM 提供动态接口.
在内部,这个类将维护一个代表字典:
"GetTheAnswer" -> () => { return 42; }
"Add" -> (int a, int b) => { return a + b; }
...
Run Code Online (Sandbox Code Playgroud)
客户端代码将是一些VBA.
这是我天真想象的工作流程:
DynamicComponent(至少得到Excel/VBA提供的存根)["GetTheAnswer" -> 1, "Add" -> 2]GetTheAnswer和Add我的第一个问题:这可能吗?
如果不是:为什么?
如果是的话:怎么样?
根据我对COM的了解,如果可能的话,IDispatch COM接口是我最好的朋友.
而且,根据我的理解,.Net 4 的ICustomQueryInterface接口也可以提供很大的帮助.
但是,如今COM并不是真正的尖端;)很难找到像代码样本这样的资源.
我发现了这个有趣的示例:https : //clrinterop.codeplex.com/releases/view/32350,它使用ICustomQueryInterface接口实现COM聚合
但它不是动态的,而是基于静态定义的类型和接口. …
我无法成功调用create_session成员。是回归Type mismatch
// COM class -> member
virtual HRESULT __stdcall create_session(
/*[in]*/ BSTR pbszName,
/*[in]*/ long i32Value ) = 0;
Run Code Online (Sandbox Code Playgroud)
尝试调用create_session方法如下:
// test.cpp
HRESULT create_session( IDispatch *dispatch, WCHAR *member ) {
// WCHAR *member = tlib_help::s2ws( "create_session" );
DISPID dispid = -1;
HRESULT hr = dispatch->GetIDsOfNames( IID_NULL, &member, 1, LOCALE_SYSTEM_DEFAULT, &dispid );
if ( SUCCEEDED( hr ) ) {
DISPPARAMS *dispparams = new DISPPARAMS( );
dispparams->cArgs = 2;
dispparams->cNamedArgs = 1;
VARIANTARG *rgvarg = new …Run Code Online (Sandbox Code Playgroud) 我有一个C++ DLL,需要在C#类库中调用一个函数(传递一个值,返回一个值).
我唯一的选择是给C#DLL一个COM接口,并使用IDispatch从C++调用它?
这是最好的方法吗?
我正在使用Turbo Delphi 2006.
DLL将作为VBA/DLL组合的一部分从Excel中调用.
问题的第一部分是试图找出如何向DLL传递对当前Excel会话的引用.我见过的大多数其他代码都是它启动了一个单独的Excel实例,而不是你所在的实例.
我已经看到一些C++代码创建了一个实例,IDispatch然后将一些东西传递给IDispatch对象的方法,但不知道很多C++.
有任何想法吗?
idispatch ×8
c# ×4
com ×4
c++ ×3
delphi ×2
dll ×2
.net ×1
activex ×1
com-interop ×1
delphi-xe2 ×1
excel ×1
interop ×1
iunknown ×1
properties ×1
vba ×1