-
Notifications
You must be signed in to change notification settings - Fork 4
/
AboutBox.cs
171 lines (144 loc) · 4.3 KB
/
AboutBox.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
namespace Menees.Windows.Forms
{
#region Using Directives
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Reflection;
using System.Runtime.InteropServices;
using System.Text;
using System.Windows.Forms;
using Menees.Diagnostics;
using Menees.Shell;
#endregion
internal partial class AboutBox : ExtendedForm
{
#region Private Data Members
private readonly Assembly callingAssembly;
private readonly string repository;
#endregion
#region Constructors
public AboutBox(Assembly callingAssembly, string? repository)
{
this.InitializeComponent();
this.callingAssembly = callingAssembly;
this.repository = repository ?? ApplicationInfo.ApplicationName.Replace(" ", string.Empty);
string applicationName = ApplicationInfo.ApplicationName;
this.Text = "About " + applicationName;
this.productName.Text = applicationName;
this.version.Text = ShellUtility.GetVersionInfo(callingAssembly);
this.copyright.Text = ShellUtility.GetCopyrightInfo(callingAssembly);
}
#endregion
#region Public Methods
public void Execute(IWin32Window? owner)
{
bool useDesktopAsOwner = owner == null;
if (owner is Control control)
{
Form form = control.FindForm();
if (form != null)
{
this.icon.Image = form.Icon.ToBitmap();
// This is important for tray icon apps where the main form may be hidden.
useDesktopAsOwner = !form.Visible;
}
else
{
useDesktopAsOwner = true;
}
}
else if (owner != null)
{
// We should only get here for a WPF app or an unmanaged app.
// From WinUser.h
const int WM_GETICON = 0x007F;
IntPtr iconBig = (IntPtr)1;
IntPtr iconHandle = NativeMethods.SendMessage(new HandleRef(null, owner.Handle), WM_GETICON, iconBig, IntPtr.Zero);
if (iconHandle != IntPtr.Zero)
{
using (Icon ownerIcon = Icon.FromHandle(iconHandle))
{
if (ownerIcon != null)
{
this.icon.Image = ownerIcon.ToBitmap();
}
}
}
}
if (useDesktopAsOwner)
{
// If there's no owner window, then this dialog should be centered on the screen.
this.StartPosition = FormStartPosition.CenterScreen;
this.ShowInTaskbar = true;
}
if (this.icon.Image == null)
{
using (Icon? appIcon = Icon.ExtractAssociatedIcon(ApplicationInfo.ExecutableFile))
{
if (appIcon != null)
{
this.icon.Image = appIcon.ToBitmap();
}
}
}
this.ShowDialog(owner);
}
#endregion
#region Private Methods
private void VisitLink(LinkLabel linkLabel, string? linkUrl = null)
{
if (WindowsUtility.ShellExecute(this, linkUrl ?? linkLabel.Text))
{
linkLabel.Links[0].Visited = true;
}
}
private void WebLink_LinkClicked(object sender, LinkLabelLinkClickedEventArgs e)
{
this.VisitLink(this.webLink);
}
private void EmailLink_LinkClicked(object sender, LinkLabelLinkClickedEventArgs e)
{
// UriBuilder always adds a '/' after the email address, which shows up in the opened
// mail message's To field. So we'll manually build a mailto-compatible Uri.
string link = string.Format("mailto:{0}?subject={1} {2}", this.emailLink.Text, this.productName.Text, this.version.Text);
this.VisitLink(this.emailLink, link);
}
private void AboutBox_Shown(object sender, EventArgs e)
{
this.updateChecker.RunWorkerAsync();
}
private void UpdateChecker_DoWork(object sender, DoWorkEventArgs e)
{
Release? latest = Release.FindGithubLatest(this.repository);
if (latest != null)
{
Version? appVersion = ReflectionUtility.GetVersion(this.callingAssembly);
if (latest.Version > appVersion)
{
e.Result = latest;
}
}
}
private void UpdateChecker_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
{
if (e.Error == null && e.Result is Release latest && !this.updateLink.Disposing && !this.Disposing)
{
this.updateLink.Tag = latest;
this.updateLink.Text = $"★ Version {latest.Version} update available!";
this.updateLink.Visible = true;
}
}
private void UpdateLink_LinkClicked(object sender, LinkLabelLinkClickedEventArgs e)
{
if (this.updateLink.Tag is Release latest)
{
this.VisitLink(this.updateLink, latest.HtmlUri.ToString());
}
}
#endregion
}
}