使用CefSharp WinForms下载文件

25

我正在尝试使用CefSharp WinForms从我的应用程序下载一些文件(图像、音频文件或其他)。我阅读了许多其他帖子,但似乎都无法正常工作。

您有没有实现CefSharp下载程序的示例代码?

我尝试了下载一些文件,但什么都没发生。


你到底要做什么?想显示一个保存对话框吗? - amaitland
请分享您尝试过的代码。您能比“什么都没有发生”更具体些吗? - sab669
我在其他帖子上读到了一些关于这个的内容,尝试了所有的方法,但都没有成功。我特别尝试了像这样实现代码的方法:https://groups.google.com/forum/?nomobile=true#!topic/cefsharp/bS8PhHRlSAc我想知道在这种情况下应该使用什么方法,因为我没有找到任何相关信息。 - crasholino
我的答案是为那些有着和我一样问题的人准备的,但当然这个解决方案也可以被任何其他没有DownloadHandler类的项目使用。这个类对于下载管理器的正确工作是必不可少的。 - crasholino
4个回答

27

经过两天的努力,我终于做到了。 对于有相同问题的人,这里有一个简单的解决方案。 如果你正在使用MinimalExample,你需要下载Cefsharp示例(cefsharp-master),解压缩并按照以下步骤操作:

  1. 右键单击你的项目->添加现有项
  2. 浏览到cefsharp-master->CefSharp.example->选择DownloadHandler.cs
  3. 进入BrowserForm.cs类并输入以下内容:

    browser.DownloadHandler = new DownloadHandler();

  4. 完成!



DownloadHandler.cs

// Copyright © 2013 The CefSharp Authors. All rights reserved.
//
// Use of this source code is governed by a BSD-style license that can be found in the LICENSE file.

using System;

namespace CefSharp.Example.Handlers
{
    public class DownloadHandler : IDownloadHandler
    {
        public event EventHandler<DownloadItem> OnBeforeDownloadFired;

        public event EventHandler<DownloadItem> OnDownloadUpdatedFired;

        public void OnBeforeDownload(IWebBrowser chromiumWebBrowser, IBrowser browser, DownloadItem downloadItem, IBeforeDownloadCallback callback)
        {
            OnBeforeDownloadFired?.Invoke(this, downloadItem);

            if (!callback.IsDisposed)
            {
                using (callback)
                {
                    callback.Continue(downloadItem.SuggestedFileName, showDialog: true);
                }
            }
        }

        public void OnDownloadUpdated(IWebBrowser chromiumWebBrowser, IBrowser browser, DownloadItem downloadItem, IDownloadItemCallback callback)
        {
            OnDownloadUpdatedFired?.Invoke(this, downloadItem);
        }
    }
}

1
我应该把 browser.DownloadHandler = new DownloadHandler(); 放在哪里?是在初始方法内还是浏览器打开方法内? - Robbi Nespu
为什么在 OnBeforeDownloadcallback 被处理掉了,但是在 OnDownloadUpdated 中没有。难道不应该在两个地方都处理掉吗? - Juan
非常感谢您!这让我花了三天的时间!非常感谢!!! - charles chen
最新的CEFSharp版本需要实现IDownloadHandler接口并且实现CanDownload函数。 - Alex P.

19

要解决这个问题,只需在此处下载DownloadHandler.cs类

然后将其导入到您的Visual Studio项目中,并将以下行添加到主窗体的代码中:

MyBrowser.DownloadHandler = new DownloadHandler();

并将这段代码添加到顶部:

using CefSharp.Example;

然后尝试从您的浏览器下载一些东西,它应该可以工作!


4
源代码链接返回404错误。最好将源代码嵌入到文本中。 - Jim Gomes
运行得非常好! - Jack

11

我加入了以下内容,因为在线使用DownloadHandler类的示例中,很少展示OnBeforeDownloadFired()的实现,并且在引用的DownloadHandler.cs文件中也没有包含该实现。

这有助于解决下载文件(例如.mobi电子书)时遇到的问题,如果下载链接具有"_blank"目标,则必须阻止弹出窗口并在浏览器中打开一个新的自定义选项卡,但是当发生这种情况时,不会触发下载对话框。

我认为这是正确的。希望能够帮到您或者至少给您一个起点:

DownloadHandler downer = new DownloadHandler(this);
browser.DownloadHandler = downer;
downer.OnBeforeDownloadFired += OnBeforeDownloadFired;
downer.OnDownloadUpdatedFired += OnDownloadUpdatedFired;

private void OnBeforeDownloadFired(object sender, DownloadItem e)
{
    this.UpdateDownloadAction("OnBeforeDownload", e);
}

private void OnDownloadUpdatedFired(object sender, DownloadItem e)
{
    this.UpdateDownloadAction("OnDownloadUpdated", e);
}

private void UpdateDownloadAction(string downloadAction, DownloadItem downloadItem)
{
    /*
    this.Dispatcher.Invoke(() =>
    {
        var viewModel = (BrowserTabViewModel)this.DataContext;
        viewModel.LastDownloadAction = downloadAction;
        viewModel.DownloadItem = downloadItem;
    });
    */
}

// ...

public class DownloadHandler : IDownloadHandler
{
    public event EventHandler<DownloadItem> OnBeforeDownloadFired;

    public event EventHandler<DownloadItem> OnDownloadUpdatedFired;

    MainForm mainForm;

    public DownloadHandler(MainForm form)
    {
        mainForm = form;
    }

    public void OnBeforeDownload(IBrowser browser, DownloadItem downloadItem, IBeforeDownloadCallback callback)
    {
        var handler = OnBeforeDownloadFired;
        if (handler != null)
        {
            handler(this, downloadItem);
        }

        if (!callback.IsDisposed)
        {
            using (callback)
            {
                callback.Continue(downloadItem.SuggestedFileName, showDialog: true);
            }
        }
    }

    public void OnDownloadUpdated(IBrowser browser, DownloadItem downloadItem, IDownloadItemCallback callback)
    {
        var handler = OnDownloadUpdatedFired;
        if (handler != null)
        {
            handler(this, downloadItem);
        }
    }
}

// ...

{btsdaf} - Zero Infinity
我不知道在编写"CefSharp.Example"时,“Continue”参数是如何设置的。此时,您可以安全地将“showDialog: true”替换为“true”。 - Tiago Freitas Leal

2
在你的主窗体中添加这个。
 CefBrowser = new ChromiumWebBrowser("http://google.com", null);
            CefBrowser.Margin = Padding.Empty;
            // browsers.Size = new Size(900, 600);// note here

            DownloadHandler downloadHandler = new DownloadHandler();
            CefBrowser.DownloadHandler = downloadHandler;

只需创建名为DownloadHandler的类。
  public class DownloadHandler : IDownloadHandler
{
    public event EventHandler<DownloadItem> OnBeforeDownloadFired;

    public event EventHandler<DownloadItem> OnDownloadUpdatedFired;

    public void OnBeforeDownload(IWebBrowser chromiumWebBrowser, IBrowser browser, DownloadItem downloadItem,
        IBeforeDownloadCallback callback)
    {
        OnBeforeDownloadFired?.Invoke(this, downloadItem);

        if (!callback.IsDisposed)
        {
            using (callback)
            {
                callback.Continue(downloadItem.SuggestedFileName, showDialog: true);
            }
        }
    }

    public void OnDownloadUpdated(IWebBrowser chromiumWebBrowser, IBrowser browser, DownloadItem downloadItem,
        IDownloadItemCallback callback)
    {
        OnDownloadUpdatedFired?.Invoke(this, downloadItem);
    }
}

最终它的工作方式如下:

enter image description here


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接