Merge pull request #922 from atom/dialog-thread
Run asynchronous file dialog in new thread on Windows
This commit is contained in:
commit
5bed184014
2 changed files with 68 additions and 14 deletions
|
@ -15,6 +15,7 @@
|
||||||
#include "base/strings/string_util.h"
|
#include "base/strings/string_util.h"
|
||||||
#include "base/strings/string_split.h"
|
#include "base/strings/string_split.h"
|
||||||
#include "base/strings/utf_string_conversions.h"
|
#include "base/strings/utf_string_conversions.h"
|
||||||
|
#include "base/threading/thread.h"
|
||||||
#include "base/win/registry.h"
|
#include "base/win/registry.h"
|
||||||
#include "third_party/wtl/include/atlapp.h"
|
#include "third_party/wtl/include/atlapp.h"
|
||||||
#include "third_party/wtl/include/atldlgs.h"
|
#include "third_party/wtl/include/atldlgs.h"
|
||||||
|
@ -113,6 +114,50 @@ class FileDialog {
|
||||||
DISALLOW_COPY_AND_ASSIGN(FileDialog);
|
DISALLOW_COPY_AND_ASSIGN(FileDialog);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct RunState {
|
||||||
|
base::Thread* dialog_thread;
|
||||||
|
base::MessageLoop* ui_message_loop;
|
||||||
|
};
|
||||||
|
|
||||||
|
bool CreateDialogThread(RunState* run_state) {
|
||||||
|
base::Thread* thread = new base::Thread("AtomShell_FileDialogThread");
|
||||||
|
thread->init_com_with_mta(false);
|
||||||
|
if (!thread->Start())
|
||||||
|
return false;
|
||||||
|
|
||||||
|
run_state->dialog_thread = thread;
|
||||||
|
run_state->ui_message_loop = base::MessageLoop::current();
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
void RunOpenDialogInNewThread(const RunState& run_state,
|
||||||
|
atom::NativeWindow* parent,
|
||||||
|
const std::string& title,
|
||||||
|
const base::FilePath& default_path,
|
||||||
|
const Filters& filters,
|
||||||
|
int properties,
|
||||||
|
const OpenDialogCallback& callback) {
|
||||||
|
std::vector<base::FilePath> paths;
|
||||||
|
bool result = ShowOpenDialog(parent, title, default_path, filters, properties,
|
||||||
|
&paths);
|
||||||
|
run_state.ui_message_loop->PostTask(FROM_HERE,
|
||||||
|
base::Bind(callback, result, paths));
|
||||||
|
run_state.ui_message_loop->DeleteSoon(FROM_HERE, run_state.dialog_thread);
|
||||||
|
}
|
||||||
|
|
||||||
|
void RunSaveDialogInNewThread(const RunState& run_state,
|
||||||
|
atom::NativeWindow* parent,
|
||||||
|
const std::string& title,
|
||||||
|
const base::FilePath& default_path,
|
||||||
|
const Filters& filters,
|
||||||
|
const SaveDialogCallback& callback) {
|
||||||
|
base::FilePath path;
|
||||||
|
bool result = ShowSaveDialog(parent, title, default_path, filters, &path);
|
||||||
|
run_state.ui_message_loop->PostTask(FROM_HERE,
|
||||||
|
base::Bind(callback, result, path));
|
||||||
|
run_state.ui_message_loop->DeleteSoon(FROM_HERE, run_state.dialog_thread);
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace
|
} // namespace
|
||||||
|
|
||||||
bool ShowOpenDialog(atom::NativeWindow* parent_window,
|
bool ShowOpenDialog(atom::NativeWindow* parent_window,
|
||||||
|
@ -162,20 +207,22 @@ bool ShowOpenDialog(atom::NativeWindow* parent_window,
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ShowOpenDialog(atom::NativeWindow* parent_window,
|
void ShowOpenDialog(atom::NativeWindow* parent,
|
||||||
const std::string& title,
|
const std::string& title,
|
||||||
const base::FilePath& default_path,
|
const base::FilePath& default_path,
|
||||||
const Filters& filters,
|
const Filters& filters,
|
||||||
int properties,
|
int properties,
|
||||||
const OpenDialogCallback& callback) {
|
const OpenDialogCallback& callback) {
|
||||||
std::vector<base::FilePath> paths;
|
RunState run_state;
|
||||||
bool result = ShowOpenDialog(parent_window,
|
if (!CreateDialogThread(&run_state)) {
|
||||||
title,
|
callback.Run(false, std::vector<base::FilePath>());
|
||||||
default_path,
|
return;
|
||||||
filters,
|
}
|
||||||
properties,
|
|
||||||
&paths);
|
run_state.dialog_thread->message_loop()->PostTask(
|
||||||
callback.Run(result, paths);
|
FROM_HERE,
|
||||||
|
base::Bind(&RunOpenDialogInNewThread, run_state, parent, title,
|
||||||
|
default_path, filters, properties, callback));
|
||||||
}
|
}
|
||||||
|
|
||||||
bool ShowSaveDialog(atom::NativeWindow* parent_window,
|
bool ShowSaveDialog(atom::NativeWindow* parent_window,
|
||||||
|
@ -218,15 +265,21 @@ bool ShowSaveDialog(atom::NativeWindow* parent_window,
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ShowSaveDialog(atom::NativeWindow* parent_window,
|
void ShowSaveDialog(atom::NativeWindow* parent,
|
||||||
const std::string& title,
|
const std::string& title,
|
||||||
const base::FilePath& default_path,
|
const base::FilePath& default_path,
|
||||||
const Filters& filters,
|
const Filters& filters,
|
||||||
const SaveDialogCallback& callback) {
|
const SaveDialogCallback& callback) {
|
||||||
base::FilePath path;
|
RunState run_state;
|
||||||
bool result = ShowSaveDialog(parent_window, title, default_path, filters,
|
if (!CreateDialogThread(&run_state)) {
|
||||||
&path);
|
callback.Run(false, base::FilePath());
|
||||||
callback.Run(result, path);
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
run_state.dialog_thread->message_loop()->PostTask(
|
||||||
|
FROM_HERE,
|
||||||
|
base::Bind(&RunSaveDialogInNewThread, run_state, parent, title,
|
||||||
|
default_path, filters, callback));
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace file_dialog
|
} // namespace file_dialog
|
||||||
|
|
|
@ -136,6 +136,7 @@
|
||||||
4005, # (node.h) macro redefinition
|
4005, # (node.h) macro redefinition
|
||||||
4189, # local variable is initialized but not referenced
|
4189, # local variable is initialized but not referenced
|
||||||
4201, # (uv.h) nameless struct/union
|
4201, # (uv.h) nameless struct/union
|
||||||
|
4503, # decorated name length exceeded, name was truncated
|
||||||
4800, # (v8.h) forcing value to bool 'true' or 'false'
|
4800, # (v8.h) forcing value to bool 'true' or 'false'
|
||||||
4819, # The file contains a character that cannot be represented in the current code page
|
4819, # The file contains a character that cannot be represented in the current code page
|
||||||
4996, # (atlapp.h) 'GetVersionExW': was declared deprecated
|
4996, # (atlapp.h) 'GetVersionExW': was declared deprecated
|
||||||
|
|
Loading…
Reference in a new issue