본문

WebBrowser Control 사용시. 페이지로딩이 완료되었는지 확인하기


WebBrowser 컨트롤은 웹페이지 로드가 완료되는 시점에서 DocumentComplete이벤트를 생성하며, 이를 위해 이벤트 핸들러를 만들어 처리할 수 있습니다. 이 게시물은 WebBrowser 컨트롤 사용시 페이지 로딩의 완료여부를 판별할 수 있는 방법들에 대해 소개합니다.

WebBrowser 컨트롤은 ReadyState 속성이 READYSTATE_COMPLETE로 변했을때 DocumentComplete 이벤트를 생성합니다. 이 이벤트는 WebBrowser 컨트롤이 웹페이지 다운로드를 완료했다는것을 의미합니다. 해당 이벤트에 대해 알아두어야 할 사항은 다음과 같습니다. 
 
  • 페이지에 프레임이 없는 경우(단일페이지), DocumentComplete는 페이지 로드 완료시 한번만 발생된다.
  • 여러 프레임이 존재하는 경우 DocumentComplete도 마찬가지로 여러번 발생된다. 모든 프레임이 이 이벤트를 발생시키는건 아니지만, DowonloadBegin 이벤트를 발생시키는 모든 프레임은 이에 상응하는 DocumnetComplete를 발생시킨다.
  • DocumentComplete 이벤트 발생시, 인자값으로 해당 프레임의 IDispatch를 가리키는 IDispatch* 를 갖는다.
  • 최상위(DOM) 프레임은 가장 나중에 DocumentComplete를 발생한다. 그러므로 페이지 로드 완료를 확인하기 위해서, IDispatch* 인자값이 WebBrowser 컨트롤의 IDispatch와 동일한 항목을 가리키는지 확인하면 된다.

비주얼 베이직으로 페이지가 모두 로드되었는지 확인하는 방법은 다음과 같습니다

Private Sub WebBrowser1_DocumentComplete(ByVal pDisp As Object, URL As Variant)
    If (pDisp Is WebBrowser1.Object) Then
        Debug.Print "Web document is finished downloading"
    End If
End
Sub


만약 최상위 프레임이 변하는것이 아니라, 프레임 독자적으로 페이지가 변하는 경우, DocumentComplete는 최상위 프레임이 아닌, 해당 프레임의 로드가 완료되는 시점에서 호출이 됩니다. 다음와 같은 경우를 생각해보세요

WebBrowser 컨트롤이 frameset을 포함합니다. frameset에 속하는 어떤 프레임상에서 유저가 한 링크를 클릭하여 그 프레임 상에서 새로운 페이지를 불러옵니다 (단, 다른 프레임들의 변화는 없습니다) 새로운 페이지 내에는 또다른 여러개의 프레임이 존재할 수 있습니다. 따라서 각각의 하위 프레임마다 DocumentComplete 이벤트가 발생하게 됩니다. 하지만 최상위 프레임이 변하지 않았기 때문에, DocumentComplete가 가장 마지막으로 호출 될때의 IDispatch는 새로운 페이지를 포함하는 프레임을 가리키게 될 것입니다.

이러한 경우에서, 가장 마지막으로 발생하는 프레임을 찾는데에 관심이 있다면, DocumentComplete에서의 IDispatch가 가장 먼저 호출되는 NavigateCompete2 이벤트에서의 IDispatch와 동일한 값을 갖는지 확인하는 방법을 사용하실 수있습니다. 최상위 프레임을 로드할때에 가장 먼저 NavigateComplete2가 발생하고, 마찬가지로 최상위 프레임이 최종적으로 로드된 시점이 바로 마지막 DocumentComplete가 호출되는 시점이기 때문입니다. 아래 C++ 코드를 참고하세요

LPDISPATCH glpDisp = NULL; //전역 LPDISPATCH

void CWebbrDlg::OnNavigateComplete2Explorer1(LPDISPATCH pDisp, VARIANT FAR* URL) {
// glpDisp가 NULL인지 확인한다. NULL일 경우 현재 최상위 프레임을 다루고 있다는것을 의미하므로 LPDISPATCH를 저장한다
    if (!glpDisp) glpDisp = pDisp;
}

void CWebbrDlg::OnDocumentCompleteExplorer1(LPDISPATCH pDisp, VARIANT FAR* URL) {
    if (glpDisp && glpDisp == pDisp) {
    // 만약 DocumentComplete에서의 LPDISPATCH와 기존 전역변수에 저장한 값이 동일한값을 가질경우 이는 최종적으로 페이지가 로드되었다는것을 의미한다. 다음 사용을 위하여 glpDisp를 초기화한다.
        TRACE("Document is done downloading");
        glpDisp = NULL;
    }
}

 

댓글

Holic Spirit :: Tistory Edition

design by tokiidesu. powerd by kakao.