Skip to content

Commit 24829b2

Browse files
committed
Add dialog type & focus path editor when changing
1 parent 091f0ec commit 24829b2

File tree

1 file changed

+66
-22
lines changed

1 file changed

+66
-22
lines changed

Flow.Launcher.Infrastructure/QuickSwitch/Models/WindowsDialog.cs

Lines changed: 66 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,8 @@
55
using Windows.Win32;
66
using Windows.Win32.Foundation;
77
using Windows.Win32.UI.WindowsAndMessaging;
8+
using WindowsInput;
9+
using WindowsInput.Native;
810

911
namespace Flow.Launcher.Infrastructure.QuickSwitch.Models
1012
{
@@ -80,7 +82,10 @@ internal class WindowsDialogTab : IQuickSwitchDialogWindowTab
8082

8183
private static readonly string ClassName = nameof(WindowsDialogTab);
8284

85+
private static readonly InputSimulator _inputSimulator = new();
86+
8387
private bool _legacy { get; set; } = false;
88+
private DialogType _type { get; set; } = DialogType.None;
8489

8590
private HWND _pathControl { get; set; } = HWND.Null;
8691
private HWND _pathEditor { get; set; } = HWND.Null;
@@ -90,31 +95,36 @@ internal class WindowsDialogTab : IQuickSwitchDialogWindowTab
9095
public WindowsDialogTab(HWND handle)
9196
{
9297
Handle = handle;
93-
GetPathControlEditor();
98+
GetPathControlEditor(true);
9499
GetFileEditor();
95100
GetOpenButton();
96101
}
97102

98-
private bool GetPathControlEditor()
103+
private bool GetPathControlEditor(bool focus)
99104
{
105+
if (focus)
106+
{
107+
// Alt-D or Ctrl-L to focus on the path input box
108+
_inputSimulator.Keyboard.ModifiedKeyStroke(VirtualKeyCode.LMENU, VirtualKeyCode.VK_D);
109+
// _inputSimulator.Keyboard.ModifiedKeyStroke(VirtualKeyCode.LCONTROL, VirtualKeyCode.VK_L);
110+
}
111+
100112
// Get the handle of the path editor
101-
// The window with class name "ComboBoxEx32" is not visible when the path editor is not with the keyboard focus
113+
// "ComboBoxEx32" is not visible when the path editor is not with the keyboard focus
102114
_pathControl = PInvoke.GetDlgItem(Handle, 0x0000); // WorkerW
103115
_pathControl = PInvoke.GetDlgItem(_pathControl, 0xA005); // ReBarWindow32
104116
_pathControl = PInvoke.GetDlgItem(_pathControl, 0xA205); // Address Band Root
105117
_pathControl = PInvoke.GetDlgItem(_pathControl, 0x0000); // msctls_progress32
106118
_pathControl = PInvoke.GetDlgItem(_pathControl, 0xA205); // ComboBoxEx32
107119
if (_pathControl == HWND.Null)
108120
{
109-
// https://github.com/idkidknow/Flow.Launcher.Plugin.DirQuickJump/issues/1
110-
// The dialog is a legacy one, so we edit file name editor directly.
111-
_legacy = true;
112121
_pathEditor = HWND.Null;
113-
Log.Info(ClassName, "Failed to find path control handle - Legacy dialog");
122+
_legacy = true;
123+
Log.Info(ClassName, "Legacy dialog");
124+
return false;
114125
}
115126
else
116127
{
117-
_legacy = false;
118128
_pathEditor = PInvoke.GetDlgItem(_pathControl, 0xA205); // ComboBox
119129
_pathEditor = PInvoke.GetDlgItem(_pathEditor, 0xA205); // Edit
120130
if (_pathEditor == HWND.Null)
@@ -135,7 +145,7 @@ private bool GetFileEditor()
135145
_fileEditor = PInvoke.GetDlgItem(_fileEditor, 0x047C); // Edit
136146
if (_fileEditor == HWND.Null)
137147
{
138-
// Get the handle of the file name editor of Save/SaveAs file dialog
148+
// Get the handle of the file name editor of Save / SaveAs file dialog
139149
_fileEditor = PInvoke.GetDlgItem(Handle, 0x0000); // DUIViewWndClassName
140150
_fileEditor = PInvoke.GetDlgItem(_fileEditor, 0x0000); // DirectUIHWND
141151
_fileEditor = PInvoke.GetDlgItem(_fileEditor, 0x0000); // FloatNotifySink
@@ -144,8 +154,19 @@ private bool GetFileEditor()
144154
if (_fileEditor == HWND.Null)
145155
{
146156
Log.Error(ClassName, "Failed to find file name editor handle");
157+
_type = DialogType.None;
147158
return false;
148159
}
160+
else
161+
{
162+
Log.Debug(ClassName, "File dialog type: Save / Save As");
163+
_type = DialogType.SaveOrSaveAs;
164+
}
165+
}
166+
else
167+
{
168+
Log.Debug(ClassName, "File dialog type: Open");
169+
_type = DialogType.Open;
149170
}
150171

151172
return true;
@@ -166,7 +187,7 @@ private bool GetOpenButton()
166187

167188
public string GetCurrentFolder()
168189
{
169-
if (_pathEditor.IsNull && !GetPathControlEditor()) return string.Empty;
190+
if (_pathEditor.IsNull) return string.Empty;
170191
return GetWindowText(_pathEditor);
171192
}
172193

@@ -178,20 +199,23 @@ public string GetCurrentFile()
178199

179200
public bool JumpFolder(string path, bool auto)
180201
{
181-
if (_legacy || auto)
202+
if (auto)
182203
{
183-
// https://github.com/idkidknow/Flow.Launcher.Plugin.DirQuickJump/issues/1
184-
// The dialog is a legacy one, so we edit file name text box directly
185-
if (_fileEditor.IsNull && !GetFileEditor()) return false;
186-
SetWindowText(_fileEditor, path);
187-
188-
if (_openButton.IsNull && !GetOpenButton()) return false;
189-
PInvoke.SendMessage(_openButton, PInvoke.BM_CLICK, 0, 0);
204+
// Use legacy jump folder method for auto quick switch because file editor is default value.
205+
// After setting path using file editor, we do not need to revert its value.
206+
return JumpFolderWithFileEditor(path);
207+
}
190208

191-
return true;
209+
if (_legacy)
210+
{
211+
// https://github.com/idkidknow/Flow.Launcher.Plugin.DirQuickJump/issues/1
212+
// The dialog is a legacy one, so we can only edit file editor directly.
213+
return JumpFolderWithFileEditor(path);
192214
}
193215

194-
if (_pathControl.IsNull && !GetPathControlEditor()) return false;
216+
// Alt-D or Ctrl-L to focus on the path input box
217+
_inputSimulator.Keyboard.ModifiedKeyStroke(VirtualKeyCode.LMENU, VirtualKeyCode.VK_D);
218+
// _inputSimulator.Keyboard.ModifiedKeyStroke(VirtualKeyCode.LCONTROL, VirtualKeyCode.VK_L);
195219

196220
var timeOut = !SpinWait.SpinUntil(() =>
197221
{
@@ -204,15 +228,28 @@ public bool JumpFolder(string path, bool auto)
204228
return false;
205229
}
206230

207-
if (_pathEditor.IsNull && !GetPathControlEditor()) return false;
231+
if (_pathEditor.IsNull) return false;
208232
SetWindowText(_pathEditor, path);
209233

234+
_inputSimulator.Keyboard.KeyPress(VirtualKeyCode.RETURN);
235+
236+
return true;
237+
}
238+
239+
private bool JumpFolderWithFileEditor(string path)
240+
{
241+
if (_fileEditor.IsNull && !GetFileEditor()) return false;
242+
SetWindowText(_fileEditor, path);
243+
244+
if (_openButton.IsNull && !GetOpenButton()) return false;
245+
PInvoke.SendMessage(_openButton, PInvoke.BM_CLICK, 0, 0);
246+
210247
return true;
211248
}
212249

213250
public bool JumpFile(string path)
214251
{
215-
if (_fileEditor.IsNull && !GetPathControlEditor()) return false;
252+
if (_fileEditor.IsNull && !GetFileEditor()) return false;
216253
SetWindowText(_fileEditor, path);
217254

218255
return true;
@@ -251,5 +288,12 @@ public void Dispose()
251288
{
252289
Handle = HWND.Null;
253290
}
291+
292+
private enum DialogType
293+
{
294+
None,
295+
Open,
296+
SaveOrSaveAs
297+
}
254298
}
255299
}

0 commit comments

Comments
 (0)