麻豆小视频在线观看_中文黄色一级片_久久久成人精品_成片免费观看视频大全_午夜精品久久久久久久99热浪潮_成人一区二区三区四区

首頁 > 開發 > Java > 正文

在C#中調用VBScript、JavaScript等腳本的實現

2024-07-21 02:27:14
字體:
來源:轉載
供稿:網友

以前在做工作流(workflow)項目的時候,里面有一項就是在用戶制定流程定義時可以編寫腳本來控制活動的跳轉,而這些腳本定義后存在數據庫中,當流程啟動的時候,工作流引擎會控制活動執行順序,串型的兩個活動比較簡單,但有的活動到下一個活動有條件判斷,或者存在多個分支,簡單的還好,只要在數據庫表中加個字段就可以實現,復雜一點的就需要通過腳本實現了。當時經驗不夠,幾天都沒找到快速的解決辦法,想自己寫一個自定義腳本引擎沒有把握,而且時間也不夠,還是在網上找找看吧,花了一些時間,還是找到了一個自認為比較好的解決辦法,寫出來同大家分享。
下面通過兩部分來說明實現以及應用。


一.使用msscriptcontrol

到微軟的網站上下載windows script control,它是一個activex(r) 控件,所以在.net中使用我interop了一下。下載安裝完成后,新建一個c#的windows應用程序項目,在解決方案資源管理器中選中引用節點,右鍵點擊選擇添加引用菜單,彈出添加引用對話框,單擊瀏覽找到安裝windows script control的目錄,選取msscript.ocx文件確定。那么在引用節點下會增加一個msscriptcontrol組件,下面是他interop后的所有對象。



scriptcontrol 對支持 activex(tm) script 的宿主 script 引擎提供簡單接口。接下來我們對被轉化成scriptcontrolclass類的scriptcontrol的屬性和方法進行一些說明。
屬性
allowui 屬性:應用于 scriptcontrol 本身或 scirpt 引擎顯示的用戶界面元素,可讀寫。
codeobject 屬性:返回對象,該對象用于調用指定模塊的公用成員。只讀。
error 屬性:返回 error 對象,其中包含所發生的最后一個錯誤的相關詳細信息。只讀。
language 屬性:設置或返回正在使用的 script 語言名稱??勺x寫。
modules 屬性:為 scriptcontrol 對象返回模塊集合。只讀。
procedures 屬性:返回在指定模塊中定義的過程集合。只讀。
sitehwnd 屬性:設置或返回窗口的 hwnd,通過執行 script 代碼,此窗口用于顯示對話框和其他用戶界面元素。可讀寫。
state 屬性:設置或返回 scriptcontrol 對象的模式??勺x寫。
timeout 屬性:設置或返回時間(毫秒),此時間后用戶可選擇中止 script 代碼的執行或允許代碼繼續執行。可讀寫。
usesafesubset 屬性:設置或返回 boolean 值,指明宿主應用程序是否有保密性要求。如果宿主應用程序需要安全控制,則 usesafesubset 為 true,否則為 false??勺x寫。
方法
addcode 方法:向模塊添加指定代碼。可多次調用 addcode 方法。
addobject 方法:使主機對象模型對 script 引擎可用。
eval 方法:計算表達式并返回結果。
executestatement 方法:執行指定的語句。
reset 方法:放棄所有已經添加到 scriptcontrol 中的 script 代碼和對象。
run 方法:運行指定過程。
事件
error 事件:出現運行時錯誤時,發生此事件。
timeout 事件:當超出了 timeout 屬性指定的時間且用戶在結果對話框中選定了 end 時,發生此事件。
補充幾點
allowui 屬性如果設置為false,則顯示對話框之類的語句不起作用,如在 vbscript 中msgbox 語句,javascript中的alert等,并且如果執行的腳本超出timeout設置的毫秒數,也不會跳出超出時間提醒的對話框,反之則相反;重新設置 language 屬性會清空addcode加載的代碼;對于timeout屬性,發生超時時,scriptcontrol 檢查對象的 allowui 屬性,確定是否允許顯示用戶界面元素。
如果讀者需要更詳細的了解,可以查看msdn文檔。
為了使控件更容易使用,我用一個scriptengine類包裝了一下,下面是完整代碼:

using system;
using msscriptcontrol;
using system.text;
namespace zz
{
    /// <summary>
     /// 腳本類型
     /// </summary>
     public enum scriptlanguage
     {
         /// <summary>
         /// jscript腳本語言
         /// </summary>
         jscript,
         /// <summary>
         /// vbscript腳本語言
         /// </summary>
         vbscript,
         /// <summary>
         /// javascript腳本語言
         /// </summary>
         javascript
     }
     /// <summary>
     /// 腳本運行錯誤代理
     /// </summary>
     public delegate void runerrorhandler();
     /// <summary>
     /// 腳本運行超時代理
     /// </summary>
     public delegate void runtimeouthandler();
     /// <summary>
     /// scriptengine類
     /// </summary>
     public class scriptengine
     {
         private scriptcontrol msc;
         //定義腳本運行錯誤事件
         public event runerrorhandler runerror;
         //定義腳本運行超時事件
         public event runtimeouthandler runtimeout;
         /// <summary>
         ///構造函數
         /// </summary>
         public scriptengine():this(scriptlanguage.vbscript)
         {
         }
         /// <summary>
         /// 構造函數
         /// </summary>
         /// <param name="language">腳本類型</param>
         public scriptengine(scriptlanguage language)
         {
              this.msc = new scriptcontrolclass();
              this.msc.usesafesubset = true;
              this.msc.language = language.tostring();
              ((dscriptcontrolsource_event)this.msc).error += new dscriptcontrolsource_erroreventhandler(scriptengine_error);
              ((dscriptcontrolsource_event)this.msc).timeout += new dscriptcontrolsource_timeouteventhandler(scriptengine_timeout);
         }
         /// <summary>
         /// 運行eval方法
         /// </summary>
         /// <param name="expression">表達式</param>
         /// <param name="codebody">函數體</param>
         /// <returns>返回值object</returns>
         public object eval(string expression,string codebody)
         {
              msc.addcode(codebody);
              return msc.eval(expression);
         }
         /// <summary>
         /// 運行eval方法
         /// </summary>
         /// <param name="language">腳本語言</param>
         /// <param name="expression">表達式</param>
         /// <param name="codebody">函數體</param>
         /// <returns>返回值object</returns>
         public object eval(scriptlanguage language,string expression,string codebody)
         {
              if(this.language != language)
                   this.language = language;
              return eval(expression,codebody);
         }
         /// <summary>
         /// 運行run方法
         /// </summary>
         /// <param name="mainfunctionname">入口函數名稱</param>
         /// <param name="parameters">參數</param>
         /// <param name="codebody">函數體</param>
         /// <returns>返回值object</returns>
         public object run(string mainfunctionname,object[] parameters,string codebody)
         {
              this.msc.addcode(codebody);
              return msc.run(mainfunctionname,ref parameters);
          }
         /// <summary>
         /// 運行run方法
         /// </summary>
         /// <param name="language">腳本語言</param>
         /// <param name="mainfunctionname">入口函數名稱</param>
         /// <param name="parameters">參數</param>
         /// <param name="codebody">函數體</param>
         /// <returns>返回值object</returns>
         public object run(scriptlanguage language,string mainfunctionname,object[] parameters,string codebody)
         {
              if(this.language != language)
                   this.language = language;
              return run(mainfunctionname,parameters,codebody);
         }
         /// <summary>
         /// 放棄所有已經添加到 scriptcontrol 中的 script 代碼和對象
         /// </summary>
         public void reset()
         {
              this.msc.reset();
         }
         /// <summary>
         /// 獲取或設置腳本語言
         /// </summary>
         public scriptlanguage language
         {
              get{return (scriptlanguage)enum.parse(typeof(scriptlanguage),this.msc.language,false);}
              set{this.msc.language = value.tostring();}
         }
         /// <summary>
         /// 獲取或設置腳本執行時間,單位為毫秒
         /// </summary>
         public int timeout
         {
              get{return this.msc.timeout;}
              set{this.msc.timeout = value;}
         }
         /// <summary>
         /// 設置是否顯示用戶界面元素
         /// </summary>
         public bool allowui
         {
              get{return this.msc.allowui;}
              set{this.msc.allowui = value;}
         }
         /// <summary>
         /// 宿主應用程序是否有保密性要求
         /// </summary>
         public bool usesafesubset
         {
              get{return this.msc.usesafesubset;}
              set{this.msc.usesafesubset = true;}
         }
         /// <summary>
         /// runerror事件激發
         /// </summary>
         private void onerror()
         {
              if(runerror!=null)
                   runerror();
         }
         /// <summary>
         /// ontimeout事件激發
         /// </summary>
         private void ontimeout()
         {
              if(runtimeout!=null)
                   runtimeout();
         }
         private void scriptengine_error()
         {
              onerror();
         }
         private void scriptengine_timeout()
         {
              ontimeout();
         }
     }
}
上面的包裝定義了一個scriptlanguage枚舉,這樣操作起來更方便一點。另外腳本引擎包括了error事件和timeout事件,根據實際使用情況可進行注冊。
 
二.腳本引擎演示
     我建了個窗體程序,測試包括腳本語言的選擇,是否開啟allowui屬性,超時時間的設置,以及腳本引擎調用方法的選擇。測試程序代碼比較長,下面列出了主要部分:
