[Feature] CodeBuity&Refactor #49

This commit is contained in:
Markus Hofknecht 2020-03-16 14:45:19 +01:00
parent 41991c206e
commit 5a30e8c25c
18 changed files with 322 additions and 289 deletions

View file

@ -1,8 +1,8 @@
using Clearcove.Logging; using Microsoft.WindowsAPICodePack.Dialogs;
using Microsoft.WindowsAPICodePack.Dialogs;
using System.Diagnostics; using System.Diagnostics;
using System.IO; using System.IO;
using System.Reflection; using System.Reflection;
using SystemTrayMenu.Helper;
namespace SystemTrayMenu namespace SystemTrayMenu
{ {
@ -30,7 +30,7 @@ namespace SystemTrayMenu
FileVersionInfo versionInfo = FileVersionInfo. FileVersionInfo versionInfo = FileVersionInfo.
GetVersionInfo(Assembly.GetEntryAssembly().Location); GetVersionInfo(Assembly.GetEntryAssembly().Location);
new Logger(nameof(Config)).Info($"Settings upgraded from " + Log.Info($"Settings upgraded from " +
$"%localappdata%\\{versionInfo.CompanyName}\\"); $"%localappdata%\\{versionInfo.CompanyName}\\");
} }
} }

View file

@ -6,6 +6,7 @@ using System.IO;
using System.Reflection; using System.Reflection;
using System.Text.RegularExpressions; using System.Text.RegularExpressions;
using System.Windows.Forms; using System.Windows.Forms;
using SystemTrayMenu.Helper;
namespace SystemTrayMenu.Controls namespace SystemTrayMenu.Controls
{ {
@ -23,9 +24,9 @@ namespace SystemTrayMenu.Controls
public AboutBox() public AboutBox()
{ {
InitializeComponent(); InitializeComponent();
buttonOk.Text = Program.Translate("buttonOk"); buttonOk.Text = Language.Translate("buttonOk");
buttonDetails.Text = Program.Translate("buttonDetails"); buttonDetails.Text = Language.Translate("buttonDetails");
buttonSystemInfo.Text = Program.Translate("buttonSystemInfo"); buttonSystemInfo.Text = Language.Translate("buttonSystemInfo");
} }
private bool _IsPainted = false; private bool _IsPainted = false;

View file

@ -8,6 +8,7 @@ using System.Globalization;
using System.Linq; using System.Linq;
using System.Reflection; using System.Reflection;
using System.Windows.Forms; using System.Windows.Forms;
using SystemTrayMenu.Helper;
namespace SystemTrayMenu.Controls namespace SystemTrayMenu.Controls
{ {
@ -23,7 +24,7 @@ namespace SystemTrayMenu.Controls
ContextMenuStrip menu = new ContextMenuStrip(); ContextMenuStrip menu = new ContextMenuStrip();
menu.BackColor = SystemColors.Control; menu.BackColor = SystemColors.Control;
ToolStripMenuItem changeFolder = new ToolStripMenuItem(); ToolStripMenuItem changeFolder = new ToolStripMenuItem();
changeFolder.Text = Program.Translate("Folder"); changeFolder.Text = Language.Translate("Folder");
changeFolder.Click += ChangeFolder_Click; changeFolder.Click += ChangeFolder_Click;
void ChangeFolder_Click(object sender, EventArgs e) void ChangeFolder_Click(object sender, EventArgs e)
{ {
@ -34,15 +35,15 @@ namespace SystemTrayMenu.Controls
ToolStripMenuItem changeLanguage = new ToolStripMenuItem() ToolStripMenuItem changeLanguage = new ToolStripMenuItem()
{ {
Name = "changeLanguage", Name = "changeLanguage",
Text = Program.Translate("Language") Text = Language.Translate("Language")
}; };
foreach (CultureInfo cultureInfo in foreach (CultureInfo cultureInfo in
GetCultureList(CultureTypes.AllCultures)) GetCultureList(CultureTypes.AllCultures))
{ {
if (Program.Languages.Contains(cultureInfo.Name)) if (MenuDefines.Languages.Contains(cultureInfo.Name))
{ {
ToolStripItem language = changeLanguage.DropDownItems. ToolStripItem language = changeLanguage.DropDownItems.
Add(Program.Translate(cultureInfo.EnglishName)); Add(Language.Translate(cultureInfo.EnglishName));
language.Click += Language_Click; language.Click += Language_Click;
void Language_Click(object sender, EventArgs e) void Language_Click(object sender, EventArgs e)
{ {
@ -64,7 +65,7 @@ namespace SystemTrayMenu.Controls
menu.Items.Add(changeLanguage); menu.Items.Add(changeLanguage);
ToolStripMenuItem autostart = new ToolStripMenuItem(); ToolStripMenuItem autostart = new ToolStripMenuItem();
autostart.Text = Program.Translate("Autostart"); autostart.Text = Language.Translate("Autostart");
//autostart.Image.HorizontalResolution.wi.c.sc.Select .ImageScaling = ToolStripItemImageScaling.None; //autostart.Image.HorizontalResolution.wi.c.sc.Select .ImageScaling = ToolStripItemImageScaling.None;
if (Properties.Settings.Default.IsAutostartActivated) if (Properties.Settings.Default.IsAutostartActivated)
{ {
@ -106,8 +107,8 @@ namespace SystemTrayMenu.Controls
ToolStripMenuItem hotKey = new ToolStripMenuItem(); ToolStripMenuItem hotKey = new ToolStripMenuItem();
string hotKeyText = string hotKeyText =
$"{Program.Translate("CTRL")} + " + $"{Language.Translate("CTRL")} + " +
$"{Program.Translate("ALT")} + "; $"{Language.Translate("ALT")} + ";
hotKey.ImageScaling = ToolStripItemImageScaling.SizeToFit; hotKey.ImageScaling = ToolStripItemImageScaling.SizeToFit;
if (string.IsNullOrEmpty(Properties.Settings.Default.HotKey)) if (string.IsNullOrEmpty(Properties.Settings.Default.HotKey))
@ -141,7 +142,7 @@ namespace SystemTrayMenu.Controls
menu.Items.Add(seperator); menu.Items.Add(seperator);
ToolStripMenuItem openLog = new ToolStripMenuItem(); ToolStripMenuItem openLog = new ToolStripMenuItem();
openLog.Text = Program.Translate("Log File"); openLog.Text = Language.Translate("Log File");
openLog.Click += OpenLog_Click; openLog.Click += OpenLog_Click;
void OpenLog_Click(object sender, EventArgs e) void OpenLog_Click(object sender, EventArgs e)
{ {
@ -152,7 +153,7 @@ namespace SystemTrayMenu.Controls
menu.Items.Add(new ToolStripSeparator()); menu.Items.Add(new ToolStripSeparator());
ToolStripMenuItem about = new ToolStripMenuItem(); ToolStripMenuItem about = new ToolStripMenuItem();
about.Text = Program.Translate("About"); about.Text = Language.Translate("About");
about.Click += About_Click; about.Click += About_Click;
void About_Click(object sender, EventArgs e) void About_Click(object sender, EventArgs e)
{ {
@ -184,7 +185,7 @@ namespace SystemTrayMenu.Controls
menu.Items.Add(new ToolStripSeparator()); menu.Items.Add(new ToolStripSeparator());
ToolStripMenuItem restart = new ToolStripMenuItem(); ToolStripMenuItem restart = new ToolStripMenuItem();
restart.Text = Program.Translate("Restart"); restart.Text = Language.Translate("Restart");
restart.Click += Restart_Click; restart.Click += Restart_Click;
void Restart_Click(object sender, EventArgs e) void Restart_Click(object sender, EventArgs e)
{ {
@ -193,7 +194,7 @@ namespace SystemTrayMenu.Controls
menu.Items.Add(restart); menu.Items.Add(restart);
ToolStripMenuItem exit = new ToolStripMenuItem(); ToolStripMenuItem exit = new ToolStripMenuItem();
exit.Text = Program.Translate("Exit"); exit.Text = Language.Translate("Exit");
exit.Click += Exit_Click; exit.Click += Exit_Click;
void Exit_Click(object sender, EventArgs e) void Exit_Click(object sender, EventArgs e)
{ {
@ -227,7 +228,7 @@ namespace SystemTrayMenu.Controls
public static Bitmap ResizeImage(Image image) public static Bitmap ResizeImage(Image image)
{ {
int length = (int)Math.Round( int length = (int)Math.Round(
16 * Program.ScalingFactor, 0, 16 * Scaling.Factor, 0,
MidpointRounding.AwayFromZero); MidpointRounding.AwayFromZero);
return ResizeImage(image, length, length); return ResizeImage(image, length, length);
} }

View file

@ -1,5 +1,6 @@
using System; using System;
using System.Windows.Forms; using System.Windows.Forms;
using SystemTrayMenu.Helper;
namespace SystemTrayMenu.Controls namespace SystemTrayMenu.Controls
{ {
@ -10,14 +11,14 @@ namespace SystemTrayMenu.Controls
public AskHotKeyForm() public AskHotKeyForm()
{ {
InitializeComponent(); InitializeComponent();
this.Text = Program.Translate("Shortcut key"); this.Text = Language.Translate("Shortcut key");
this.labelCaption.Text = $"{Program.Translate("Shortcut key")} " + this.labelCaption.Text = $"{Language.Translate("Shortcut key")} " +
$"{Program.Translate("(e.g. F10)")}"; $"{Language.Translate("(e.g. F10)")}";
this.labelText.Text = this.labelText.Text =
Program.Translate("CTRL") + " + " + Language.Translate("CTRL") + " + " +
Program.Translate("ALT") + " + ?"; Language.Translate("ALT") + " + ?";
this.buttonOk.Text = Program.Translate("buttonOk"); this.buttonOk.Text = Language.Translate("buttonOk");
} }
private void ButtonOk_Click(object sender, EventArgs e) private void ButtonOk_Click(object sender, EventArgs e)

View file

@ -91,11 +91,11 @@ namespace SystemTrayMenu
} }
break; break;
case Type.Empty: case Type.Empty:
SetTitle(Program.Translate("Folder empty")); SetTitle(Language.Translate("Folder empty"));
labelTitle.BackColor = MenuDefines.Background; labelTitle.BackColor = MenuDefines.Background;
break; break;
case Type.NoAccess: case Type.NoAccess:
SetTitle(Program.Translate("Folder inaccessible")); SetTitle(Language.Translate("Folder inaccessible"));
labelTitle.BackColor = MenuDefines.Background; labelTitle.BackColor = MenuDefines.Background;
break; break;
case Type.MaxReached: case Type.MaxReached:
@ -195,7 +195,7 @@ namespace SystemTrayMenu
AdjustDataGridViewSize(); AdjustDataGridViewSize();
int x = menuPredecessor.Location.X - Width + int x = menuPredecessor.Location.X - Width +
(int)Math.Round(Program.ScalingFactor, 0, (int)Math.Round(Scaling.Factor, 0,
MidpointRounding.AwayFromZero); MidpointRounding.AwayFromZero);
RowData trigger = (RowData)Tag; RowData trigger = (RowData)Tag;

View file

@ -1,5 +1,4 @@
using Clearcove.Logging; using IWshRuntimeLibrary;
using IWshRuntimeLibrary;
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.ComponentModel; using System.ComponentModel;
@ -48,15 +47,11 @@ namespace SystemTrayMenu.Controls
{ {
bool isLnkDirectory = false; bool isLnkDirectory = false;
Logger log = new Logger(nameof(RowData));
if (string.IsNullOrEmpty(TargetFilePath)) if (string.IsNullOrEmpty(TargetFilePath))
{ {
log.Warn($"ReadIcon called but TargetFilePath not set."); Log.Info($"TargetFilePath from {resolvedLnkPath} empty");
return isLnkDirectory;
} }
else if (isDirectory)
if (isDirectory)
{ {
Icon = IconReader.GetFolderIcon(TargetFilePath, Icon = IconReader.GetFolderIcon(TargetFilePath,
IconReader.FolderType.Closed, false); IconReader.FolderType.Closed, false);
@ -68,16 +63,16 @@ namespace SystemTrayMenu.Controls
if (fileExtension == ".lnk") if (fileExtension == ".lnk")
{ {
handled = SetLnk(log, ref isLnkDirectory, handled = SetLnk(ref isLnkDirectory,
ref resolvedLnkPath); ref resolvedLnkPath);
} }
else if (fileExtension == ".url") else if (fileExtension == ".url")
{ {
handled = SetUrl(log); handled = SetUrl();
} }
else if (fileExtension == ".sln") else if (fileExtension == ".sln")
{ {
handled = SetSln(log); handled = SetSln();
} }
if (!handled) if (!handled)
@ -98,8 +93,7 @@ namespace SystemTrayMenu.Controls
} }
catch (Exception ex) catch (Exception ex)
{ {
log.Info($"TargetFilePath:'{TargetFilePath}'"); Log.Error($"TargetFilePath:'{TargetFilePath}'", ex);
log.Error($"{ex.ToString()}");
} }
} }
} }
@ -107,7 +101,7 @@ namespace SystemTrayMenu.Controls
return isLnkDirectory; return isLnkDirectory;
} }
private bool SetLnk(Logger log, ref bool isLnkDirectory, private bool SetLnk(ref bool isLnkDirectory,
ref string resolvedLnkPath) ref string resolvedLnkPath)
{ {
bool handled = false; bool handled = false;
@ -122,7 +116,8 @@ namespace SystemTrayMenu.Controls
else if (string.IsNullOrEmpty(resolvedLnkPath)) else if (string.IsNullOrEmpty(resolvedLnkPath))
{ {
ResolvedFileNotFound = true; ResolvedFileNotFound = true;
log.Info($"Resolve '{TargetFilePath}' not possible => no icon"); Log.Info($"Resolve *.Lnk '{TargetFilePath}' empty => no icon");
#warning [Feature] Resolve network root #48, start here
} }
else else
{ {
@ -145,8 +140,7 @@ namespace SystemTrayMenu.Controls
} }
catch (Exception ex) catch (Exception ex)
{ {
log.Info($"iconLocation:'{iconLocation}'"); Log.Error($"iconLocation:'{iconLocation}'", ex);
log.Error($"{ex.ToString()}");
} }
} }
} }
@ -159,7 +153,7 @@ namespace SystemTrayMenu.Controls
return handled; return handled;
} }
private bool SetUrl(Logger log) private bool SetUrl()
{ {
bool handled = false; bool handled = false;
string iconFile = string.Empty; string iconFile = string.Empty;
@ -172,7 +166,7 @@ namespace SystemTrayMenu.Controls
string browserPath = FileUrl.GetDefaultBrowserPath(); string browserPath = FileUrl.GetDefaultBrowserPath();
if (string.IsNullOrEmpty(browserPath)) if (string.IsNullOrEmpty(browserPath))
{ {
log.Info($"No default browser found!"); Log.Info($"No default browser found!");
} }
else else
{ {
@ -187,14 +181,13 @@ namespace SystemTrayMenu.Controls
} }
else else
{ {
log.Info($"Resolve '{TargetFilePath}' not possible => no icon"); Log.Info($"Resolve *.URL '{TargetFilePath}' not possible => no icon");
} }
} }
catch (Exception ex) catch (Exception ex)
{ {
log.Info($"TargetFilePath:'{TargetFilePath}', " + Log.Error($"TargetFilePath:'{TargetFilePath}', " +
$"iconFile:'{iconFile}'"); $"iconFile:'{iconFile}'", ex);
log.Error($"{ex.ToString()}");
} }
SetText($"{FileInfo.Name.Substring(0, FileInfo.Name.Length - 4)}"); SetText($"{FileInfo.Name.Substring(0, FileInfo.Name.Length - 4)}");
@ -204,7 +197,7 @@ namespace SystemTrayMenu.Controls
[DllImport("shell32.dll")] [DllImport("shell32.dll")]
static extern int FindExecutable(string lpFile, string lpDirectory, [Out] StringBuilder lpResult); static extern int FindExecutable(string lpFile, string lpDirectory, [Out] StringBuilder lpResult);
private bool SetSln(Logger log) private bool SetSln()
{ {
bool handled = false; bool handled = false;
var executable = new StringBuilder(1024); var executable = new StringBuilder(1024);
@ -220,9 +213,8 @@ namespace SystemTrayMenu.Controls
} }
catch (Exception ex) catch (Exception ex)
{ {
log.Info($"TargetFilePath:'{TargetFilePath}', " + Log.Error($"TargetFilePath:'{TargetFilePath}', " +
$"executable:'{executable.ToString()}'"); $"executable:'{executable.ToString()}'",ex);
log.Error($"{ex.ToString()}");
} }
return handled; return handled;
@ -239,7 +231,7 @@ namespace SystemTrayMenu.Controls
} }
#warning sort this class and check for duplicated #warning CodeBuity&Refactor #49 - sort this class and check for duplicated
public event Action<object, EventArgs> OpenMenu; public event Action<object, EventArgs> OpenMenu;
@ -253,10 +245,8 @@ namespace SystemTrayMenu.Controls
// FontStyle.Regular, GraphicsUnit.Pixel); // FontStyle.Regular, GraphicsUnit.Pixel);
WaitMenuOpen waitMenuOpen = new WaitMenuOpen(); WaitMenuOpen waitMenuOpen = new WaitMenuOpen();
bool resolvedFileNotFound = false;
bool disposed = false; bool disposed = false;
Logger log = new Logger(nameof(RowData));
internal string TargetFilePathOrig; internal string TargetFilePathOrig;
internal bool HiddenEntry; internal bool HiddenEntry;
@ -322,9 +312,8 @@ namespace SystemTrayMenu.Controls
} }
catch (Exception ex) catch (Exception ex)
{ {
log.Info($"TargetFilePath:'{TargetFilePath}', " + Log.Error($"TargetFilePath:'{TargetFilePath}', " +
$"=>DirectoryNotFound?"); $"=>DirectoryNotFound?", ex);
log.Error($"{ex.ToString()}");
ex = new DirectoryNotFoundException(); ex = new DirectoryNotFoundException();
MessageBox.Show(ex.Message); MessageBox.Show(ex.Message);
} }
@ -360,13 +349,8 @@ namespace SystemTrayMenu.Controls
} }
catch (Exception ex) catch (Exception ex)
{ {
log.Info($"TargetFilePath:'{ TargetFilePath}', " + Log.Error($"TargetFilePath:'{ TargetFilePath}', " +
$"=>FileNotFound?"); $"=>FileNotFound?", ex);
log.Error($"{ex.ToString()}");
if (resolvedFileNotFound)
{
ex = new FileNotFoundException();
}
MessageBox.Show(ex.Message); MessageBox.Show(ex.Message);
} }
} }
@ -378,7 +362,7 @@ namespace SystemTrayMenu.Controls
{ {
IsContextMenuOpen = true; IsContextMenuOpen = true;
#warning is there any other possiblity to raise selection changed event? dataGridView.ClearSelection(); seems to overwrite selected #warning CodeBuity&Refactor #49 is there any other possiblity to raise selection changed event? dataGridView.ClearSelection(); seems to overwrite selected
IsSelected = true; IsSelected = true;
dgv.Rows[RowIndex].Selected = true; dgv.Rows[RowIndex].Selected = true;
@ -482,7 +466,7 @@ namespace SystemTrayMenu.Controls
row.Tag = data; row.Tag = data;
} }
#warning either not public and as inline method or we want probably to move that code somewhere else #warning CodeBuity&Refactor #49 either not public and as inline method or we want probably to move that code somewhere else
public Icon AddIconOverlay(Icon originalIcon, Icon overlay) public Icon AddIconOverlay(Icon originalIcon, Icon overlay)
{ {
var target = new Bitmap(originalIcon.Width, originalIcon.Height, PixelFormat.Format32bppArgb); var target = new Bitmap(originalIcon.Width, originalIcon.Height, PixelFormat.Format32bppArgb);

View file

@ -1,5 +1,4 @@
using Clearcove.Logging; using System;
using System;
using System.Linq; using System.Linq;
using System.Windows.Forms; using System.Windows.Forms;
using SystemTrayMenu.Controls; using SystemTrayMenu.Controls;
@ -15,7 +14,6 @@ namespace SystemTrayMenu.Handler
public Action<int, int, DataGridView> RowDeselected; public Action<int, int, DataGridView> RowDeselected;
public event EventHandler Cleared; public event EventHandler Cleared;
Logger log = new Logger(nameof(KeyboardInput));
private Menu[] menus; private Menu[] menus;
KeyboardHook hook = new KeyboardHook(); KeyboardHook hook = new KeyboardHook();
@ -66,8 +64,7 @@ namespace SystemTrayMenu.Handler
} }
catch (Exception ex) catch (Exception ex)
{ {
log.Info($"key:'{key.ToString()}'"); Log.Error($"key:'{key.ToString()}'", ex);
log.Error($"{ex.ToString()}");
Properties.Settings.Default.HotKey = string.Empty; Properties.Settings.Default.HotKey = string.Empty;
Properties.Settings.Default.Save(); Properties.Settings.Default.Save();
MessageBox.Show(ex.Message); MessageBox.Show(ex.Message);
@ -126,14 +123,6 @@ namespace SystemTrayMenu.Handler
} }
} }
internal bool IsAnyMenuSelectedByKey()
{
Menu menu = null;
DataGridView dgv = null;
string textselected = string.Empty;
return IsAnyMenuSelectedByKey(ref dgv, ref menu, ref textselected);
}
private bool IsAnyMenuSelectedByKey( private bool IsAnyMenuSelectedByKey(
ref DataGridView dgv, ref DataGridView dgv,
ref Menu menuFromSelected, ref Menu menuFromSelected,
@ -153,7 +142,7 @@ namespace SystemTrayMenu.Handler
{ {
isStillSelected = true; isStillSelected = true;
menuFromSelected = rowData.SubMenu; menuFromSelected = rowData.SubMenu;
#warning refactor datagridviewrow get #warning CodeBuity&Refactor #49 refactor datagridviewrow get
textselected = dgv.Rows[iRowKey]. textselected = dgv.Rows[iRowKey].
Cells[1].Value.ToString(); Cells[1].Value.ToString();
} }
@ -260,11 +249,6 @@ namespace SystemTrayMenu.Handler
toClear = true; toClear = true;
} }
} }
else
{
log.Info("indexMenuByKey = menus.Where(m => m != null).Count()" +
"=> menus[iMenuKey] == null");
}
} }
break; break;
case Keys.Right: case Keys.Right:

