Skip to content

Commit e3f5fba

Browse files
authored
[PTRun][WindowWalker]Don't hang when closing an unresponsive window (#33167)
* add(windowWalkerComponents): added a "Responding" variable signifying if a process is responding or not * add(win32NativeMethod): added "SendMessageTimeout" method in the common Win32 namespace * refactor(windowWalkerWindow): added an implementation of the helper function for closing the window using the newly defined method refactor(windowWalkerWindow): added a thread to run, whenever "CloseThisWindow" is called * refactor(resultHelper): used localizable strings for printing the responding text add(resources): added "Not Responding" localizable text to the resources file * refactor(resultHelper): refactored the message in case of a "Not Responding" task * refactor(resultHelper): modified the formatting of the subtitle * refactor(window): refactored the helper function and removed the unnecessary variable * refactor(windowProcess): changed the variable name from "Responding" to "IsResponding" * add: added try-catch to isResponding getter
1 parent 126a03e commit e3f5fba

File tree

6 files changed

+57
-2
lines changed

6 files changed

+57
-2
lines changed

src/modules/launcher/Plugins/Microsoft.Plugin.WindowWalker/Components/ResultHelper.cs

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -92,6 +92,11 @@ private static string GetSubtitle(Window window)
9292
subtitleText += $" ({window.Process.ProcessID})";
9393
}
9494

95+
if (!window.Process.IsResponding)
96+
{
97+
subtitleText += $" [{Resources.wox_plugin_windowwalker_NotResponding}]";
98+
}
99+
95100
if (WindowWalkerSettings.Instance.SubtitleShowDesktopName && Main.VirtualDesktopHelperInstance.GetDesktopCount() > 1)
96101
{
97102
subtitleText += $" - {Resources.wox_plugin_windowwalker_Desktop}: {window.Desktop.Name}";
@@ -148,7 +153,8 @@ private static ToolTipData GetToolTip(Window window, bool debugToolTip)
148153
$"Desktop number: {window.Desktop.Number}\n" +
149154
$"Desktop is visible: {window.Desktop.IsVisible}\n" +
150155
$"Desktop position: {window.Desktop.Position}\n" +
151-
$"Is AllDesktops view: {window.Desktop.IsAllDesktopsView}";
156+
$"Is AllDesktops view: {window.Desktop.IsAllDesktopsView}\n" +
157+
$"Responding: {window.Process.IsResponding}";
152158

153159
return new ToolTipData(window.Title, text);
154160
}

src/modules/launcher/Plugins/Microsoft.Plugin.WindowWalker/Components/Window.cs

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@
88
using System.Diagnostics;
99
using System.Globalization;
1010
using System.Text;
11+
using System.Threading;
1112
using System.Threading.Tasks;
1213
using Wox.Plugin.Common.VirtualDesktop.Helper;
1314
using Wox.Plugin.Common.Win32;
@@ -234,12 +235,21 @@ internal void SwitchToWindow()
234235
NativeMethods.FlashWindow(Hwnd, true);
235236
}
236237

238+
/// <summary>
239+
/// Helper function to close the window
240+
/// </summary>
241+
internal void CloseThisWindowHelper()
242+
{
243+
_ = NativeMethods.SendMessageTimeout(Hwnd, Win32Constants.WM_SYSCOMMAND, Win32Constants.SC_CLOSE, 0, 0x0000, 5000, out _);
244+
}
245+
237246
/// <summary>
238247
/// Closes the window
239248
/// </summary>
240249
internal void CloseThisWindow()
241250
{
242-
_ = NativeMethods.SendMessage(Hwnd, Win32Constants.WM_SYSCOMMAND, Win32Constants.SC_CLOSE);
251+
Thread thread = new(new ThreadStart(CloseThisWindowHelper));
252+
thread.Start();
243253
}
244254

245255
/// <summary>

src/modules/launcher/Plugins/Microsoft.Plugin.WindowWalker/Components/WindowProcess.cs

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,30 @@ internal uint ProcessID
3333
get; private set;
3434
}
3535

36+
/// <summary>
37+
/// Gets a value indicating whether the process is responding or not
38+
/// </summary>
39+
internal bool IsResponding
40+
{
41+
get
42+
{
43+
try
44+
{
45+
return Process.GetProcessById((int)ProcessID).Responding;
46+
}
47+
catch (InvalidOperationException)
48+
{
49+
// Thrown when process not exist.
50+
return true;
51+
}
52+
catch (NotSupportedException)
53+
{
54+
// Thrown when process is not running locally.
55+
return true;
56+
}
57+
}
58+
}
59+
3660
/// <summary>
3761
/// Gets the id of the thread
3862
/// </summary>

src/modules/launcher/Plugins/Microsoft.Plugin.WindowWalker/Properties/Resources.Designer.cs

Lines changed: 9 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/modules/launcher/Plugins/Microsoft.Plugin.WindowWalker/Properties/Resources.resx

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -202,4 +202,7 @@
202202
<data name="wox_plugin_windowwalker_SettingSubtitleDesktopName_Description" xml:space="preserve">
203203
<value>This information is only shown in subtitle and tool tip, if you have at least two desktops.</value>
204204
</data>
205+
<data name="wox_plugin_windowwalker_NotResponding" xml:space="preserve">
206+
<value>Not Responding</value>
207+
</data>
205208
</root>

src/modules/launcher/Wox.Plugin/Common/Win32/NativeMethods.cs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -81,6 +81,9 @@ public static class NativeMethods
8181
[DllImport("user32.dll")]
8282
public static extern int SendMessage(IntPtr hWnd, int msg, int wParam);
8383

84+
[DllImport("user32.dll")]
85+
public static extern int SendMessageTimeout(IntPtr hWnd, uint msg, UIntPtr wParam, IntPtr lParam, int fuFlags, int uTimeout, out int lpdwResult);
86+
8487
[DllImport("kernel32.dll")]
8588
[return: MarshalAs(UnmanagedType.Bool)]
8689
public static extern bool CloseHandle(IntPtr hObject);

0 commit comments

Comments
 (0)