using system;
using system.drawing;
using system.collections;
using system.componentmodel;
using system.windows.forms;
using system.data;
namespace zz
{
     public class form1 : system.windows.forms.form
     {
         private scriptengine scriptengine;
         private system.windows.forms.checkbox checkboxallowui;
         private system.windows.forms.textbox textboxresult;
         private system.windows.forms.numericupdown numericupdowntimeout;
         private system.windows.forms.textbox textboxcodebody;
         private system.windows.forms.button buttonrun;
         private system.windows.forms.button buttoncancel;
         private system.windows.forms.combobox comboboxscript;
         private system.windows.forms.textbox textboxparams;
         private system.windows.forms.radiobutton radiobuttoneval;
         private system.windows.forms.radiobutton radiobuttonrun;
         private system.windows.forms.textbox textboxmethodname;
         private system.componentmodel.container components = null;
 
         public form1()
         {
              initializecomponent();
              this.comboboxscript.selectedindex = 0;
              this.scriptengine = new scriptengine();
              this.scriptengine.usesafesubset = true;
              this.scriptengine.runerror += new runerrorhandler(scriptengine_runerror);
              this.scriptengine.runtimeout += new runtimeouthandler(scriptengine_runtimeout);
         }
         protected override void dispose( bool disposing )
         {
              if( disposing )
                   if (components != null)
                       components.dispose();
              base.dispose( disposing );
         }
         #region windows 窗體設計器生成的代碼
         private void initializecomponent()
         {
              //省略
         }
         #endregion
          [stathread]
         static void main()
         {
              application.run(new form1());
         }
         //運行腳本
         private void buttonrun_click(object sender, system.eventargs e)
         {
              this.scriptengine.reset();
              this.scriptengine.language = (scriptlanguage)enum.parse(typeof(scriptlanguage),this.comboboxscript.selecteditem.tostring());
              this.scriptengine.timeout = (int)this.numericupdowntimeout.value;
              this.scriptengine.allowui = this.checkboxallowui.checked;
              if(this.radiobuttoneval.checked)//執行eval方法
              {
                   this.textboxresult.text = this.scriptengine.eval(this.textboxmethodname.text+"("+this.textboxparams.text+")",this.textboxcodebody.text).tostring();
              }
              else//執行run方法
              {
                   string[] parameters = (string[])this.textboxparams.text.split(',');
                   object [] paramarray = new object[parameters.length];
                   for(int i = 0;i<parameters.length;i++)
                       paramarray[i] = int32.parse(parameters[i]);
                   this.textboxresult.text = this.scriptengine.run(this.textboxmethodname.text,paramarray,this.textboxcodebody.text).tostring();
              }
         }
         //退出程序
         private void buttoncancel_click(object sender, system.eventargs e)
         {
              this.close();
         }
         //錯誤函數
         private void scriptengine_runerror()
         {
              messagebox.show("runerror執行腳本錯誤!");
         }
         private void scriptengine_runtimeout()
         {
              messagebox.show("runtimeout執行腳本超時,引發錯誤!");
         }
     }
}

下面是測試程序運行界面:

在文本框中寫了一個javascript的函數。輸入12,輸出12000012。
如果把超時時間調整為1毫秒,那么執行該腳本就會跳出下面的超時提醒框,同時激發事件。

總結,上面演示了javascript腳本,如果有興趣讀者可以寫一些vbsript函數進行測試,腳本語言也只列出了三種,看了幫助,他還支持其他一些腳本,如果需要可以添加。另外,因為是調用com,有些返回值是obejct類型的,需要進行轉換。在csdn的技術論壇c#板塊下時常有朋友問這方面的問題,對于碰到這類問題的朋友,希望通過這篇文章能獲得一些你需要的幫助,很高興能和搞.net的朋友進行交流,我的郵件地址[email protected]
發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
主站蜘蛛池模板: 久久欧美亚洲另类专区91大神 | a级高清免费毛片av在线 | av电影在线播放 | 狠狠干最新网址 | 在线看免电影网站 | 天天操很很操 | 19禁国产精品福利视频 | 久久色网站 | 强伦女教师视频 | 免费毛片随便看 | 羞羞草视频 | 久久精品国产99久久6动漫亮点 | 干色视频 | 亚洲精品免费播放 | 久久久国产一区二区三区 | 日本看片一区二区三区高清 | 精品国产一区二区三区蜜殿 | 毛片免费在线视频 | 精品国产一区二区三区四区在线 | 精品国产乱码一区二区三区四区 | 精品国产一区二区三区天美传媒 | 双性精h调教灌尿打屁股的文案 | 午夜视频免费播放 | 国产精品久久久久永久免费 | 三人弄娇妻高潮3p视频 | 黄a大片| 日本黄色一级视频 | 精品国产一区二区三区免费 | 午夜国产成人 | 免费国产一级淫片 | 一区在线不卡 | 黄色免费大片 | 一级做a爱片性色毛片高清 日本一区二区在线看 | 国产精品视频导航 | 日韩 综合| 在线亚州 | 成人做爰s片免费看网站 | 国产免费视频一区二区裸体 | 亚洲成人国产综合 | 欧美一级黄色录像片 | 欧美羞羞视频 |