首页 新闻 论坛 群组 Blog 文档 下载 读书 Tag 网摘 搜索 .NET Java 游戏 视频 人才 外包 培训 数据库 书店 程序员
中国软件网
欢迎您:游客 | 登录 注册 帮助
  • 求教各位牛人IHTMLDocument2获取内嵌框架问题
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    • jjqingwa
    • 等级:
    • 可用分等级:
    • 总技术分:
    • 总技术分排名:
    • 结帖率:
    发表于:2008-08-19 20:34:17 楼主
    IHTMLDocument2获取内嵌框架问题,下断跟踪发现使用get_frame获取到的值为空~这个问题头痛了几天~一直没解决~望各位牛人帮小弟解惑~具体代码如下(希望各位牛人指出错误之处及更改方法,小弟感激不尽):


    #include "stdio.h"
    #include "string.h"
    #include "windows.h"
    #include "mshtml.h"
    #include "atlbase.h"
    #include "oleacc.h" 

    void GetFrame(IHTMLDocument2 *pIHTMLDocument2)
    {
    if(!pIHTMLDocument2)
    return; 
        HRESULT hr;     
    CComPtr <IHTMLFramesCollection2> spFramesCollection2; 
    pIHTMLDocument2->get_frames(&spFramesCollection2);   
    long nFrameCount=0;
    hr=spFramesCollection2->get_length(&nFrameCount); 
    if(FAILED(hr)||0==nFrameCount)
    return;   
    for(long i=0;i <nFrameCount;i++) 

    CComVariant vDispWin2;
    hr=spFramesCollection2->item(&CComVariant(i),&vDispWin2); 
    if(FAILED(hr))
    continue;     
    CComQIPtr <IHTMLWindow2> spWin2=vDispWin2.pdispVal; 
    if(!spWin2)
    continue;   
    CComPtr <IHTMLDocument2> spDoc2; 
    spWin2->get_document(&spDoc2);   

    }


    IHTMLDocument2 *OnGetDocInterface(HWND hWnd)
    {
    IHTMLDocument2* pDoc2=NULL;
    CComPtr <IHTMLDocument2> spDoc;
    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
    hWndChild=hWnd;
    if ( hWndChild )
    {
    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) )
    {
    CComPtr <IDispatch> spDisp;
    CComQIPtr <IHTMLWindow2> spWin;
    spDoc->get_Script( &spDisp );
    spWin = spDisp;
    spWin->get_document( &pDoc2 );
    }
    }
    } // else document not ready
    } // else Internet EXPlorer is not running
    ::FreeLibrary( hInst );
    } // else Active Accessibility is not installed
    CoUninitialize();
    return pDoc2;
    }


    BOOL Find()
    {
    HWND hwnd;
    char ClassName[255];
    hwnd=GetForegroundWindow();
    GetClassName(hwnd,ClassName,255);
    if(strcmp(ClassName,"IEFrame")==0)
    {
    hwnd=FindWindowEx(hwnd,NULL,"Shell DocObject View",NULL);
    hwnd=FindWindowEx(hwnd,NULL,"Internet Explorer_Server",NULL);
    GetFrame(OnGetDocInterface(hwnd));
    }
    return TRUE;
    }

    void main()
    {
    while(TRUE)
    {
    Find();
    }
    }
    10  修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    • jameshooo
    • 等级:
    • 可用分等级:
    • 总技术分:
    • 总技术分排名:
    • 2

      5

    发表于:2008-08-21 13:15:221楼 得分:0
    IHTMLDocument2::get_frames 是不可信的,用get_all或者getElementsByTagName能取到框架
    修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    • jjqingwa
    • 等级:
    • 可用分等级:
    • 总技术分:
    • 总技术分排名:
    发表于:2008-08-21 18:37:422楼 得分:0
    get_all或者getElementsByTagName方法貌似不能得到框架的IHTMLDocument2接口~必须要得到框架的IHTMLDocument2接口哦
    修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    • jameshooo
    • 等级:
    • 可用分等级:
    • 总技术分:
    • 总技术分排名:
    • 2

      5

    发表于:2008-08-21 22:23:353楼 得分:0
    从frame元素获得IHTMLDocument2接口的过程:
    IHTMLFrameElement or IHTMLIFrameElement ::QueryInterface --> IHTMLFrameBase2
    IHTMLFrameBase2::get_contentWindow --> IHTMLWindow2
    IHTMLWindow2::get_document --> IHTMLDocument2

    重要提醒,如果框架中的URL跟当前页面的URL不属于同一个域的话,上述过程会失败,主要是因为系统安全限制
    修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    • jjqingwa
    • 等级:
    • 可用分等级:
    • 总技术分:
    • 总技术分排名:
    发表于:2008-08-24 19:20:034楼 得分:0
    谢谢jameshooo 兄弟~按你的方法代码中~不过中途出了点小问题~编译'IHTMLFrameBase2' : undeclared identifier未定义~不知道需要包含哪个.h和lib~目前已有头文件如下~
    #include "stdio.h"
    #include "string.h"
    #include "windows.h"
    #include "mshtml.h"
    #include "atlbase.h"
    #include "oleacc.h"
    #include "comutil.h" 
    修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    • jameshooo
    • 等级:
    • 可用分等级:
    • 总技术分:
    • 总技术分排名:
    • 2

      5

    发表于:2008-08-24 22:32:115楼 得分:0
    仔细找找,所有这些接口应该都定义在mshtml.h里面的
    修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    • lion_wing
    • 等级:
    • 可用分等级:
    • 总技术分:
    • 总技术分排名:
    发表于:2008-08-26 16:22:256楼 得分:0
    IHTMLDocument2* GetDocFromFrame(IHTMLDocument2* pDoc2)
    {
      CComPtr <IHTMLDocument3> pDoc3;
      CComPtr <IHTMLDocument2> pDoc2Frame;

      hr = pDoc2->QueryInterface(IID_IHTMLDocument3,(void**)&pDoc3) ;
      if(hr==S_OK)
      {
        CComBSTR bstrName("FRAME");//CComBSTR bstrName("IFRAME");
        CComPtr <IHTMLElementCollection> pElemCollFrame;
        hr=pDoc3->getElementsByTagName(bstrName,&pElemCollFrame);
        if (hr!=S_OK) return NULL;

        long pLength;
        hr=pElemCollFrame->get_length(&pLength);
        if(hr!=S_OK) return NULL;
       
        for(int i=0;i <pLength;i++)
        {
          IDispatch *pDispFrame=NULL;
          CComVariant vIndex=i;
          hr=pElemCollFrame->item(vIndex,vIndex,&pDispFrame);
          if(hr!=S_OK) continue;
         
          CComPtr <IHTMLElement> pElemFrame;
          hr=pDispFrame->QueryInterface(IID_IHTMLElement,(void**)&pElemFrame);
          if(hr!=S_OK) continue;

          CComPtr <IHTMLFrameBase2> pFrameBase2;
          hr=pElemFrame->QueryInterface(IID_IHTMLFrameBase2,(void**)&pFrameBase2);
          if(hr!=S_OK) continue;
         
          CComPtr <IHTMLWindow2> pWindow2;
          hr=pFrameBase2->get_contentWindow(&pWindow2);
          if(hr==S_OK)
          {
            hr=pWindow2->get_document(&pDoc2Frame);
            if (hr==S_OK)
            {
              return pDoc2Frame;
            }
          }
        }
        pDispFrame->Release();
      }
      return NULL;
    }
    修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    • lion_wing
    • 等级:
    • 可用分等级:
    • 总技术分:
    • 总技术分排名:
    发表于:2008-08-26 16:23:187楼 得分:0
    升级SDK,或用VC7、VC8
    修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    • jjqingwa
    • 等级:
    • 可用分等级:
    • 总技术分:
    • 总技术分排名:
    发表于:2008-08-26 19:54:008楼 得分:0
    升级SDK后再编译貌似出现exe.obj : error LNK2001: unresolved external symbol _IID_IHTMLFrameBase2 错误~修改lib的先后顺序后出现uuid.lib(mshtml_i.obj) : fatal error LNK1103: debugging information corrupt; recompile module错误~
    这个问题真是头都大了~2周了~这个框架问题还没搞定
    修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    • jjqingwa
    • 等级:
    • 可用分等级:
    • 总技术分:
    • 总技术分排名:
    发表于:2008-08-26 19:59:089楼 得分:0
    而且你提供的那段代码我早测试过了~CComPtr <IHTMLDocument3>都通不过~最新SDK貌似都不包括这个~难道真要去vs2005或者vc7环境下?还是看有什么办法vc6下解决问题
    修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    • jameshooo
    • 等级:
    • 可用分等级:
    • 总技术分:
    • 总技术分排名:
    • 2

      5

    发表于:2008-08-26 23:32:2510楼 得分:0
    干脆在stdafx.h里面的末尾增加一句:
    #import "mshtml.tlb"
    这样当前系统的IE版本支持的接口全部都生成出来了
    修改 删除 举报 引用 回复
    进入用户个人空间
    加为好友
    发送私信
    在线聊天
    • jjqingwa
    • 等级:
    • 可用分等级:
    • 总技术分:
    • 总技术分排名:
    发表于:2008-08-27 20:04:0011楼 得分:0
    hoho~~jameshooo兄按你的方法试了还是不行~一样的效果~方便加Q指点下不~偶把偶的Q号发站内短信你~
    修改 删除 举报 引用 回复

    网站简介广告服务网站地图帮助联系方式诚聘英才English 问题报告
    北京创新乐知广告有限公司 版权所有 京 ICP 证 070598 号
    世纪乐知(北京)网络技术有限公司 提供技术支持
    Copyright © 2000-2008, CSDN.NET, All Rights Reserved