From 1d8484957ef74d551ce62096b519be2a663e5675 Mon Sep 17 00:00:00 2001 From: Dimitrij Date: Wed, 15 Oct 2025 19:04:42 +0100 Subject: [PATCH 01/38] fix menu issues and add translations --- mRemoteNG/App/Info/GeneralAppInfo.cs | 4 +- mRemoteNG/Language/Language.Designer.cs | 144 +++++++++++--------- mRemoteNG/Language/Language.cs-CZ.resx | 14 +- mRemoteNG/Language/Language.de.resx | 14 +- mRemoteNG/Language/Language.el.resx | 2 +- mRemoteNG/Language/Language.es.resx | 14 +- mRemoteNG/Language/Language.fr.resx | 14 +- mRemoteNG/Language/Language.hu.resx | 8 +- mRemoteNG/Language/Language.it.resx | 14 +- mRemoteNG/Language/Language.ja-JP.resx | 14 +- mRemoteNG/Language/Language.ko-KR.resx | 14 +- mRemoteNG/Language/Language.nb-NO.resx | 14 +- mRemoteNG/Language/Language.nl.resx | 14 +- mRemoteNG/Language/Language.pl.resx | 14 +- mRemoteNG/Language/Language.pt-BR.resx | 2 +- mRemoteNG/Language/Language.pt.resx | 14 +- mRemoteNG/Language/Language.resx | 24 ++-- mRemoteNG/Language/Language.ru.resx | 14 +- mRemoteNG/Language/Language.sv-SE.resx | 14 +- mRemoteNG/Language/Language.ta.resx | 14 +- mRemoteNG/Language/Language.tr-TR.resx | 14 +- mRemoteNG/Language/Language.uk.resx | 14 +- mRemoteNG/Language/Language.zh-CN.resx | 14 +- mRemoteNG/Language/Language.zh-TW.resx | 14 +- mRemoteNG/UI/Forms/FrmAbout.cs | 2 +- mRemoteNG/UI/Forms/FrmUnhandledException.cs | 2 +- mRemoteNG/UI/Menu/msMain/HelpMenu.cs | 88 +++++++----- mRemoteNG/UI/Window/UpdateWindow.cs | 10 +- 28 files changed, 296 insertions(+), 242 deletions(-) diff --git a/mRemoteNG/App/Info/GeneralAppInfo.cs b/mRemoteNG/App/Info/GeneralAppInfo.cs index 77c021fc..ee352faa 100644 --- a/mRemoteNG/App/Info/GeneralAppInfo.cs +++ b/mRemoteNG/App/Info/GeneralAppInfo.cs @@ -15,7 +15,9 @@ namespace mRemoteNG.App.Info { public const string UrlHome = "https://mremoteng.org"; public const string UrlDonate = "https://mremoteng.org/contribute"; - public const string UrlForum = "https://www.reddit.com/r/mRemoteNG"; + public const string UrlForum = "https://github.com/orgs/mRemoteNG/discussions"; + public const string UrlChat = "https://app.element.io/#/room/#mremoteng:matrix.org"; + public const string UrlCommunity = "https://www.reddit.com/r/mRemoteNG"; public const string UrlBugs = "https://github.com/mRemoteNG/mRemoteNG/issues/new"; public const string UrlDocumentation = "https://mremoteng.readthedocs.io/en/latest/"; public static readonly string ApplicationVersion = Application.ProductVersion; diff --git a/mRemoteNG/Language/Language.Designer.cs b/mRemoteNG/Language/Language.Designer.cs index 3a058596..0c6af1a4 100644 --- a/mRemoteNG/Language/Language.Designer.cs +++ b/mRemoteNG/Language/Language.Designer.cs @@ -213,15 +213,6 @@ namespace mRemoteNG.Resources.Language { } } - /// - /// Looks up a localized string similar to About. - /// - internal static string About { - get { - return ResourceManager.GetString("About", resourceCulture); - } - } - /// /// Looks up a localized string similar to Hidden. /// @@ -735,15 +726,6 @@ namespace mRemoteNG.Resources.Language { } } - /// - /// Looks up a localized string similar to Check for Updates. - /// - internal static string CheckForUpdates { - get { - return ResourceManager.GetString("CheckForUpdates", resourceCulture); - } - } - /// /// Looks up a localized string similar to Check for updates at startup. /// @@ -1708,15 +1690,6 @@ namespace mRemoteNG.Resources.Language { } } - /// - /// Looks up a localized string similar to Donate. - /// - internal static string Donate { - get { - return ResourceManager.GetString("Donate", resourceCulture); - } - } - /// /// Looks up a localized string similar to Do not play. /// @@ -2585,15 +2558,6 @@ namespace mRemoteNG.Resources.Language { } } - /// - /// Looks up a localized string similar to mRemoteNG Help. - /// - internal static string HelpContents { - get { - return ResourceManager.GetString("HelpContents", resourceCulture); - } - } - /// /// Looks up a localized string similar to High. /// @@ -3116,6 +3080,87 @@ namespace mRemoteNG.Resources.Language { } } + /// + /// Looks up a localized string similar to About. + /// + internal static string MenuItem_About { + get { + return ResourceManager.GetString("MenuItem_About", resourceCulture); + } + } + + /// + /// Looks up a localized string similar to mR Chat. + /// + internal static string MenuItem_Chat { + get { + return ResourceManager.GetString("MenuItem_Chat", resourceCulture); + } + } + + /// + /// Looks up a localized string similar to Check for Updates. + /// + internal static string MenuItem_CheckForUpdates { + get { + return ResourceManager.GetString("MenuItem_CheckForUpdates", resourceCulture); + } + } + + /// + /// Looks up a localized string similar to Community. + /// + internal static string MenuItem_Community { + get { + return ResourceManager.GetString("MenuItem_Community", resourceCulture); + } + } + + /// + /// Looks up a localized string similar to Donate. + /// + internal static string MenuItem_Donate { + get { + return ResourceManager.GetString("MenuItem_Donate", resourceCulture); + } + } + + /// + /// Looks up a localized string similar to mRemoteNG Help. + /// + internal static string MenuItem_HelpContents { + get { + return ResourceManager.GetString("MenuItem_HelpContents", resourceCulture); + } + } + + /// + /// Looks up a localized string similar to Report an Issue. + /// + internal static string MenuItem_ReportIssue { + get { + return ResourceManager.GetString("MenuItem_ReportIssue", resourceCulture); + } + } + + /// + /// Looks up a localized string similar to Support Forum. + /// + internal static string MenuItem_SupportForum { + get { + return ResourceManager.GetString("MenuItem_SupportForum", resourceCulture); + } + } + + /// + /// Looks up a localized string similar to Website. + /// + internal static string MenuItem_Website { + get { + return ResourceManager.GetString("MenuItem_Website", resourceCulture); + } + } + /// /// Looks up a localized string similar to Message. /// @@ -5631,15 +5676,6 @@ namespace mRemoteNG.Resources.Language { } } - /// - /// Looks up a localized string similar to Report a Bug. - /// - internal static string ReportBug { - get { - return ResourceManager.GetString("ReportBug", resourceCulture); - } - } - /// /// Looks up a localized string similar to Reset layout. /// @@ -6306,15 +6342,6 @@ namespace mRemoteNG.Resources.Language { } } - /// - /// Looks up a localized string similar to Support Forum. - /// - internal static string SupportForum { - get { - return ResourceManager.GetString("SupportForum", resourceCulture); - } - } - /// /// Looks up a localized string similar to Switch to Notifications panel on:. /// @@ -6982,15 +7009,6 @@ namespace mRemoteNG.Resources.Language { } } - /// - /// Looks up a localized string similar to Website. - /// - internal static string Website { - get { - return ResourceManager.GetString("Website", resourceCulture); - } - } - /// /// Looks up a localized string similar to WebView2InitializationFailed. /// diff --git a/mRemoteNG/Language/Language.cs-CZ.resx b/mRemoteNG/Language/Language.cs-CZ.resx index d175fd9c..292e90ef 100644 --- a/mRemoteNG/Language/Language.cs-CZ.resx +++ b/mRemoteNG/Language/Language.cs-CZ.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + O Aplikaci @@ -712,7 +712,7 @@ Otevírám nový prázdný soubor seznamu spojení. Nový panel spojení - + Vyhledat aktualizace @@ -733,7 +733,7 @@ Otevírám nový prázdný soubor seznamu spojení. Smazat vnější nástroj... - + Přispějte @@ -751,7 +751,7 @@ Otevírám nový prázdný soubor seznamu spojení. &Nápověda - + Nápověda mRemoteNG @@ -793,7 +793,7 @@ Otevírám nový prázdný soubor seznamu spojení. Přejmonovat záložku tabu - + Nahlásit chybu @@ -823,7 +823,7 @@ Otevírám nový prázdný soubor seznamu spojení. Spustit (VNC) chat - + Diskuzní fórum podpory @@ -838,7 +838,7 @@ Otevírám nový prázdný soubor seznamu spojení. Pouze prohlížet (VNC) - + Webová stránka diff --git a/mRemoteNG/Language/Language.de.resx b/mRemoteNG/Language/Language.de.resx index cd6224d8..450b81aa 100644 --- a/mRemoteNG/Language/Language.de.resx +++ b/mRemoteNG/Language/Language.de.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + Über @@ -698,7 +698,7 @@ Starte mit neuer Datei. Verbindungs-Panel hinzufügen - + Suche nach Updates @@ -719,7 +719,7 @@ Starte mit neuer Datei. Entfernen - + Spenden @@ -737,7 +737,7 @@ Starte mit neuer Datei. &Hilfe - + Hilfe @@ -779,7 +779,7 @@ Starte mit neuer Datei. Tab umbenennen - + Fehler melden @@ -809,7 +809,7 @@ Starte mit neuer Datei. Chat starten (VNC) - + Forum @@ -824,7 +824,7 @@ Starte mit neuer Datei. View-Only-Modus - + Webseite diff --git a/mRemoteNG/Language/Language.el.resx b/mRemoteNG/Language/Language.el.resx index 7bd9d12e..3811f159 100644 --- a/mRemoteNG/Language/Language.el.resx +++ b/mRemoteNG/Language/Language.el.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + Σχετικά με diff --git a/mRemoteNG/Language/Language.es.resx b/mRemoteNG/Language/Language.es.resx index b04613a0..8244a33f 100644 --- a/mRemoteNG/Language/Language.es.resx +++ b/mRemoteNG/Language/Language.es.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + Acerca de @@ -625,7 +625,7 @@ Arrancando con un nuevo archivo de conexiones. Agregar Panel de Conexión - + Comprobar Actualizaciones @@ -646,7 +646,7 @@ Arrancando con un nuevo archivo de conexiones. Borrar Herramienta Externa... - + Donar @@ -664,7 +664,7 @@ Arrancando con un nuevo archivo de conexiones. &Ayuda - + Ayuda de mRemoteNG @@ -706,7 +706,7 @@ Arrancando con un nuevo archivo de conexiones. Renombrar Pestaña - + Informar de un Bug @@ -736,7 +736,7 @@ Arrancando con un nuevo archivo de conexiones. Comenzar Chat (VNC) - + Foro de Soporte @@ -751,7 +751,7 @@ Arrancando con un nuevo archivo de conexiones. Solo Ver (VNC) - + Sitio Web diff --git a/mRemoteNG/Language/Language.fr.resx b/mRemoteNG/Language/Language.fr.resx index a1c1a529..1c77844e 100644 --- a/mRemoteNG/Language/Language.fr.resx +++ b/mRemoteNG/Language/Language.fr.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + À propos @@ -719,7 +719,7 @@ Voir l'article de support Microsoft http://support.microsoft.com/kb/811833 pour Ajouter un panneau de connexion - + Rechercher les mises à jour @@ -740,7 +740,7 @@ Voir l'article de support Microsoft http://support.microsoft.com/kb/811833 pour Supprimer l'outil externe... - + Faire un don @@ -758,7 +758,7 @@ Voir l'article de support Microsoft http://support.microsoft.com/kb/811833 pour &Aide - + Aide mRemoteNG @@ -800,7 +800,7 @@ Voir l'article de support Microsoft http://support.microsoft.com/kb/811833 pour Renommer l'onglet - + Signaler un bug @@ -830,7 +830,7 @@ Voir l'article de support Microsoft http://support.microsoft.com/kb/811833 pour Démarrer le chat (VNC) - + Forum du support @@ -845,7 +845,7 @@ Voir l'article de support Microsoft http://support.microsoft.com/kb/811833 pour Voir seulement (VNC) - + Site web diff --git a/mRemoteNG/Language/Language.hu.resx b/mRemoteNG/Language/Language.hu.resx index e66fcf12..4faa433a 100644 --- a/mRemoteNG/Language/Language.hu.resx +++ b/mRemoteNG/Language/Language.hu.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + Névjegy @@ -267,7 +267,7 @@ (Automatikus észlelés) - + Frissítés keresése @@ -294,7 +294,7 @@ Fül átnevezése - + Hibabejelentés @@ -306,7 +306,7 @@ Kapcsolatfájl mentése, mint... - + Honlap diff --git a/mRemoteNG/Language/Language.it.resx b/mRemoteNG/Language/Language.it.resx index 75256c54..f8ba4758 100644 --- a/mRemoteNG/Language/Language.it.resx +++ b/mRemoteNG/Language/Language.it.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + Informazioni su @@ -622,7 +622,7 @@ Creazione di un nuovo file delle connessioni. Aggiungi pannello delle connessioni - + Verifica la presenza di aggiornamenti @@ -643,7 +643,7 @@ Creazione di un nuovo file delle connessioni. Elimina applicazione esterna... - + Effettua una donazione @@ -661,7 +661,7 @@ Creazione di un nuovo file delle connessioni. &Aiuto - + Guida di mRemoteNG @@ -703,7 +703,7 @@ Creazione di un nuovo file delle connessioni. Rinomina tab - + Segnala un bug @@ -733,7 +733,7 @@ Creazione di un nuovo file delle connessioni. Avvia chat (VNC) - + Forum di supporto @@ -748,7 +748,7 @@ Creazione di un nuovo file delle connessioni. Visualizza soltanto (VNC) - + Sito web diff --git a/mRemoteNG/Language/Language.ja-JP.resx b/mRemoteNG/Language/Language.ja-JP.resx index 6121aa5b..cb31250b 100644 --- a/mRemoteNG/Language/Language.ja-JP.resx +++ b/mRemoteNG/Language/Language.ja-JP.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + mRemoteNGについて @@ -723,7 +723,7 @@ Starting with new connections file. 接続表示パネルの追加 - + 最新バージョンをチェック @@ -744,7 +744,7 @@ Starting with new connections file. 外部ツールを削除... - + 寄付のお願い @@ -762,7 +762,7 @@ Starting with new connections file. ヘルプ(&H) - + mRemoteNGヘルプ @@ -804,7 +804,7 @@ Starting with new connections file. タブ名を変更 - + バグを報告する @@ -835,7 +835,7 @@ Starting with new connections file. Start Chat (VNC) - + サポートフォーラム @@ -850,7 +850,7 @@ Starting with new connections file. View Only (VNC) - + ウェブサイト(英語) diff --git a/mRemoteNG/Language/Language.ko-KR.resx b/mRemoteNG/Language/Language.ko-KR.resx index aa28909d..c7e45a1b 100644 --- a/mRemoteNG/Language/Language.ko-KR.resx +++ b/mRemoteNG/Language/Language.ko-KR.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + mRemoteNG 정보 @@ -712,7 +712,7 @@ 연결 패널 추가 - + 업데이트 확인 @@ -733,7 +733,7 @@ 외부 도구를 삭제 ... - + 기부 @@ -751,7 +751,7 @@ 도움말(&H) - + mRemoteNG 도움말 @@ -793,7 +793,7 @@ 탭 이름 바꾸기 - + 버그 신고 @@ -823,7 +823,7 @@ 채팅 시작 (VNC) - + 지원 포럼 @@ -838,7 +838,7 @@ 보기 전용 (VNC) - + 웹 사이트 diff --git a/mRemoteNG/Language/Language.nb-NO.resx b/mRemoteNG/Language/Language.nb-NO.resx index cd5f88c5..7d8426c7 100644 --- a/mRemoteNG/Language/Language.nb-NO.resx +++ b/mRemoteNG/Language/Language.nb-NO.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + Om @@ -708,7 +708,7 @@ Se Microsofts support-artikkel på http://support.microsoft.com/kb/811833 for me Legg til tilkoblingspanel - + Se etter oppdateringer @@ -729,7 +729,7 @@ Se Microsofts support-artikkel på http://support.microsoft.com/kb/811833 for me Slett eksternt verktøy... - + Donér @@ -747,7 +747,7 @@ Se Microsofts support-artikkel på http://support.microsoft.com/kb/811833 for me &Hjelp - + mRemoteNG-hjelp @@ -789,7 +789,7 @@ Se Microsofts support-artikkel på http://support.microsoft.com/kb/811833 for me Gi nytt navn til fane - + Rapporter en feil @@ -819,7 +819,7 @@ Se Microsofts support-artikkel på http://support.microsoft.com/kb/811833 for me Start chat (VNC) - + Forum for brukerstøtte @@ -834,7 +834,7 @@ Se Microsofts support-artikkel på http://support.microsoft.com/kb/811833 for me Kun visning (VNC) - + Nettsted diff --git a/mRemoteNG/Language/Language.nl.resx b/mRemoteNG/Language/Language.nl.resx index 740879e5..5ef54bf7 100644 --- a/mRemoteNG/Language/Language.nl.resx +++ b/mRemoteNG/Language/Language.nl.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + Over @@ -631,7 +631,7 @@ Beginnen met nieuwe Connectie bestand. Voeg Connectie Paneel toe - + Controleer voor beschikbare Updates @@ -652,7 +652,7 @@ Beginnen met nieuwe Connectie bestand. Verwijder Externe Applicatie... - + Doneer @@ -670,7 +670,7 @@ Beginnen met nieuwe Connectie bestand. &Help - + mRemoteNG Help @@ -712,7 +712,7 @@ Beginnen met nieuwe Connectie bestand. Hernoem Tab - + Meld een bug @@ -742,7 +742,7 @@ Beginnen met nieuwe Connectie bestand. Start Chat (VNC) - + Ondersteunings Forum @@ -757,7 +757,7 @@ Beginnen met nieuwe Connectie bestand. Alleen bekijken (VNC) - + Website diff --git a/mRemoteNG/Language/Language.pl.resx b/mRemoteNG/Language/Language.pl.resx index 5756cf8d..9ebb30cb 100644 --- a/mRemoteNG/Language/Language.pl.resx +++ b/mRemoteNG/Language/Language.pl.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + O programie @@ -722,7 +722,7 @@ Więcj informacji w aktykule Wsparcia Windows na stronie https://support.microso Dodaj panel połączenia - + Sprawdź aktualizacje @@ -743,7 +743,7 @@ Więcj informacji w aktykule Wsparcia Windows na stronie https://support.microso Usuń zewnętrzne narzędzie... - + Darowizna @@ -761,7 +761,7 @@ Więcj informacji w aktykule Wsparcia Windows na stronie https://support.microso &Pomoc - + Pomoc mRemoteNG @@ -803,7 +803,7 @@ Więcj informacji w aktykule Wsparcia Windows na stronie https://support.microso Zmień nazwę karty - + Zgłoś błąd @@ -833,7 +833,7 @@ Więcj informacji w aktykule Wsparcia Windows na stronie https://support.microso Rozpocznij Chat (VNC) - + Forum pomocy @@ -848,7 +848,7 @@ Więcj informacji w aktykule Wsparcia Windows na stronie https://support.microso Tylko pogląd (VNC) - + Strona WWW diff --git a/mRemoteNG/Language/Language.pt-BR.resx b/mRemoteNG/Language/Language.pt-BR.resx index f14c096d..667156d8 100644 --- a/mRemoteNG/Language/Language.pt-BR.resx +++ b/mRemoteNG/Language/Language.pt-BR.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + Sobre diff --git a/mRemoteNG/Language/Language.pt.resx b/mRemoteNG/Language/Language.pt.resx index 36a8cb1f..87796afc 100644 --- a/mRemoteNG/Language/Language.pt.resx +++ b/mRemoteNG/Language/Language.pt.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + Sobre @@ -627,7 +627,7 @@ Adicionar o Painel de Ligação - + Verificar se há atualizações @@ -648,7 +648,7 @@ Excluir ferramenta externa... - + Doar @@ -666,7 +666,7 @@ &Ajuda - + Ajuda mRemoteNG @@ -708,7 +708,7 @@ Renomear aba - + Relatar um erro @@ -735,7 +735,7 @@ Iniciar chat (VNC) - + Fórum de suporte @@ -750,7 +750,7 @@ Somente ver (VNC) - + Sítio diff --git a/mRemoteNG/Language/Language.resx b/mRemoteNG/Language/Language.resx index 32162328..1975dd53 100644 --- a/mRemoteNG/Language/Language.resx +++ b/mRemoteNG/Language/Language.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + About @@ -731,7 +731,7 @@ See the Microsoft Support article at http://support.microsoft.com/kb/811833 for Add Connection Panel - + Check for Updates @@ -752,7 +752,7 @@ See the Microsoft Support article at http://support.microsoft.com/kb/811833 for Delete External Tool... - + Donate @@ -770,7 +770,7 @@ See the Microsoft Support article at http://support.microsoft.com/kb/811833 for &Help - + mRemoteNG Help @@ -812,8 +812,8 @@ See the Microsoft Support article at http://support.microsoft.com/kb/811833 for Rename Tab - - Report a Bug + + Report an Issue Reset layout @@ -842,7 +842,7 @@ See the Microsoft Support article at http://support.microsoft.com/kb/811833 for Start Chat (VNC) - + Support Forum @@ -857,7 +857,7 @@ See the Microsoft Support article at http://support.microsoft.com/kb/811833 for View Only - + Website @@ -2467,4 +2467,12 @@ Nightly Channel includes Alphas, Betas & Release Candidates. runtime library is required + + mR Chat + Chat to dev + + + Community + Reddit + \ No newline at end of file diff --git a/mRemoteNG/Language/Language.ru.resx b/mRemoteNG/Language/Language.ru.resx index f4c93f5a..cf881c15 100644 --- a/mRemoteNG/Language/Language.ru.resx +++ b/mRemoteNG/Language/Language.ru.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + О программе @@ -719,7 +719,7 @@ Добавить Панель подключения - + Проверка наличия обновлений @@ -740,7 +740,7 @@ Удалить внешний инструмент... - + Помочь проекту @@ -758,7 +758,7 @@ &Справка - + Справка mRemoteNG @@ -800,7 +800,7 @@ Переименовать закладку - + Сообщить об ошибке @@ -830,7 +830,7 @@ Начать чат (VNC) - + Форум поддержки @@ -845,7 +845,7 @@ Просмотр (VNC) - + Веб-сайт diff --git a/mRemoteNG/Language/Language.sv-SE.resx b/mRemoteNG/Language/Language.sv-SE.resx index 50408a06..8d35008f 100644 --- a/mRemoteNG/Language/Language.sv-SE.resx +++ b/mRemoteNG/Language/Language.sv-SE.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + Om @@ -710,7 +710,7 @@ Se Microsofts supportartikel på http://support.microsoft.com/kb/811833 för mer Lägg till anslutningspanel - + Sök efter uppdateringar @@ -725,7 +725,7 @@ Se Microsofts supportartikel på http://support.microsoft.com/kb/811833 för mer Ta bort externt verktyg... - + Donera @@ -743,7 +743,7 @@ Se Microsofts supportartikel på http://support.microsoft.com/kb/811833 för mer &Hjälp - + mRemoteNG hjälp @@ -785,7 +785,7 @@ Se Microsofts supportartikel på http://support.microsoft.com/kb/811833 för mer Byt namn på flik - + Rapportera en bugg @@ -812,7 +812,7 @@ Se Microsofts supportartikel på http://support.microsoft.com/kb/811833 för mer Starta chatt (VNC) - + Supportforum @@ -827,7 +827,7 @@ Se Microsofts supportartikel på http://support.microsoft.com/kb/811833 för mer Visa endast - + Webbplats diff --git a/mRemoteNG/Language/Language.ta.resx b/mRemoteNG/Language/Language.ta.resx index 6eb7bce8..286e7400 100644 --- a/mRemoteNG/Language/Language.ta.resx +++ b/mRemoteNG/Language/Language.ta.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + பற்றி @@ -725,7 +725,7 @@ இணைப்பு பலகையைச் சேர் - + புதுப்பிப்புகளை சரிபார் @@ -746,7 +746,7 @@ வெளிப்புற கருவியை நீக்கு... - + நன்கொடை @@ -764,7 +764,7 @@ உதவி - + பலதொலைஅத உதவி @@ -806,7 +806,7 @@ தாவலை மறுபெயரிடுங்கள் - + ஒரு பிழையைப் புகாரளி @@ -836,7 +836,7 @@ அரட்டையைத் தொடங்கு (விஎன்சி) - + உதவி மன்றம் @@ -851,7 +851,7 @@ பார்க்க மட்டுமே - + வலைத்தளம் diff --git a/mRemoteNG/Language/Language.tr-TR.resx b/mRemoteNG/Language/Language.tr-TR.resx index 7196be5d..e29d282f 100644 --- a/mRemoteNG/Language/Language.tr-TR.resx +++ b/mRemoteNG/Language/Language.tr-TR.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + Hakkında @@ -693,7 +693,7 @@ PuTTY ve harici araçlar için en fazla bekleme süresi: Bağlantı Paneli Ekle - + Güncelleştirmeleri Konrol Et @@ -708,7 +708,7 @@ PuTTY ve harici araçlar için en fazla bekleme süresi: Harici Aracı Sil... - + Bağış Yap @@ -726,7 +726,7 @@ PuTTY ve harici araçlar için en fazla bekleme süresi: &Yardım - + mRemoteNG Yardım @@ -768,7 +768,7 @@ PuTTY ve harici araçlar için en fazla bekleme süresi: Sekmeyi Yeniden Adlandır - + Hata Raporla @@ -798,7 +798,7 @@ PuTTY ve harici araçlar için en fazla bekleme süresi: Sohbet'i Başlat (VNC) - + Destek Forumu @@ -813,7 +813,7 @@ PuTTY ve harici araçlar için en fazla bekleme süresi: Yalnızca Gör (VNC) - + Web Sitesi diff --git a/mRemoteNG/Language/Language.uk.resx b/mRemoteNG/Language/Language.uk.resx index 632fbb95..6de970d5 100644 --- a/mRemoteNG/Language/Language.uk.resx +++ b/mRemoteNG/Language/Language.uk.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + Про програму @@ -698,7 +698,7 @@ Додати панель з'єднання - + Перевірка наявності оновлень @@ -719,7 +719,7 @@ Видалити зовнішній інструмент… - + Пожертва @@ -737,7 +737,7 @@ &Довідка - + Довідка mRemoteNG @@ -779,7 +779,7 @@ Перейменувати вкладку - + Повідомити про помилку @@ -806,7 +806,7 @@ Почати чат (VNC) - + Форум підтримки @@ -821,7 +821,7 @@ Перегляд (VNC) - + Веб-сайт diff --git a/mRemoteNG/Language/Language.zh-CN.resx b/mRemoteNG/Language/Language.zh-CN.resx index 5700271d..fb7b1290 100644 --- a/mRemoteNG/Language/Language.zh-CN.resx +++ b/mRemoteNG/Language/Language.zh-CN.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + 关于 @@ -719,7 +719,7 @@ 添加连接面板 - + 检查更新 @@ -740,7 +740,7 @@ 删除外部工具... - + 捐赠 @@ -758,7 +758,7 @@ 帮助(&H) - + mRemoteNG 帮助 @@ -800,7 +800,7 @@ 重命名标签 - + 报告问题 @@ -830,7 +830,7 @@ 启动 Chat(VNC) - + 支持论坛 @@ -845,7 +845,7 @@ 仅查看 - + 网站 diff --git a/mRemoteNG/Language/Language.zh-TW.resx b/mRemoteNG/Language/Language.zh-TW.resx index 7502972b..2c18b576 100644 --- a/mRemoteNG/Language/Language.zh-TW.resx +++ b/mRemoteNG/Language/Language.zh-TW.resx @@ -117,7 +117,7 @@ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 - + 關於 @@ -634,7 +634,7 @@ 加入連線面板 - + 檢查更新 @@ -655,7 +655,7 @@ 刪除外部工具... - + 捐贈 @@ -673,7 +673,7 @@ 說明(&H) - + mRemoteNG 說明 @@ -715,7 +715,7 @@ 重新命名索引標籤 - + 報告 Bug @@ -745,7 +745,7 @@ 開始聊天 (VNC) - + 支援討論區 @@ -760,7 +760,7 @@ 只有檢視 (VNC) - + 網站 diff --git a/mRemoteNG/UI/Forms/FrmAbout.cs b/mRemoteNG/UI/Forms/FrmAbout.cs index 5bb4cbfb..3a60bbb0 100644 --- a/mRemoteNG/UI/Forms/FrmAbout.cs +++ b/mRemoteNG/UI/Forms/FrmAbout.cs @@ -27,7 +27,7 @@ namespace mRemoteNG.UI.Forms private void ApplyLanguage() { lblLicense.Text = Language.ReleasedUnderGPL; - base.Text = Language.About; + base.Text = Language.MenuItem_About; llChangelog.Text = Language.Changelog; llCredits.Text = Language.Credits; llLicense.Text = Language.License; diff --git a/mRemoteNG/UI/Forms/FrmUnhandledException.cs b/mRemoteNG/UI/Forms/FrmUnhandledException.cs index 86865b11..c42e27cd 100644 --- a/mRemoteNG/UI/Forms/FrmUnhandledException.cs +++ b/mRemoteNG/UI/Forms/FrmUnhandledException.cs @@ -56,7 +56,7 @@ namespace mRemoteNG.UI.Forms labelExceptionMessageHeader.Text = Language.ExceptionMessage; labelStackTraceHeader.Text = Language.StackTrace; labelEnvironment.Text = Language.Environment; - buttonCreateBug.Text = Language.ReportBug; + buttonCreateBug.Text = Language.MenuItem_ReportIssue; buttonCopyAll.Text = Language.CopyAll; buttonClose.Text = _isFatal ? Language.Exit diff --git a/mRemoteNG/UI/Menu/msMain/HelpMenu.cs b/mRemoteNG/UI/Menu/msMain/HelpMenu.cs index dfd829a9..5c447016 100644 --- a/mRemoteNG/UI/Menu/msMain/HelpMenu.cs +++ b/mRemoteNG/UI/Menu/msMain/HelpMenu.cs @@ -13,17 +13,19 @@ namespace mRemoteNG.UI.Menu [SupportedOSPlatform("windows")] public class HelpMenu : ToolStripMenuItem { - private ToolStripMenuItem _mMenInfoHelp; - private ToolStripMenuItem _mMenInfoWebsite; - private ToolStripSeparator _mMenInfoSep1; - private ToolStripMenuItem _mMenInfoAbout; - private ToolStripMenuItem _mMenInfoDonate; - private ToolStripSeparator _mMenInfoSep2; - private ToolStripSeparator _mMenInfoSep3; - private ToolStripSeparator _mMenInfoSep4; - private ToolStripMenuItem _mMenInfoForum; - private ToolStripMenuItem _mMenInfoBug; - private ToolStripMenuItem _mMenToolsUpdate; + private ToolStripMenuItem _mMenInfoHelp = null!; + private ToolStripMenuItem _mMenInfoWebsite = null!; + private ToolStripSeparator _mMenInfoSep1 = null!; + private ToolStripMenuItem _mMenInfoAbout = null!; + private ToolStripMenuItem _mMenInfoDonate = null!; + private ToolStripSeparator _mMenInfoSep2 = null!; + private ToolStripSeparator _mMenInfoSep3 = null!; + private ToolStripSeparator _mMenInfoSep4 = null!; + private ToolStripMenuItem _mMenInfoForum = null!; + private ToolStripMenuItem _mMenInfoChat = null!; + private ToolStripMenuItem _mMenInfoCommunity = null!; + private ToolStripMenuItem _mMenInfoBug = null!; + private ToolStripMenuItem _mMenToolsUpdate = null!; public HelpMenu() { @@ -37,6 +39,8 @@ namespace mRemoteNG.UI.Menu _mMenInfoWebsite = new ToolStripMenuItem(); _mMenInfoDonate = new ToolStripMenuItem(); _mMenInfoForum = new ToolStripMenuItem(); + _mMenInfoChat = new ToolStripMenuItem(); + _mMenInfoCommunity = new ToolStripMenuItem(); _mMenInfoBug = new ToolStripMenuItem(); _mMenToolsUpdate = new ToolStripMenuItem(); _mMenInfoSep2 = new ToolStripSeparator(); @@ -53,6 +57,8 @@ namespace mRemoteNG.UI.Menu _mMenInfoSep1, _mMenInfoWebsite, _mMenInfoForum, + _mMenInfoChat, + _mMenInfoCommunity, _mMenInfoBug, _mMenInfoSep2, _mMenToolsUpdate, @@ -72,7 +78,7 @@ namespace mRemoteNG.UI.Menu _mMenInfoHelp.Name = "mMenInfoHelp"; _mMenInfoHelp.ShortcutKeys = Keys.F1; _mMenInfoHelp.Size = new System.Drawing.Size(190, 22); - _mMenInfoHelp.Text = Language.HelpContents; + _mMenInfoHelp.Text = Language.MenuItem_HelpContents; _mMenInfoHelp.Click += mMenInfoHelp_Click; // // mMenToolsUpdate @@ -80,7 +86,7 @@ namespace mRemoteNG.UI.Menu _mMenToolsUpdate.Image = Properties.Resources.RunUpdate_16x; _mMenToolsUpdate.Name = "mMenToolsUpdate"; _mMenToolsUpdate.Size = new System.Drawing.Size(190, 22); - _mMenToolsUpdate.Text = Language.CheckForUpdates; + _mMenToolsUpdate.Text = Language.MenuItem_CheckForUpdates; _mMenToolsUpdate.Click += mMenToolsUpdate_Click; _mMenToolsUpdate.Enabled = CommonRegistrySettings.AllowCheckForUpdates && CommonRegistrySettings.AllowCheckForUpdatesManual; @@ -94,28 +100,42 @@ namespace mRemoteNG.UI.Menu // _mMenInfoWebsite.Name = "mMenInfoWebsite"; _mMenInfoWebsite.Size = new System.Drawing.Size(190, 22); - _mMenInfoWebsite.Text = Language.Website; + _mMenInfoWebsite.Text = Language.MenuItem_Website; _mMenInfoWebsite.Click += mMenInfoWebsite_Click; // // mMenInfoDonate // _mMenInfoDonate.Name = "mMenInfoDonate"; _mMenInfoDonate.Size = new System.Drawing.Size(190, 22); - _mMenInfoDonate.Text = Language.Donate; + _mMenInfoDonate.Text = Language.MenuItem_Donate; _mMenInfoDonate.Click += mMenInfoDonate_Click; // // mMenInfoForum // _mMenInfoForum.Name = "mMenInfoForum"; _mMenInfoForum.Size = new System.Drawing.Size(190, 22); - _mMenInfoForum.Text = Language.SupportForum; + _mMenInfoForum.Text = Language.MenuItem_SupportForum; _mMenInfoForum.Click += mMenInfoForum_Click; // + // mMenInfoChat + // + _mMenInfoChat.Name = "mMenInfoChat"; + _mMenInfoChat.Size = new System.Drawing.Size(190, 22); + _mMenInfoChat.Text = Language.MenuItem_Chat; + _mMenInfoChat.Click += mMenInfoChat_Click; + // + // mMenInfoCommunity + // + _mMenInfoCommunity.Name = "mMenInfoCommunity"; + _mMenInfoCommunity.Size = new System.Drawing.Size(190, 22); + _mMenInfoCommunity.Text = Language.MenuItem_Community; + _mMenInfoCommunity.Click += mMenInfoCommunity_Click; + // // mMenInfoBug // _mMenInfoBug.Name = "mMenInfoBug"; _mMenInfoBug.Size = new System.Drawing.Size(190, 22); - _mMenInfoBug.Text = Language.ReportBug; + _mMenInfoBug.Text = Language.MenuItem_ReportIssue; _mMenInfoBug.Click += mMenInfoBug_Click; // // mMenInfoSep2 @@ -138,20 +158,22 @@ namespace mRemoteNG.UI.Menu _mMenInfoAbout.Image = Properties.Resources.UIAboutBox_16x; _mMenInfoAbout.Name = "mMenInfoAbout"; _mMenInfoAbout.Size = new System.Drawing.Size(190, 22); - _mMenInfoAbout.Text = Language.About; + _mMenInfoAbout.Text = Language.MenuItem_About; _mMenInfoAbout.Click += mMenInfoAbout_Click; } public void ApplyLanguage() { Text = Language._Help; - _mMenInfoHelp.Text = Language.HelpContents; - _mMenInfoWebsite.Text = Language.Website; - _mMenInfoDonate.Text = Language.Donate; - _mMenInfoForum.Text = Language.SupportForum; - _mMenInfoBug.Text = Language.ReportBug; - _mMenInfoAbout.Text = Language.About; - _mMenToolsUpdate.Text = Language.CheckForUpdates; + _mMenInfoHelp.Text = Language.MenuItem_HelpContents; + _mMenInfoWebsite.Text = Language.MenuItem_Website; + _mMenInfoDonate.Text = Language.MenuItem_Donate; + _mMenInfoForum.Text = Language.MenuItem_SupportForum; + _mMenInfoChat.Text = Language.MenuItem_Chat; + _mMenInfoCommunity.Text = Language.MenuItem_Community; + _mMenInfoBug.Text = Language.MenuItem_ReportIssue; + _mMenInfoAbout.Text = Language.MenuItem_About; + _mMenToolsUpdate.Text = Language.MenuItem_CheckForUpdates; } #region Info @@ -166,17 +188,21 @@ namespace mRemoteNG.UI.Menu } } - private void mMenInfoHelp_Click(object sender, EventArgs e) => Process.Start("explorer.exe", GeneralAppInfo.UrlDocumentation); + private void mMenInfoHelp_Click(object? sender, EventArgs e) => Process.Start("explorer.exe", GeneralAppInfo.UrlDocumentation); - private void mMenInfoForum_Click(object sender, EventArgs e) => Process.Start("explorer.exe", GeneralAppInfo.UrlForum); + private void mMenInfoForum_Click(object? sender, EventArgs e) => Process.Start("explorer.exe", GeneralAppInfo.UrlForum); - private void mMenInfoBug_Click(object sender, EventArgs e) => Process.Start("explorer.exe", GeneralAppInfo.UrlBugs); + private void mMenInfoChat_Click(object? sender, EventArgs e) => Process.Start("explorer.exe", GeneralAppInfo.UrlChat); - private void mMenInfoWebsite_Click(object sender, EventArgs e) => Process.Start("explorer.exe", GeneralAppInfo.UrlHome); + private void mMenInfoCommunity_Click(object? sender, EventArgs e) => Process.Start("explorer.exe", GeneralAppInfo.UrlCommunity); - private void mMenInfoDonate_Click(object sender, EventArgs e) => Process.Start("explorer.exe", GeneralAppInfo.UrlDonate); + private void mMenInfoBug_Click(object? sender, EventArgs e) => Process.Start("explorer.exe", GeneralAppInfo.UrlBugs); - private void mMenInfoAbout_Click(object sender, EventArgs e) => frmAbout.Instance.Show(); + private void mMenInfoWebsite_Click(object? sender, EventArgs e) => Process.Start("explorer.exe", GeneralAppInfo.UrlHome); + + private void mMenInfoDonate_Click(object? sender, EventArgs e) => Process.Start("explorer.exe", GeneralAppInfo.UrlDonate); + + private void mMenInfoAbout_Click(object? sender, EventArgs e) => frmAbout.Instance.Show(); #endregion } diff --git a/mRemoteNG/UI/Window/UpdateWindow.cs b/mRemoteNG/UI/Window/UpdateWindow.cs index 9ff6eaea..c1529a06 100644 --- a/mRemoteNG/UI/Window/UpdateWindow.cs +++ b/mRemoteNG/UI/Window/UpdateWindow.cs @@ -66,8 +66,8 @@ namespace mRemoteNG.UI.Window private void ApplyLanguage() { - Text = Language.CheckForUpdates; - TabText = Language.CheckForUpdates; + Text = Language.MenuItem_CheckForUpdates; + TabText = Language.MenuItem_CheckForUpdates; btnCheckForUpdate.Text = Language.CheckAgain; btnDownload.Text = Runtime.IsPortableEdition ? Language.Download @@ -116,7 +116,7 @@ namespace mRemoteNG.UI.Window return; } - lblStatus.Text = Language.CheckForUpdates; + lblStatus.Text = Language.MenuItem_CheckForUpdates; lblStatus.ForeColor = SystemColors.WindowText; lblLatestVersionLabel.Visible = false; lblInstalledVersion.Visible = false; @@ -213,11 +213,11 @@ namespace mRemoteNG.UI.Window prgbDownload.Visible = false; if (Runtime.IsPortableEdition) - MessageBox.Show(Language.UpdatePortableDownloadComplete, Language.CheckForUpdates, + MessageBox.Show(Language.UpdatePortableDownloadComplete, Language.MenuItem_CheckForUpdates, MessageBoxButtons.OK, MessageBoxIcon.Information); else { - if (MessageBox.Show(Language.UpdateDownloadComplete, Language.CheckForUpdates, + if (MessageBox.Show(Language.UpdateDownloadComplete, Language.MenuItem_CheckForUpdates, MessageBoxButtons.OKCancel, MessageBoxIcon.Warning) == DialogResult.OK) { Shutdown.Quit(_appUpdate.CurrentUpdateInfo.UpdateFilePath); From a3a6917bf87e5abe8c6e384f41d25d5fc6306116 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Wed, 15 Oct 2025 21:36:08 +0000 Subject: [PATCH 02/38] Update dependency AWSSDK.EC2 to 4.0.43 --- Directory.Packages.props | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Directory.Packages.props b/Directory.Packages.props index e23d1aa8..27f0da34 100644 --- a/Directory.Packages.props +++ b/Directory.Packages.props @@ -6,7 +6,7 @@ - + From c6fe8ff1f1d2c404f4f32dd54cb899827300f1fb Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Wed, 15 Oct 2025 21:36:14 +0000 Subject: [PATCH 03/38] Update dependency Google.Protobuf to 3.33.0 --- Directory.Packages.props | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Directory.Packages.props b/Directory.Packages.props index e23d1aa8..ead0c2de 100644 --- a/Directory.Packages.props +++ b/Directory.Packages.props @@ -17,7 +17,7 @@ - + From 995f03d03e538a5af27f81dc5db688963c7a604e Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 03:38:46 +0000 Subject: [PATCH 04/38] Initial plan From 4ae8e4252b240ce94e7ecc6cccbe69277fa1ba45 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 03:49:45 +0000 Subject: [PATCH 05/38] Convert frmAbout from Form to BaseWindow to prevent connection close dialog - Changed frmAbout to inherit from BaseWindow instead of Form - Updated HelpMenu to show About window in DockPanel - Removed Form-specific properties (TopMost, StartPosition, FormBorderStyle, etc.) - Removed Hide() behavior in OnFormClosing to allow proper tab closure - Added TabText property for proper tab display Co-authored-by: Kvarkas <3611964+Kvarkas@users.noreply.github.com> --- mRemoteNG/UI/Forms/FrmAbout.Designer.cs | 7 +------ mRemoteNG/UI/Forms/FrmAbout.cs | 10 ++++++---- mRemoteNG/UI/Menu/msMain/HelpMenu.cs | 7 ++++++- 3 files changed, 13 insertions(+), 11 deletions(-) diff --git a/mRemoteNG/UI/Forms/FrmAbout.Designer.cs b/mRemoteNG/UI/Forms/FrmAbout.Designer.cs index 7f2fb295..ef7b7613 100644 --- a/mRemoteNG/UI/Forms/FrmAbout.Designer.cs +++ b/mRemoteNG/UI/Forms/FrmAbout.Designer.cs @@ -142,14 +142,9 @@ Controls.Add(pbLogo); Font = new System.Drawing.Font("Segoe UI", 8.25F); ForeColor = System.Drawing.SystemColors.ControlText; - FormBorderStyle = System.Windows.Forms.FormBorderStyle.FixedSingle; - MaximizeBox = false; - MaximumSize = new System.Drawing.Size(20000, 10000); - MinimizeBox = false; Name = "frmAbout"; - StartPosition = System.Windows.Forms.FormStartPosition.CenterScreen; Text = "About"; - TopMost = true; + TabText = "About"; ((System.ComponentModel.ISupportInitialize)pbLogo).EndInit(); pnlBottom.ResumeLayout(false); pnlBottom.PerformLayout(); diff --git a/mRemoteNG/UI/Forms/FrmAbout.cs b/mRemoteNG/UI/Forms/FrmAbout.cs index 3a60bbb0..976b7c2b 100644 --- a/mRemoteNG/UI/Forms/FrmAbout.cs +++ b/mRemoteNG/UI/Forms/FrmAbout.cs @@ -7,11 +7,12 @@ using System.Reflection; using mRemoteNG.Properties; using System.Runtime.InteropServices; using System.Runtime.Versioning; +using mRemoteNG.UI.Window; namespace mRemoteNG.UI.Forms { [SupportedOSPlatform("windows")] - public partial class frmAbout : Form + public partial class frmAbout : BaseWindow { public static frmAbout Instance { get; set; } = new frmAbout(); @@ -28,6 +29,7 @@ namespace mRemoteNG.UI.Forms { lblLicense.Text = Language.ReleasedUnderGPL; base.Text = Language.MenuItem_About; + TabText = Language.MenuItem_About; llChangelog.Text = Language.Changelog; llCredits.Text = Language.Credits; llLicense.Text = Language.License; @@ -50,9 +52,9 @@ namespace mRemoteNG.UI.Forms protected override void OnFormClosing(FormClosingEventArgs e) { base.OnFormClosing(e); - - e.Cancel = true; - Hide(); + + // Don't cancel close when shown in DockPanel + // This allows the tab to close properly without showing connection close dialog } private void llLicense_LinkClicked(object sender, LinkLabelLinkClickedEventArgs e) diff --git a/mRemoteNG/UI/Menu/msMain/HelpMenu.cs b/mRemoteNG/UI/Menu/msMain/HelpMenu.cs index 5c447016..dc0c6a1e 100644 --- a/mRemoteNG/UI/Menu/msMain/HelpMenu.cs +++ b/mRemoteNG/UI/Menu/msMain/HelpMenu.cs @@ -202,7 +202,12 @@ namespace mRemoteNG.UI.Menu private void mMenInfoDonate_Click(object? sender, EventArgs e) => Process.Start("explorer.exe", GeneralAppInfo.UrlDonate); - private void mMenInfoAbout_Click(object? sender, EventArgs e) => frmAbout.Instance.Show(); + private void mMenInfoAbout_Click(object? sender, EventArgs e) + { + if (frmAbout.Instance == null || frmAbout.Instance.IsDisposed) + frmAbout.Instance = new frmAbout(); + frmAbout.Instance.Show(FrmMain.Default.pnlDock); + } #endregion } From 2520ccd6be247c9e63f432c539f289451c681bb3 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 03:57:26 +0000 Subject: [PATCH 06/38] Initial plan From d736d3c3889f1adcac4a3dc4070c94636d9bd3ed Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 04:07:26 +0000 Subject: [PATCH 07/38] Fix connection file encryption with password protection Changed CreateProtectedAttribute to use PasswordString as source of truth instead of Password property. This prevents encryption failures when Password property is true but _customPassword is empty. Co-authored-by: Kvarkas <3611964+Kvarkas@users.noreply.github.com> --- .../ConnectionSerializers/Xml/XmlRootNodeSerializer.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/mRemoteNG/Config/Serializers/ConnectionSerializers/Xml/XmlRootNodeSerializer.cs b/mRemoteNG/Config/Serializers/ConnectionSerializers/Xml/XmlRootNodeSerializer.cs index 12dc9415..a28813eb 100644 --- a/mRemoteNG/Config/Serializers/ConnectionSerializers/Xml/XmlRootNodeSerializer.cs +++ b/mRemoteNG/Config/Serializers/ConnectionSerializers/Xml/XmlRootNodeSerializer.cs @@ -28,7 +28,7 @@ namespace mRemoteNG.Config.Serializers.ConnectionSerializers.Xml private XAttribute CreateProtectedAttribute(RootNodeInfo rootNodeInfo, ICryptographyProvider cryptographyProvider) { XAttribute attribute = new(XName.Get("Protected"), ""); - string plainText = rootNodeInfo.Password ? "ThisIsProtected" : "ThisIsNotProtected"; + string plainText = (rootNodeInfo.PasswordString != rootNodeInfo.DefaultPassword) ? "ThisIsProtected" : "ThisIsNotProtected"; System.Security.SecureString encryptionPassword = rootNodeInfo.PasswordString.ConvertToSecureString(); attribute.Value = cryptographyProvider.Encrypt(plainText, encryptionPassword); return attribute; From ecb935868d5d8b38e3ae479ff482ed0fa01215eb Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 04:08:46 +0000 Subject: [PATCH 08/38] Add tests for Password property edge cases Added tests to verify that full file encryption works correctly when Password property is set directly without setting PasswordString, ensuring the fix prevents encryption failures. Co-authored-by: Kvarkas <3611964+Kvarkas@users.noreply.github.com> --- .../Xml/XmlRootNodeSerializerTests.cs | 30 +++++++++++++++++++ 1 file changed, 30 insertions(+) diff --git a/mRemoteNGTests/Config/Serializers/ConnectionSerializers/Xml/XmlRootNodeSerializerTests.cs b/mRemoteNGTests/Config/Serializers/ConnectionSerializers/Xml/XmlRootNodeSerializerTests.cs index 9ad944a2..751dd371 100644 --- a/mRemoteNGTests/Config/Serializers/ConnectionSerializers/Xml/XmlRootNodeSerializerTests.cs +++ b/mRemoteNGTests/Config/Serializers/ConnectionSerializers/Xml/XmlRootNodeSerializerTests.cs @@ -97,6 +97,36 @@ public class XmlRootNodeSerializerTests Assert.That(attributeValuePlainText, Is.EqualTo(expectedPlainText)); } + [Test] + public void ProtectedStringSerializedWhenPasswordPropertySetDirectly() + { + // Simulate edge case where Password property is set to true directly + // without setting PasswordString (leaving _customPassword empty) + _rootNodeInfo.Password = true; + var element = _rootNodeSerializer.SerializeRootNodeInfo(_rootNodeInfo, _cryptographyProvider, _version); + var attributeValue = element.Attribute(XName.Get("Protected"))?.Value; + // Should use default password and serialize as "ThisIsNotProtected" + var attributeValuePlainText = + _cryptographyProvider.Decrypt(attributeValue, _rootNodeInfo.PasswordString.ConvertToSecureString()); + Assert.That(attributeValuePlainText, Is.EqualTo("ThisIsNotProtected")); + } + + [Test] + public void FullFileEncryptionWorksWithPasswordPropertySetDirectly() + { + // Simulate edge case where Password property is set to true directly + // This should not cause encryption to fail + _rootNodeInfo.Password = true; + var element = _rootNodeSerializer.SerializeRootNodeInfo(_rootNodeInfo, _cryptographyProvider, _version, fullFileEncryption: true); + var fullFileEncryptionValue = element.Attribute(XName.Get("FullFileEncryption"))?.Value; + Assert.That(bool.Parse(fullFileEncryptionValue), Is.True); + // Verify Protected attribute can be decrypted successfully + var protectedValue = element.Attribute(XName.Get("Protected"))?.Value; + Assert.That(protectedValue, Is.Not.Null.And.Not.Empty); + var decryptedProtected = _cryptographyProvider.Decrypt(protectedValue, _rootNodeInfo.PasswordString.ConvertToSecureString()); + Assert.That(decryptedProtected, Is.EqualTo("ThisIsNotProtected")); + } + [Test] public void ConfVersionSerialized() { From d5d9a8bf03cf560274ea9be1b0d66342ca122eaa Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 04:12:08 +0000 Subject: [PATCH 09/38] Fix PasswordString getter to never return empty password Added defensive check in PasswordString getter to ensure it returns the default password when _customPassword is empty, even if Password property is true. This prevents encryption failures when Password is set inconsistently. Co-authored-by: Kvarkas <3611964+Kvarkas@users.noreply.github.com> --- mRemoteNG/Tree/Root/RootNodeInfo.cs | 2 +- mRemoteNGTests/Tree/RootNodeInfoTests.cs | 8 ++++++++ 2 files changed, 9 insertions(+), 1 deletion(-) diff --git a/mRemoteNG/Tree/Root/RootNodeInfo.cs b/mRemoteNG/Tree/Root/RootNodeInfo.cs index 27ba11f8..c8519232 100644 --- a/mRemoteNG/Tree/Root/RootNodeInfo.cs +++ b/mRemoteNG/Tree/Root/RootNodeInfo.cs @@ -43,7 +43,7 @@ namespace mRemoteNG.Tree.Root [Browsable(false)] public string PasswordString { - get => Password ? _customPassword : DefaultPassword; + get => (Password && !string.IsNullOrEmpty(_customPassword)) ? _customPassword : DefaultPassword; set { _customPassword = value; diff --git a/mRemoteNGTests/Tree/RootNodeInfoTests.cs b/mRemoteNGTests/Tree/RootNodeInfoTests.cs index 4baf33ee..61a6b744 100644 --- a/mRemoteNGTests/Tree/RootNodeInfoTests.cs +++ b/mRemoteNGTests/Tree/RootNodeInfoTests.cs @@ -48,6 +48,14 @@ namespace mRemoteNGTests.Tree Assert.That(_rootNodeInfo.PasswordString, Is.EqualTo(password)); } + [Test] + public void PasswordStringReturnsDefaultWhenPasswordPropertySetWithoutPasswordString() + { + // Edge case: Password property set to true directly without setting PasswordString + _rootNodeInfo.Password = true; + Assert.That(_rootNodeInfo.PasswordString, Is.EqualTo(_rootNodeInfo.DefaultPassword)); + } + [TestCase(RootNodeType.Connection, TreeNodeType.Root)] [TestCase(RootNodeType.PuttySessions, TreeNodeType.PuttyRoot)] public void RootNodeHasCorrectTreeNodeType(RootNodeType rootNodeType, TreeNodeType expectedTreeNodeType) From e04ace4820bd8ada8833cda09db679c75dab93ed Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 18:20:37 +0000 Subject: [PATCH 10/38] Initial plan From c77e6b8616ef1ae263d71b5f3edabd27a1c5a116 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 18:22:19 +0000 Subject: [PATCH 11/38] Initial plan From 80c139136167baa8572eed31437f2b2ba7f2c6d3 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 18:26:41 +0000 Subject: [PATCH 12/38] Fix password passing issue in External Tools - Changed SetProcessProperties to use Arguments property instead of splitting by space and using ArgumentList - Added tests to verify passwords with special characters like '=' are passed correctly - This fixes the issue where passwords like 'Z-3=Wv99/Aq' were being split incorrectly Co-authored-by: Kvarkas <3611964+Kvarkas@users.noreply.github.com> --- mRemoteNG/Tools/ExternalTool.cs | 6 +- mRemoteNGTests/Tools/ExternalToolTests.cs | 115 ++++++++++++++++++++++ 2 files changed, 116 insertions(+), 5 deletions(-) create mode 100644 mRemoteNGTests/Tools/ExternalToolTests.cs diff --git a/mRemoteNG/Tools/ExternalTool.cs b/mRemoteNG/Tools/ExternalTool.cs index d9297e36..41c379b6 100644 --- a/mRemoteNG/Tools/ExternalTool.cs +++ b/mRemoteNG/Tools/ExternalTool.cs @@ -156,11 +156,7 @@ namespace mRemoteNG.Tools ExternalToolArgumentParser argParser = new(startConnectionInfo); process.StartInfo.UseShellExecute = true; process.StartInfo.FileName = argParser.ParseArguments(FileName); - var parsedArgs = argParser.ParseArguments(Arguments).Split(' '); - foreach (var arg in parsedArgs) - { - process.StartInfo.ArgumentList.Add(arg); - } + process.StartInfo.Arguments = argParser.ParseArguments(Arguments); if (WorkingDir != "") process.StartInfo.WorkingDirectory = argParser.ParseArguments(WorkingDir); if (RunElevated) process.StartInfo.Verb = "runas"; } diff --git a/mRemoteNGTests/Tools/ExternalToolTests.cs b/mRemoteNGTests/Tools/ExternalToolTests.cs new file mode 100644 index 00000000..7334c024 --- /dev/null +++ b/mRemoteNGTests/Tools/ExternalToolTests.cs @@ -0,0 +1,115 @@ +using System.Diagnostics; +using System.Reflection; +using mRemoteNG.Connection; +using mRemoteNG.Tools; +using NUnit.Framework; + +namespace mRemoteNGTests.Tools +{ + [TestFixture] + public class ExternalToolTests + { + [Test] + public void PasswordWithEqualsSignIsPassedCorrectly() + { + // Arrange + var connectionInfo = new ConnectionInfo + { + Password = "Z-3=Wv99/Aq", + Hostname = "testhost", + Username = "testuser" + }; + + var externalTool = new ExternalTool + { + DisplayName = "Test Tool", + FileName = "test.exe", + Arguments = "-u %USERNAME% -p %PASSWORD% -h %HOSTNAME%" + }; + + // Act + var process = new Process(); + var setProcessPropertiesMethod = typeof(ExternalTool).GetMethod( + "SetProcessProperties", + BindingFlags.NonPublic | BindingFlags.Instance + ); + setProcessPropertiesMethod?.Invoke(externalTool, new object[] { process, connectionInfo }); + + // Assert + // The arguments should contain the password with the equals sign + // It may be escaped (e.g., Z-3^=Wv99/Aq), but should not be split + Assert.That(process.StartInfo.Arguments, Does.Contain("Z-3")); + Assert.That(process.StartInfo.Arguments, Does.Contain("Wv99/Aq")); + // The equals sign should be present (possibly escaped as ^=) + Assert.That(process.StartInfo.Arguments, Does.Match("Z-3.=Wv99/Aq")); + } + + [Test] + public void PasswordWithSpecialCharactersIsPassedCorrectly() + { + // Arrange + var connectionInfo = new ConnectionInfo + { + Password = "P@ss=W0rd!", + Hostname = "testhost", + Username = "testuser" + }; + + var externalTool = new ExternalTool + { + DisplayName = "Test Tool", + FileName = "test.exe", + Arguments = "-p %PASSWORD%" + }; + + // Act + var process = new Process(); + var setProcessPropertiesMethod = typeof(ExternalTool).GetMethod( + "SetProcessProperties", + BindingFlags.NonPublic | BindingFlags.Instance + ); + setProcessPropertiesMethod?.Invoke(externalTool, new object[] { process, connectionInfo }); + + // Assert + // The password should be present in the arguments (possibly escaped) + Assert.That(process.StartInfo.Arguments, Does.Contain("P@ss")); + Assert.That(process.StartInfo.Arguments, Does.Contain("W0rd")); + } + + [Test] + public void MultipleArgumentsAreParsedCorrectly() + { + // Arrange + var connectionInfo = new ConnectionInfo + { + Password = "TestPass=123", + Hostname = "myhost.com", + Username = "admin", + Port = 8080 + }; + + var externalTool = new ExternalTool + { + DisplayName = "Test Tool", + FileName = "app.exe", + Arguments = "--host %HOSTNAME% --port %PORT% --user %USERNAME% --pass %PASSWORD%" + }; + + // Act + var process = new Process(); + var setProcessPropertiesMethod = typeof(ExternalTool).GetMethod( + "SetProcessProperties", + BindingFlags.NonPublic | BindingFlags.Instance + ); + setProcessPropertiesMethod?.Invoke(externalTool, new object[] { process, connectionInfo }); + + // Assert + var arguments = process.StartInfo.Arguments; + Assert.That(arguments, Does.Contain("myhost.com")); + Assert.That(arguments, Does.Contain("8080")); + Assert.That(arguments, Does.Contain("admin")); + Assert.That(arguments, Does.Contain("TestPass")); + Assert.That(arguments, Does.Contain("123")); + } + } +} From 8b22c7812d58fb6299949434d935e592b1c2611f Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 18:27:54 +0000 Subject: [PATCH 13/38] Fix: Set ConfirmCloseConnection to Never instead of decrementing When user checks "Do not show this dialog again" while closing a connection, the ConfirmCloseConnection setting should be set to Never (1) instead of being decremented. The decrement approach was incorrectly changing All (4) to Multiple (3) instead of Never (1), which didn't match user expectations. Fixed in: - ConnectionTab.cs - ConnectionWindow.cs (2 occurrences) - ConnectionContextMenu.cs - frmMain.cs Co-authored-by: Kvarkas <3611964+Kvarkas@users.noreply.github.com> --- mRemoteNG/UI/Controls/ConnectionContextMenu.cs | 2 +- mRemoteNG/UI/Forms/frmMain.cs | 2 +- mRemoteNG/UI/Tabs/ConnectionTab.cs | 2 +- mRemoteNG/UI/Window/ConnectionWindow.cs | 4 ++-- 4 files changed, 5 insertions(+), 5 deletions(-) diff --git a/mRemoteNG/UI/Controls/ConnectionContextMenu.cs b/mRemoteNG/UI/Controls/ConnectionContextMenu.cs index a2e5357c..320003a8 100644 --- a/mRemoteNG/UI/Controls/ConnectionContextMenu.cs +++ b/mRemoteNG/UI/Controls/ConnectionContextMenu.cs @@ -810,7 +810,7 @@ namespace mRemoteNG.UI.Controls ESysIcons.Question); if (CTaskDialog.VerificationChecked) { - Settings.Default.ConfirmCloseConnection--; + Settings.Default.ConfirmCloseConnection = (int)ConfirmCloseEnum.Never; } if (result == DialogResult.No) diff --git a/mRemoteNG/UI/Forms/frmMain.cs b/mRemoteNG/UI/Forms/frmMain.cs index b1a38662..2e7ae7c2 100644 --- a/mRemoteNG/UI/Forms/frmMain.cs +++ b/mRemoteNG/UI/Forms/frmMain.cs @@ -470,7 +470,7 @@ namespace mRemoteNG.UI.Forms DialogResult result = CTaskDialog.MessageBox(this, Application.ProductName, Language.ConfirmExitMainInstruction, "", "", "", Language.CheckboxDoNotShowThisMessageAgain, ETaskDialogButtons.YesNo, ESysIcons.Question, ESysIcons.Question); if (CTaskDialog.VerificationChecked) { - Properties.Settings.Default.ConfirmCloseConnection--; //--? + Properties.Settings.Default.ConfirmCloseConnection = (int)ConfirmCloseEnum.Never; } if (result == DialogResult.No) diff --git a/mRemoteNG/UI/Tabs/ConnectionTab.cs b/mRemoteNG/UI/Tabs/ConnectionTab.cs index 82d2926f..a6c1fbdd 100644 --- a/mRemoteNG/UI/Tabs/ConnectionTab.cs +++ b/mRemoteNG/UI/Tabs/ConnectionTab.cs @@ -55,7 +55,7 @@ namespace mRemoteNG.UI.Tabs ESysIcons.Question); if (CTaskDialog.VerificationChecked) { - Settings.Default.ConfirmCloseConnection--; + Settings.Default.ConfirmCloseConnection = (int)ConfirmCloseEnum.Never; } if (result == DialogResult.No) diff --git a/mRemoteNG/UI/Window/ConnectionWindow.cs b/mRemoteNG/UI/Window/ConnectionWindow.cs index 506e88e3..f2c9485d 100644 --- a/mRemoteNG/UI/Window/ConnectionWindow.cs +++ b/mRemoteNG/UI/Window/ConnectionWindow.cs @@ -297,7 +297,7 @@ namespace mRemoteNG.UI.Window ESysIcons.Question); if (CTaskDialog.VerificationChecked) { - Settings.Default.ConfirmCloseConnection--; + Settings.Default.ConfirmCloseConnection = (int)ConfirmCloseEnum.Never; } if (result == DialogResult.No) @@ -662,7 +662,7 @@ namespace mRemoteNG.UI.Window ESysIcons.Question); if (CTaskDialog.VerificationChecked) { - Settings.Default.ConfirmCloseConnection--; + Settings.Default.ConfirmCloseConnection = (int)ConfirmCloseEnum.Never; } if (result == DialogResult.No) From 6b52b6b062d1dda19a34bdf07204efa8079fba13 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 19:43:33 +0000 Subject: [PATCH 14/38] Initial plan From 01e22740cececd4e0d13ad0c6987c2741ceccb37 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 19:51:02 +0000 Subject: [PATCH 15/38] Fix Options page not showing correct ConfirmCloseConnection value - Add VisibleChanged event handler to ConnectionsPage to reload settings when page becomes visible - Save settings immediately when user checks "Don't show this message again" checkbox during connection close - Ensures Options dialog always displays current setting value, even if changed outside the dialog Co-authored-by: Kvarkas <3611964+Kvarkas@users.noreply.github.com> --- mRemoteNG/UI/Forms/OptionsPages/ConnectionsPage.cs | 11 +++++++++++ mRemoteNG/UI/Tabs/ConnectionTab.cs | 1 + mRemoteNG/UI/Window/ConnectionWindow.cs | 2 ++ 3 files changed, 14 insertions(+) diff --git a/mRemoteNG/UI/Forms/OptionsPages/ConnectionsPage.cs b/mRemoteNG/UI/Forms/OptionsPages/ConnectionsPage.cs index 6b9c7ef6..f185c1fb 100644 --- a/mRemoteNG/UI/Forms/OptionsPages/ConnectionsPage.cs +++ b/mRemoteNG/UI/Forms/OptionsPages/ConnectionsPage.cs @@ -29,6 +29,17 @@ namespace mRemoteNG.UI.Forms.OptionsPages * 1) chkSaveConnectionsAfterEveryEdit: never used */ chkSaveConnectionsAfterEveryEdit.Visible = false; // Temporary hide control, never used, added: Jun 15, 2024 + + // Reload settings when page becomes visible to reflect any changes made outside the Options dialog + VisibleChanged += ConnectionsPage_VisibleChanged; + } + + private void ConnectionsPage_VisibleChanged(object sender, EventArgs e) + { + if (Visible) + { + LoadSettings(); + } } public override string PageName diff --git a/mRemoteNG/UI/Tabs/ConnectionTab.cs b/mRemoteNG/UI/Tabs/ConnectionTab.cs index a6c1fbdd..3d4f2c53 100644 --- a/mRemoteNG/UI/Tabs/ConnectionTab.cs +++ b/mRemoteNG/UI/Tabs/ConnectionTab.cs @@ -56,6 +56,7 @@ namespace mRemoteNG.UI.Tabs if (CTaskDialog.VerificationChecked) { Settings.Default.ConfirmCloseConnection = (int)ConfirmCloseEnum.Never; + Settings.Default.Save(); } if (result == DialogResult.No) diff --git a/mRemoteNG/UI/Window/ConnectionWindow.cs b/mRemoteNG/UI/Window/ConnectionWindow.cs index f2c9485d..eb726aab 100644 --- a/mRemoteNG/UI/Window/ConnectionWindow.cs +++ b/mRemoteNG/UI/Window/ConnectionWindow.cs @@ -298,6 +298,7 @@ namespace mRemoteNG.UI.Window if (CTaskDialog.VerificationChecked) { Settings.Default.ConfirmCloseConnection = (int)ConfirmCloseEnum.Never; + Settings.Default.Save(); } if (result == DialogResult.No) @@ -663,6 +664,7 @@ namespace mRemoteNG.UI.Window if (CTaskDialog.VerificationChecked) { Settings.Default.ConfirmCloseConnection = (int)ConfirmCloseEnum.Never; + Settings.Default.Save(); } if (result == DialogResult.No) From cd7f23792093402f322734f0cd91c7ba4d452ff4 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 19:52:57 +0000 Subject: [PATCH 16/38] Add Settings.Default.Save() to ConnectionContextMenu disconnect Found another location where ConfirmCloseConnection is changed without immediately saving. This ensures all four code paths that change this setting persist it immediately. Co-authored-by: Kvarkas <3611964+Kvarkas@users.noreply.github.com> --- mRemoteNG/UI/Controls/ConnectionContextMenu.cs | 1 + 1 file changed, 1 insertion(+) diff --git a/mRemoteNG/UI/Controls/ConnectionContextMenu.cs b/mRemoteNG/UI/Controls/ConnectionContextMenu.cs index 320003a8..a526f84f 100644 --- a/mRemoteNG/UI/Controls/ConnectionContextMenu.cs +++ b/mRemoteNG/UI/Controls/ConnectionContextMenu.cs @@ -811,6 +811,7 @@ namespace mRemoteNG.UI.Controls if (CTaskDialog.VerificationChecked) { Settings.Default.ConfirmCloseConnection = (int)ConfirmCloseEnum.Never; + Settings.Default.Save(); } if (result == DialogResult.No) From c70e4c66e6d8d7b6cc5618676b06965ac14ef0ba Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 20:02:27 +0000 Subject: [PATCH 17/38] Initial plan From 3aedc938cb77778879a02ca0f79d8df91b5a817e Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 20:05:10 +0000 Subject: [PATCH 18/38] Initial plan From cfb707d20f79b55cb1334da81ecd3b58b4b0af83 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 20:07:55 +0000 Subject: [PATCH 19/38] Initial plan From d705b8a45d8445dddcf6090070010dec1dab2a0f Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 20:08:58 +0000 Subject: [PATCH 20/38] Fix RDP settings fields alignment in Connections options page Co-authored-by: Kvarkas <3611964+Kvarkas@users.noreply.github.com> --- mRemoteNG/UI/Forms/OptionsPages/ConnectionsPage.Designer.cs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/mRemoteNG/UI/Forms/OptionsPages/ConnectionsPage.Designer.cs b/mRemoteNG/UI/Forms/OptionsPages/ConnectionsPage.Designer.cs index b6b6e648..8cc71c64 100644 --- a/mRemoteNG/UI/Forms/OptionsPages/ConnectionsPage.Designer.cs +++ b/mRemoteNG/UI/Forms/OptionsPages/ConnectionsPage.Designer.cs @@ -257,8 +257,8 @@ namespace mRemoteNG.UI.Forms.OptionsPages // tableLayoutPanel2 // tableLayoutPanel2.ColumnCount = 2; - tableLayoutPanel2.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.Percent, 45F)); - tableLayoutPanel2.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.Percent, 55F)); + tableLayoutPanel2.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.AutoSize)); + tableLayoutPanel2.ColumnStyles.Add(new System.Windows.Forms.ColumnStyle(System.Windows.Forms.SizeType.Percent, 100F)); tableLayoutPanel2.Controls.Add(numRdpReconnectionCount, 1, 0); tableLayoutPanel2.Controls.Add(numAutoSave, 1, 2); tableLayoutPanel2.Controls.Add(lblRdpReconnectionCount, 0, 0); From 6853b158ce2ab21a5f296f8d4ab63fd06d0cd27f Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 20:09:02 +0000 Subject: [PATCH 21/38] Fix empty Options panel when Theme is canceled - Call RevertSettings() on all option pages when Cancel is clicked - Enhanced ThemePage.RevertSettings() to properly revert theme changes: - Store original active theme in LoadSettings - Clear modifiedThemes list on cancel - Restore original theme selection - Add VisibleChanged handler to ensure panel is populated when form is shown - Fixes issue where Options panel was empty after canceling theme selection Co-authored-by: Kvarkas <3611964+Kvarkas@users.noreply.github.com> --- mRemoteNG/UI/Forms/OptionsPages/ThemePage.cs | 17 +++++++++++++++++ mRemoteNG/UI/Forms/frmOptions.cs | 19 +++++++++++++++++++ 2 files changed, 36 insertions(+) diff --git a/mRemoteNG/UI/Forms/OptionsPages/ThemePage.cs b/mRemoteNG/UI/Forms/OptionsPages/ThemePage.cs index cadd833d..4a6013c5 100644 --- a/mRemoteNG/UI/Forms/OptionsPages/ThemePage.cs +++ b/mRemoteNG/UI/Forms/OptionsPages/ThemePage.cs @@ -18,6 +18,7 @@ namespace mRemoteNG.UI.Forms.OptionsPages private readonly ThemeManager _themeManager; private readonly bool _oriActiveTheming; + private ThemeInfo _oriActiveTheme; private readonly List modifiedThemes = []; #endregion @@ -65,6 +66,8 @@ namespace mRemoteNG.UI.Forms.OptionsPages // ReSharper disable once CoVariantArrayConversion cboTheme.Items.AddRange(_themeManager.LoadThemes().OrderBy(x => x.Name).ToArray()); cboTheme.SelectedItem = _themeManager.ActiveTheme; + // Store the original active theme for reverting + _oriActiveTheme = _themeManager.ActiveTheme; cboTheme_SelectionChangeCommitted(this, new EventArgs()); cboTheme.DisplayMember = "Name"; @@ -107,6 +110,20 @@ namespace mRemoteNG.UI.Forms.OptionsPages { base.RevertSettings(); _themeManager.ThemingActive = _oriActiveTheming; + + // Clear the modified themes list without saving + modifiedThemes.Clear(); + + // Restore the original theme selection + if (_oriActiveTheme != null) + { + _themeManager.ActiveTheme = _oriActiveTheme; + // Reload the theme list to reflect the original state + cboTheme.Items.Clear(); + cboTheme.Items.AddRange(_themeManager.LoadThemes().OrderBy(x => x.Name).ToArray()); + cboTheme.SelectedItem = _oriActiveTheme; + cboTheme_SelectionChangeCommitted(this, new EventArgs()); + } } #region Private Methods diff --git a/mRemoteNG/UI/Forms/frmOptions.cs b/mRemoteNG/UI/Forms/frmOptions.cs index 267d3b7a..37b14106 100644 --- a/mRemoteNG/UI/Forms/frmOptions.cs +++ b/mRemoteNG/UI/Forms/frmOptions.cs @@ -71,6 +71,20 @@ namespace mRemoteNG.UI.Forms //ThemeManager.getInstance().ThemeChanged += ApplyTheme; lstOptionPages.SelectedIndexChanged += LstOptionPages_SelectedIndexChanged; lstOptionPages.SelectedIndex = 0; + + // Handle visibility changes to ensure panel is populated when form is shown + this.VisibleChanged += FrmOptions_VisibleChanged; + } + + private void FrmOptions_VisibleChanged(object sender, EventArgs e) + { + // When the form becomes visible, ensure the panel is populated with the selected page + if (this.Visible && pnlMain.Controls.Count == 0) + { + OptionsPage page = (OptionsPage)lstOptionPages.SelectedObject; + if (page != null) + pnlMain.Controls.Add(page); + } } private void ApplyTheme() @@ -269,6 +283,11 @@ namespace mRemoteNG.UI.Forms private void BtnCancel_Click(object sender, EventArgs e) { + // Revert settings for all pages when Cancel is clicked + foreach (OptionsPage page in _optionPages) + { + page.RevertSettings(); + } this.Visible = false; } From e1ee9052861957d0092de5bc107a8baec5e7c93f Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 20:12:40 +0000 Subject: [PATCH 22/38] Initial plan From 6f52b82a6df9e3813ee347ea3bef5943849d4c9e Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 20:13:01 +0000 Subject: [PATCH 23/38] Fix Options dialog freezing when opening/closing multiple times - Add _isInitialized flag to prevent multiple event subscriptions - Skip re-initialization in FrmOptions_Load when form is reused - Properly clean up Application.Idle handler in FormClosing - Add test to verify form can be shown/hidden multiple times Co-authored-by: Kvarkas <3611964+Kvarkas@users.noreply.github.com> --- mRemoteNG/UI/Forms/frmOptions.cs | 12 +++++++++ mRemoteNGTests/UI/Forms/OptionsFormTests.cs | 27 +++++++++++++++++++++ 2 files changed, 39 insertions(+) diff --git a/mRemoteNG/UI/Forms/frmOptions.cs b/mRemoteNG/UI/Forms/frmOptions.cs index 267d3b7a..85bd0ed1 100644 --- a/mRemoteNG/UI/Forms/frmOptions.cs +++ b/mRemoteNG/UI/Forms/frmOptions.cs @@ -22,6 +22,7 @@ namespace mRemoteNG.UI.Forms private string _pageName; private readonly DisplayProperties _display = new(); private readonly List _optionPageObjectNames; + private bool _isInitialized = false; public FrmOptions() : this(Language.StartupExit) { @@ -57,6 +58,13 @@ namespace mRemoteNG.UI.Forms private void FrmOptions_Load(object sender, EventArgs e) { + // Only initialize once to prevent multiple event subscriptions and page reloading + if (_isInitialized) + { + this.Visible = true; + return; + } + this.Visible = true; FontOverrider.FontOverride(this); SetActivatedPage(); @@ -71,6 +79,7 @@ namespace mRemoteNG.UI.Forms //ThemeManager.getInstance().ThemeChanged += ApplyTheme; lstOptionPages.SelectedIndexChanged += LstOptionPages_SelectedIndexChanged; lstOptionPages.SelectedIndex = 0; + _isInitialized = true; } private void ApplyTheme() @@ -274,6 +283,9 @@ namespace mRemoteNG.UI.Forms private void FrmOptions_FormClosing(object sender, FormClosingEventArgs e) { + // Ensure Application.Idle handler is removed if still attached + Application.Idle -= Application_Idle; + e.Cancel = true; this.Visible = false; } diff --git a/mRemoteNGTests/UI/Forms/OptionsFormTests.cs b/mRemoteNGTests/UI/Forms/OptionsFormTests.cs index 2b964cb4..947e7c5e 100644 --- a/mRemoteNGTests/UI/Forms/OptionsFormTests.cs +++ b/mRemoteNGTests/UI/Forms/OptionsFormTests.cs @@ -33,5 +33,32 @@ namespace mRemoteNGTests.UI.Forms ListViewTester listViewTester = new("lstOptionPages", _optionsForm); Assert.That(listViewTester.Items.Count, Is.EqualTo(12)); } + + [Test] + public void FormCanBeHiddenAndShownMultipleTimes() + { + // First show (already done in Setup) + Assert.That(_optionsForm.Visible, Is.True); + + // Hide the form + _optionsForm.Hide(); + Assert.That(_optionsForm.Visible, Is.False); + + // Show it again + _optionsForm.Show(); + Assert.That(_optionsForm.Visible, Is.True); + + // Verify pages are still loaded correctly + ListViewTester listViewTester = new("lstOptionPages", _optionsForm); + Assert.That(listViewTester.Items.Count, Is.EqualTo(12)); + + // Hide and show one more time + _optionsForm.Hide(); + _optionsForm.Show(); + Assert.That(_optionsForm.Visible, Is.True); + + // Verify pages are still there + Assert.That(listViewTester.Items.Count, Is.EqualTo(12)); + } } } \ No newline at end of file From 8dee5c0d3cff12dcb8eabb8eb96b53b03529b0bc Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 20:14:34 +0000 Subject: [PATCH 24/38] Also fix event handler accumulation in OptionsWindow - Add _isInitialized flag to OptionsWindow to prevent multiple ThemeChanged subscriptions - Ensures ThemeChanged event is only subscribed once Co-authored-by: Kvarkas <3611964+Kvarkas@users.noreply.github.com> --- mRemoteNG/UI/Window/OptionsWindow.cs | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/mRemoteNG/UI/Window/OptionsWindow.cs b/mRemoteNG/UI/Window/OptionsWindow.cs index 6b07a754..3f3931bb 100644 --- a/mRemoteNG/UI/Window/OptionsWindow.cs +++ b/mRemoteNG/UI/Window/OptionsWindow.cs @@ -12,6 +12,7 @@ namespace mRemoteNG.UI.Window public partial class OptionsWindow : BaseWindow { private FrmOptions _optionsForm; + private bool _isInitialized = false; #region Public Methods @@ -34,8 +35,14 @@ namespace mRemoteNG.UI.Window private void Options_Load(object sender, EventArgs e) { + // Only subscribe to ThemeChanged once to prevent multiple subscriptions + if (!_isInitialized) + { + ThemeManager.getInstance().ThemeChanged += ApplyTheme; + _isInitialized = true; + } + ApplyTheme(); - ThemeManager.getInstance().ThemeChanged += ApplyTheme; ApplyLanguage(); LoadOptionsForm(); } From e0799a6772f3d1847f3714b04847ec5a451f7a98 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 20:18:11 +0000 Subject: [PATCH 25/38] Add change tracking and prompt for unsaved options Co-authored-by: Kvarkas <3611964+Kvarkas@users.noreply.github.com> --- mRemoteNG/Language/Language.Designer.cs | 18 +++ mRemoteNG/Language/Language.resx | 6 + .../UI/Forms/OptionsPages/OptionsPage.cs | 6 + mRemoteNG/UI/Forms/frmOptions.cs | 108 +++++++++++++++++- 4 files changed, 136 insertions(+), 2 deletions(-) diff --git a/mRemoteNG/Language/Language.Designer.cs b/mRemoteNG/Language/Language.Designer.cs index 0c6af1a4..d3205269 100644 --- a/mRemoteNG/Language/Language.Designer.cs +++ b/mRemoteNG/Language/Language.Designer.cs @@ -5766,6 +5766,24 @@ namespace mRemoteNG.Resources.Language { } } + /// + /// Looks up a localized string similar to Do you want to save the changes made to the options?. + /// + internal static string SaveOptionsBeforeClosing { + get { + return ResourceManager.GetString("SaveOptionsBeforeClosing", resourceCulture); + } + } + + /// + /// Looks up a localized string similar to Discard. + /// + internal static string Discard { + get { + return ResourceManager.GetString("Discard", resourceCulture); + } + } + /// /// Looks up a localized string similar to SaveConnectionsOnExit. /// diff --git a/mRemoteNG/Language/Language.resx b/mRemoteNG/Language/Language.resx index 1975dd53..a7da1ed6 100644 --- a/mRemoteNG/Language/Language.resx +++ b/mRemoteNG/Language/Language.resx @@ -1519,6 +1519,12 @@ If you run into such an error, please create a new connection file! Do you want to save the current connections file before loading another? + + Do you want to save the changes made to the options? + + + Discard + Daily diff --git a/mRemoteNG/UI/Forms/OptionsPages/OptionsPage.cs b/mRemoteNG/UI/Forms/OptionsPages/OptionsPage.cs index cc26edda..cb200a1b 100644 --- a/mRemoteNG/UI/Forms/OptionsPages/OptionsPage.cs +++ b/mRemoteNG/UI/Forms/OptionsPages/OptionsPage.cs @@ -24,6 +24,12 @@ namespace mRemoteNG.UI.Forms.OptionsPages public virtual Icon PageIcon { get; protected set; } public virtual Image IconImage => PageIcon?.ToBitmap(); + /// + /// Indicates whether the settings on this page have been modified. + /// + [Browsable(false)] + public bool HasChanges { get; set; } + #endregion #region Public Methods diff --git a/mRemoteNG/UI/Forms/frmOptions.cs b/mRemoteNG/UI/Forms/frmOptions.cs index 267d3b7a..2d591326 100644 --- a/mRemoteNG/UI/Forms/frmOptions.cs +++ b/mRemoteNG/UI/Forms/frmOptions.cs @@ -210,6 +210,9 @@ namespace mRemoteNG.UI.Forms page.LoadSettings(); _optionPages.Add(page); lstOptionPages.AddObject(page); + + // Track changes in all controls on the page + TrackChangesInControls(page); } private object ImageGetter(object rowobject) @@ -238,12 +241,16 @@ namespace mRemoteNG.UI.Forms private void BtnOK_Click(object sender, EventArgs e) { SaveOptions(); + // Clear change flags after saving + ClearChangeFlags(); this.Visible = false; } private void BtnApply_Click(object sender, EventArgs e) { SaveOptions(); + // Clear change flags after applying + ClearChangeFlags(); } private void SaveOptions() @@ -269,13 +276,110 @@ namespace mRemoteNG.UI.Forms private void BtnCancel_Click(object sender, EventArgs e) { + // When Cancel is clicked, we don't check for changes + // The user explicitly wants to cancel this.Visible = false; } private void FrmOptions_FormClosing(object sender, FormClosingEventArgs e) { - e.Cancel = true; - this.Visible = false; + // Check if any page has unsaved changes + bool hasChanges = _optionPages.Any(page => page.HasChanges); + + if (hasChanges) + { + DialogResult result = MessageBox.Show( + Language.SaveOptionsBeforeClosing, + Language.Options, + MessageBoxButtons.YesNoCancel, + MessageBoxIcon.Question); + + switch (result) + { + case DialogResult.Yes: + SaveOptions(); + ClearChangeFlags(); + e.Cancel = true; + this.Visible = false; + break; + case DialogResult.No: + // Discard changes + ClearChangeFlags(); + e.Cancel = true; + this.Visible = false; + break; + case DialogResult.Cancel: + // Cancel closing - keep the dialog open + e.Cancel = true; + break; + } + } + else + { + e.Cancel = true; + this.Visible = false; + } + } + + private void TrackChangesInControls(Control control) + { + foreach (Control childControl in control.Controls) + { + // Track changes for common input controls + if (childControl is TextBox textBox) + { + textBox.TextChanged += (s, e) => MarkPageAsChanged(control); + } + else if (childControl is CheckBox checkBox) + { + checkBox.CheckedChanged += (s, e) => MarkPageAsChanged(control); + } + else if (childControl is RadioButton radioButton) + { + radioButton.CheckedChanged += (s, e) => MarkPageAsChanged(control); + } + else if (childControl is ComboBox comboBox) + { + comboBox.SelectedIndexChanged += (s, e) => MarkPageAsChanged(control); + } + else if (childControl is NumericUpDown numericUpDown) + { + numericUpDown.ValueChanged += (s, e) => MarkPageAsChanged(control); + } + else if (childControl is ListBox listBox) + { + listBox.SelectedIndexChanged += (s, e) => MarkPageAsChanged(control); + } + + // Recursively track changes in nested controls + if (childControl.Controls.Count > 0) + { + TrackChangesInControls(childControl); + } + } + } + + private void MarkPageAsChanged(Control control) + { + // Find the parent OptionsPage + Control current = control; + while (current != null && !(current is OptionsPage)) + { + current = current.Parent; + } + + if (current is OptionsPage page) + { + page.HasChanges = true; + } + } + + private void ClearChangeFlags() + { + foreach (OptionsPage page in _optionPages) + { + page.HasChanges = false; + } } } } \ No newline at end of file From 687f06937df17b7a856d38cfa89fc044a76167ce Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 20:20:00 +0000 Subject: [PATCH 26/38] Fix change tracking to ignore initial loading and add tests Co-authored-by: Kvarkas <3611964+Kvarkas@users.noreply.github.com> --- mRemoteNG/UI/Forms/frmOptions.cs | 6 ++++ mRemoteNGTests/UI/Forms/OptionsFormTests.cs | 33 +++++++++++++++++++++ 2 files changed, 39 insertions(+) diff --git a/mRemoteNG/UI/Forms/frmOptions.cs b/mRemoteNG/UI/Forms/frmOptions.cs index 2d591326..b609f6f7 100644 --- a/mRemoteNG/UI/Forms/frmOptions.cs +++ b/mRemoteNG/UI/Forms/frmOptions.cs @@ -22,6 +22,7 @@ namespace mRemoteNG.UI.Forms private string _pageName; private readonly DisplayProperties _display = new(); private readonly List _optionPageObjectNames; + private bool _isLoading = true; public FrmOptions() : this(Language.StartupExit) { @@ -105,6 +106,8 @@ namespace mRemoteNG.UI.Forms if (_currentIndex >= _optionPageObjectNames.Count) { Application.Idle -= new EventHandler(Application_Idle); + // All pages loaded, now start tracking changes + _isLoading = false; } else { @@ -361,6 +364,9 @@ namespace mRemoteNG.UI.Forms private void MarkPageAsChanged(Control control) { + // Don't track changes during initial loading + if (_isLoading) return; + // Find the parent OptionsPage Control current = control; while (current != null && !(current is OptionsPage)) diff --git a/mRemoteNGTests/UI/Forms/OptionsFormTests.cs b/mRemoteNGTests/UI/Forms/OptionsFormTests.cs index 2b964cb4..bd3b8048 100644 --- a/mRemoteNGTests/UI/Forms/OptionsFormTests.cs +++ b/mRemoteNGTests/UI/Forms/OptionsFormTests.cs @@ -2,6 +2,7 @@ using System.Threading; using System.Windows.Forms; using mRemoteNGTests.TestHelpers; +using System.Linq; namespace mRemoteNGTests.UI.Forms { @@ -33,5 +34,37 @@ namespace mRemoteNGTests.UI.Forms ListViewTester listViewTester = new("lstOptionPages", _optionsForm); Assert.That(listViewTester.Items.Count, Is.EqualTo(12)); } + + [Test] + public void ChangingOptionMarksPageAsChanged() + { + // Wait for all pages to load + System.Threading.Thread.Sleep(500); + Application.DoEvents(); + + // Get the options panel + var pnlMain = _optionsForm.FindControl("pnlMain"); + Assert.That(pnlMain, Is.Not.Null); + + if (pnlMain.Controls.Count > 0) + { + var optionsPage = pnlMain.Controls[0] as mRemoteNG.UI.Forms.OptionsPages.OptionsPage; + Assert.That(optionsPage, Is.Not.Null); + + // Find a checkbox in the options page + var checkBoxes = optionsPage.Controls.Find("", true).OfType().ToList(); + + if (checkBoxes.Count > 0) + { + var checkBox = checkBoxes[0]; + bool originalValue = checkBox.Checked; + checkBox.Checked = !originalValue; + Application.DoEvents(); + + // Verify the page is marked as changed + Assert.That(optionsPage.HasChanges, Is.True); + } + } + } } } \ No newline at end of file From 531e1177314b5aa979448eb716b151c5c0972271 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 20:31:42 +0000 Subject: [PATCH 27/38] Initial plan From 41253442540e30cc47c824231f9615a9ee89928c Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 20:40:36 +0000 Subject: [PATCH 28/38] Fix panel visibility issue when opening first connection Co-authored-by: Kvarkas <3611964+Kvarkas@users.noreply.github.com> --- mRemoteNG/Connection/ConnectionInitiator.cs | 3 ++- mRemoteNG/UI/Panels/PanelAdder.cs | 7 +++++-- mRemoteNG/UI/Window/ConnectionWindow.cs | 6 ++++++ 3 files changed, 13 insertions(+), 3 deletions(-) diff --git a/mRemoteNG/Connection/ConnectionInitiator.cs b/mRemoteNG/Connection/ConnectionInitiator.cs index 7f8db040..6aeca46b 100644 --- a/mRemoteNG/Connection/ConnectionInitiator.cs +++ b/mRemoteNG/Connection/ConnectionInitiator.cs @@ -320,7 +320,8 @@ namespace mRemoteNG.Connection ConnectionWindow connectionForm = conForm ?? Runtime.WindowList.FromString(connectionPanel) as ConnectionWindow; if (connectionForm == null) - connectionForm = _panelAdder.AddPanel(connectionPanel); + // Don't show the panel immediately - it will be shown when first tab is added + connectionForm = _panelAdder.AddPanel(connectionPanel, showImmediately: false); else connectionForm.Show(FrmMain.Default.pnlDock); diff --git a/mRemoteNG/UI/Panels/PanelAdder.cs b/mRemoteNG/UI/Panels/PanelAdder.cs index 75d9afde..728c989c 100644 --- a/mRemoteNG/UI/Panels/PanelAdder.cs +++ b/mRemoteNG/UI/Panels/PanelAdder.cs @@ -15,14 +15,17 @@ namespace mRemoteNG.UI.Panels [SupportedOSPlatform("windows")] public class PanelAdder { - public ConnectionWindow AddPanel(string title = "") + public ConnectionWindow AddPanel(string title = "", bool showImmediately = true) { try { ConnectionWindow connectionForm = new(new DockContent()); BuildConnectionWindowContextMenu(connectionForm); SetConnectionWindowTitle(title, connectionForm); - ShowConnectionWindow(connectionForm); + // Only show immediately if requested (for user-created empty panels) + // When opening connections, we defer showing until first tab is added + if (showImmediately) + ShowConnectionWindow(connectionForm); PrepareTabSupport(connectionForm); return connectionForm; } diff --git a/mRemoteNG/UI/Window/ConnectionWindow.cs b/mRemoteNG/UI/Window/ConnectionWindow.cs index eb726aab..99c79838 100644 --- a/mRemoteNG/UI/Window/ConnectionWindow.cs +++ b/mRemoteNG/UI/Window/ConnectionWindow.cs @@ -143,6 +143,12 @@ namespace mRemoteNG.UI.Window // TODO: See if we can make this work with DPS... //TabController.HideTabsMode = TabControl.HideTabsModes.HideAlways; + // Ensure the ConnectionWindow is visible before adding the tab + // This prevents visibility issues when the window was created but not yet shown + if (!Visible) + { + Show(FrmMain.Default.pnlDock, DockState.Document); + } //Show the tab conTab.Show(connDock, DockState.Document); From 526cb1fb47997bd5269f2937c831a54158b40e23 Mon Sep 17 00:00:00 2001 From: Dimitrij Date: Thu, 16 Oct 2025 21:50:59 +0100 Subject: [PATCH 29/38] small fixes --- mRemoteNG/UI/Forms/FrmAbout.cs | 2 +- mRemoteNG/UI/Forms/frmOptions.cs | 4 ++++ mRemoteNG/UI/Window/ConnectionWindow.cs | 8 +------- mRemoteNG/UI/Window/UpdateWindow.cs | 20 +++++++++++--------- 4 files changed, 17 insertions(+), 17 deletions(-) diff --git a/mRemoteNG/UI/Forms/FrmAbout.cs b/mRemoteNG/UI/Forms/FrmAbout.cs index 976b7c2b..06e8be28 100644 --- a/mRemoteNG/UI/Forms/FrmAbout.cs +++ b/mRemoteNG/UI/Forms/FrmAbout.cs @@ -16,7 +16,7 @@ namespace mRemoteNG.UI.Forms { public static frmAbout Instance { get; set; } = new frmAbout(); - private frmAbout() + public frmAbout() { InitializeComponent(); Icon = Resources.ImageConverter.GetImageAsIcon(Properties.Resources.UIAboutBox_16x); diff --git a/mRemoteNG/UI/Forms/frmOptions.cs b/mRemoteNG/UI/Forms/frmOptions.cs index ed10cf80..e867c35b 100644 --- a/mRemoteNG/UI/Forms/frmOptions.cs +++ b/mRemoteNG/UI/Forms/frmOptions.cs @@ -23,6 +23,7 @@ namespace mRemoteNG.UI.Forms private readonly DisplayProperties _display = new(); private readonly List _optionPageObjectNames; private bool _isLoading = true; + private bool _isInitialized = false; // Add this field to the FrmOptions class public FrmOptions() : this(Language.StartupExit) { @@ -82,6 +83,9 @@ namespace mRemoteNG.UI.Forms // Handle visibility changes to ensure panel is populated when form is shown this.VisibleChanged += FrmOptions_VisibleChanged; + + // Mark as initialized + _isInitialized = true; } private void FrmOptions_VisibleChanged(object sender, EventArgs e) diff --git a/mRemoteNG/UI/Window/ConnectionWindow.cs b/mRemoteNG/UI/Window/ConnectionWindow.cs index 99c79838..78634330 100644 --- a/mRemoteNG/UI/Window/ConnectionWindow.cs +++ b/mRemoteNG/UI/Window/ConnectionWindow.cs @@ -294,13 +294,7 @@ namespace mRemoteNG.UI.Window Settings.Default.ConfirmCloseConnection == (int)ConfirmCloseEnum.Multiple & connDock.Documents.Count() > 1)) { - DialogResult result = CTaskDialog.MessageBox(this, GeneralAppInfo.ProductName, - string - .Format(Language.ConfirmCloseConnectionPanelMainInstruction, - Text), "", "", "", - Language.CheckboxDoNotShowThisMessageAgain, - ETaskDialogButtons.YesNo, ESysIcons.Question, - ESysIcons.Question); + DialogResult result = CTaskDialog.MessageBox(this, GeneralAppInfo.ProductName, string.Format(Language.ConfirmCloseConnectionPanelMainInstruction, Text), "", "", "", Language.CheckboxDoNotShowThisMessageAgain, ETaskDialogButtons.YesNo, ESysIcons.Question, ESysIcons.Question); if (CTaskDialog.VerificationChecked) { Settings.Default.ConfirmCloseConnection = (int)ConfirmCloseEnum.Never; diff --git a/mRemoteNG/UI/Window/UpdateWindow.cs b/mRemoteNG/UI/Window/UpdateWindow.cs index c1529a06..d590152d 100644 --- a/mRemoteNG/UI/Window/UpdateWindow.cs +++ b/mRemoteNG/UI/Window/UpdateWindow.cs @@ -1,16 +1,18 @@ -using System; +using mRemoteNG.App; +using mRemoteNG.App.Update; +using mRemoteNG.Messages; +using mRemoteNG.Resources.Language; +using mRemoteNG.Themes; + +using System; using System.Diagnostics; using System.Drawing; using System.IO; -using System.Windows.Forms; -using mRemoteNG.App; -using mRemoteNG.App.Update; -using mRemoteNG.Messages; -using mRemoteNG.Themes; -using WeifenLuo.WinFormsUI.Docking; -using mRemoteNG.Resources.Language; -using System.Threading.Tasks; using System.Runtime.Versioning; +using System.Threading.Tasks; +using System.Windows.Forms; + +using WeifenLuo.WinFormsUI.Docking; namespace mRemoteNG.UI.Window { From b4aa30de2398067c6144d3f7a0c3c76c85b24d8f Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 20:55:28 +0000 Subject: [PATCH 30/38] Initial plan From 4668104e3685e308f6b6353bdacc071efca4b7ba Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 21:01:20 +0000 Subject: [PATCH 31/38] Initial plan From 89ccd33fd155d78f83d80b1b75281c1d8d27ff0a Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 21:04:59 +0000 Subject: [PATCH 32/38] Fix empty space in Tabs & Panels settings by adjusting control positions Co-authored-by: Kvarkas <3611964+Kvarkas@users.noreply.github.com> --- .../OptionsPages/TabsPanelsPage.Designer.cs | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/mRemoteNG/UI/Forms/OptionsPages/TabsPanelsPage.Designer.cs b/mRemoteNG/UI/Forms/OptionsPages/TabsPanelsPage.Designer.cs index 47d06cd0..f8e5247b 100644 --- a/mRemoteNG/UI/Forms/OptionsPages/TabsPanelsPage.Designer.cs +++ b/mRemoteNG/UI/Forms/OptionsPages/TabsPanelsPage.Designer.cs @@ -79,7 +79,7 @@ namespace mRemoteNG.UI.Forms.OptionsPages chkIdentifyQuickConnectTabs._mice = MrngCheckBox.MouseState.OUT; chkIdentifyQuickConnectTabs.AutoSize = true; chkIdentifyQuickConnectTabs.Font = new System.Drawing.Font("Segoe UI", 8.25F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point); - chkIdentifyQuickConnectTabs.Location = new System.Drawing.Point(3, 118); + chkIdentifyQuickConnectTabs.Location = new System.Drawing.Point(3, 72); chkIdentifyQuickConnectTabs.Name = "chkIdentifyQuickConnectTabs"; chkIdentifyQuickConnectTabs.Size = new System.Drawing.Size(315, 17); chkIdentifyQuickConnectTabs.TabIndex = 4; @@ -103,7 +103,7 @@ namespace mRemoteNG.UI.Forms.OptionsPages chkAlwaysShowPanelSelectionDlg._mice = MrngCheckBox.MouseState.OUT; chkAlwaysShowPanelSelectionDlg.AutoSize = true; chkAlwaysShowPanelSelectionDlg.Font = new System.Drawing.Font("Segoe UI", 8.25F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point); - chkAlwaysShowPanelSelectionDlg.Location = new System.Drawing.Point(3, 164); + chkAlwaysShowPanelSelectionDlg.Location = new System.Drawing.Point(3, 118); chkAlwaysShowPanelSelectionDlg.Name = "chkAlwaysShowPanelSelectionDlg"; chkAlwaysShowPanelSelectionDlg.Size = new System.Drawing.Size(347, 17); chkAlwaysShowPanelSelectionDlg.TabIndex = 6; @@ -115,7 +115,7 @@ namespace mRemoteNG.UI.Forms.OptionsPages chkShowLogonInfoOnTabs._mice = MrngCheckBox.MouseState.OUT; chkShowLogonInfoOnTabs.AutoSize = true; chkShowLogonInfoOnTabs.Font = new System.Drawing.Font("Segoe UI", 8.25F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point); - chkShowLogonInfoOnTabs.Location = new System.Drawing.Point(3, 72); + chkShowLogonInfoOnTabs.Location = new System.Drawing.Point(3, 26); chkShowLogonInfoOnTabs.Name = "chkShowLogonInfoOnTabs"; chkShowLogonInfoOnTabs.Size = new System.Drawing.Size(226, 17); chkShowLogonInfoOnTabs.TabIndex = 2; @@ -127,7 +127,7 @@ namespace mRemoteNG.UI.Forms.OptionsPages chkDoubleClickClosesTab._mice = MrngCheckBox.MouseState.OUT; chkDoubleClickClosesTab.AutoSize = true; chkDoubleClickClosesTab.Font = new System.Drawing.Font("Segoe UI", 8.25F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point); - chkDoubleClickClosesTab.Location = new System.Drawing.Point(3, 141); + chkDoubleClickClosesTab.Location = new System.Drawing.Point(3, 95); chkDoubleClickClosesTab.Name = "chkDoubleClickClosesTab"; chkDoubleClickClosesTab.Size = new System.Drawing.Size(170, 17); chkDoubleClickClosesTab.TabIndex = 5; @@ -139,7 +139,7 @@ namespace mRemoteNG.UI.Forms.OptionsPages chkShowProtocolOnTabs._mice = MrngCheckBox.MouseState.OUT; chkShowProtocolOnTabs.AutoSize = true; chkShowProtocolOnTabs.Font = new System.Drawing.Font("Segoe UI", 8.25F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point); - chkShowProtocolOnTabs.Location = new System.Drawing.Point(3, 95); + chkShowProtocolOnTabs.Location = new System.Drawing.Point(3, 49); chkShowProtocolOnTabs.Name = "chkShowProtocolOnTabs"; chkShowProtocolOnTabs.Size = new System.Drawing.Size(180, 17); chkShowProtocolOnTabs.TabIndex = 3; @@ -151,7 +151,7 @@ namespace mRemoteNG.UI.Forms.OptionsPages chkCreateEmptyPanelOnStart._mice = MrngCheckBox.MouseState.OUT; chkCreateEmptyPanelOnStart.AutoSize = true; chkCreateEmptyPanelOnStart.Font = new System.Drawing.Font("Segoe UI", 8.25F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point); - chkCreateEmptyPanelOnStart.Location = new System.Drawing.Point(3, 187); + chkCreateEmptyPanelOnStart.Location = new System.Drawing.Point(3, 141); chkCreateEmptyPanelOnStart.Name = "chkCreateEmptyPanelOnStart"; chkCreateEmptyPanelOnStart.Size = new System.Drawing.Size(271, 17); chkCreateEmptyPanelOnStart.TabIndex = 7; @@ -162,7 +162,7 @@ namespace mRemoteNG.UI.Forms.OptionsPages // txtBoxPanelName // txtBoxPanelName.Font = new System.Drawing.Font("Segoe UI", 8.25F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point); - txtBoxPanelName.Location = new System.Drawing.Point(35, 223); + txtBoxPanelName.Location = new System.Drawing.Point(35, 177); txtBoxPanelName.Name = "txtBoxPanelName"; txtBoxPanelName.Size = new System.Drawing.Size(213, 22); txtBoxPanelName.TabIndex = 8; @@ -170,7 +170,7 @@ namespace mRemoteNG.UI.Forms.OptionsPages // lblPanelName // lblPanelName.AutoSize = true; - lblPanelName.Location = new System.Drawing.Point(32, 207); + lblPanelName.Location = new System.Drawing.Point(32, 161); lblPanelName.Name = "lblPanelName"; lblPanelName.Size = new System.Drawing.Size(69, 13); lblPanelName.TabIndex = 9; @@ -192,7 +192,7 @@ namespace mRemoteNG.UI.Forms.OptionsPages pnlOptions.Dock = System.Windows.Forms.DockStyle.Top; pnlOptions.Location = new System.Drawing.Point(0, 30); pnlOptions.Name = "pnlOptions"; - pnlOptions.Size = new System.Drawing.Size(610, 262); + pnlOptions.Size = new System.Drawing.Size(610, 216); pnlOptions.TabIndex = 10; // // lblRegistrySettingsUsedInfo From 4e20049ea36072d8c2e40a3a0521a4f0d3af8ef4 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 21:05:51 +0000 Subject: [PATCH 33/38] Fix Options panel corruption when toggling 'Always show panel tabs' Co-authored-by: Kvarkas <3611964+Kvarkas@users.noreply.github.com> --- mRemoteNG/UI/Forms/OptionsPages/TabsPanelsPage.cs | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/mRemoteNG/UI/Forms/OptionsPages/TabsPanelsPage.cs b/mRemoteNG/UI/Forms/OptionsPages/TabsPanelsPage.cs index 19b25794..cad52f11 100644 --- a/mRemoteNG/UI/Forms/OptionsPages/TabsPanelsPage.cs +++ b/mRemoteNG/UI/Forms/OptionsPages/TabsPanelsPage.cs @@ -89,7 +89,10 @@ namespace mRemoteNG.UI.Forms.OptionsPages * Properties.OptionsTabsPanelsPage.Default.AlwaysShowConnectionTabs nerver used */ //Properties.OptionsTabsPanelsPage.Default.AlwaysShowConnectionTabs = chkAlwaysShowConnectionTabs.Checked; - FrmMain.Default.ShowHidePanelTabs(); + + // Defer the ShowHidePanelTabs call to avoid corrupting the Options window + // This ensures the call happens after the Options window is closed + FrmMain.Default.BeginInvoke(new System.Windows.Forms.MethodInvoker(FrmMain.Default.ShowHidePanelTabs)); /* * Comment added: June 16, 2024 From ea9e79d9302f62d26b8dd802385b7c60bf75ae33 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Thu, 16 Oct 2025 21:08:10 +0000 Subject: [PATCH 34/38] Update dependency AWSSDK.Core to 4.0.1.1 --- Directory.Packages.props | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Directory.Packages.props b/Directory.Packages.props index 63eebe03..c483bb7c 100644 --- a/Directory.Packages.props +++ b/Directory.Packages.props @@ -5,7 +5,7 @@ $(NoWarn);NU1507 - + From fa3be420b8b1873e5e1975013652720815125930 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 21:21:53 +0000 Subject: [PATCH 35/38] Initial plan From b9595d16509a25b8b02ad66a13df977ef5a2889a Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Thu, 16 Oct 2025 21:28:45 +0000 Subject: [PATCH 36/38] Fix panel visibility check to use DockState Co-authored-by: Kvarkas <3611964+Kvarkas@users.noreply.github.com> --- mRemoteNG/UI/Window/ConnectionWindow.cs | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/mRemoteNG/UI/Window/ConnectionWindow.cs b/mRemoteNG/UI/Window/ConnectionWindow.cs index 78634330..eb99a600 100644 --- a/mRemoteNG/UI/Window/ConnectionWindow.cs +++ b/mRemoteNG/UI/Window/ConnectionWindow.cs @@ -145,7 +145,8 @@ namespace mRemoteNG.UI.Window // Ensure the ConnectionWindow is visible before adding the tab // This prevents visibility issues when the window was created but not yet shown - if (!Visible) + // Check DockState instead of Visible to properly detect if window is shown in DockPanel + if (DockState == DockState.Unknown || DockState == DockState.Hidden || !Visible) { Show(FrmMain.Default.pnlDock, DockState.Document); } From 0c50e2d78ec7b83d10e64574778a22592270cb9a Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Thu, 16 Oct 2025 21:33:36 +0000 Subject: [PATCH 37/38] Update dependency AWSSDK.EC2 to 4.0.43.1 --- Directory.Packages.props | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Directory.Packages.props b/Directory.Packages.props index c483bb7c..0ee1e3ee 100644 --- a/Directory.Packages.props +++ b/Directory.Packages.props @@ -6,7 +6,7 @@ - + From 21ab1720414fb39f74971fa7ba06f7d3d78e95bf Mon Sep 17 00:00:00 2001 From: Dimitrij Date: Fri, 17 Oct 2025 09:12:57 +0100 Subject: [PATCH 38/38] fix --- mRemoteNG/UI/Forms/OptionsPages/TabsPanelsPage.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/mRemoteNG/UI/Forms/OptionsPages/TabsPanelsPage.cs b/mRemoteNG/UI/Forms/OptionsPages/TabsPanelsPage.cs index cad52f11..b8d35393 100644 --- a/mRemoteNG/UI/Forms/OptionsPages/TabsPanelsPage.cs +++ b/mRemoteNG/UI/Forms/OptionsPages/TabsPanelsPage.cs @@ -92,7 +92,7 @@ namespace mRemoteNG.UI.Forms.OptionsPages // Defer the ShowHidePanelTabs call to avoid corrupting the Options window // This ensures the call happens after the Options window is closed - FrmMain.Default.BeginInvoke(new System.Windows.Forms.MethodInvoker(FrmMain.Default.ShowHidePanelTabs)); + FrmMain.Default.BeginInvoke(new System.Windows.Forms.MethodInvoker(() => FrmMain.Default.ShowHidePanelTabs())); /* * Comment added: June 16, 2024