开发环境:VS7,Windows XP,Windows 2K

  在VS7中添加了一种新的对话框类:CDHtmlDialog,顾名思义就是能够显示DHTML内容的对话框,但不同与以前的CHTMLView不同的是添加了对DHTML的支持,能够响应各种DHTML的事件,而且能够方便的得到网页上的各种内容和输入。在这以前要完成这些功能必须通过复杂的COM接口来完成,而现在MS MFC已经为我们做好了这一切。 
   在下面我会按照下面的顺序讲解CDHtmlDialog的用法。但本文也只能对DHTML对话框的功能进行部分的讲解,更多更全的说明需要大家自己摸索和查找资料。本文的目的是在于讲解如何得到和设置网页上的各种元素的值,如何处理事件。 
   此外在阅读本文前你必须对HTML和DHTML有所了解。

类成员函数介绍

   构造函数

   CDHtmlDialog( ); 
   CDHtmlDialog( 
   LPCTSTR lpszTemplateName, 
   LPCTSTR szHtmlResID, 
   CWnd *pParentWnd = NULL 
   ); 
   CDHtmlDialog( 
   UINT nIDTemplate, 
   UINT nHtmlResID = 0, 
   CWnd *pParentWnd = NULL 
   );

   你可以看到和CDialog不同的就在于第二个参数,表示在对话框创建时是否自动加载HTML,这里必须说明的是HTML必须以资源的形式存放,这个参数指明的是资源的ID或名称。

  

   或者你可以利用

   BOOL LoadFromResource( 
   LPCTSTR lpszResource 
   ); 
   BOOL LoadFromResource( 
   UINT nRes 
   ); 
   将HTML内容在后期进行装载。

  页面浏览

   此外一些函数如:OnNavigateComplete,OnBeforeNavigate,Navigate等用于页面转换的函数,在以前的CHtmlView中就有这里就不再作讲解。

得到当前URL

   void GetCurrentUrl( 
   CString& szUrl 
   );

得到网页中的DHTML元素的指定接口

   HRESULT GetElementInterface( 
   LPCTSTR szElementId, 
   REFIID riid, 
   void** ppvObj 
   );

   第一个参数指定,第二个参数指定接口ID,第三个参数返回接口指针。

得到网页中的DHTML元素的IHTMLElement接口

   HRESULT GetElement( 
   LPCTSTR szElementId, 
   IHTMLElement **pphtmlElement 
   ); 
   相当于调用 GetElementInterface(szElementId,IHTMLElement,pphtmlElement);

   这个函数非常的重要,因为如果要得到DHTML的内容就必须通过页面上的各个元素的属性来得到,例如:对于Input type=text的属性value就是输入的值,对于p的属性innerText就是段落中的内容。

   函数的第二个参数就是元素的名称。

   函数的第二个参数,是一个指向指针的指针,通过它得到IHTMLElement的接口。函数返回值是HRESULT其值的定义符合COM中对返回值的定义。(如果你不了解,可以简单的检测返回值是否等于S_OK)

得到元素的innerText和innerHTML的属性

   innerHTML属性: 
   BSTR GetElementHtml( 
   LPCTSTR szElementId 
   ); 
   innerText属性: 
   BSTR GetElementText( 
   LPCTSTR szElementId 
   ); 
   相当于调用IHTMLElement接口的gett_innerHTML和get_innerText方法

   与之对应的是设置元素的innerText和InnerHTML属性: 
   innerHTML属性: 
   void SetElementHtml( 
   LPCTSTR szElementId, 
   BSTR bstrText 
   ); 
   innerText属性: 
   void SetElementText( 
   LPCTSTR szElementId, 
   BSTR bstrText 
   ); 
   相当于调用IHTMLElement接口的put_innerHTML和put_innerText方法

示范代码

   假设页面上的代码为:<p id=p2>test</p>,执行下面代码可以显示原来的内容和将新内容设置为:abcdefg

   CComPtr<IHTMLElement> spP1; 
   HRESULT hr = S_OK;

   // Use the template overload 
   hr = GetElementInterface("p2", &spP1); 
   // 或者 hr = GetElement("p2", &spP1); 
   // 或者 hr = GetElementInterface("p2", IID_IHTMLElement, reinterpret_cast<void**>(&spP1)); 
   if(S_OK == hr) 
   { 
   BSTR bStr; 
   spP1->get_innerHTML(&bStr); 
   CString szTemp; 
   szTemp = bStr; 
   AfxMessageBox(szTemp);

   CString strTable="abcdefg"; 
   BSTR bstrTable = strTable.AllocSysString(); 
   spP1->put_innerHTML(bstrTable); 
   } 
   或者利用SetElementHtml和SetElementText来进行设置: 
   BSTR bStr; 
   bStr = GetElementHtml("p2"); 
   CString szTemp; 
   szTemp = bStr; 
   AfxMessageBox(szTemp); 
   CString strTable="ABCDEFG"; 
   BSTR bstrTable = strTable.AllocSysString(); 
   //spP1->put_innerHTML(bstrTable); 
   SetElementHtml("p2",bstrTable); 
事件处理映射宏

基本格式

BEGIN_DHTML_EVENT_MAP(className ) 
   DHTML_EVENT_ONCLICK(elemName, memberFxn ) //处理onclick事件 
   DHTML_EVENT_ONFOCUS(elemName, memberFxn ) //处理onfocus事件 
   DHTML_EVENT_ONKEYDOWN(elemName, memberFxn ) //处理onkeydown事件 
   DHTML_EVENT_ONMOUSEMOVE(elemName, memberFxn ) //处理mousemove事件 
   DHTML_EVENT_ONMOUSEOUT(elemName, memberFxn ) //处理mousemoveout事件 
   等等……… 
   END_DHTML_EVENT_MAP()

   更详细的说明可以查阅MSDN中DHTML Event Map Macros部分。MSDN中对可以处理的事件进行了详细的说明。DHTML中的事件与Windows中消息不是同一个概念,虽然映射宏的形式很相同。

添加映射处理代码

   我在VC7中没有发现自动添加各种事件映射的方法,只能通过手工添加代码的方式。

   定义事件处理函数: 
   函数原型为:HRESULT urClass::OnXXXXX(IHTMLElement* /*pElement*/) 
   添加消息映射: 
   BEGIN_DHTML_EVENT_MAP(urClass) 
   DHTML_EVENT_ONCLICK(_T("id name"), OnXXXXX) 
   END_DHTML_EVENT_MAP()

   下面是一段示范代码: 
   // mydlg.h 
   class CmydhtmlDlg : public CDHtmlDialog 
   { 
   // 构造 
   public: 
   CmydhtmlDlg(CWnd* pParent = NULL); // 标准构造函数

   // 对话框数据 
   enum { IDD = IDD_MYDHTML_DIALOG, IDH = IDR_HTML_MYDHTML_DIALOG };

   protected: 
   virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV 支持 
   HRESULT OnButtonOK(IHTMLElement *pElement); 
   HRESULT OnButtonCancel(IHTMLElement *pElement); 
   HRESULT OnButtonTest1(IHTMLElement *pElement); 
   HRESULT OnButtonTest2(IHTMLElement *pElement); 
   HRESULT OnButtonTest3(IHTMLElement *pElement); 
   HRESULT OnSelectTest1(IHTMLElement *pElement); 
   HRESULT OnDivMouseMove1(IHTMLElement *pElement); 
   HRESULT OnDivMouseOut1(IHTMLElement *pElement);

   //mydlg.cpp 
   BEGIN_DHTML_EVENT_MAP(CmydhtmlDlg) 
   DHTML_EVENT_ONCLICK(_T("ButtonOK"), OnButtonOK) 
   DHTML_EVENT_ONCLICK(_T("ButtonCancel"), OnButtonCancel) 
   DHTML_EVENT_ONCLICK(_T("Test1"), OnButtonTest1) 
   DHTML_EVENT_ONCLICK(_T("Test2"), OnButtonTest2) 
   DHTML_EVENT_ONCLICK(_T("Test3"), OnButtonTest3) 
   DHTML_EVENT_ONCHANGE(_T("s1"), OnSelectTest1) 
   DHTML_EVENT_ONMOUSEMOVE(_T("d1"), OnDivMouseMove1 ) 
   DHTML_EVENT_ONMOUSEOUT(_T("d1"), OnDivMouseOut1 ) 
   END_DHTML_EVENT_MAP()

   HRESULT CmydhtmlDlg::OnButtonOK(IHTMLElement* /*pElement*/) 
   { 
   OnOK(); 
   return S_OK; 
   }

   HRESULT CmydhtmlDlg::OnButtonCancel(IHTMLElement* /*pElement*/) 
   { 
   OnCancel(); 
   return S_OK; 
   }

   HRESULT CmydhtmlDlg::OnButtonTest1(IHTMLElement* /*pElement*/) 
   { 
   AfxMessageBox("test1 button clicked"); 
   return S_OK; 
   }

   HRESULT CmydhtmlDlg::OnSelectTest1(IHTMLElement* /*pElement*/) 
   { 
   TRACE("select1 changed\n"); 
   return S_OK; 
   }

   HRESULT CmydhtmlDlg::OnDivMouseMove1(IHTMLElement* /*pElement*/) 
   { 
   TRACE("div1 mouse move\n"); 
   return S_OK; 
   }

   HRESULT CmydhtmlDlg::OnDivMouseOut1(IHTMLElement* /*pElement*/) 
   { 
   TRACE("div1 mouse out\n"); 
   return S_OK; 
   }

各种DDX帮助宏

DDX宏介绍

如同CDialog类一样,CHtmlDialog也提供各种DDX帮助宏来与HTML页面上的控件交换数据。

  遗憾的是VS7中无法为CDHTMLDialog 的子类自动添加DDX变量,必须通过手工添加。

   设置innerText和innerHTML属性

   DDX_DHtml_ElementInnerText( 
   CDataExchange* dx, 
   LPCTSTR name, 
   CString& var 
   ) 
   和 
    DDX_DHtml_ElementInnerHtml( 
   CDataExchange* dx, 
   LPCTSTR name, 
   CString& var 
   ) 
   相当与前面提到的设置和获取innerText,innerHTML属性。

   获取和设置控件中的值

  在DHTML中利用“对象名程.value”可以得到控件中输入的值,利用DDX也同样可以得到。

   DDX_DHtml_ElementValue( 
   CDataExchange* dx, 
   LPCTSTR name, 
   var 
   ) 
   用于在控件和对象之间交换数据。

   使用方法

  假设HTML文件中代码如下

   <p id="p4"><b>p4 for ddx</b></p> 
   <input type="text" ID="input1" size="20" value="input1 for ddx" NAME="input1"> 
   <input type="text" ID="input2" size="20" value="101" NAME="input2">

   在H文件中添加变量定义: 
   public: //DDX 
   CString m_szP4,m_szInput1; 
   int m_iInput2;

   在类的构造函数中赋初值: 
   CmydhtmlDlg::CmydhtmlDlg(CWnd* pParent /*=NULL*/) 
   : CDHtmlDialog(CmydhtmlDlg::IDD, CmydhtmlDlg::IDH, pParent) 
   { 
   m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME); 
   m_szP4 = "test for p4"; 
   m_szInput1= "test for input1"; 
   m_iInput2 = 101; 
   }

   在CPP文件中的void CmydhtmlDlg::DoDataExchange(CDataExchange* pDX)函数中添加代码: 
   void CmydhtmlDlg::DoDataExchange(CDataExchange* pDX) 
   { 
   CDHtmlDialog::DoDataExchange(pDX); 
   //// for html ddx 
   DDX_DHtml_ElementInnerHtml(pDX,"p4",m_szP4); //对应 p4 
   DDX_DHtml_ElementValue(pDX,"input1",m_szInput1); //对应 input1 
   DDX_DHtml_ElementValue(pDX,"input2",m_iInput2); //对应 input2 
   } 
   使用是与CDialog一样利用UpdateData。 
   HRESULT CmydhtmlDlg::OnButtonTest4(IHTMLElement* /*pElement*/) 
   { 
   UpdateData(); 
   TRACE("p4=%s\n",m_szP4); 
   CString szTemp=m_szP4; 
   m_szP4 =m_szInput1; 
   m_szInput1=szTemp; //对换p4和input1中内容 
   m_iInput2 ++; //将input2中数字加一 
   UpdateData(FALSE); 
   return S_OK; 
   }

