vc++调用msscript.ocx解析实现C++与JavaScript脚本交互
ScriptControl接口
属性名称 |
类型 |
备注 |
AllowUI |
BOOL |
检测是否允许运行用户的接口元素。如果为False,则诸如消息框之类的界面元素不可见。 |
CodeObject |
Object |
脚本暴露给宿主调用的对象。只读。 |
Modules |
Modules |
宿主提供给脚本的组件库模块。只读。(COM组件通常都是以对象收集的形式向用户提供可以留给用户二次开发的对象集合,每一个收集即一个Modules) |
Language |
String |
设置或获取脚本引擎解释的语言,例如:VBScript、JScript。 |
Name |
String |
脚本引擎的名称。只读。 |
Procedures |
Procedures |
返回模块中定义的过程的集合 |
SitehWnd |
HWND |
在脚本中显示UI的父窗口句柄 |
State |
Enum |
设置或返回控件的状态,如果为0,控件只执行语句但不转发事件,为1则为加入的本控件接受的对象转发事件。 |
Timeout |
Long |
控件的执行脚本的超时值,-1表示不超时 |
UseSafeSubset |
BOOL |
设置或返回宿主程序是否关心安全。宿主程序的安全级别可以从此属性设置 |
Error |
Error |
错误对象,发生错误时,此属性返回一个错误对象 |
方法名称 |
参数 |
功能 |
AddCode |
Code As String |
往脚本引擎中加入要执行的脚本 |
AddObject |
Name As String, Object As Object, [AddMembers As Boolean = False] |
往脚本引擎加入一个对象,以便在脚本中可以使用该对象提供的方法等。 |
Eval |
Expression As String |
表达式求值 |
ExecuteStatement |
Statement As String |
解释并执行脚本语句 |
Reset |
丢弃所有的对象和代码,将State属性置0。 |
|
Run |
ProcedureName As String, ParamArray Parameters() As Variant |
运行一个指定的过程 |
事件名称 |
功能 |
Error |
有错误发生时激发该事件 |
TimeOut |
执行过程超时时发生 |
一般使用方法
1、在程序中加入ScriptControl
2、定义一个ScriptControl的实例
3、调用AddCode等方法向脚本引擎中加入要执行的脚本。
4、调用Run执行要执行的脚本函数。
1.导入msscript.ocx
#import "C:\\Windows\\syswow64\\msscript.ocx" no_namespace
这一步步能忘记否则无法生成com接口文件
下面的就是代码了
fstream m_fs;
long Error_code=NULL;
long Error_Line = NULL;
BSTR Error_content;
HRESULT hr = ::CoInitialize(NULL); //初始化com库
IScriptControlPtr m_IScritp(__uuidof(ScriptControl));
IScriptErrorPtr m_IScript_Error = m_IScritp->Error;
//hr = m_IScritp->get_Error(&m_IScript_Error);
m_IScritp->Language = "javascript"; //设置语言的格式
m_fs.open("QQ.js", ios::in | ios::_Nocreate);
if (!m_fs.is_open()) {
m_fs.close();
return ;
}
//得到文件的大小
m_fs.seekg(, ios::end);
streamoff length;
DWORD i = ;
string m_str;
length = m_fs.tellg();
i = (DWORD)length;
char* strTemp = new char[i];
if (!strTemp)return;
memset(strTemp, , i);
m_fs.seekg(, ios::beg);
m_fs.read(strTemp, length);
m_str.append(strTemp);
m_fs.close(); //关闭文件流
//size_t max_size =m_str.max_size();
/*hr = m_IScritp->AddCode(m_str.c_str()); //把代码加载到解释器里
if (FAILED(hr)) {
hr = m_IScript_Error->get_Number(&Error_code);
hr = m_IScript_Error->get_Line(&Error_Line);
hr = m_IScript_Error->get_Description(&Error_content);
};*/
hr=m_IScritp->ExecuteStatement(m_str.c_str()); //ExecuteStatement 和AddCode 一样都是将代码加入解释器 使用任意一个都可以
if (FAILED(hr)) {
hr = m_IScript_Error->get_Number(&Error_code); //获取错误的代码
hr = m_IScript_Error->get_Line(&Error_Line); //获取错误的行号
hr = m_IScript_Error->get_Description(&Error_content); //获取具体错误的文本描述
};
_bstr_t eval = "getEncryption(\"123456\",\"\",\"!VVZ\",0);";
_variant_t r_st;
LPSAFEARRAY pSafearray; //安全数组指针
SAFEARRAYBOUND rgsabound[];
/*
SAFEARRAYBOUND是一个结构体,里面有两个变量,ULONG cElements表示的是元素的数目(更准确的说是在本维中的数目);
LONG lLbound表示的是一个逻辑起点序号,实际访问内存的时候,安全数组会将程序指定的序号减去lLbound,
比如你将其设置为10000,a[10000]这相当于A[0],a[999]数组越界,所以在没有特殊要求的情况下,lLbound一般为0。
还有一点,定义的时候是SAFEARRAYBOUND rgsaBound[1], 这点要解释一下,rgsaBound[1]表示的是一位数组,
二维数组要定义为rgsaBound[2],这里主要讲解一位数组,更高维数大家可以去搜一下,和一维的相似。
*/
rgsabound[].cElements = ;
rgsabound[].lLbound = ;
pSafearray = SafeArrayCreate(VT_VARIANT, , rgsabound);
/*
第一个参数VT_VARIANT表示数组的类型,第二个参数表示创建数组的维数,本例中是一维,第三个参数是对这个数组各个维度的描述。
SafeArrayCreate()就是创建SAFEARRAY的函数,准确的说是在堆中创建了一个SAFEARRAY,也就是说在这个函数里面,
调用了new或者malloc()之类的申请了一个空间 最后使用SafeArrayDestroy() 释放内部申请的空间
*/
if (!pSafearray)
{
return;
}
VARIANT vFlavors[]; for (LONG i = ;i<;i++)
{
VariantInit(&vFlavors[i]);
V_VT(&vFlavors[i]) = VT_BSTR;
if (i==)
{
vFlavors[i].vt = VT_INT; //最后一个参数是整数
}
}
vFlavors[].bstrVal = SysAllocString(OLESTR(""));
vFlavors[].bstrVal = SysAllocString(OLESTR(""));
vFlavors[].bstrVal = SysAllocString(OLESTR("!VVZ"));
vFlavors[].intVal = ; for (LONG l=;l<;l++)
{
SafeArrayPutElement(pSafearray, &l, &vFlavors[l]);
/*
第一个参数是指向SAFEARRAY的指针;
第二个参数是long型数组元素下标的指针,
第三个参数就是要放置的那个值得指针了。
*/
if (l<)
{
SysFreeString(vFlavors[l].bstrVal);
} }
r_st = m_IScritp->Run("getEncryption",&pSafearray);
if (r_st.vt==VT_NULL || r_st.vt ==VT_EMPTY) {
hr = m_IScript_Error->get_Number(&Error_code);
hr = m_IScript_Error->get_Line(&Error_Line);
hr = m_IScript_Error->get_Description(&Error_content);
};
/*
m_IScript_Error->get_Column();
m_IScript_Error->get_HelpContext();
m_IScript_Error->get_Source();
m_IScript_Error->get_Text();
*/
SafeArrayDestroy(pSafearray);//释放数组空间
delete [] strTemp;
::CoUninitialize();
vc++调用msscript.ocx解析实现C++与JavaScript脚本交互的更多相关文章
- VC调用javascript的几种方法
第一种:通过execScript调用.这种方法,虽然操作方便,但不能获取返回值.m_spHtmlDoc->get_parentWindow(&m_pHtmlWindow);VARIANT ...
- c++builder调用VC的dll以及VC调用c++builder的dll
解析__cdecl,__fastcall, __stdcall 的不同:在函数调用过程中,会使用堆栈,这三个表示不同的堆栈调用方式和释放方式. 比如说__cdecl,它是标准的c方法的堆栈调用方式,就 ...
- JAVA方法调用中的解析与分派
JAVA方法调用中的解析与分派 本文算是<深入理解JVM>的读书笔记,参考书中的相关代码示例,从字节码指令角度看看解析与分派的区别. 方法调用,其实就是要回答一个问题:JVM在执行一个方法 ...
- VC调用DLL
VC调用DLL 调用DLL有两种方法:静态调用和动态调用. (一).静态调用其步骤如下: 1.把你的youApp.DLL拷到你目标工程(需调用youApp.DLL的工程)的Debug目录下; 2. ...
- VC调用MATLAB
最近项目要用VC调用MATLAB,今天闲来无事,在这里稍微总结了一下初级的用法,大家共同学习: 首先在MATLAB Command Window里输入mbuild -setup,一步步走 还有一个me ...
- VC调用易语言DLL
易语言方面: .版本 .子程序 show, , 公开 ' 本名称子程序用作测试程序用,仅在开发及调试环境中有效,编译发布程序前将被系统自动清空,请将所有用作测试的临时代码放在本子程序中. ***注意不 ...
- C#调用第三方ocx控件 (winform /aspx)
C#调用第三方ocx控件 1..net环境在工具箱上点右键,选择自定义工具箱,然后选择你需要的COM或者OCX控件就可以了. 2.在自定义工具箱中加入相应的控件,设置id,在客户端脚本中直接引用它 ...
- ADO方式,VC调用Execute执行INSERT INTO插入变量SQL语句的写法
ADO方式,VC调用Execute执行INSERT INTO插入变量SQL语句的写法 有些情况下,SQL SERVER 2008r2中需要保存float,int类型的数据,当C 中的变量为double ...
- VBA中使用JavaScript脚本语言解析JSON数据
JSON:JavaScript 对象表示法(JavaScript Object Notation) 和xml相似,都是文本形式(保存在文本文件中或字符串等形式),比如: jsstr = {" ...
随机推荐
- @uoj - 435@ 【集训队作业2018】Simple Tree
目录 @description@ @solution@ @accepted code@ @details@ @description@ 有一棵有根树,根为 1,点有点权. 现在有 m 次操作,操作有 ...
- LeetCode63 Unique Paths II
题目: Follow up for "Unique Paths": Now consider if some obstacles are added to the grids. H ...
- SDUT-2132_数据结构实验之栈与队列二:一般算术表达式转换成后缀式
数据结构实验之栈与队列二:一般算术表达式转换成后缀式 Time Limit: 1000 ms Memory Limit: 65536 KiB Problem Description 对于一个基于二元运 ...
- List of the best open source software applications
List of the best open source software applications by Ryan • Oct 25th, 2008 • Category: Featured Art ...
- html实体字符转换成字符串
function EntityToString(value) { let tag = document.createElement("div"); tag.innerHTML = ...
- EC Round 41 (Rated for Div. 2)主席树 E. Tufurama
简单分析一下,对于x<y,求a[x]>=y 同时a[y]>=x 再简化一下,求1-a[y]区间内大于>=y的个数...主席树牛逼 #include<iostream> ...
- 支付宝防并发方案之"一锁二判三更新"
每年支付宝在双11和双12的活动中,都展示了绝佳的技术能力.这个能力不但体现在处理高TPS量的访问,更体现在几乎不会出错,不会出现重复支付的情况,那这个是怎么做到的呢? 诚然,为了实现在高并发下仍不会 ...
- AUTOSSH设置ssh隧道,实现反向代理访问内网主机
内网主机上配置: autossh -M -CNR :localhost: ubuntu@123.207.121.121 可以实现将访问主机123.207.121.121的1234端口的数据,通过隧道转 ...
- Echarts Map地图下钻至县级
**准备工作:**1.首先使用vue-cli的脚手架生成vue项目. 2.然后使用npm安装echartsnpm install echarts -S 3.安装完后再mian.js中挂载到vue的实例 ...
- TP5 在模板读出Session值
模板取值: <p class="info">后台登录中心{$Request.session.username}</p> 也可以 {$Think.sessio ...