Как автоматизировать IE webapp, который всплывает модальный диалог HTML?

[еще раз пересмотрела для ясности]

у меня есть программа на C++, который взаимодействует с веб-сайтом. Сайт специфичен для IE, и моя программа тоже.

я подключаюсь к работающему экземпляру IE обычным способом (процесс -- см. код). Как только я получу IWebBrowser2, У меня нет проблем получая IHTMLDocument2 и взаимодействовать с индивидуалом IHTMLElement объекты, заполнение полей и нажатие кнопок.

но если на веб-странице есть javascript, который вызывает

1 ответов


я не знаю, почему вы хотите получить IServiceProvider или IWebBrowser2 Если ты хочешь IHTMLElement. Вы можете получить их, позвонив в IHTMLDocument ' s get_all() метод.

этот фрагмент кода показывает, как это работает:

#include <Windows.h>
#include <mshtml.h>
#include <Exdisp.h>
#include <atlbase.h>
#include <SHLGUID.h>
#include <oleacc.h>
#include <comdef.h>
#include <tchar.h>

HRESULT EnumElements(HINSTANCE hOleAccInst, HWND child)
{
    HRESULT hr;

    UINT nMsg = ::RegisterWindowMessage(_T("WM_HTML_GETOBJECT"));
    LRESULT lRes = 0;
    ::SendMessageTimeout(child, nMsg, 0L, 0L, SMTO_ABORTIFHUNG, 1000, (PDWORD)&lRes);

    LPFNOBJECTFROMLRESULT pfObjectFromLresult = (LPFNOBJECTFROMLRESULT)::GetProcAddress(hOleAccInst, "ObjectFromLresult");
    if (pfObjectFromLresult == NULL)
        return S_FALSE;

    CComPtr<IHTMLDocument2> spDoc;
    hr = (*pfObjectFromLresult)(lRes, IID_IHTMLDocument2, 0, (void**)&spDoc);
    if (FAILED(hr)) return hr;

    CComPtr<IHTMLElementCollection> spElementCollection;
    hr = spDoc->get_all(&spElementCollection);
    if (FAILED(hr)) return hr;

    CComBSTR url;
    spDoc->get_URL(&url);
    printf("URL: %ws\n", url);

    long lElementCount;
    hr = spElementCollection->get_length(&lElementCount);
    if (FAILED(hr)) return hr;
    printf("Number of elements: %d", lElementCount);

    VARIANT vIndex; vIndex.vt = VT_I4;
    VARIANT vSubIndex; vSubIndex.vt = VT_I4; vSubIndex.lVal = 0;
    for (vIndex.lVal = 0; vIndex.lVal < lElementCount; vIndex.lVal++)
    {
        CComPtr<IDispatch> spDispatchElement;
        if (FAILED(spElementCollection->item(vIndex, vSubIndex, &spDispatchElement)))
            continue;
        CComPtr<IHTMLElement> spElement;
        if (FAILED(spDispatchElement->QueryInterface(IID_IHTMLElement, (void**)&spElement)))
            continue;
        CComBSTR tagName;
        if (SUCCEEDED(spElement->get_tagName(&tagName)))
        {
            printf("%ws\n", tagName);
        }
    }
    return S_OK;
}

int _tmain(int argc, _TCHAR* argv[])
{
    ::CoInitialize(NULL);
    HINSTANCE hInst = ::LoadLibrary(_T("OLEACC.DLL"));
    if (hInst != NULL)
    {
        HRESULT hr = EnumElements(hInst, (HWND)0x000F05E4);    // Handle to Internet Explorer_Server determined with Spy++ :)
        ::FreeLibrary(hInst);
    }
    ::CoUninitialize();
    return 0;
}

выше код работает на обоих: обычное окно или модальное окно, просто передайте правильный HWND до