feat: add signal option to dialog.showMessageBox (#26102)
* mac: add dialog.closeMessageBox API * win: Implement dialog.closeMessageBox * mac: Return cancelId with closeMessageBox * gtk: Implement dialog.closeMessageBox * win: Fix 32bit build * win: Reduce the scope of lock * fix: Build error after rebase * feat: Use AbortSignal to close message box * chore: silently handle duplicate ID * win: Add more notes about the threads * chore: apply reviews * fix: base::NoDestructor should be warpped in function * chore: fix style on windows
This commit is contained in:
parent
4b780f9770
commit
05ba6359d0
9 changed files with 276 additions and 24 deletions
|
@ -2,15 +2,19 @@
|
|||
// Use of this source code is governed by the MIT license that can be
|
||||
// found in the LICENSE file.
|
||||
|
||||
#include "shell/browser/ui/gtk_util.h"
|
||||
#include "shell/browser/ui/message_box.h"
|
||||
|
||||
#include <map>
|
||||
|
||||
#include "base/callback.h"
|
||||
#include "base/containers/contains.h"
|
||||
#include "base/no_destructor.h"
|
||||
#include "base/strings/string_util.h"
|
||||
#include "base/strings/utf_string_conversions.h"
|
||||
#include "shell/browser/browser.h"
|
||||
#include "shell/browser/native_window_observer.h"
|
||||
#include "shell/browser/native_window_views.h"
|
||||
#include "shell/browser/ui/gtk_util.h"
|
||||
#include "shell/browser/unresponsive_suppressor.h"
|
||||
#include "ui/base/glib/glib_signal.h"
|
||||
#include "ui/gfx/image/image_skia.h"
|
||||
|
@ -38,10 +42,17 @@ MessageBoxSettings::~MessageBoxSettings() = default;
|
|||
|
||||
namespace {
|
||||
|
||||
// <ID, messageBox> map
|
||||
std::map<int, GtkWidget*>& GetDialogsMap() {
|
||||
static base::NoDestructor<std::map<int, GtkWidget*>> dialogs;
|
||||
return *dialogs;
|
||||
}
|
||||
|
||||
class GtkMessageBox : public NativeWindowObserver {
|
||||
public:
|
||||
explicit GtkMessageBox(const MessageBoxSettings& settings)
|
||||
: cancel_id_(settings.cancel_id),
|
||||
: id_(settings.id),
|
||||
cancel_id_(settings.cancel_id),
|
||||
parent_(static_cast<NativeWindow*>(settings.parent_window)) {
|
||||
// Create dialog.
|
||||
dialog_ =
|
||||
|
@ -50,6 +61,8 @@ class GtkMessageBox : public NativeWindowObserver {
|
|||
GetMessageType(settings.type), // type
|
||||
GTK_BUTTONS_NONE, // no buttons
|
||||
"%s", settings.message.c_str());
|
||||
if (id_)
|
||||
GetDialogsMap()[*id_] = dialog_;
|
||||
if (!settings.detail.empty())
|
||||
gtk_message_dialog_format_secondary_text(GTK_MESSAGE_DIALOG(dialog_),
|
||||
"%s", settings.detail.c_str());
|
||||
|
@ -183,6 +196,9 @@ class GtkMessageBox : public NativeWindowObserver {
|
|||
private:
|
||||
electron::UnresponsiveSuppressor unresponsive_suppressor_;
|
||||
|
||||
// The id of the dialog.
|
||||
absl::optional<int> id_;
|
||||
|
||||
// The id to return when the dialog is closed without pressing buttons.
|
||||
int cancel_id_ = 0;
|
||||
|
||||
|
@ -196,6 +212,8 @@ class GtkMessageBox : public NativeWindowObserver {
|
|||
};
|
||||
|
||||
void GtkMessageBox::OnResponseDialog(GtkWidget* widget, int response) {
|
||||
if (id_)
|
||||
GetDialogsMap().erase(*id_);
|
||||
gtk_widget_hide(dialog_);
|
||||
|
||||
if (response < 0)
|
||||
|
@ -217,9 +235,20 @@ int ShowMessageBoxSync(const MessageBoxSettings& settings) {
|
|||
|
||||
void ShowMessageBox(const MessageBoxSettings& settings,
|
||||
MessageBoxCallback callback) {
|
||||
if (settings.id && base::Contains(GetDialogsMap(), *settings.id))
|
||||
CloseMessageBox(*settings.id);
|
||||
(new GtkMessageBox(settings))->RunAsynchronous(std::move(callback));
|
||||
}
|
||||
|
||||
void CloseMessageBox(int id) {
|
||||
auto it = GetDialogsMap().find(id);
|
||||
if (it == GetDialogsMap().end()) {
|
||||
LOG(ERROR) << "CloseMessageBox called with nonexistent ID";
|
||||
return;
|
||||
}
|
||||
gtk_window_close(GTK_WINDOW(it->second));
|
||||
}
|
||||
|
||||
void ShowErrorBox(const std::u16string& title, const std::u16string& content) {
|
||||
if (Browser::Get()->is_ready()) {
|
||||
electron::MessageBoxSettings settings;
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue