您的位置:首页 > Web前端 > JavaScript

JavaScript Calls from C++

2010-04-27 09:43 225 查看

最近要用到相关技术,先贴在这,有空再翻页。

本文转自:

http://www.codeguru.com/Cpp/I-N/ieprogram/article.php/c4399

http://www.codeguru.com/cpp/i-n/ieprogram/article.php/c4399/JavaScript-Calls-from-C.htm
http://www.codeproject.com/KB/COM/jscalls.aspx








Introduction

Sometimes, when we are using the IE Browser Control inside of a C++ application, we need to access the HTML elements. We can do it by using standard COM objects such as
IWebBrowser2
,
IHTMLDocument2
, and so forth. By doing this, we easily can implement features such as click button, click anchor, get input string, get HTML text, and so on. Unfortunately, Microsoft did not provide similar objects for JavaScript. In any case, it is possible to make a control for the JavaScript object inside an HTML page by using a traditional COM approach. This article describes the class
CWebPage
that allows you to do it and a technique to call a JavaScript function from C++ code.

How to Do This

As the result of using the presented class, it will be easy to call any JavaScript function from C++ code. To implement this feature, we should get a pointer to the
IHTMLDocument2
interface. If we are using the
CHtmlView
class from MFC, we can get one by using member function
CHtmlView::GetHtmlDocument()
. In the case of using the
IWebBrowser
or
IWebBrowser2
components, the function
get_Document
will bring us the desired interface. Here is an example:

CComPtr<IDispatch> spDisp = CHtmlView::GetHtmlDocument();
m_webPage.SetDocument(spDisp);


The rest of the things will be done by the
CWebPage
class. Here is an example of a JavaScript call without parameters.

m_webPage.CallJScript("Welcome");

The example of the JavaScript call with two parameters will look like this:

m_webPage.CallJScript("Miltiply","2.34","3.32");

The Class Implementation

class CWebPage
{
public:
  CWebPage();
  virtual ~CWebPage();
  bool SetDocument(IDispatch* pDisp);
  LPDISPATCH GetHtmlDocument() const;
  const CString GetLastError() const;
  bool GetJScript(CComPtr<IDispatch>& spDisp);
  bool GetJScripts(CComPtr<IHTMLElementCollection>& spColl);
  CString ScanJScript(CString& strAText,CStringArray& args);
  bool CallJScript(const CString strFunc);
  bool CallJScript(const CString strFunc,const CString strArg1);
  bool CallJScript(const CString strFunc,const CString strArg1,
                   const CString strArg2);
  bool CallJScript(const CString strFunc,const CString strArg1,
                   const CString strArg2,const CString strArg3);
  bool CallJScript(const CString strFunc,const 
                         CStringArray& paramArray);
protected
  CComPtr<IHTMLDocument2> m_spDoc;
};




Calling Technique

The previously mentioned technique splits the following steps:

Getting a pointer to the
IHTMLDocument2
interface.

Getting
IDispatch
for a JavaScript object in an HTML document.

Getting
DISPID
for a given name of a JavaScript function.

Putting parameters to the
DISPPARAM
structure.

Calling a JavaScript function by using the Invoke method of the
IDispatch
interface.

Here is an example of getting a
IDispatch
pointer to the Java Scripts objects:

bool CWebPage::GetJScript(CComPtr<IDispatch>& spDisp)
{
  HRESULT hr = m_spDoc->get_Script(&spDisp);
  ATLASSERT(SUCCEEDED(hr));
  return SUCCEEDED(hr);
}


And here is the final function to call JavaScript:

CComVariant CWebPage::CallJScript(const CString strFunc,
                                  const CStringArray&
								  paramArray)
{
	//Getting IDispatch for Java Script objects
	CComPtr<IDispatch> spScript;
	if(!GetJScript(spScript))
	{
		ShowError("Cannot GetScript");
		return false;
	}
	//Find dispid for given function in the object
	
	CComBSTR bstrMember(strFunc);
	DISPID dispid = NULL;
	HRESULT hr = spScript->GetIDsOfNames(IID_NULL,&bstrMember,1,
		LOCALE_SYSTEM_DEFAULT,&dispid);
	if(FAILED(hr))
	{
		ShowError(GetSystemErrorMessage(hr));
		return false;
	}
	
	const int arraySize = paramArray.GetSize();
	
	//Putting parameters
	DISPPARAMS dispparams;
	memset(&dispparams, 0, sizeof dispparams);
	dispparams.cArgs      = arraySize;
	dispparams.rgvarg     = new VARIANT[dispparams.cArgs];
	dispparams.cNamedArgs = 0;
	for( int i = 0; i < arraySize; i++)
	{
		CComBSTR> bstr = paramArray.GetAt(arraySize - 1 - i);
		// back reading
		bstr.CopyTo(&dispparams.rgvarg[i].bstrVal);
		dispparams.rgvarg[i].vt = VT_BSTR;
	}
	
	EXCEPINFO excepInfo;
	memset(&excepInfo, 0, sizeof excepInfo);
	CComVariant vaResult;
	UINT nArgErr = (UINT)-1;      // initialize to invalid arg
	
	//Call JavaScript function
	hr = spScript->Invoke(dispid,IID_NULL,0,
		DISPATCH_METHOD,&dispparams,
		&vaResult,&excepInfo,&nArgErr);
	delete [] dispparams.rgvarg;
	if(FAILED(hr))
	{
		ShowError(GetSystemErrorMessage(hr));
		return false;
	}
	return vaResult;
}



Notes About the Demo

To call a JavaScript function from the demo, you should select the function in the tree of the left window. After this, press the ! button on the menu bar.

Downloads

Download demo project - 34 Kb
Download source - 3 Kb
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: