CefSharp禁止弹出新窗体,在同一窗口打开链接,并且支持带type="POST" target="_blank"的链接_.NET_编程开发_程序员俱乐部

中国优秀的程序员网站程序员频道CXYCLUB技术地图
热搜:
更多>>
 
您所在的位置: 程序员俱乐部 > 编程开发 > .NET > CefSharp禁止弹出新窗体,在同一窗口打开链接,并且支持带type="POST" target="_blank"的链接

CefSharp禁止弹出新窗体,在同一窗口打开链接,并且支持带type="POST" target="_blank"的链接

 2017/10/23 15:47:14  秋荷雨翔  程序员俱乐部  我要评论(0)
  • 摘要:1、实现ILifeSpanHandler接口,为了支持带type="POST"target="_blank"的链接,并且为了后面能够获取到ChromiumWebBrowser并释放旧的ChromiumWebBrowser,新窗体还是要让它弹的,只不过后面会隐藏它,代码如下:usingCefSharp;usingCefSharp.WinForms;usingSystem;usingSystem.Collections.Generic;usingSystem.Linq;usingSystem
  • 标签:ARP

1、实现ILifeSpanHandler接口,为了支持带type="POST" target="_blank"的链接,并且为了后面能够获取到ChromiumWebBrowser并释放旧的ChromiumWebBrowser,新窗体还是要让它弹的,只不过后面会隐藏它,代码如下:

class="code_img_closed" src="/Upload/Images/2017102315/0015B68B3C38AA5B.gif" alt="" />logs_code_hide('c4c8ca03-121e-4514-bcfa-4112ac122b8f',event)" src="/Upload/Images/2017102315/2B1B950FA3DF188F.gif" alt="" />
using CefSharp;
using CefSharp.WinForms;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace MyBrowser
{
    public class CefLifeSpanHandler : CefSharp.ILifeSpanHandler
    {
        public CefLifeSpanHandler()
        {

        }

        public bool DoClose(IWebBrowser browserControl, CefSharp.IBrowser browser)
        {
            if (browser.IsDisposed || browser.IsPopup)
            {
                return false;
            }

            return true;
        }

        public void OnAfterCreated(IWebBrowser browserControl, IBrowser browser)
        {

        }

        public void OnBeforeClose(IWebBrowser browserControl, IBrowser browser)
        {
        }

        public bool OnBeforePopup(IWebBrowser browserControl, IBrowser browser, IFrame frame, string targetUrl, string targetFrameName, WindowOpenDisposition targetDisposition, bool userGesture, IWindowInfo windowInfo, ref bool noJavascriptAccess, out IWebBrowser newBrowser)
        {
            var chromiumWebBrowser = (ExtChromiumBrowser)browserControl;

            ExtChromiumBrowser extBrowser = new ExtChromiumBrowser(targetUrl) { Dock = DockStyle.Fill };

            var windowX = windowInfo.X;
            var windowY = windowInfo.Y;
            var windowWidth = (windowInfo.Width == int.MinValue) ? 600 : windowInfo.Width;
            var windowHeight = (windowInfo.Height == int.MinValue) ? 800 : windowInfo.Height;

            chromiumWebBrowser.Invoke(new Action(() =>
            {
                var popup = new Form
                {
                    Left = windowX,
                    Top = windowY,
                    Width = windowWidth,
                    Height = windowHeight,
                    Text = targetFrameName
                };

                popup.CreateControl();

                var control = new Control();
                control.Dock = DockStyle.Fill;
                control.CreateControl();

                popup.Controls.Add(control);

                popup.Show();

                var rect = control.ClientRectangle;

                windowInfo.SetAsChild(control.Handle, rect.Left, rect.Top, rect.Right, rect.Bottom);

                NewWindowEventArgs e = new NewWindowEventArgs(extBrowser, targetUrl, popup);
                chromiumWebBrowser.OnNewWindow(e);
            }));

            newBrowser = null;
            return false;
        }

    }
}
View Code

2、使用ILifeSpanHandler接口:

using CefSharp.WinForms;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms.Integration;

namespace MyBrowser
{
    public class ExtChromiumBrowser : ChromiumWebBrowser
    {
        public ExtChromiumBrowser()
            : base("about:_blank")
        {
            this.LifeSpanHandler = new CefLifeSpanHandler();
            this.DownloadHandler = new DownloadHandler(this);
        }

        public ExtChromiumBrowser(string adress)
            : base(adress)
        {
            this.LifeSpanHandler = new CefLifeSpanHandler();
            this.DownloadHandler = new DownloadHandler(this);
        }

        public event EventHandler<NewWindowEventArgs> StartNewWindow;

        public void OnNewWindow(NewWindowEventArgs e)
        {
            if (StartNewWindow != null)
            {
                StartNewWindow(this, e);
            }
        }
    }
}
View Code

3、定义NewWindowEventArgs:

using CefSharp;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace MyBrowser
{
    public class NewWindowEventArgs : EventArgs
    {
        private ExtChromiumBrowser _browser;
        public ExtChromiumBrowser Browser
        {
            get { return _browser; }
            set { value = _browser; }
        }

        private string _url;
        public string Url
        {
            get { return _url; }
            set { value = _url; }
        }

        private Form _form;
        public Form Form
        {
            get { return _form; }
            set { value = _form; }
        }

        public NewWindowEventArgs(ExtChromiumBrowser browser, string url, Form form)
        {
            _url = url;
            _browser = browser;
            _form = form;
        }
    }
}
View Code

4、实现StartNewWindow,在StartNewWindow事件中做了三件事,一是替换掉旧的ChromiumWebBrowser,二是释放掉旧的ChromiumWebBrowser,三是隐藏弹出的新窗体,实际效果可能会看到Windows任务栏的图标会闪一下消失,那就是弹出的新窗体被隐藏了。这个实现方法比较变态,但是如果不让新窗体弹出,就不支持带type="POST" target="_blank"的链接,因为没有把数据POST到服务器,如果让新窗体弹出,但是使用新窗体中的Control作为Child,而不new一个新的ChromiumWebBrowser,那么找不到新ChromiumWebBrowser,虽然它可以正常显示,但获取不到它,后面无法释放。

private void Window_Loaded(object sender, RoutedEventArgs e)
{
    _browser = new ExtChromiumBrowser() { Dock = DockStyle.Fill };
    BindBrowser(_browser);
    _browser.FrameLoadEnd += FrameLoadEnd;
    _browser.Load(_tokenUrl);
    host.Child = _browser;
}

private void BindBrowser(ExtChromiumBrowser browser)
{
    browser.StartNewWindow += (s, e) =>
    {
        this.Dispatcher.BeginInvoke(new Action(() =>
        {
            _browser = e.Browser;
            BindBrowser(e.Browser);
            host.Child = e.Browser;

            e.Browser.FrameLoadStart += (ss, ee) =>
            {
                this.Dispatcher.BeginInvoke(new Action(() =>
                {
                    (ss as ExtChromiumBrowser).Focus();
                }));
            };

            e.Form.Visible = false;
            Task.Factory.StartNew(() =>
            {
                Thread.Sleep(1000);
                this.Dispatcher.BeginInvoke(new Action(() =>
                {
                    e.Form.Dispose();
                    browser.Dispose();
                }));
            });
        }));
    };
}
View Code

 

发表评论
用户名: 匿名