再升級(jí)版說明:通過frame的get_location屬性,指定frame來獲取其元素,,減少遞歸和循環(huán),,減少循環(huán)和遞歸,基于效能提升門戶生產(chǎn)地址獲取主叫,,可從6s壓縮到1s,,耗時(shí)在于指定frame所有元素循環(huán)上。
1.獨(dú)立代碼
//--------------獲取效能提升門戶主叫---------------------------------------//
#include <atlbase.h>
#include <mshtml.h>
#include <winuser.h>
#include <comdef.h>
#include <string.h>
void EnumIE(void);//處理網(wǎng)頁
void EnummiddleFrame(IHTMLDocument2 * pIHTMLDocument2);//處理框架
void EnumleftFrame(IHTMLDocument2 * pIHTMLDocument2);//處理框架
CComModule _Module; //使用CComDispatchDriver ATL的智能指針,,此處必須聲明
#include <atlcom.h>
void EnumAllElement(IHTMLDocument2 * pIHTMLDocument2);//獲取網(wǎng)頁內(nèi)元素
CString glb_strCaller;//全局主叫
void EnumIE(void)
{
CComPtr<IShellWindows> spShellWin;
HRESULT hr=spShellWin.CoCreateInstance(CLSID_ShellWindows);
if (FAILED(hr))
{
return;
}
long nCount=0; //取得瀏覽器實(shí)例個(gè)數(shù)(Explorer和IExplorer)
spShellWin->get_Count(&nCount);
if (0==nCount)
{
return;
}
for(int i=0; i<nCount; i++)
{
CComPtr<IDispatch> spDispIE;
hr=spShellWin->Item(CComVariant((long)i), &spDispIE);
if (FAILED(hr)) continue;
CComQIPtr<IWebBrowser2>spBrowser=spDispIE;
if (!spBrowser) continue;
CComPtr<IDispatch> spDispDoc;
hr=spBrowser->get_Document(&spDispDoc);
if (FAILED(hr)) continue;
CComQIPtr<IHTMLDocument2>spDocument2 =spDispDoc;
if (!spDocument2) continue;
//Modify by Fang jiansheng 2011-04-02
//*******************************************************************************
CString cIEUrl_Filter; //設(shè)置的URL(必須是此URL的網(wǎng)站才有效);
cIEUrl_Filter=" //*******************************************************************************
CComBSTR IEUrl;
spBrowser->get_LocationURL(&IEUrl);
CString cIEUrl_Get; //從機(jī)器上取得的HTTP的完整的URL;
cIEUrl_Get=IEUrl;
cIEUrl_Get=cIEUrl_Get.Left(cIEUrl_Filter.GetLength()); //截取前面N位
if (strcmp(cIEUrl_Get,cIEUrl_Filter)==0)
{
// 程序運(yùn)行到此,,已經(jīng)找到了IHTMLDocument2的接口指針
EnummiddleFrame(spDocument2);
}
}
}
//在框架內(nèi)獲取主叫
void EnumAllElement(IHTMLDocument2 * pIHTMLDocument2) //枚舉所有字段
{
if (!pIHTMLDocument2) return;
HRESULT hr;
CComQIPtr<IHTMLElementCollection> spAllElement;
hr=pIHTMLDocument2->get_all(&spAllElement);//獲取所有網(wǎng)頁內(nèi)所有元素
if (FAILED(hr)) return;
long nLength = 0;
spAllElement->get_length (&nLength);
for (int i = 0; i < nLength; i++)
{
CComPtr<IDispatch> pDisp;
hr = spAllElement->item(COleVariant((long)i),COleVariant((long)0),&pDisp); //獲取單個(gè)元素
if(SUCCEEDED(hr))
{
//CComQIPtr <IHTMLElement, &IID_IHTMLElement> pElement(pDisp);
CComQIPtr<IHTMLElement, &IID_IHTMLElement> pElement;
pDisp->QueryInterface(&pElement);
BSTR bId;
pElement->get_id(&bId);//可以獲取其他特征,根據(jù)具體元素而定
CString strId=bId;
if(!strId.IsEmpty() && strId=="callNo")//根據(jù)id是主叫號(hào)碼獲取值或作其他處理
{
IHTMLInputTextElement* input;
pDisp->QueryInterface(IID_IHTMLInputTextElement,(void**)&input);
BSTR bVal;
input->get_value(&bVal);
if(bVal==NULL) glb_strCaller="";
else glb_strCaller=bVal;
break;
}
}
}
}
void EnumleftFrame(IHTMLDocument2 * pIHTMLDocument2)
{
if (!pIHTMLDocument2) return;
HRESULT hr;
CComPtr<IHTMLFramesCollection2> spFramesCollection2;
pIHTMLDocument2->get_frames(&spFramesCollection2); //取得框架frame的集合
long nFrameCount=0; //取得子框架個(gè)數(shù)
hr=spFramesCollection2->get_length(&nFrameCount);
if (FAILED(hr)|| 0==nFrameCount) return;
for(long i=0; i<nFrameCount; i++)
{
CComVariant vDispWin2; //取得子框架的自動(dòng)化接口
hr = spFramesCollection2->item(&CComVariant(i), &vDispWin2);
if (FAILED(hr)) continue;
CComQIPtr<IHTMLWindow2>spWin2 = vDispWin2.pdispVal;
//CComQIPtr<IHTMLFrameElement, &IID_IHTMLFrameElement> pFrmElement=vDispWin2.pdispVal;
if (!spWin2) continue; //取得子框架的 IHTMLWindow2 接口
CComPtr <IHTMLLocation> spLoc;
spWin2->get_location(&spLoc);//獲取frame的頁面地址
BSTR bHref;
spLoc->get_href(&bHref);//獲取鏈接地址
CString strHref=bHref;
if(!strHref.IsEmpty() && strHref==" {
//效能提升門戶中間框架leftFrame的頁面地址
CComPtr <IHTMLDocument2> spDoc2;
spWin2->get_document(&spDoc2); //取得子框架的 IHTMLDocument2 接口
EnumAllElement(spDoc2);//獲取效能提升門戶主叫
break;
}
}
}
void EnummiddleFrame(IHTMLDocument2 * pIHTMLDocument2)
{
if (!pIHTMLDocument2) return;
HRESULT hr;
CComPtr<IHTMLFramesCollection2> spFramesCollection2;
pIHTMLDocument2->get_frames(&spFramesCollection2); //取得框架frame的集合
long nFrameCount=0; //取得子框架個(gè)數(shù)
hr=spFramesCollection2->get_length(&nFrameCount);
if (FAILED(hr)|| 0==nFrameCount) return;
for(long i=0; i<nFrameCount; i++)
{
CComVariant vDispWin2; //取得子框架的自動(dòng)化接口
hr = spFramesCollection2->item(&CComVariant(i), &vDispWin2);
if (FAILED(hr)) continue;
CComQIPtr<IHTMLWindow2>spWin2 = vDispWin2.pdispVal;
//CComQIPtr<IHTMLFrameElement, &IID_IHTMLFrameElement> pFrmElement=vDispWin2.pdispVal;
if (!spWin2) continue; //取得子框架的 IHTMLWindow2 接口
CComPtr <IHTMLLocation> spLoc;
spWin2->get_location(&spLoc);//獲取frame的頁面地址
BSTR bHref;
spLoc->get_href(&bHref);//獲取鏈接地址
CString strHref=bHref;
if(!strHref.IsEmpty() && strHref==" {
//效能提升門戶中間框架middleFrame的頁面地址
CComPtr <IHTMLDocument2> spDoc2;
spWin2->get_document(&spDoc2); //取得子框架的 IHTMLDocument2 接口
EnumleftFrame(spDoc2);//獲取效能提升門戶左邊框架leftFrame
break;
}
}
}
////////////////////////////////////////////////////////////////////////////////////////////////
//-----------結(jié)束---------------------//
2.執(zhí)行代碼:
void CDemoDlg::OnOK()
{
// TODO: Add extra validation here
::CoInitialize(NULL); //初始化COM
EnumIE(); //枚舉瀏覽器
::CoUninitialize(); //釋放COM
//CDialog::OnOK();
}