View file

@ -1,5 +1,4 @@
using Clearcove.Logging; using System;
using System;
using System.Runtime.InteropServices; using System.Runtime.InteropServices;
using System.Windows.Forms; using System.Windows.Forms;
@ -90,13 +89,8 @@ namespace SystemTrayMenu
timerFadeHalf.Stop(); timerFadeHalf.Stop();
timerFadeIn.Start(); timerFadeIn.Start();
} }
#warning #35 [BUG] Rare ObjectDisposedException, todo: fix root cause //see #35 [BUG], from late mouse events
else if (form.IsDisposed) else if (!form.IsDisposed)
{
new Logger(nameof(FadeForm)).Warn(
$"{Environment.StackTrace.ToString()}");
}
else
{ {
ShowInactiveTopmost(form); ShowInactiveTopmost(form);
timerFadeOut.Stop(); timerFadeOut.Stop();

View file

@ -136,9 +136,7 @@ namespace SystemTrayMenu.Helper
} }
catch (Exception ex) catch (Exception ex)
{ {
Logger log = new Logger(nameof(IconReader)); Log.Error($"filePath:'{filePath}'", ex);
log.Info($"filePath:'{filePath}'");
log.Error($"{ex.ToString()}");
} }
// Cleanup // Cleanup
@ -196,9 +194,7 @@ namespace SystemTrayMenu.Helper
} }
catch (Exception ex) catch (Exception ex)
{ {
Logger log = new Logger(nameof(IconReader)); Log.Error($"directoryPath:'{directoryPath}'", ex);
log.Info($"directoryPath:'{directoryPath}'");
log.Error($"{ex.ToString()}");
} }
// Cleanup // Cleanup

