Skip to content

Commit e2e1b76

Browse files
authored
[wpigui] Fix PFD file dialogs not closing after window closing (#5530)
Also applies samhocevar/portable-file-dialogs#91 to properly retrieve the HWND on Windows.
1 parent 86d7bbc commit e2e1b76

File tree

2 files changed

+19
-9
lines changed

2 files changed

+19
-9
lines changed

wpigui/src/main/native/cpp/portable-file-dialogs.cpp

Lines changed: 17 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -702,6 +702,12 @@ HANDLE internal::platform::new_style_context::create()
702702

703703
// dialog implementation
704704

705+
internal::dialog::~dialog() {
706+
if (m_async->m_running) {
707+
kill();
708+
}
709+
}
710+
705711
bool internal::dialog::ready(int timeout /* = default_wait_timeout */) const
706712
{
707713
return m_async->ready(timeout);
@@ -804,7 +810,7 @@ class internal::file_dialog::Impl {
804810
#if _WIN32
805811
static int CALLBACK bffcallback(HWND hwnd, UINT uMsg, LPARAM, LPARAM pData);
806812
#if PFD_HAS_IFILEDIALOG
807-
std::string select_folder_vista(IFileDialog *ifd, bool force_path);
813+
std::string select_folder_vista(IFileDialog *ifd, bool force_path, HWND active_window);
808814
#endif
809815

810816
std::wstring m_wtitle;
@@ -831,8 +837,9 @@ internal::file_dialog::file_dialog(type in_type,
831837
}
832838
filter_list += '\0';
833839

840+
HWND active_window = GetActiveWindow();
834841
m_async->start_func([this, in_type, title, default_path, filter_list,
835-
options](int *exit_code) -> std::string
842+
options, active_window](int *exit_code) -> std::string
836843
{
837844
(void)exit_code;
838845
m_impl->m_wtitle = internal::str2wstr(title);
@@ -858,7 +865,7 @@ internal::file_dialog::file_dialog(type in_type,
858865

859866
// In case CoCreateInstance fails (which it should not), try legacy approach
860867
if (SUCCEEDED(hr))
861-
return m_impl->select_folder_vista(ifd, options & opt::force_path);
868+
return m_impl->select_folder_vista(ifd, options & opt::force_path, active_window);
862869
}
863870
#endif
864871

@@ -892,7 +899,7 @@ internal::file_dialog::file_dialog(type in_type,
892899
OPENFILENAMEW ofn;
893900
memset(&ofn, 0, sizeof(ofn));
894901
ofn.lStructSize = sizeof(OPENFILENAMEW);
895-
ofn.hwndOwner = GetActiveWindow();
902+
ofn.hwndOwner = active_window;
896903

897904
ofn.lpstrFilter = wfilter_list.c_str();
898905

@@ -1169,7 +1176,7 @@ int CALLBACK internal::file_dialog::Impl::bffcallback(HWND hwnd, UINT uMsg,
11691176
}
11701177

11711178
#if PFD_HAS_IFILEDIALOG
1172-
std::string internal::file_dialog::Impl::select_folder_vista(IFileDialog *ifd, bool force_path)
1179+
std::string internal::file_dialog::Impl::select_folder_vista(IFileDialog *ifd, bool force_path, HWND active_window)
11731180
{
11741181
std::string result;
11751182

@@ -1206,7 +1213,7 @@ std::string internal::file_dialog::Impl::select_folder_vista(IFileDialog *ifd, b
12061213
ifd->SetOptions(FOS_PICKFOLDERS | FOS_FORCEFILESYSTEM);
12071214
ifd->SetTitle(m_wtitle.c_str());
12081215

1209-
hr = ifd->Show(GetActiveWindow());
1216+
hr = ifd->Show(active_window);
12101217
if (SUCCEEDED(hr))
12111218
{
12121219
IShellItem* item;
@@ -1393,13 +1400,15 @@ message::message(std::string const &title,
13931400
m_mappings[IDRETRY] = button::retry;
13941401
m_mappings[IDIGNORE] = button::ignore;
13951402

1396-
m_async->start_func([text, title, style](int* exit_code) -> std::string
1403+
HWND active_window = GetActiveWindow();
1404+
1405+
m_async->start_func([text, title, style, active_window](int* exit_code) -> std::string
13971406
{
13981407
auto wtext = internal::str2wstr(text);
13991408
auto wtitle = internal::str2wstr(title);
14001409
// Apply new visual style (required for all Windows versions)
14011410
internal::platform::new_style_context ctx;
1402-
*exit_code = MessageBoxW(GetActiveWindow(), wtext.c_str(), wtitle.c_str(), style);
1411+
*exit_code = MessageBoxW(active_window, wtext.c_str(), wtitle.c_str(), style);
14031412
return "";
14041413
});
14051414

wpigui/src/main/native/include/portable-file-dialogs.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -128,6 +128,7 @@ class executor;
128128
class dialog : protected settings
129129
{
130130
public:
131+
virtual ~dialog();
131132
bool ready(int timeout = default_wait_timeout) const;
132133
bool kill() const;
133134

@@ -146,7 +147,7 @@ class dialog : protected settings
146147
std::shared_ptr<executor> m_async;
147148
};
148149

149-
class file_dialog : public dialog
150+
class file_dialog : public internal::dialog
150151
{
151152
protected:
152153
enum type

0 commit comments

Comments
 (0)