一个简单的例子

   最后介绍一下如何利用VC7创建一个利用CDHtmlDialog的工程。

  首先创建工程,进行如下设置:

  

   在资源管理中修改HTML文件:

   

   最后添加自己的代码。我提供的例子中所使用的函数在上面都已经提到。

VC7 HTML Dialog开发实例讲解的更多相关文章

  1. S3C2440上RTC时钟驱动开发实例讲解(转载)

    嵌入式Linux之我行,主要讲述和总结了本人在学习嵌入式linux中的每个步骤.一为总结经验,二希望能给想入门嵌入式Linux的朋友提供方便.如有错误之处,谢请指正. 共享资源,欢迎转载:http:/ ...

  2. Cocos2d-x 3.X手游开发实例详解

    Cocos2d-x 3.X手游开发实例详解(最新最简Cocos2d-x手机游戏开发学习方法,以热门游戏2048.卡牌为例,完整再现手游的开发过程,实例丰富,代码完备,Cocos2d-x作者之一林顺和泰 ...

  3. 实例讲解基于 React+Redux 的前端开发流程

    原文地址:https://segmentfault.com/a/1190000005356568 前言:在当下的前端界,react 和 redux 发展得如火如荼,react 在 github 的 s ...

  4. 使用Jquery+EasyUI 进行框架项目开发案例讲解之三---角色管理源码分享

    使用Jquery+EasyUI 进行框架项目开发案例讲解之三 角色管理源码分享    在上两篇文章  <使用Jquery+EasyUI进行框架项目开发案例讲解之一---员工管理源码分享> ...

  5. 使用Jquery+EasyUI 进行框架项目开发案例讲解之二---用户管理源码分享

    使用Jquery+EasyUI 进行框架项目开发案例讲解之二 用户管理源码分享   在上一篇文章<使用Jquery+EasyUI进行框架项目开发案例讲解之一---员工管理源码分享>我们分享 ...

  6. 【推荐】使用Jquery+EasyUI进行框架项目开发案例讲解之一---员工管理源码分享

    使用Jquery+EasyUI 进行框架项目开发案例讲解之一 员工管理源码分享   在开始讲解之前,我们先来看一下什么是Jquery EasyUI?jQuery EasyUI是一组基于jQuery的U ...

  7. 使用Jquery+EasyUI进行框架项目开发案例讲解之一---员工管理源码分享

    使用Jquery+EasyUI进行框架项目开发案例讲解之一---员工管理源码分享 使用Jquery+EasyUI 进行框架项目开发案例讲解之一 员工管理源码分享    在开始讲解之前,我们先来看一下什 ...

  8. (转)使用Jquery+EasyUI 进行框架项目开发案例讲解之四---组织机构管理源码分享

    原文地址:http://www.cnblogs.com/huyong/p/3404647.html 在上三篇文章  <使用Jquery+EasyUI进行框架项目开发案例讲解之一---员工管理源码 ...

  9. (转)使用Jquery+EasyUI进行框架项目开发案例讲解之一---员工管理源码分享

    原文地址:http://www.cnblogs.com/huyong/archive/2013/09/24/3334848.html 使用Jquery+EasyUI 进行框架项目开发案例讲解之一 员工 ...

随机推荐

  1. CLR via C# 摘要一:托管程序的执行模型

    托管程序的执行模型大致如下: 编译源代码为程序集(dll或exe文件),程序集包括了记录相关信息的元数据和IL代码 执行程序集文件时,启动CLR,JIT负责把IL编译为本地代码并执行 IL是微软推出的 ...

  2. apache 使用 .htaccess 导致500错误

    今天在win主机上配置了一个apache+mysql+php 的环境,一切看似正常了.结果将程序转移过来,打开网站的时候,出现了500错误.于是乎查原因: 首先,怀疑的是连接mysql出错了,找出配置 ...

  3. FileInputFormat

    MapReduce框架要处理数据的文件类型 FileInputFormat这个类决定. TextInputFormat是框架默认的文件类型,可以处理Text文件类型,如果你要处理的文件类型不是Text ...

  4. 快排找第k大模板

    int get_kth(int l,int r) { if (l==r) return a[r]; ]; while (i<j) { while (a[i]<mid) i++; while ...

  5. unity3d触屏操作对象运动

    using UnityEngine; using System.Collections; public class robot : MonoBehaviour { private GameObject ...

  6. UiAutomator源码分析之获取控件信息

    根据上一篇文章<UiAutomator源码分析之注入事件>开始时提到的计划,这一篇文章我们要分析的是第二点: 如何获取控件信息 我们在测试脚本中初始化一个UiObject的时候通常是像以下 ...

  7. [PCB设计] 3、用CAM350修改GERBER文件(删除某些部分)

    1.问题产生 由于在电子元件封装时阻焊开窗未处理好,生成的GERBER文件在生产钢网时容易出现错误.比如:测试点上不需要上锡,如果封装元件时采用焊盘修改而来,结果往往使paste层在该测试点上有覆盖, ...

  8. 关于用jQuery的animate方法实现的动画在IE中失效的原因以及解决方法

    这几天在学jQuery,本身还只是一个新手,写了一个简单的动画--圆形头像的缩放.本身是用Firefox进行调试的,一切进行的很顺利,缩放可以按照预期执行,结果拿到IE上去之后,发现缩放动画失效了.后 ...

  9. FTP的主动和被动模式详解

    详见:http://blog.yemou.net/article/query/info/tytfjhfascvhzxcytp25 主动模式FTP与被动模式FTP该如何选择 一.主动模式的实现与特点. ...

  10. CM记录-部署cdh5.3.3集群

    1.安装操作系统,保证联网环境,本文以CentOS 6.8为操作系统(略) 2.wget下载安装包(以5.3.3为例) #mkdir /usr/cdh ---新建cm安装目录 #cd /usr/cdh ...