46
Helper/Language.cs Normal file
View file

@ -0,0 +1,46 @@
using System.Globalization;
using System.Resources;
using System.Threading;
using SystemTrayMenu.Properties;
namespace SystemTrayMenu.Helper
{
internal static class Language
{
internal static CultureInfo Culture;
internal static void Initialize()
{
if (string.IsNullOrEmpty(
Settings.Default.CurrentCultureInfoName))
{
Settings.Default.CurrentCultureInfoName = "en";
CultureInfo currentCulture =
Thread.CurrentThread.CurrentCulture;
foreach (string language in MenuDefines.Languages)
{
string twoLetter = currentCulture.Name.
Substring(0, 2);
if (language == currentCulture.Name ||
language == twoLetter)
{
Settings.Default.
CurrentCultureInfoName = language;
}
}
Settings.Default.Save();
}
Culture = CultureInfo.CreateSpecificCulture(
Settings.Default.CurrentCultureInfoName);
}
internal static string Translate(string id)
{
ResourceManager rm = new ResourceManager(
"SystemTrayMenu.Resources.lang",
typeof(Menu).Assembly);
return rm.GetString(id, Culture);
}
}
}

54
Helper/Log.cs Normal file
View file

@ -0,0 +1,54 @@
using Clearcove.Logging;
using System;
using System.Diagnostics;
using System.IO;
using System.Reflection;
namespace SystemTrayMenu.Helper
{
internal static class Log
{
static Logger log = new Logger("");
internal static void Initialize()
{
Logger.Start(new FileInfo(GetLogFilePath()));
}
internal static void Info(string message)
{
log.Info(message);
}
internal static void Warn(string message)
{
log.Warn($"{message}{Environment.NewLine}" +
$"{Environment.StackTrace.ToString()}");
}
internal static void Error(string message, Exception ex)
{
log.Error($"{message}{Environment.NewLine}" +
$"{ex.ToString()}");
}
internal static string GetLogFilePath()
{
return Path.Combine(Path.GetDirectoryName(
Assembly.GetExecutingAssembly().Location),
$"log-{Environment.MachineName}.txt");
}
internal static void OpenLogFile()
{
Process.Start(GetLogFilePath());
}
internal static void ApplicationStart()
{
Assembly assembly = Assembly.GetExecutingAssembly();
log.Info($"Application Start " +
assembly.ManifestModule.FullyQualifiedName + "|" +
assembly.GetName().Version.ToString() + "|" +
$" ScalingFactor={Scaling.Factor}");
}
}
}

47
Helper/Scaling.cs Normal file
View file

@ -0,0 +1,47 @@
using System;
using System.Drawing;
using System.Runtime.InteropServices;
namespace SystemTrayMenu.Helper
{
internal static class Scaling
{
internal static float Factor = 1;
internal static void Initialize()
{
CalculateScalingFactor();
SetProcessDPIAwareWhenNecessary();
}
[DllImport("gdi32.dll")]
static extern int GetDeviceCaps(IntPtr hdc, int nIndex);
enum DeviceCap
{
VERTRES = 10,
DESKTOPVERTRES = 117,
// http://pinvoke.net/default.aspx/gdi32/GetDeviceCaps.html
}
static void CalculateScalingFactor()
{
Graphics g = Graphics.FromHwnd(IntPtr.Zero);
IntPtr desktop = g.GetHdc();
int LogicalScreenHeight = GetDeviceCaps(desktop, (int)DeviceCap.VERTRES);
int PhysicalScreenHeight = GetDeviceCaps(desktop, (int)DeviceCap.DESKTOPVERTRES);
Factor = (float)PhysicalScreenHeight / (float)LogicalScreenHeight; // 1.25 = 125%
}
[DllImport("user32.dll")]
static extern bool SetProcessDPIAware();
static void SetProcessDPIAwareWhenNecessary()
{
if (Environment.OSVersion.Version.Major >= 6)
{
SetProcessDPIAware();
}
}
}
}

