COMコンポーネントでJavaScript関数を呼び出す


転載先:http://blog.csdn.net/cheungmine/article/details/1451489
 
 
要求は簡単であり、すなわちCOMコンポーネントAがIEで実行され、JavaScript(JS)を使用してAを呼び出す方法longCalc()であり、この方法は時間のかかる操作であり、IEの現在の進捗状況を通知することを要求する.コールバック関数を使用して、scriptCallbackFuncという名前を設定する必要があります.このテクノロジーを実現するのは簡単です.
1、構成要素(C++)
コンポーネントAのメソッドはIDLで定義されます.
[id(2)] HRESULT longCalc([in] DOUBLE v1, [in] DOUBLE v2, [in, optional] VARIANT scriptCallback);


コンポーネントAの方法実装:
//        : 
// scriptCallbackFunc(LONG nCurrentProgress, LONG nTotalProgress, BSTR bstrProgressName);
//     JS     
STDMETHODIMP CA:: longCalc (DOUBLE v1, DOUBLE v2, VARIANT scriptCallback)
{
    CComPtr<IDispatch> spCallback;
    if (scriptCallback.vt == VT_DISPATCH)
         spCallback = scriptCallback.pdispVal;
    

    //     
    CComVariant varResult;
    CComVariant avarParams[3];
    avarParams[0] = “      ”;        // bstrProgressName
    avarParams[0].vt = VT_BSTR;
    avarParams[1] = 100;                              // nTotalProgress
    avarParams[1].vt = VT_I4;
    avarParams[2] = 0;                                 // nCurrentProgress
    avarParams[2].vt = VT_I4;
    DISPPARAMS params = { avarParams, NULL, 3, 0 };


    if(spCallback)
          spCallback->Invoke(0, 
                IID_NULL, 
                LOCALE_USER_DEFAULT, 
                DISPATCH_METHOD, 
                ¶ms, &varResult, NULL, NULL);

    BOOL  bFinished = false;
    

    while(!bFinished)
    {
         //     …
         Sleep(1000);
         v1 = v1+v2;
  
        //     
        if(spCallback)
        {
            avarParams[0] = “      …”;
            avarParams[2] = 0;
            spCallback->Invoke(0, 
                         IID_NULL, 
                         LOCALE_USER_DEFAULT, 
                         DISPATCH_METHOD, 
                         ¶ms, &varResult, NULL, NULL);
          }

          if(…)
                 bFinished = TRUE;
     }  // while OK!

      return S_OK;
}

2、取引先(JS)
<script language="javascript">
<!--
      //       :scriptCallbackFunc
      function scfDisplayProgress(nCurrentProgress, nTotalProgress, bstrProgressName)
      {
             window.status = bstrProgressName + “:”+(nCurrentProgress *100/TotalProgress);
      }
 
      //        longCalc
      var objA = new ActiveXObject(“MyCom.A”);

       //     :     IE       
       objA. longCalc (100, 200, scfDisplayProgress); 

       //      
       objA. longCalc (100, 200); 
//-->
</script>

3説明
このテクノロジーはスクリプトにのみ適用されます.VB、C++のお客様には向いていません.このテクノロジーは、接続ポイント、イベントとは無関係です.マイクロソフトのXML DOMオブジェクトはこの方法を広く使用している.