使用 HttpClient 下载文件并回调显示进度
简介
原帮助类代码参考 WebApi 帮助类,新增下载文件方法,使用 WPF 调用下载并回调显示下载进度。显示下载文件大小以及下载速度。
代码
帮助类代码
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82
|
public static async Task<bool> DownloadAsync(Uri baseAddress, string requestUrl, IDictionary<string, string> parameters, string saveFilePath, Action<object, HttpProgressEventArgs> progressAction = null, string token = null) { ProgressMessageHandler progress = new ProgressMessageHandler(); progress.HttpReceiveProgress += (s, e) => { progressAction?.Invoke(s, e); };
HttpClient httpClient = HttpClientFactory.Create(progress); httpClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
try { if (!string.IsNullOrEmpty(token)) { httpClient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", token); } httpClient.Timeout = TimeSpan.FromMinutes(20);
StringBuilder builder = new StringBuilder(); builder.Append(baseAddress); builder.Append(requestUrl); if (parameters != null && parameters.Count >= 1) { builder.Append("?"); int i = 0; foreach (var item in parameters) { if (i > 0) { builder.Append("&"); } builder.AppendFormat("{0}={1}", item.Key, item.Value); i++; } }
using (HttpResponseMessage response = await httpClient.GetAsync(builder.ToString())) { if (response.IsSuccessStatusCode) { using (FileStream fs = File.Create(saveFilePath)) { Stream stream = await response.Content.ReadAsStreamAsync(); stream.CopyTo(fs); stream.Close(); stream.Dispose(); fs.Close(); fs.Dispose(); return true; } } else { return false; } } } catch (Exception ex) { TXTHelper.Logs(ex.ToString()); return false; } finally { httpClient.Dispose(); httpClient = null; GC.Collect(); } }
|
进度条样式
1 2 3 4 5
| <Grid> <ProgressBar x:Name="progressBar" HorizontalAlignment="Left" Height="13" Margin="10,10,0,0" VerticalAlignment="Top" Width="100" Maximum="1" Minimum="0"/> <Label x:Name="number" HorizontalAlignment="Left" Margin="10,28,0,0" VerticalAlignment="Top" Width="319" Height="41"/> <Label x:Name="number2" HorizontalAlignment="Left" Margin="10,58,0,0" VerticalAlignment="Top" Width="319" Height="41"/> </Grid>
|
调用下载
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86
| private async void MainWindow_Loaded(object sender, RoutedEventArgs e) { string ServerUrl = ""; string SavePath = @"";
var vDownload = await HttpClientHelper.DownloadAsync(new Uri(ServerUrl), null, null, SavePath, DownloadProgressChanged); MessageBox.Show($"保存{(vDownload ? "成功" : "失败")}"); }
private void DownloadProgressChanged(object arg1, HttpProgressEventArgs arg2) { this.Dispatcher.Invoke(new Action(() => { if (arg2.ProgressPercentage >= 0 && arg2.ProgressPercentage <= 100) { progressBar.Value = arg2.ProgressPercentage / 100.0; number.Content = $"{ByteChange(arg2.BytesTransferred)}/{ByteChange(arg2.TotalBytes)}"; CalcDownloadSpeed(DateTime.Now, arg2.BytesTransferred); } })); }
private DateTime lastTime = DateTime.Now; private long BytesTransferred = 0;
private void CalcDownloadSpeed(DateTime time, long bytesTransferred) { if (lastTime.Second != time.Second) { this.Dispatcher.Invoke(new Action(() => { number2.Content = $"Speed: {ByteChange(bytesTransferred - BytesTransferred)}/s"; }));
lastTime = time; BytesTransferred = bytesTransferred; } }
private string ByteChange(long? TotalBytes) { long kb = 1024; long mb = kb * kb; long gb = mb * kb; long tb = gb * kb;
if (TotalBytes >= tb) { return $"{Math.Round((decimal)TotalBytes / tb, 2)}TB"; } else if (TotalBytes >= gb) { return $"{Math.Round((decimal)TotalBytes / gb, 2)}GB"; } else if (TotalBytes >= mb) { return $"{Math.Round((decimal)TotalBytes / mb, 2)}MB"; } else if (TotalBytes >= kb) { return $"{Math.Round((decimal)TotalBytes / kb, 2)}KB"; } else { return $"{TotalBytes}B"; } }
|