Microsoft KB Archive/249232

= How to get IHTMLDocument2 from a HWND =

Article ID: 249232

Article Last Modified on 9/27/2006

-

APPLIES TO


 * Microsoft Internet Explorer 4.0 128-Bit Edition
 * Microsoft Internet Explorer 4.01 Service Pack 2
 * Microsoft Internet Explorer 4.01 Service Pack 1
 * Microsoft Internet Explorer 4.01 Service Pack 2
 * Microsoft Internet Explorer 5.0
 * Microsoft Internet Explorer 5.5

-



This article was previously published under Q249232



SUMMARY
This article shows how to get the IHTMLDocument2 interface from a HWND. If Microsoft Active Accessibility (MSAA) is installed, you can send the WM_HTML_GETOBJECT message to the document's window (with the window class "Internet Explorer_Server") and then pass the result from SendMessage to an MSAA function, ObjectFromLresult, to get a fully marshaled IHTMLDocument2 pointer.



MORE INFORMATION
You must have Active Accessibility components installed on the system for the code described in this section to work. Client developers can use the SDK to develop and update Active Accessibility aids. If you incorporate the latest version of Active Accessibility and distribute new versions of your accessibility aids, you must distribute the runtime components (RDK) for clients that have been developed for Microsoft Windows 95, Windows 98, or Windows NT 4.0 with Service Pack 4 or 5. It's not necessary to include the RDK for clients developed solely for Windows 2000, or for Windows NT 4.0 with Service Pack 6. The new components are already included in these operating systems.

See the "References" section of this article for information about Active Accessibility and where to download the Active Accessibility SDK.
 * 1) include 
 * 2) include 
 * 3) include 

BOOL CALLBACK EnumChildProc(HWND hwnd,LPARAM lParam) {   TCHAR   buf[100];

if ( _tcscmp( buf, _T("Internet Explorer_Server") ) == 0 ) {       *(HWND*)lParam = hwnd; return FALSE; }   else return TRUE; };

//You can store the interface pointer in a member variable //for easier access void CDlg::OnGetDocInterface(HWND hWnd) {   CoInitialize( NULL );

// Explicitly load MSAA so we know if it's installed HINSTANCE hInst = ::LoadLibrary( _T("OLEACC.DLL") ); if ( hInst != NULL ) {       if ( hWnd != NULL ) {           HWND hWndChild=NULL; // Get 1st document window ::EnumChildWindows( hWnd, EnumChildProc, (LPARAM)&hWndChild ); if ( hWndChild ) {               CComPtr spDoc; LRESULT lRes; UINT nMsg = ::RegisterWindowMessage( _T("WM_HTML_GETOBJECT") ); ::SendMessageTimeout( hWndChild, nMsg, 0L, 0L, SMTO_ABORTIFHUNG, 1000, (DWORD*)&lRes );

LPFNOBJECTFROMLRESULT pfObjectFromLresult = (LPFNOBJECTFROMLRESULT)::GetProcAddress( hInst, _T("ObjectFromLresult") ); if ( pfObjectFromLresult != NULL ) {                   HRESULT hr; hr = (*pfObjectFromLresult)( lRes, IID_IHTMLDocument, 0, (void**)&spDoc ); if ( SUCCEEDED(hr) ) {                       // Change background color to red spDoc->put_bgColor( CComVariant("red") ); }               }            } // else document not ready } // else Internet Explorer is not running ::FreeLibrary( hInst ); } // else Active Accessibility is not installed CoUninitialize; } NOTE: Before Internet Explorer 5.5, frames were implemented by hosting a new instance of Shdocvw.dll, and each frame had a separate window associated with it. Internet Explorer 5.5 implements native frames for better performance, and all frames are rendered by the same instance of Shdocvw.dll. Since there will not be a HWND for each frame for Internet Explorer 5.5 and later, the sample code described in this section will work to get to the document of the main window only. You can still get to each frame's document by using the frames collection of the main document.