View file

@ -0,0 +1,55 @@
using Clearcove.Logging;
using System;
using System.Diagnostics;
using System.Linq;
namespace SystemTrayMenu.Helper
{
internal static class SingleAppInstance
{
internal static void Initialize()
{
Logger log = new Logger(nameof(SingleAppInstance));
if (IsAnyOtherInstancesofAppAlreadyRunning())
{
KillOtherInstancesOfApp();
bool KillOtherInstancesOfApp()
{
bool killedAProcess = false;
int ownPID = Process.GetCurrentProcess().Id;
try
{
foreach (Process p in Process.GetProcessesByName(
Process.GetCurrentProcess().ProcessName).
Where(p => p.Id != ownPID))
{
p.Kill();
p.WaitForExit();
killedAProcess = true;
}
}
catch (Exception exception)
{
log.Warn($"{exception.ToString()}");
}
return killedAProcess;
}
}
bool IsAnyOtherInstancesofAppAlreadyRunning()
{
//string pid = Process.Id.ToString();
foreach (Process p in Process.GetProcessesByName(
Process.GetCurrentProcess().ProcessName).
Where(s => s.Id != Process.GetCurrentProcess().Id))
{
return true;
}
return false;
}
}
}
}

View file

@ -1,9 +1,13 @@
using System.Drawing; using System.Collections.Generic;
using System.Drawing;
namespace SystemTrayMenu namespace SystemTrayMenu
{ {
public static class MenuDefines public static class MenuDefines
{ {
public static readonly List<string> Languages =
new List<string>() { "en", "de" };
// windows explorer background white // windows explorer background white
public static Color File = Color.White; public static Color File = Color.White;
public static Color Folder = Color.White; public static Color Folder = Color.White;

View file

@ -1,197 +1,74 @@
using Clearcove.Logging; using Clearcove.Logging;
using System; using System;
using System.Collections.Generic;
using System.Diagnostics; using System.Diagnostics;
using System.Drawing;
using System.Globalization;
using System.IO;
using System.Linq;
using System.Reflection; using System.Reflection;
using System.Resources;
using System.Runtime.InteropServices;
using System.Threading; using System.Threading;
using System.Windows.Forms; using System.Windows.Forms;
using SystemTrayMenu.Helper;
namespace SystemTrayMenu namespace SystemTrayMenu
{ {
static class Program static class Program
{ {
public static readonly List<string> Languages =
new List<string>() { "en", "de" };
public static CultureInfo Culture;
public static float ScalingFactor = 1;
private const string IconDir = "Icons\\";
[System.Runtime.InteropServices.DllImport("user32.dll")]
private static extern bool SetProcessDPIAware();
/// <summary>
/// The main entry point for the application.
/// </summary>
[STAThread] [STAThread]
static void Main() static void Main()
{ {
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Logger log = new Logger(nameof(Program));
Logger.Start(new FileInfo(GetLogFilePath()));
if (IsAppAlreadyRunning("SystemTrayMenu"))
{
KillOtherSystemTrayMenus();
}
GetDefaultLanguage();
ScalingFactor = GetScalingFactor();
if (Environment.OSVersion.Version.Major >= 6)
{
SetProcessDPIAware();
}
try try
{ {
bool cancelAppRun = false; Log.Initialize();
using (new SystemTrayMenu(ref cancelAppRun)) SingleAppInstance.Initialize();
Language.Initialize();
if (Config.LoadOrSetByUser())
{ {
if (!cancelAppRun) Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.ThreadException += ThreadException;
void ThreadException(object s, ThreadExceptionEventArgs t)
{
AskUserSendError(t.Exception);
}
Scaling.Initialize();
using (new SystemTrayMenu())
{ {
Application.ThreadException += Application_ThreadException;
void Application_ThreadException(object sender, ThreadExceptionEventArgs threadException)
{
AskUserSendErrorAndRestartApp(log, threadException.Exception);
}
Application.Run(); Application.Run();
} }
} }
} }
catch (Exception ex) catch (Exception ex)
{ {
AskUserSendErrorAndRestartApp(log, ex); AskUserSendError(ex);
} }
finally finally
{ {
Logger.ShutDown(); Logger.ShutDown();
} }
void AskUserSendError(Exception ex)
{
Log.Error("Application Crashed", ex);
#warning [Feature] When Error ask user to send us #47, todo own dialog, lines here too long
if (MessageBox.Show("A problem has been encountered and the application needs to restart. " +
"Reporting this error will help us make our product better. Press yes to open your standard email app.",
"SystemTrayMenu BugSplat", MessageBoxButtons.YesNo) == DialogResult.Yes)
{
Process.Start("mailto:" + "markus@hofknecht.eu" +
"?subject=SystemTrayMenu Bug reported" +
"&body=" + ex.ToString());
}
Logger.ShutDown();
Restart();
}
} }
static void AskUserSendErrorAndRestartApp(Logger log, Exception exception) internal static void Restart()
{ {
log.Error($"{exception.ToString()}");
if (MessageBox.Show("A problem has been encountered and the application needs to restart. " +
"Reporting this error will help us make our product better. Press yes to open your standard email app.",
"SystemTrayMenu BugSplat", MessageBoxButtons.YesNo) == DialogResult.Yes)
{
Process.Start("mailto:" + "markus@hofknecht.eu" +
"?subject=SystemTrayMenu Bug reported" +
"&body=" + exception.ToString());
}
Logger.ShutDown();
Process.Start(Assembly.GetExecutingAssembly(). Process.Start(Assembly.GetExecutingAssembly().
ManifestModule.FullyQualifiedName); ManifestModule.FullyQualifiedName);
} }
static bool KillOtherSystemTrayMenus()
{
bool killedAProcess = false;
int ownPID = Process.GetCurrentProcess().Id;
try
{
foreach (Process p in
Process.GetProcessesByName("SystemTrayMenu").
Where(p => p.Id != ownPID))
{
p.Kill();
p.WaitForExit();
killedAProcess = true;
}
}
catch (Exception exception)
{
Logger log = new Logger(nameof(Program));
log.Warn($"{exception.ToString()}");
}
return killedAProcess;
}
static bool IsAppAlreadyRunning(string processName)
{
foreach (Process p in Process.GetProcessesByName(processName).
Where(s => s.Id != Process.GetCurrentProcess().Id))
{
return true;
}
return false;
}
internal static string GetLogFilePath()
{
return Path.Combine(Path.GetDirectoryName(
System.Reflection.Assembly.GetExecutingAssembly().Location),
$"log-{System.Environment.MachineName}.txt");
}
private static void GetDefaultLanguage()
{
if (string.IsNullOrEmpty(Properties.Settings.Default.
CurrentCultureInfoName))
{
Properties.Settings.Default.CurrentCultureInfoName = "en";
CultureInfo currentCulture = Thread.CurrentThread.
CurrentCulture;
foreach (string language in Languages)
{
string twoLetter = currentCulture.Name.Substring(0, 2);
if (language == currentCulture.Name ||
language == twoLetter)
{
Properties.Settings.Default.CurrentCultureInfoName =
language;
}
}
Properties.Settings.Default.Save();
}
Culture = CultureInfo.CreateSpecificCulture(
Properties.Settings.Default.CurrentCultureInfoName);
}
[DllImport("gdi32.dll")]
static extern int GetDeviceCaps(IntPtr hdc, int nIndex);
public enum DeviceCap
{
VERTRES = 10,
DESKTOPVERTRES = 117,
// http://pinvoke.net/default.aspx/gdi32/GetDeviceCaps.html
}
static float GetScalingFactor()
{
Graphics g = Graphics.FromHwnd(IntPtr.Zero);
IntPtr desktop = g.GetHdc();
int LogicalScreenHeight = GetDeviceCaps(desktop, (int)DeviceCap.VERTRES);
int PhysicalScreenHeight = GetDeviceCaps(desktop, (int)DeviceCap.DESKTOPVERTRES);
float ScreenScalingFactor = (float)PhysicalScreenHeight / (float)LogicalScreenHeight;
return ScreenScalingFactor; // 1.25 = 125%
}
internal static string Translate(string id)
{
ResourceManager rm = new ResourceManager(
"SystemTrayMenu.Resources.lang",
typeof(Menu).Assembly);
return rm.GetString(id, Culture);
}
} }
} }

View file

@ -31,5 +31,5 @@ using System.Runtime.InteropServices;
// You can specify all the values or you can default the Build and Revision Numbers // You can specify all the values or you can default the Build and Revision Numbers
// by using the '*' as shown below: // by using the '*' as shown below:
// [assembly: AssemblyVersion("1.0.*")] // [assembly: AssemblyVersion("1.0.*")]
[assembly: AssemblyVersion("0.9.2.2")] [assembly: AssemblyVersion("0.9.2.3")]
[assembly: AssemblyFileVersion("0.9.2.2")] [assembly: AssemblyFileVersion("0.9.2.3")]

View file

@ -7,7 +7,6 @@ using System.Diagnostics;
using System.Drawing; using System.Drawing;
using System.IO; using System.IO;
using System.Linq; using System.Linq;
using System.Reflection;
using System.Windows.Forms; using System.Windows.Forms;
using SystemTrayMenu.Controls; using SystemTrayMenu.Controls;
using SystemTrayMenu.Handler; using SystemTrayMenu.Handler;
@ -42,12 +41,9 @@ namespace SystemTrayMenu
DataGridView dgvFromLastMouseEvent = null; DataGridView dgvFromLastMouseEvent = null;
DataGridViewCellEventArgs cellEventArgsFromLastMouseEvent = null; DataGridViewCellEventArgs cellEventArgsFromLastMouseEvent = null;
public SystemTrayMenu(ref bool cancelAppRun) public SystemTrayMenu()
{ {
log.Info("Application Start " + Log.ApplicationStart();
Assembly.GetExecutingAssembly().
GetName().Version.ToString() +
$" ScalingFactor={Program.ScalingFactor}");
try try
{ {
@ -120,9 +116,9 @@ namespace SystemTrayMenu
//if (!IsNotifyIconInTaskbar()) //if (!IsNotifyIconInTaskbar())
//{ //{
// //DragDropHintForm hintForm = new DragDropHintForm( // //DragDropHintForm hintForm = new DragDropHintForm(
// // Program.Translate("HintDragDropTitle"), // // Language.Translate("HintDragDropTitle"),
// // Program.Translate("HintDragDropText"), // // Language.Translate("HintDragDropText"),
// // Program.Translate("buttonOk")); // // Language.Translate("buttonOk"));
// //hintForm.Show(); // //hintForm.Show();
//} //}
#endregion #endregion
@ -179,6 +175,7 @@ namespace SystemTrayMenu
WindowToTop.ForceForegroundWindow(menus[0].Handle); WindowToTop.ForceForegroundWindow(menus[0].Handle);
} }
menuNotifyIcon.OpenLog += Log.OpenLogFile;
menuNotifyIcon.ChangeFolder += ChangeFolder; menuNotifyIcon.ChangeFolder += ChangeFolder;
void ChangeFolder() void ChangeFolder()
{ {
@ -188,12 +185,6 @@ namespace SystemTrayMenu
} }
} }
menuNotifyIcon.OpenLog += OpenLog;
void OpenLog()
{
Process.Start(Program.GetLogFilePath());
}
Microsoft.Win32.SystemEvents.DisplaySettingsChanged += SystemEvents_DisplaySettingsChanged; Microsoft.Win32.SystemEvents.DisplaySettingsChanged += SystemEvents_DisplaySettingsChanged;
void SystemEvents_DisplaySettingsChanged(object sender, EventArgs e) void SystemEvents_DisplaySettingsChanged(object sender, EventArgs e)
{ {
@ -205,8 +196,7 @@ namespace SystemTrayMenu
void ApplicationRestart() void ApplicationRestart()
{ {
Dispose(); Dispose();
Process.Start(Assembly.GetExecutingAssembly(). Program.Restart();
ManifestModule.FullyQualifiedName);
} }
messageFilter.MouseMove += FadeInIfNeeded; messageFilter.MouseMove += FadeInIfNeeded;
@ -231,11 +221,6 @@ namespace SystemTrayMenu
messageFilter.MouseLeave += fastLeave.Start; messageFilter.MouseLeave += fastLeave.Start;
fastLeave.Leave += FadeHalfOrOutIfNeeded; fastLeave.Leave += FadeHalfOrOutIfNeeded;
if (!Config.LoadOrSetByUser())
{
cancelAppRun = true;
}
} }
void FadeInIfNeeded() void FadeInIfNeeded()
@ -327,7 +312,7 @@ namespace SystemTrayMenu
int newWith = (menu.Width - 2 + menuPredecessor.Width); int newWith = (menu.Width - 2 + menuPredecessor.Width);
if (directionToRight) if (directionToRight)
{ {
#warning is this still correct? #warning CodeBuity&Refactor #49 is this still correct?
if (widthPredecessors - menu.Width <= -2) // -1*2 padding if (widthPredecessors - menu.Width <= -2) // -1*2 padding
{ {
directionToRight = false; directionToRight = false;

View file

@ -165,7 +165,11 @@
<Compile Include="Helper\File\FileIni.cs" /> <Compile Include="Helper\File\FileIni.cs" />
<Compile Include="Helper\File\FileLnk.cs" /> <Compile Include="Helper\File\FileLnk.cs" />
<Compile Include="Helper\KeyboardHook.cs" /> <Compile Include="Helper\KeyboardHook.cs" />
<Compile Include="Helper\Log.cs" />
<Compile Include="Helper\SingleAppInstance.cs" />
<Compile Include="Helper\MessageFilter.cs" /> <Compile Include="Helper\MessageFilter.cs" />
<Compile Include="Helper\Language.cs" />
<Compile Include="Helper\Scaling.cs" />
<Compile Include="Helper\ShellContextMenu.cs" /> <Compile Include="Helper\ShellContextMenu.cs" />
<Compile Include="Helper\File\FileUrl.cs" /> <Compile Include="Helper\File\FileUrl.cs" />
<Compile Include="Handler\WaitFastLeave.cs" /> <Compile Include="Handler\WaitFastLeave.cs" />