如何在C中加载和调用VBScript函数?
我们的客户要求在我们的产品中发生特定操作时调用VBScript函数.我一直在尝试研究
Windows Scripting技术,但我很难找到我需要的东西.希望你们中的一些人可以提供帮助.
我们的产品是原生C Windows产品.客户将指定我们将加载的VBScript文件,并且每当发生特定事件时,我们将调用VBScript中的特定函数并让它执行其操作.我们可以在脚本的命名空间内提供对象,以便它也可以访问有关我们产品的信息. 我在MSDN上找到了关于IActiveScript接口的一些信息,以及一些相关的东西,但是找不到任何实例化实现VBScript接口的COM对象的例子. 我知道PowerShell现在可能是一个更好的选择,但我们的客户被困在许多遗留系统中,而VBScript就是他们所知道的. 您可以提供的任何帮助(链接或其他)将不胜感激! 解决方法
我已经整理了一个“Hello World”IActiveScript C ATL控制台应用程序:
>定义CSimpleScriptSite类 >实现IActiveScriptSite接口(必填) >使用CoCreateInstance新的IActiveSite对象 >创建VBScript和JScript的实例 >样本: >在JScript中计算表达式 码: #include "stdafx.h" #include <atlbase.h> #include <activscp.h> class CSimpleScriptSite : public IActiveScriptSite,public IActiveScriptSiteWindow { public: CSimpleScriptSite() : m_cRefCount(1),m_hWnd(NULL) { } // IUnknown STDMETHOD_(ULONG,AddRef)(); STDMETHOD_(ULONG,Release)(); STDMETHOD(QueryInterface)(REFIID riid,void **ppvObject); // IActiveScriptSite STDMETHOD(GetLCID)(LCID *plcid){ *plcid = 0; return S_OK; } STDMETHOD(GetItemInfo)(LPCOLESTR pstrName,DWORD dwReturnMask,IUnknown **ppiunkItem,ITypeInfo **ppti) { return TYPE_E_ELEMENTNOTFOUND; } STDMETHOD(GetDocVersionString)(BSTR *pbstrVersion) { *pbstrVersion = SysAllocString(L"1.0"); return S_OK; } STDMETHOD(OnScriptTerminate)(const VARIANT *pvarResult,const EXCEPINFO *pexcepinfo) { return S_OK; } STDMETHOD(OnStateChange)(SCRIPTSTATE ssScriptState) { return S_OK; } STDMETHOD(OnScriptError)(IActiveScriptError *pIActiveScriptError) { return S_OK; } STDMETHOD(OnEnterScript)(void) { return S_OK; } STDMETHOD(OnLeaveScript)(void) { return S_OK; } // IActiveScriptSiteWindow STDMETHOD(GetWindow)(HWND *phWnd) { *phWnd = m_hWnd; return S_OK; } STDMETHOD(EnableModeless)(BOOL fEnable) { return S_OK; } // Miscellaneous HRESULT SetWindow(HWND hWnd) { m_hWnd = hWnd; return S_OK; } public: LONG m_cRefCount; HWND m_hWnd; }; STDMETHODIMP_(ULONG) CSimpleScriptSite::AddRef() { return InterlockedIncrement(&m_cRefCount); } STDMETHODIMP_(ULONG) CSimpleScriptSite::Release() { if (!InterlockedDecrement(&m_cRefCount)) { delete this; return 0; } return m_cRefCount; } STDMETHODIMP CSimpleScriptSite::QueryInterface(REFIID riid,void **ppvObject) { if (riid == IID_IUnknown || riid == IID_IActiveScriptSiteWindow) { *ppvObject = (IActiveScriptSiteWindow *) this; AddRef(); return NOERROR; } if (riid == IID_IActiveScriptSite) { *ppvObject = (IActiveScriptSite *) this; AddRef(); return NOERROR; } return E_NOINTERFACE; } int _tmain(int argc,_TCHAR* argv[]) { HRESULT hr = S_OK; hr = CoInitializeEx(NULL,COINIT_MULTITHREADED); // Initialize CSimpleScriptSite* pScriptSite = new CSimpleScriptSite(); CComPtr<IActiveScript> spJScript; CComPtr<IActiveScriptParse> spJScriptParse; hr = spJScript.CoCreateInstance(OLESTR("JScript")); hr = spJScript->SetScriptSite(pScriptSite); hr = spJScript->QueryInterface(&spJScriptParse); hr = spJScriptParse->InitNew(); CComPtr<IActiveScript> spVBScript; CComPtr<IActiveScriptParse> spVBScriptParse; hr = spVBScript.CoCreateInstance(OLESTR("VBScript")); hr = spVBScript->SetScriptSite(pScriptSite); hr = spVBScript->QueryInterface(&spVBScriptParse); hr = spVBScriptParse->InitNew(); // Run some scripts CComVariant result; EXCEPINFO ei = { }; hr = spJScriptParse->ParseScriptText(OLESTR("(new Date()).getTime()"),NULL,SCRIPTTEXT_ISEXPRESSION,&result,&ei); hr = spVBScriptParse->ParseScriptText(OLESTR("Now"),&ei); hr = spVBScriptParse->ParseScriptText(OLESTR("MsgBox "Hello World! The current time is: " & Now"),&ei); // Cleanup spVBScriptParse = NULL; spVBScript = NULL; spJScriptParse = NULL; spJScript = NULL; pScriptSite->Release(); pScriptSite = NULL; ::CoUninitialize(); return 0; } (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |