简体   繁体   English

C#-在下载正常进行时,进度栏保持为0%(webclient)

[英]C# - Progress Bar stays to 0% while the download works (webclient)

I've been working on this xaml file. 我一直在研究这个xaml文件。 I want to download a target file. 我要下载目标文件。 As far as I could go I can download the file, however my progress bar isn't working properly (it stays to 0%) 据我所知,我可以下载文件,但是进度条无法正常运行(保持为0%)

As I am new to this language I don't know every references etc. So maybe I'm missing something. 由于我是该语言的新手,所以我并不了解所有参考文献,因此也许我缺少了一些东西。

Here is the full code: (I have unused imports but I'll remove it later) 这是完整的代码:(我有未使用的导入,但稍后再删除)

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Net;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Windows.Controls;
using System.Windows;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Forms;
using System.Windows.Shapes;
using System.Net.Mime;

namespace DownloadingFileWindow
{
    public partial class MainWindow : Window
    {
        public MainWindow()
        {
            InitializeComponent();
        }

        WebClient client = new WebClient();
        string url = "https://download.filezilla-project.org/client/FileZilla_3.32.0_win64-setup_bundled.exe";

        private void btnDownload_Click(object sender, RoutedEventArgs e)
        {
            client.Headers.Add("user-agent", "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.2; .NET CLR 1.0.3705;)");

            //client.OpenRead(url);
            //string header_contentDisposition = client.ResponseHeaders["content-disposition"];
            //string filename = new ContentDisposition(header_contentDisposition).FileName;

            if (!string.IsNullOrEmpty(url))
            {
                Thread thread = new Thread(() =>
                    {
                        Uri uri = new Uri(url);
                        string fileName = System.IO.Path.GetFileName(uri.AbsolutePath);
                        client.DownloadFileAsync(uri, System.Windows.Forms.Application.StartupPath + "/" + fileName);
                    });
                    thread.Start();
            }
        }

        private void MainWindow_Load(object sender, EventArgs e)
        {
            client.DownloadProgressChanged += Client_DownloadProgressChanged;
            client.DownloadFileCompleted += Client_DownloadFileCompleted;
        }

        private void Client_DownloadFileCompleted(object sender, AsyncCompletedEventArgs e)
        {
            System.Windows.Forms.MessageBox.Show("Download OK!", "Message", MessageBoxButtons.OK, MessageBoxIcon.Information);
        }

        private void Client_DownloadProgressChanged(object sender, DownloadProgressChangedEventArgs e)
        {
                progressBar.Minimum = 0;
                double receive = double.Parse(e.BytesReceived.ToString());
                double total = double.Parse(e.TotalBytesToReceive.ToString());
                double percentage = receive / total * 100;
                lblStatus.Text = $"{string.Format("{0:0.##}", percentage)}%";
                progressBar.Value = int.Parse(Math.Truncate(percentage).ToString());
        }
    }
}

I think that there is multi-threading issue. 我认为存在多线程问题。 As you are using another thread for downloading that's why in Client_DownloadProgressChanged event handler, the Dispatcher could not access the controls like progressBar and lblStatus. 当您使用另一个线程进行下载时,这就是为什么在Client_DownloadProgressChanged事件处理程序中,分派器无法访问诸如progressBar和lblStatus之类的控件的原因。

First you should write 首先你应该写

progressBar.Minimum = 0;

this line in MainWindow_Load event handler because there is no need for this to be set in progresschanged event handler. MainWindow_Load事件处理程序中的这一行,因为不需要在progresschanged事件处理程序中设置此行。 And you should replace 而且你应该更换

lblStatus.Text = $"{string.Format("{0:0.##}", percentage)}%";
progressBar.Value = int.Parse(Math.Truncate(percentage).ToString());

with

if (!Dispatcher.CheckAccess())
{
    Dispatcher.Invoke(() =>
    {
        lblStatus.Content = $"{string.Format("{0:0.##}", percentage)}%";
        progressBar.Value = int.Parse(Math.Truncate(percentage).ToString());
    });
}
else
{
    lblStatus.Content = $"{string.Format("{0:0.##}", percentage)}%";
    progressBar.Value = int.Parse(Math.Truncate(percentage).ToString());
}

You can check documentation about dispatcher here . 您可以在此处查看有关调度程序的文档。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM