首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> C語言 >> VC >> VC 教學

VC++ HTML 程式設計精要:IWebBrowser2、MSHTML DOM 操作、自動化填表與 BHO 事件捕獲

     編輯:VC 教學

核心介面架構

IWebBrowser2          // 瀏覽器控制核心:導航、文檔存取
    → get_Document() → IDispatch
        → QueryInterface → IHTMLDocument2 (MSHTML DOM 根)
            → get_all() → IHTMLElementCollection (所有元素)
            → getElementById/TagName → IHTMLElement (單一元素)
            → createEventObject / fireEvent → 事件模擬

場景一:提取網頁特定資料

// 取得 IHTMLDocument2*
IHTMLDocument2* pDoc = nullptr;
pWebBrowser->get_Document((IDispatch**)&pDoc);
if (!pDoc) return;

// 方法 A:依 Tag 取得集合
IHTMLElementCollection* pColl = nullptr;
pDoc->get_all(&pColl);

// 方法 B:依 ID 直接取得
IHTMLElement* pElem = nullptr;
pDoc->getElementById(CComBSTR(_T("targetId")), &pElem);

// 方法 C:依 TagName 取得集合再遍歷
IHTMLElementCollection* pTags = nullptr;
pDoc->getElementsByTagName(CComBSTR(_T("a")), &pTags);
long len = 0; pTags->get_length(&len);
for (long i = 0; i < len; ++i) {
    CComVariant idx(i), idx2(0);
    CComPtr pDisp;
    pTags->item(idx, idx2, &pDisp);
    CComQIPtr pEl(pDisp);
    CComBSTR innerText, href;
    pEl->get_innerText(&innerText);
    pEl->getAttribute(CComBSTR(_T("href")), 0, &href);
    // 判斷是否目標連結...
}

場景二:IXMLHTTPRequest 純 HTTP 抓取 + 字串解析 (無瀏覽器控件)


IXMLHTTPRequest* pHttp = nullptr;
CoCreateInstance(CLSID_XMLHTTP, NULL, CLSCTX_INPROC_SERVER, 
                 IID_IXMLHTTPRequest, (void**)&pHttp);

pHttp->open(CComBSTR(_T("GET")), CComBSTR(url), VARIANT_FALSE, vtEmpty, vtEmpty);
pHttp->send(vtEmpty);

long status = 0; pHttp->get_status(&status);
if (status == 200) {
    CComBSTR responseText;
    pHttp->get_responseText(&responseText);
    // CString str = responseText; 正則/字串搜尋提取...
}

場景三:自動填表 (input/select/textarea)


// 通用輸入框
void SetInputValue(IHTMLElementCollection* pAll, LPCTSTR name, LPCTSTR value) {
    CComPtr pDisp;
    pAll->item(CComVariant(name), CComVariant(0L), &pDisp);
    CComQIPtr pInput(pDisp);
    if (pInput) pInput->put_value(CComBSTR(value));
}

// 下拉選單
void SetSelectValue(IHTMLElementCollection* pAll, LPCTSTR name, long index) {
    CComPtr pDisp;
    pAll->item(CComVariant(name), CComVariant(0L), &pDisp);
    CComQIPtr pSelect(pDisp);
    if (pSelect) pSelect->put_selectedIndex(index);
}

// 文字區域
void SetTextareaValue(IHTMLElementCollection* pAll, LPCTSTR name, LPCTSTR value) {
    CComPtr pDisp;
    pAll->item(CComVariant(name), CComVariant(0L), &pDisp);
    CComQIPtr pTextarea(pDisp);
    if (pTextarea) pTextarea->put_value(CComBSTR(value));
}

場景四:BHO (Browser Helper Object) 捕獲點擊事件

  1. 實作 IObjectWithSite::SetSite 取得 IWebBrowser2
  2. 連接 DWebBrowserEvents2::DocumentComplete 事件
  3. 在 DocumentComplete 中:pDisp->QueryInterface(IID_IHTMLDocument2) → HTMLDocumentEvents2::onclick 連接
  4. 事件回呼參數 IHTMLEventObj* pEvtObj → get_srcElement() 取得觸發元素 → 解析屬性

// BHO 事件連接片段
void STDMETHODCALLTYPE OnDocumentComplete(IDispatch* pDisp, VARIANT* URL) {
    CComQIPtr pDoc(pDisp);
    if (!pDoc) return;
    
    CComQIPtr pDocEvents(pDoc);
    if (pDocEvents) {
        // 建議使用 AtlAdvise 連接事件汲
        // 需實作 IDispatch Invoke 捕獲 DISPID_HTMLDOCUMENTEVENTS2_ONCLICK
    }
}

關鍵介面對照表

介面用途常用方法
IWebBrowser2瀏覽器控制Navigate, get_Document, ExecWB, Quit
IHTMLDocument2DOM 文檔根get_all, getElementById, getElementsByTagName, createElement
IHTMLElement通用元素get_innerText, put_innerText, getAttribute, setAttribute, click
IHTMLInputElement<input> 專用put_value, get_value, get_type
IHTMLSelectElement<select> 專用put_selectedIndex, get_options, add/remove
IHTMLTextAreaElement<textarea> 專用put_value, get_value
IHTMLEventObj事件物件get_srcElement, get_type, get_keyCode, returnValue

避坑指南

  • 介面釋放:所有 QueryInterface/get_* 取得的介面指標必須 Release(),建議使用 CComPtr/CComQIPtr 智慧指標
  • 跨域限制:腳本存取不同域文檔會被拒絕 (安全性),需信任區域設定或簽名 ActiveX
  • 文檔就緒狀態:操作 DOM 前確認 IWebBrowser2::get_ReadyState == READYSTATE_COMPLETE
  • 編碼問題:get_innerText 回傳 BSTR (UTF-16),轉換用 CW2A/CW2T 或 WideCharToMultiByte
  • BHO 註冊:需註冊至 HKLM\SOFTWARE\Microsoft\Windows\CurrentVersion\Explorer\Browser Helper Objects\{CLSID}

掌握 IWebBrowser2 → IHTMLDocument2 → IHTMLElementCollection → IHTMLElement 介面鏈,配合 IXMLHTTPRequest 輕量抓取與 BHO 事件捕獲,即可構建強大的網頁自動化、資料擷取、測試工具。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved