Squirrel.windows: Working with a progress bar... any examples?

Created on 11 May 2017  路  5Comments  路  Source: Squirrel/Squirrel.Windows

Is it possible create a progress bar to show how much has downloaded and/or give an estimation ?

Most helpful comment

@JonZso Hi
Here is my code that runs on application start and performs update if needed, while showing progress bar. I had a lot of troubles with trying to run async methods synchroniously and updating the UI at the same time, so I ended up doing it async.

Here is how I use it on application start:
```c#
if (Updater.IsDeployed)
{
if (!Updater.SetUpSquirrelAndCheckUpdates())
//if we ended up here then either there are no updates or we failed to update
MyApp.Init();
}
else
MyApp.Init();

Where `MyApp.Init()` initialises my app and `Updater.IsDeployed` indicates that the app is deployed via Squirrel.

Here is how I do update and report progress:

```c#
        public static bool SetUpSquirrelAndCheckUpdates()
        {
            using (var mgr = new UpdateManager(Updater.UpdatePath))
            {

                if (!Environment.GetCommandLineArgs().Contains("--squirrel-updated"))
                {
                    SquirrelAwareApp.HandleEvents(
                          onInitialInstall: v => mgr.CreateShortcutForThisExe(),
                          onAppUninstall: v => mgr.RemoveShortcutForThisExe()
                          );
                }

                var progressWindow = new DownloadProgress();
                try
                {
                    var updateInfo = mgr.CheckForUpdate().Result;
                    if (updateInfo.CurrentlyInstalledVersion.Version < updateInfo.FutureReleaseEntry.Version)
                    {
                        if (SingleMessageBox.ShowYesNo($"New version is availlable {updateInfo.FutureReleaseEntry.Version} Update ? ", "New version") == MessageBoxResult.Yes)
                        {
                            progressWindow.Show();
                            progressWindow.SetText("Downloading updates...");

                            mgr.DownloadReleases(updateInfo.ReleasesToApply, progressWindow.UpdateProgress)
                                .ContinueWith((t) =>
                                {
                                    Application.Current.Dispatcher.Invoke(() =>
                                    {
                                        progressWindow.SetText("Installing updates...");
                                        progressWindow.UpdateProgress(0);
                                    });
                                    mgr.ApplyReleases(updateInfo, progressWindow.UpdateProgress)
                                    .ContinueWith((x) =>
                                    {
                                        Application.Current.Dispatcher.Invoke(() =>
                                        {
                                            progressWindow.CanClose = true;
                                            UpdateManager.RestartApp();
                                            return false;
                                        });
                                    });
                                });
                        }
                        else
                            return false;

                        return true;
                    }
                    return false;
                }
                catch (Exception exc)
                {
                   //log
                    progressWindow.CanClose = true;
                    progressWindow.Close();
                    return false;
                }
            }
        }

I made DownloadWindow unclosable and it has a textblock named tb and a progress bar named prgBar. Note that you probably don't need to call apps Dispatcher in UpdateProgress method, but currently I have it and I can't test if it is needed right at the moment

DownloadWindow methods:
```c#
public bool CanClose { get; set; } = false;
private void Window_Closing(object sender, System.ComponentModel.CancelEventArgs e)
{
e.Cancel = !CanClose;
}
public void SetText(string text)
{
tb.Text = text;
}

    public void UpdateProgress(int i)
    {
        Application.Current.Dispatcher.Invoke(() => this.prgBar.Value = i);
    }

```
I hope you'll find it usefull.
Cheers

All 5 comments

In my case, I create a timer when it started, and check files status every 1 second. Knowing the status, I can show a spinning icon. It would be great if I can estimate the time but I guess it is not possible due to a dependency of network speed.

There's an extension method for the UpdateManager class, UpdateApp(), that has an overload that exposes a progress callback. How you deliver that data up to your UI layer I leave to you, but that's the Squirrel touchpoint I would suggest.

@JonZso Hi
Here is my code that runs on application start and performs update if needed, while showing progress bar. I had a lot of troubles with trying to run async methods synchroniously and updating the UI at the same time, so I ended up doing it async.

Here is how I use it on application start:
```c#
if (Updater.IsDeployed)
{
if (!Updater.SetUpSquirrelAndCheckUpdates())
//if we ended up here then either there are no updates or we failed to update
MyApp.Init();
}
else
MyApp.Init();

Where `MyApp.Init()` initialises my app and `Updater.IsDeployed` indicates that the app is deployed via Squirrel.

Here is how I do update and report progress:

```c#
        public static bool SetUpSquirrelAndCheckUpdates()
        {
            using (var mgr = new UpdateManager(Updater.UpdatePath))
            {

                if (!Environment.GetCommandLineArgs().Contains("--squirrel-updated"))
                {
                    SquirrelAwareApp.HandleEvents(
                          onInitialInstall: v => mgr.CreateShortcutForThisExe(),
                          onAppUninstall: v => mgr.RemoveShortcutForThisExe()
                          );
                }

                var progressWindow = new DownloadProgress();
                try
                {
                    var updateInfo = mgr.CheckForUpdate().Result;
                    if (updateInfo.CurrentlyInstalledVersion.Version < updateInfo.FutureReleaseEntry.Version)
                    {
                        if (SingleMessageBox.ShowYesNo($"New version is availlable {updateInfo.FutureReleaseEntry.Version} Update ? ", "New version") == MessageBoxResult.Yes)
                        {
                            progressWindow.Show();
                            progressWindow.SetText("Downloading updates...");

                            mgr.DownloadReleases(updateInfo.ReleasesToApply, progressWindow.UpdateProgress)
                                .ContinueWith((t) =>
                                {
                                    Application.Current.Dispatcher.Invoke(() =>
                                    {
                                        progressWindow.SetText("Installing updates...");
                                        progressWindow.UpdateProgress(0);
                                    });
                                    mgr.ApplyReleases(updateInfo, progressWindow.UpdateProgress)
                                    .ContinueWith((x) =>
                                    {
                                        Application.Current.Dispatcher.Invoke(() =>
                                        {
                                            progressWindow.CanClose = true;
                                            UpdateManager.RestartApp();
                                            return false;
                                        });
                                    });
                                });
                        }
                        else
                            return false;

                        return true;
                    }
                    return false;
                }
                catch (Exception exc)
                {
                   //log
                    progressWindow.CanClose = true;
                    progressWindow.Close();
                    return false;
                }
            }
        }

I made DownloadWindow unclosable and it has a textblock named tb and a progress bar named prgBar. Note that you probably don't need to call apps Dispatcher in UpdateProgress method, but currently I have it and I can't test if it is needed right at the moment

DownloadWindow methods:
```c#
public bool CanClose { get; set; } = false;
private void Window_Closing(object sender, System.ComponentModel.CancelEventArgs e)
{
e.Cancel = !CanClose;
}
public void SetText(string text)
{
tb.Text = text;
}

    public void UpdateProgress(int i)
    {
        Application.Current.Dispatcher.Invoke(() => this.prgBar.Value = i);
    }

```
I hope you'll find it usefull.
Cheers

Does this actually show you the real download progress of the file?

@shiftkey original question answered, this can be closed.

Was this page helpful?
0 / 5 - 0 ratings