From 8d1c6654f995dd7556e72eb3bb33aca5c6504df8 Mon Sep 17 00:00:00 2001 From: Nemesh Date: Wed, 27 Jul 2022 23:37:04 +0300 Subject: [PATCH] v.1.1.1 * Added a progress bar to updating process --- FloatTool/Common/Utils.cs | 57 ++++++++++++++++++++++++++++ FloatTool/FloatTool.csproj | 2 +- FloatTool/Views/UpdateWindow.xaml | 4 +- FloatTool/Views/UpdateWindow.xaml.cs | 13 +++++-- README.md | 14 ++++++- 5 files changed, 84 insertions(+), 6 deletions(-) diff --git a/FloatTool/Common/Utils.cs b/FloatTool/Common/Utils.cs index 0a4149d..12d3ab0 100644 --- a/FloatTool/Common/Utils.cs +++ b/FloatTool/Common/Utils.cs @@ -18,13 +18,70 @@ using Newtonsoft.Json; using System; using System.Collections.Generic; +using System.IO; using System.Linq; using System.Net.Http; using System.Text.RegularExpressions; +using System.Threading; using System.Threading.Tasks; namespace FloatTool { + // Taken from here: + // https://stackoverflow.com/a/46497896/16349466 + public static class StreamExtensions + { + public static async Task CopyToAsync(this Stream source, Stream destination, int bufferSize, IProgress progress = null, CancellationToken cancellationToken = default) + { + if (source == null) + throw new ArgumentNullException(nameof(source)); + if (!source.CanRead) + throw new ArgumentException("Has to be readable", nameof(source)); + if (destination == null) + throw new ArgumentNullException(nameof(destination)); + if (!destination.CanWrite) + throw new ArgumentException("Has to be writable", nameof(destination)); + if (bufferSize < 0) + throw new ArgumentOutOfRangeException(nameof(bufferSize)); + + var buffer = new byte[bufferSize]; + long totalBytesRead = 0; + int bytesRead; + while ((bytesRead = await source.ReadAsync(buffer, cancellationToken).ConfigureAwait(false)) != 0) + { + await destination.WriteAsync(buffer.AsMemory(0, bytesRead), cancellationToken).ConfigureAwait(false); + totalBytesRead += bytesRead; + progress?.Report(totalBytesRead); + } + } + } + + public static class HttpClientExtensions + { + public static async Task DownloadAsync(this HttpClient client, string requestUri, Stream destination, IProgress progress = null, CancellationToken cancellationToken = default) + { + // Get the http headers first to examine the content length + using var response = await client.GetAsync(requestUri, HttpCompletionOption.ResponseHeadersRead, cancellationToken); + var contentLength = response.Content.Headers.ContentLength; + + using var download = await response.Content.ReadAsStreamAsync(cancellationToken); + + // Ignore progress reporting when no progress reporter was + // passed or when the content length is unknown + if (progress == null || !contentLength.HasValue) + { + await download.CopyToAsync(destination, cancellationToken); + return; + } + + // Convert absolute progress (bytes downloaded) into relative progress (0% - 100%) + var relativeProgress = new Progress(totalBytes => progress.Report((float)totalBytes / contentLength.Value)); + // Use extension method to report progress while downloading + await download.CopyToAsync(destination, 81920, relativeProgress, cancellationToken); + progress.Report(1); + } + } + public static class StringExtensions { public static string FirstCharToUpper(this string input) => diff --git a/FloatTool/FloatTool.csproj b/FloatTool/FloatTool.csproj index c1f96cd..f5e3120 100644 --- a/FloatTool/FloatTool.csproj +++ b/FloatTool/FloatTool.csproj @@ -9,7 +9,7 @@ https://prevter.github.io/FloatTool https://github.com/Prevter/FloatTool en - 1.1.0 + 1.1.1 $(AssemblyVersion) Assets\Icon.ico embedded diff --git a/FloatTool/Views/UpdateWindow.xaml b/FloatTool/Views/UpdateWindow.xaml index c8927e7..6ffb7c0 100644 --- a/FloatTool/Views/UpdateWindow.xaml +++ b/FloatTool/Views/UpdateWindow.xaml @@ -79,9 +79,11 @@ -