注:本文适用.net 2.0+的winform项目

目的:

  • 点击页面中的target="_blank"链接时,弹出新窗体
  • 页面中有window.close()操作时,关闭窗体

上述窗体是指WebBrowser所在的Form,基本上,上述目的就是让该窗体表现得像个正常浏览器而已。

一、弹出新窗体

WebBrowser(下称wb)自带NewWindow事件,所以直接注册该事件即可:

private void wb_NewWindow(object sender, CancelEventArgs e)
{
e.Cancel = true;//这句加不加在我的环境里没区别,不加也不会导致打开外部浏览器
new FmWebBrowser(wb.StatusText).Show(); //FmWebBrowser即我的承载wb的窗体,本类构造函数接受一个url,Show之后会令wb访问该url。另外,该事件进入时,wb的StatusText几乎可以断定就是所点链接的href,极端情况以后遇到再说
}

二、响应页面中的window.close以关闭本窗体

由于wb没有现成的Close之类的事件,所以这个要稍稍折腾一下,就是给它加上这个事件,核心要解决的问题,就是让wb知道页面执行了window.close(),解决了这个,剩下就是把这事通知出去而已。

  1. 让wb知道页面执行了window.close(),并引发特定事件

    方法是网上抄的,原理是页面执行window.close()时wb会收到一个特定的win32消息,于是可以重载wb的WndProc方法来处理这个消息,这就需要继承wb写一个子类,子类如下:

    using System;
    using System.Security.Permissions;
    using System.Windows.Forms; namespace AhDung.WinForm.Controls
    {
    /// <summary>
    /// 增强型浏览器
    /// </summary>
    public class WebBrowserEx : WebBrowser
    {
    /// <summary>
    /// 当WebBrowser关闭后
    /// </summary>
    public event EventHandler WindowClosed; protected void OnWindowClosed(EventArgs e)
    {
    if (WindowClosed != null) { WindowClosed(this, e); }
    } [PermissionSet(SecurityAction.LinkDemand, Name = "FullTrust")]
    protected override void WndProc(ref Message m)
    {
    if (m.Msg == 0x210/*WM_PARENTNOTIFY*/)
    {
    int wp = m.WParam.ToInt32(); int X = wp & 0xFFFF;
    if (X == 0x2/*WM_DESTROY*/)//若收到该消息,引发WindowClosed事件
    {
    OnWindowClosed(EventArgs.Empty);
    }
    } base.WndProc(ref m);
    }
    }
    }
  2. 剩下就简单了,宿主窗体响应WebBrowserEx的WindowClosed事件,关闭自身就好。当然首先要把之前的WebBrowser换成上述WebBrowserEx,代码段:
    private WebBrowserEx wbex = new WebBrowserEx();
    ... public FmMain()
    {
    wbex.WindowClosed += wbex_WindowClosed;
    ...
    } void wbex_WindowClosed(object sender, System.EventArgs e)
    {
    this.Close();
    }

- 文毕 -

最新文章

  1. 2016暑假多校联合---To My Girlfriend
  2. HTML5手机APP开发入门(2)
  3. Android使用service后台更新计划任务
  4. loadrunner 一个诡异问题
  5. C语言学习总结(二) 运算流程
  6. css实现三角的一些方法
  7. EF 如何code first
  8. Table中的JCheckBox TableHeader的全选(全反选)功能
  9. 关于requirejs中的define的原理理解
  10. 经验分享:Xcode 创建.a和framework静态库
  11. sqlserver 笔记:常用字符串函数
  12. iOS安全攻防之代码混淆
  13. firewall防火墙
  14. Huginn定时时间不准确或延后问题
  15. iOS 上线过程中出现的问题总结
  16. php socket通过smtp发送邮件(纯文本、HTML,多收件人,多抄送,多密送)
  17. C++获取文件夹下所有文件名
  18. 【转】各种 NoSQL 的比较
  19. poj 2777线段树应用
  20. 洛谷P1742 最小圆覆盖(计算几何)

热门文章

  1. 浏览器中用JavaScript获取剪切板中的文件
  2. CRL快速开发框架系列教程十(导出对象结构)
  3. 终端mysql Operation not permitted错误解决方案
  4. WPF 捕获键盘输入事件
  5. js 基础篇(点击事件轮播图的实现)
  6. Android中的LinearLayout布局
  7. Android NDK debug 方法
  8. Spark Streaming+Kafka
  9. 在Mac OS X上安装ASP.NET 5(译文)
  10. 如何设计一门语言(七)——闭包、lambda和interface