using Pilz.UI; using Pilz.UI.Telerik.Dialogs; using Pilz.Updating.Client.Gui.LangRes; using Telerik.WinControls; namespace Pilz.Updating.Client.Gui; public class UpdateClientGui { // E v e n t s public event UpdateEndedEventHandler OnUpdateEnded; // F i e l d s private Form parentForm; private UpdateWindow curProgressDialog; private readonly UpdateClient updateClient; // P r o p e r t i e s public bool UseHiddenSearch { get; set; } private static Image MyAppIcon => Icon.ExtractAssociatedIcon(IO.Extensions.GetExecutablePath()).ToBitmap(); // C o n s t r u c t o r s public UpdateClientGui(UpdateClient updateClient) { this.updateClient = updateClient; updateClient.OnStatusChanged += UpdateClient_OnStatusChanged; } ~UpdateClientGui() { updateClient.OnStatusChanged -= UpdateClient_OnStatusChanged; } // F e a t u r e s public async Task UpdateInteractive(Form parentForm) { this.parentForm = parentForm; await updateClient.UpdateInteractive(); } private void EndUpdating() { EndUpdating(false); } private void EndUpdating(bool success) { curProgressDialog.AllowClose = true; curProgressDialog?.Invoke(curProgressDialog.Close); OnUpdateEnded?.Invoke(this, new(success)); } // E v e n t s private void UpdateClient_OnStatusChanged(object sender, UpdateStatusEventArgs e) { void setStatus() { if (e.Event == UpdateStatusEvent.PreEvent) SetStatus(e.Status); } switch (e.Status) { case UpdateStatus.Downloading: setStatus(); if (e.Event == UpdateStatusEvent.PostEvent) { if (e.Client.UpdatePackageInfo == null && !UseHiddenSearch) RadMessageBox.Show(UpdatingClientGuiLangRes.MsgBox_NoUpdatesFound, UpdatingClientGuiLangRes.MsgBox_NoUpdatesFound_Titel, MessageBoxButtons.OK, RadMessageIcon.Info); if (e.Client.UpdatePackageInfo != null && !ShowUpdatesAvailable(e.Client.UpdatePackageInfo)) e.Cancel = true; } break; } switch (e.Status) { case UpdateStatus.Downloading: case UpdateStatus.Extracting: case UpdateStatus.Copying: case UpdateStatus.Cleanup: case UpdateStatus.Waiting: setStatus(); break; } switch (e.Status) { case UpdateStatus.Done: EndUpdating(true); break; case UpdateStatus.Failed: case UpdateStatus.Canceled: EndUpdating(); break; } } private void SetStatus(UpdateStatus status) { var useGui = false; if (!(status == UpdateStatus.Searching && UseHiddenSearch)) { useGui = true; } if (useGui && curProgressDialog is null) { parentForm.Invoke(() => { curProgressDialog = new UpdateWindow(updateClient.ApplicationName); curProgressDialog.SetStatus(UpdateStatus.Waiting); curProgressDialog.Show(parentForm); }); } curProgressDialog?.Invoke(() => { curProgressDialog.SetStatus(status); curProgressDialog.Show(); // Might be hidden between update check and installation. }); } private bool ShowUpdatesAvailable(UpdatePackageInfo pkg) { var dres = default(DialogResult); bool cancel; // Hide progress dialog curProgressDialog?.Invoke(new Action(curProgressDialog.Hide)); // Show updates available dialog parentForm.Invoke(() => { var dialog = new UpdatesAvailableDialog( MyAppIcon, updateClient.CurrentVersion.Version.ToString(), updateClient.CurrentVersion.Channel.ToString(), updateClient.CurrentVersion.Build.ToString(), pkg.Version.Version.ToString(), pkg.Version.Channel.ToString(), pkg.Version.Build.ToString(), pkg.Notes, updateClient.InstallAsAdmin); var symbol = GlobalSymbolFactory.Instance.GetImage(GlobalSymbols.software_installer, UI.Telerik.SvgImageSize.Small).ToIcon(); dres = RadDialogBase.ShowDialog(dialog, parentForm, GeneralLangRes.Title_UpdatesAvailable, symbol).Result; }); if (dres != DialogResult.OK) { // Cancel cancel = true; EndUpdating(); } else { // Continue cancel = false; curProgressDialog?.Invoke(new Action(curProgressDialog.Show)); } return cancel; } }