From b21f6e8ce775604f883e7e781f92b9715ceac35a Mon Sep 17 00:00:00 2001 From: pakass Date: Wed, 15 Feb 2023 15:11:22 +0100 Subject: [PATCH 1/4] update SSH.NET --- mRemoteNG/mRemoteNG.csproj | 1 + 1 file changed, 1 insertion(+) diff --git a/mRemoteNG/mRemoteNG.csproj b/mRemoteNG/mRemoteNG.csproj index da66ae28..d4296496 100644 --- a/mRemoteNG/mRemoteNG.csproj +++ b/mRemoteNG/mRemoteNG.csproj @@ -82,6 +82,7 @@ + From c03d5e891d928be4b1dad94f5650b55ea0dbffa6 Mon Sep 17 00:00:00 2001 From: pakass Date: Wed, 15 Feb 2023 15:15:55 +0100 Subject: [PATCH 2/4] update Changelog --- CHANGELOG.md | 1 + 1 file changed, 1 insertion(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 6e3d5444..085b680a 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,6 +5,7 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/), ## [1.77.3] ### Added +- #1736: Update of SSH.NET to 2020.0.2 to allow File Transfer again - #2138: Improve compatibility with Remote Desktop Connection Manager v2.83 - #2123: Thycotic Secret Server - Added 2FA OTP support ### Changed From 8e2bd7997ed33a73a40ae955169f5c7cdc5656ed Mon Sep 17 00:00:00 2001 From: Dimitrij Date: Thu, 16 Feb 2023 11:12:44 +0000 Subject: [PATCH 3/4] update "Known Issues" regarding how-to update PuttyNG to latest --- mRemoteNGDocumentation/known_issues.rst | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/mRemoteNGDocumentation/known_issues.rst b/mRemoteNGDocumentation/known_issues.rst index 0c087d01..fccb0d0f 100644 --- a/mRemoteNGDocumentation/known_issues.rst +++ b/mRemoteNGDocumentation/known_issues.rst @@ -2,6 +2,12 @@ Known Issues ############ +Problems connecting to servers using SSH with mRemoteNG version below 1.77.3 +============================================================================ +Due the technological progress we are limited by puttyNG functionality exist in older versions, curently we already solve that for new releases, but due we are still in developing process we dont have stable version at the moment, so to address issue with connection to Ubuntu 22.04 or others servers who expect PubkeyAcceptedAlgorithms - manual update of PuttyNG is required: +- Download the newest prerelease of mRemoteNG: https://github.com/mRemoteNG/mRemoteNG/releases/tag/v1.77.1 +- Download newest PuttyNG exe and overwrite the version in the mRemoteNG install directory: https://github.com/mRemoteNG/PuTTYNG/releases/tag/v0.78.0.10 + CredSSP - CVE-2018-0886 - Authentication error ============================================== From 39d205bd4d661ed74a0acbfc3ca716426b46c446 Mon Sep 17 00:00:00 2001 From: BlueBlock Date: Thu, 16 Feb 2023 14:57:11 -0500 Subject: [PATCH 4/4] improve speed for the display of the options page rather than create the options page on demand, instantiate the options page immediately upon app start though in the background using idle time. --- mRemoteNG/App/Windows.cs | 12 +- mRemoteNG/UI/Forms/frmMain.cs | 20 +- mRemoteNG/UI/Forms/frmOptions.Designer.cs | 24 ++- mRemoteNG/UI/Forms/frmOptions.cs | 218 ++++++++++++++++------ 4 files changed, 193 insertions(+), 81 deletions(-) diff --git a/mRemoteNG/App/Windows.cs b/mRemoteNG/App/Windows.cs index a1085cc2..785c7aaa 100644 --- a/mRemoteNG/App/Windows.cs +++ b/mRemoteNG/App/Windows.cs @@ -1,7 +1,10 @@ -using System; +#region Usings +using System; +using mRemoteNG.Resources.Language; using mRemoteNG.UI; using mRemoteNG.UI.Forms; using mRemoteNG.UI.Window; +#endregion namespace mRemoteNG.App { @@ -39,11 +42,8 @@ namespace mRemoteNG.App _adimportForm.Show(dockPanel); break; case WindowType.Options: - using (var optionsForm = new FrmOptions()) - { - optionsForm.ShowDialog(dockPanel); - } - + FrmMain.OptionsForm.SetActivatedPage(Language.StartupExit); + FrmMain.OptionsForm.Visible = true; break; case WindowType.SSHTransfer: if (SshtransferForm == null || SshtransferForm.IsDisposed) diff --git a/mRemoteNG/UI/Forms/frmMain.cs b/mRemoteNG/UI/Forms/frmMain.cs index aa1cc45e..f758ba1c 100644 --- a/mRemoteNG/UI/Forms/frmMain.cs +++ b/mRemoteNG/UI/Forms/frmMain.cs @@ -1,4 +1,5 @@ -using Microsoft.Win32; +#region Usings +using Microsoft.Win32; using mRemoteNG.App; using mRemoteNG.App.Info; using mRemoteNG.App.Initialization; @@ -30,9 +31,8 @@ using System.Windows.Forms; using mRemoteNG.UI.Panels; using WeifenLuo.WinFormsUI.Docking; using mRemoteNG.UI.Controls; - using mRemoteNG.Resources.Language; - +#endregion // ReSharper disable MemberCanBePrivate.Global @@ -54,6 +54,7 @@ namespace mRemoteNG.UI.Forms private readonly IList _messageWriters = new List(); private readonly ThemeManager _themeManager; private readonly FileBackupPruner _backupPruner = new FileBackupPruner(); + public static FrmOptions OptionsForm; internal FullscreenHandler Fullscreen { get; set; } @@ -64,11 +65,12 @@ namespace mRemoteNG.UI.Forms { _showFullPathInTitle = Properties.OptionsAppearancePage.Default.ShowCompleteConsPathInTitle; InitializeComponent(); + Screen targetScreen = (Screen.AllScreens.Length > 1) ? Screen.AllScreens[1] : Screen.AllScreens[0]; Rectangle viewport = targetScreen.WorkingArea; - // normaly it should be screens[1] however due DPI apply 1 size "same" as default with 100% + // normally it should be screens[1] however due DPI apply 1 size "same" as default with 100% this.Left = viewport.Left + (targetScreen.Bounds.Size.Width / 2) - (this.Width / 2); this.Top = viewport.Top + (targetScreen.Bounds.Size.Height / 2) - (this.Height / 2); @@ -81,7 +83,7 @@ namespace mRemoteNG.UI.Forms _advancedWindowMenu = new AdvancedWindowMenu(this); } - + #region Properties public FormWindowState PreviousWindowState { get; set; } @@ -216,6 +218,8 @@ namespace mRemoteNG.UI.Forms Fullscreen.Value = true; } + OptionsForm = new FrmOptions(); + if (!Properties.OptionsTabsPanelsPage.Default.CreateEmptyPanelOnStartUp) return; var panelName = !string.IsNullOrEmpty(Properties.OptionsTabsPanelsPage.Default.StartUpPanelName) ? Properties.OptionsTabsPanelsPage.Default.StartUpPanelName : Language.NewPanel; @@ -356,10 +360,8 @@ namespace mRemoteNG.UI.Forms if (CTaskDialog.CommandButtonResult != 1) return; - using (var optionsForm = new FrmOptions(Language.Updates)) - { - optionsForm.ShowDialog(this); - } + OptionsForm.SetActivatedPage(Language.Updates); + OptionsForm.ShowDialog(this); } private async Task CheckForUpdates() diff --git a/mRemoteNG/UI/Forms/frmOptions.Designer.cs b/mRemoteNG/UI/Forms/frmOptions.Designer.cs index f8c12440..191d4fbc 100644 --- a/mRemoteNG/UI/Forms/frmOptions.Designer.cs +++ b/mRemoteNG/UI/Forms/frmOptions.Designer.cs @@ -30,16 +30,15 @@ namespace mRemoteNG.UI.Forms /// private void InitializeComponent() { - System.ComponentModel.ComponentResourceManager resources = new System.ComponentModel.ComponentResourceManager(typeof(FrmOptions)); this.pnlBottom = new System.Windows.Forms.Panel(); - this.btnApply = new MrngButton(); - this.btnCancel = new MrngButton(); - this.btnOK = new MrngButton(); + this.btnApply = new mRemoteNG.UI.Controls.MrngButton(); + this.btnCancel = new mRemoteNG.UI.Controls.MrngButton(); + this.btnOK = new mRemoteNG.UI.Controls.MrngButton(); this.splitter1 = new System.Windows.Forms.Splitter(); this.splitter2 = new System.Windows.Forms.Splitter(); this.pnlMain = new System.Windows.Forms.Panel(); this.lstOptionPages = new mRemoteNG.UI.Controls.MrngListView(); - this.PageName = ((BrightIdeasSoftware.OLVColumn)(new BrightIdeasSoftware.OLVColumn())); + this.PageName = new BrightIdeasSoftware.OLVColumn(); this.pnlBottom.SuspendLayout(); ((System.ComponentModel.ISupportInitialize)(this.lstOptionPages)).BeginInit(); this.SuspendLayout(); @@ -57,18 +56,18 @@ namespace mRemoteNG.UI.Forms // // btnApply // - this.btnApply._mice = MrngButton.MouseState.OUT; + this.btnApply._mice = mRemoteNG.UI.Controls.MrngButton.MouseState.OUT; this.btnApply.Location = new System.Drawing.Point(677, 5); this.btnApply.Name = "btnApply"; this.btnApply.Size = new System.Drawing.Size(75, 23); this.btnApply.TabIndex = 2; this.btnApply.Text = "Apply"; this.btnApply.UseVisualStyleBackColor = true; - this.btnApply.Click += new System.EventHandler(this.BtnOK_Click); + this.btnApply.Click += new System.EventHandler(this.BtnApply_Click); // // btnCancel // - this.btnCancel._mice = MrngButton.MouseState.OUT; + this.btnCancel._mice = mRemoteNG.UI.Controls.MrngButton.MouseState.OUT; this.btnCancel.DialogResult = System.Windows.Forms.DialogResult.Cancel; this.btnCancel.Location = new System.Drawing.Point(596, 5); this.btnCancel.Name = "btnCancel"; @@ -80,7 +79,7 @@ namespace mRemoteNG.UI.Forms // // btnOK // - this.btnOK._mice = MrngButton.MouseState.OUT; + this.btnOK._mice = mRemoteNG.UI.Controls.MrngButton.MouseState.OUT; this.btnOK.DialogResult = System.Windows.Forms.DialogResult.OK; this.btnOK.Location = new System.Drawing.Point(515, 5); this.btnOK.Name = "btnOK"; @@ -123,13 +122,11 @@ namespace mRemoteNG.UI.Forms this.lstOptionPages.CellEditUseWholeCell = false; this.lstOptionPages.Columns.AddRange(new System.Windows.Forms.ColumnHeader[] { this.PageName}); - this.lstOptionPages.Cursor = System.Windows.Forms.Cursors.Default; this.lstOptionPages.DecorateLines = true; this.lstOptionPages.Dock = System.Windows.Forms.DockStyle.Left; - this.lstOptionPages.Font = new System.Drawing.Font("Segoe UI", 8.25F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point, ((byte)(0))); + this.lstOptionPages.Font = new System.Drawing.Font("Segoe UI", 8.25F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point); this.lstOptionPages.FullRowSelect = true; this.lstOptionPages.HeaderStyle = System.Windows.Forms.ColumnHeaderStyle.None; - this.lstOptionPages.HideSelection = false; this.lstOptionPages.LabelWrap = false; this.lstOptionPages.Location = new System.Drawing.Point(0, 0); this.lstOptionPages.MultiSelect = false; @@ -162,7 +159,7 @@ namespace mRemoteNG.UI.Forms this.Controls.Add(this.lstOptionPages); this.Controls.Add(this.splitter1); this.Controls.Add(this.pnlBottom); - this.Font = new System.Drawing.Font("Segoe UI", 8.25F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point, ((byte)(0))); + this.Font = new System.Drawing.Font("Segoe UI", 8.25F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point); this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.Fixed3D; this.MaximizeBox = false; this.MinimizeBox = false; @@ -170,6 +167,7 @@ namespace mRemoteNG.UI.Forms this.ShowInTaskbar = false; this.StartPosition = System.Windows.Forms.FormStartPosition.CenterScreen; this.Text = "mRemoteNG Options"; + this.FormClosing += new System.Windows.Forms.FormClosingEventHandler(this.FrmOptions_FormClosing); this.Load += new System.EventHandler(this.FrmOptions_Load); this.pnlBottom.ResumeLayout(false); ((System.ComponentModel.ISupportInitialize)(this.lstOptionPages)).EndInit(); diff --git a/mRemoteNG/UI/Forms/frmOptions.cs b/mRemoteNG/UI/Forms/frmOptions.cs index 84e8e1ff..0babd08a 100644 --- a/mRemoteNG/UI/Forms/frmOptions.cs +++ b/mRemoteNG/UI/Forms/frmOptions.cs @@ -1,4 +1,5 @@ -using mRemoteNG.UI.Forms.OptionsPages; +#region Usings +using mRemoteNG.UI.Forms.OptionsPages; using System; using System.Collections.Generic; using System.Diagnostics; @@ -8,35 +9,55 @@ using mRemoteNG.Themes; using System.Configuration; using mRemoteNG.Properties; using mRemoteNG.Resources.Language; +#endregion namespace mRemoteNG.UI.Forms { public partial class FrmOptions : Form { - private Dictionary _pages; - private readonly string _pageName; - private readonly DisplayProperties _display = new DisplayProperties(); + private int _currentIndex = 0; + private readonly List _optionPages = new(); + private string _pageName; + private readonly DisplayProperties _display = new(); + private readonly List _optionPageObjectNames; public FrmOptions() : this(Language.StartupExit) { } - public FrmOptions(string pn) + private FrmOptions(string pageName) { Cursor.Current = Cursors.WaitCursor; Application.DoEvents(); InitializeComponent(); Icon = Resources.ImageConverter.GetImageAsIcon(Properties.Resources.Settings_16x); - _pageName = pn; + _pageName = pageName; Cursor.Current = Cursors.Default; + + _optionPageObjectNames = new List + { + nameof(StartupExitPage), + nameof(AppearancePage), + nameof(ConnectionsPage), + nameof(TabsPanelsPage), + nameof(NotificationsPage), + nameof(CredentialsPage), + nameof(SqlServerPage), + nameof(UpdatesPage), + nameof(ThemePage), + nameof(SecurityPage), + nameof(AdvancedPage), + nameof(BackupPage) + }; + + InitOptionsPagesToListView(); } private void FrmOptions_Load(object sender, EventArgs e) { - CompileListOfOptionsPages(); + this.Visible = true; FontOverrider.FontOverride(this); - AddOptionsPagesToListView(); - SetInitiallyActivatedPage(); + SetActivatedPage(); //ApplyLanguage(); // Handle the main page here and the individual pages in // AddOptionsPagesToListView() -- one less foreach loop.... @@ -67,57 +88,137 @@ namespace mRemoteNG.UI.Forms } } #endif - private void CompileListOfOptionsPages() - { - _pages = new Dictionary{}; - if (Properties.OptionsStartupExitPage.Default.cbStartupExitPageInOptionMenu == true || Properties.rbac.Default.ActiveRole == "AdminRole") - _pages.Add(typeof(StartupExitPage).Name, new StartupExitPage { Dock = DockStyle.Fill }); - if (Properties.OptionsAppearancePage.Default.cbAppearancePageInOptionMenu == true || Properties.rbac.Default.ActiveRole == "AdminRole") - _pages.Add(typeof(AppearancePage).Name, new AppearancePage { Dock = DockStyle.Fill }); - if (Properties.OptionsConnectionsPage.Default.cbConnectionsPageInOptionMenu == true || Properties.rbac.Default.ActiveRole == "AdminRole") - _pages.Add(typeof(ConnectionsPage).Name, new ConnectionsPage { Dock = DockStyle.Fill }); - if (Properties.OptionsTabsPanelsPage.Default.cbTabsPanelsPageInOptionMenu == true || Properties.rbac.Default.ActiveRole == "AdminRole") - _pages.Add(typeof(TabsPanelsPage).Name, new TabsPanelsPage { Dock = DockStyle.Fill }); - if (Properties.OptionsNotificationsPage.Default.cbNotificationsPageInOptionMenu == true || Properties.rbac.Default.ActiveRole == "AdminRole") - _pages.Add(typeof(NotificationsPage).Name, new NotificationsPage { Dock = DockStyle.Fill }); - if (Properties.OptionsCredentialsPage.Default.cbCredentialsPageInOptionMenu == true || Properties.rbac.Default.ActiveRole == "AdminRole") - _pages.Add(typeof(CredentialsPage).Name, new CredentialsPage { Dock = DockStyle.Fill }); - if (Properties.OptionsDBsPage.Default.cbDBsPageInOptionMenu == true || Properties.rbac.Default.ActiveRole == "AdminRole") - _pages.Add(typeof(SqlServerPage).Name, new SqlServerPage { Dock = DockStyle.Fill }); - if (Properties.OptionsUpdatesPage.Default.cbUpdatesPageInOptionMenu == true || Properties.rbac.Default.ActiveRole == "AdminRole") - _pages.Add(typeof(UpdatesPage).Name, new UpdatesPage { Dock = DockStyle.Fill }); - if (Properties.OptionsThemePage.Default.cbThemePageInOptionMenu == true || Properties.rbac.Default.ActiveRole == "AdminRole") - _pages.Add(typeof(ThemePage).Name, new ThemePage { Dock = DockStyle.Fill }); - if (Properties.OptionsSecurityPage.Default.cbSecurityPageInOptionMenu == true || Properties.rbac.Default.ActiveRole == "AdminRole") - _pages.Add(typeof(SecurityPage).Name, new SecurityPage { Dock = DockStyle.Fill }); - if (Properties.OptionsAdvancedPage.Default.cbAdvancedPageInOptionMenu == true || Properties.rbac.Default.ActiveRole == "AdminRole") - _pages.Add(typeof(AdvancedPage).Name, new AdvancedPage { Dock = DockStyle.Fill }); - if (Properties.OptionsBackupPage.Default.cbBacupPageInOptionMenu == true || Properties.rbac.Default.ActiveRole == "AdminRole") - _pages.Add(typeof(BackupPage).Name, new BackupPage { Dock = DockStyle.Fill }); - } - - private void AddOptionsPagesToListView() + private void InitOptionsPagesToListView() { lstOptionPages.RowHeight = _display.ScaleHeight(lstOptionPages.RowHeight); lstOptionPages.AllColumns.First().ImageGetter = ImageGetter; - foreach (var page in _pages.Select(keyValuePair => keyValuePair.Value)) + InitOptionsPage(_optionPageObjectNames[_currentIndex++]); + Application.Idle += new EventHandler(Application_Idle); + } + + private void Application_Idle(object sender, EventArgs e) + { + if (_currentIndex >= _optionPageObjectNames.Count) { - page.ApplyLanguage(); - page.LoadSettings(); - lstOptionPages.AddObject(page); + Application.Idle -= new EventHandler(Application_Idle); } + else + { + InitOptionsPage(_optionPageObjectNames[_currentIndex++]); + } + } + + private void InitOptionsPage(string pageName) + { + OptionsPage page = null; + + switch (pageName) + { + case "StartupExitPage": + { + if (Properties.OptionsStartupExitPage.Default.cbStartupExitPageInOptionMenu || + Properties.rbac.Default.ActiveRole == "AdminRole") + page = new StartupExitPage { Dock = DockStyle.Fill }; + break; + } + case "AppearancePage": + { + if (Properties.OptionsAppearancePage.Default.cbAppearancePageInOptionMenu || + Properties.rbac.Default.ActiveRole == "AdminRole") + page = new AppearancePage { Dock = DockStyle.Fill }; + break; + } + case "ConnectionsPage": + { + if (Properties.OptionsConnectionsPage.Default.cbConnectionsPageInOptionMenu || + Properties.rbac.Default.ActiveRole == "AdminRole") + page = new ConnectionsPage { Dock = DockStyle.Fill }; + break; + } + case "TabsPanelsPage": + { + if (Properties.OptionsTabsPanelsPage.Default.cbTabsPanelsPageInOptionMenu || + Properties.rbac.Default.ActiveRole == "AdminRole") + page = new TabsPanelsPage { Dock = DockStyle.Fill }; + break; + } + case "NotificationsPage": + { + if (Properties.OptionsNotificationsPage.Default.cbNotificationsPageInOptionMenu || + Properties.rbac.Default.ActiveRole == "AdminRole") + page = new NotificationsPage { Dock = DockStyle.Fill }; + break; + } + case "CredentialsPage": + { + if (Properties.OptionsCredentialsPage.Default.cbCredentialsPageInOptionMenu || + Properties.rbac.Default.ActiveRole == "AdminRole") + page = new CredentialsPage { Dock = DockStyle.Fill }; + break; + } + case "SqlServerPage": + { + if (Properties.OptionsDBsPage.Default.cbDBsPageInOptionMenu || + Properties.rbac.Default.ActiveRole == "AdminRole") + page = new SqlServerPage { Dock = DockStyle.Fill }; + break; + } + case "UpdatesPage": + { + if (Properties.OptionsUpdatesPage.Default.cbUpdatesPageInOptionMenu || + Properties.rbac.Default.ActiveRole == "AdminRole") + page = new UpdatesPage { Dock = DockStyle.Fill }; + break; + } + case "ThemePage": + { + if (Properties.OptionsThemePage.Default.cbThemePageInOptionMenu || + Properties.rbac.Default.ActiveRole == "AdminRole") + page = new ThemePage { Dock = DockStyle.Fill }; + break; + } + case "SecurityPage": + { + if (Properties.OptionsSecurityPage.Default.cbSecurityPageInOptionMenu || + Properties.rbac.Default.ActiveRole == "AdminRole") + page = new SecurityPage { Dock = DockStyle.Fill }; + break; + } + case "AdvancedPage": + { + if (Properties.OptionsAdvancedPage.Default.cbAdvancedPageInOptionMenu || + Properties.rbac.Default.ActiveRole == "AdminRole") + page = new AdvancedPage { Dock = DockStyle.Fill }; + break; + } + case "BackupPage": + { + if (Properties.OptionsBackupPage.Default.cbBacupPageInOptionMenu || + Properties.rbac.Default.ActiveRole == "AdminRole") + page = new BackupPage { Dock = DockStyle.Fill }; + break; + } + } + + if (page == null) return; + page.ApplyLanguage(); + page.LoadSettings(); + _optionPages.Add(page); + lstOptionPages.AddObject(page); } private object ImageGetter(object rowobject) { - var page = rowobject as OptionsPage; + OptionsPage page = rowobject as OptionsPage; return page?.PageIcon == null ? _display.ScaleImage(Properties.Resources.F1Help_16x) : _display.ScaleImage(page.PageIcon); } - private void SetInitiallyActivatedPage() + public void SetActivatedPage(string pageName = default) { + _pageName = pageName ?? Language.StartupExit; + var isSet = false; for (var i = 0; i < lstOptionPages.Items.Count; i++) { @@ -131,14 +232,20 @@ namespace mRemoteNG.UI.Forms lstOptionPages.Items[0].Selected = true; } - /* - * This gets called by both OK and Apply buttons. - * OK sets DialogResult = OK, Apply does not (None). - * Apply will no close the dialog. - */ private void BtnOK_Click(object sender, EventArgs e) { - foreach (var page in _pages.Values) + SaveOptions(); + this.Visible = false; + } + + private void BtnApply_Click(object sender, EventArgs e) + { + SaveOptions(); + } + + private void SaveOptions() + { + foreach (var page in _optionPages) { Debug.WriteLine(page.PageName); page.SaveSettings(); @@ -148,7 +255,6 @@ namespace mRemoteNG.UI.Forms Settings.Default.Save(); } - private void LstOptionPages_SelectedIndexChanged(object sender, EventArgs e) { pnlMain.Controls.Clear(); @@ -160,7 +266,13 @@ namespace mRemoteNG.UI.Forms private void BtnCancel_Click(object sender, EventArgs e) { - Close(); + this.Visible = false; + } + + private void FrmOptions_FormClosing(object sender, FormClosingEventArgs e) + { + e.Cancel = true; + this.Visible = false; } } } \ No newline at end of file