summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorerg@chromium.org <erg@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2010-02-24 20:05:13 +0000
committererg@chromium.org <erg@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2010-02-24 20:05:13 +0000
commitba6da1fa11a1d7635e8ad5ab282734f80e2effa2 (patch)
tree25ef44da05e764cb90e995e09b75e40387ae5ce2
parentfc9e60e86ec510dcf50fa27b6d5c9bf29cb7976f (diff)
downloadchromium_src-ba6da1fa11a1d7635e8ad5ab282734f80e2effa2.zip
chromium_src-ba6da1fa11a1d7635e8ad5ab282734f80e2effa2.tar.gz
chromium_src-ba6da1fa11a1d7635e8ad5ab282734f80e2effa2.tar.bz2
GTK: Add modal cookies confirmation prompt.
BUG=35178,36183 TEST=none Review URL: http://codereview.chromium.org/652172 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@39914 0039d316-1c4b-4281-b951-d872f2087c98
-rw-r--r--chrome/browser/cookie_modal_dialog.h5
-rw-r--r--chrome/browser/cookie_modal_dialog_gtk.cc127
-rw-r--r--chrome/browser/js_modal_dialog_gtk.cc18
-rw-r--r--chrome/browser/message_box_handler.cc18
-rwxr-xr-xchrome/chrome_browser.gypi2
-rw-r--r--chrome/common/gtk_util.cc76
-rw-r--r--chrome/common/gtk_util.h10
7 files changed, 220 insertions, 36 deletions
diff --git a/chrome/browser/cookie_modal_dialog.h b/chrome/browser/cookie_modal_dialog.h
index 11b35a1..7a6ae50 100644
--- a/chrome/browser/cookie_modal_dialog.h
+++ b/chrome/browser/cookie_modal_dialog.h
@@ -102,6 +102,11 @@ class CookiePromptModalDialog : public AppModalDialog {
// delegate could be deleted
CookiePromptModalDialogDelegate* delegate_;
+#if defined(OS_LINUX)
+ // The "remember this choice" radio button in the dialog.
+ GtkWidget* remember_radio_;
+#endif
+
DISALLOW_COPY_AND_ASSIGN(CookiePromptModalDialog);
};
diff --git a/chrome/browser/cookie_modal_dialog_gtk.cc b/chrome/browser/cookie_modal_dialog_gtk.cc
new file mode 100644
index 0000000..104ec80
--- /dev/null
+++ b/chrome/browser/cookie_modal_dialog_gtk.cc
@@ -0,0 +1,127 @@
+// Copyright (c) 2010 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "chrome/browser/cookie_modal_dialog.h"
+
+#include "app/l10n_util.h"
+#include "base/logging.h"
+#include "chrome/browser/gtk/gtk_chrome_link_button.h"
+#include "chrome/browser/views/cookie_prompt_view.h"
+#include "chrome/browser/tab_contents/tab_contents.h"
+#include "chrome/common/gtk_util.h"
+#include "grit/generated_resources.h"
+#include "grit/locale_settings.h"
+
+void CookiePromptModalDialog::CreateAndShowDialog() {
+ dialog_ = CreateNativeDialog();
+ gtk_widget_show_all(GTK_WIDGET(GTK_DIALOG(dialog_)));
+
+ // Suggest a minimum size.
+ gint width;
+ GtkRequisition req;
+ gtk_widget_size_request(dialog_, &req);
+ gtk_util::GetWidgetSizeFromResources(dialog_, IDS_ALERT_DIALOG_WIDTH_CHARS, 0,
+ &width, NULL);
+ if (width > req.width)
+ gtk_widget_set_size_request(dialog_, width, -1);
+}
+
+int CookiePromptModalDialog::GetDialogButtons() {
+ return 0;
+}
+
+void CookiePromptModalDialog::AcceptWindow() {
+ HandleDialogResponse(GTK_DIALOG(dialog_), GTK_RESPONSE_ACCEPT);
+}
+
+void CookiePromptModalDialog::CancelWindow() {
+ HandleDialogResponse(GTK_DIALOG(dialog_), GTK_RESPONSE_REJECT);
+}
+
+NativeDialog CookiePromptModalDialog::CreateNativeDialog() {
+ gfx::NativeWindow window = tab_contents_->GetMessageBoxRootWindow();
+ CookiePromptModalDialog::DialogType type = dialog_type();
+ NativeDialog dialog = gtk_dialog_new_with_buttons(
+ l10n_util::GetStringFUTF8(
+ type == CookiePromptModalDialog::DIALOG_TYPE_COOKIE ?
+ IDS_COOKIE_ALERT_TITLE : IDS_DATA_ALERT_TITLE,
+ UTF8ToUTF16(origin().host())).c_str(),
+ window,
+ GTK_DIALOG_MODAL,
+ l10n_util::GetStringUTF8(IDS_COOKIE_ALERT_BLOCK_BUTTON).c_str(),
+ GTK_RESPONSE_REJECT,
+ l10n_util::GetStringUTF8(IDS_COOKIE_ALERT_ALLOW_BUTTON).c_str(),
+ GTK_RESPONSE_ACCEPT,
+ NULL);
+
+ GtkWidget* content_area = GTK_DIALOG(dialog)->vbox;
+ gtk_box_set_spacing(GTK_BOX(content_area), gtk_util::kContentAreaSpacing);
+
+ string16 display_host = UTF8ToUTF16(origin().host());
+ GtkWidget* label = gtk_label_new(
+ l10n_util::GetStringFUTF8(
+ type == CookiePromptModalDialog::DIALOG_TYPE_COOKIE ?
+ IDS_COOKIE_ALERT_LABEL : IDS_DATA_ALERT_LABEL,
+ display_host).c_str());
+
+ gtk_box_pack_start(GTK_BOX(content_area), label, FALSE, FALSE, 0);
+
+ // Create a vbox for all the radio buttons so they aren't too far away from
+ // each other.
+ GtkWidget* radio_box = gtk_vbox_new(FALSE, gtk_util::kControlSpacing);
+ remember_radio_ = gtk_radio_button_new_with_label(NULL,
+ l10n_util::GetStringFUTF8(IDS_COOKIE_ALERT_REMEMBER_RADIO,
+ display_host).c_str());
+ gtk_box_pack_start(GTK_BOX(radio_box), remember_radio_, FALSE, FALSE, 0);
+
+ GtkWidget* ask_radio = gtk_radio_button_new_with_label_from_widget(
+ GTK_RADIO_BUTTON(remember_radio_),
+ l10n_util::GetStringUTF8(IDS_COOKIE_ALERT_ASK_RADIO).c_str());
+ gtk_box_pack_start(GTK_BOX(radio_box), ask_radio, FALSE, FALSE, 0);
+
+ gtk_box_pack_start(GTK_BOX(content_area), radio_box, FALSE, FALSE, 0);
+
+ // Now we create the details link and align it left in the button box.
+ GtkWidget* details_button = gtk_chrome_link_button_new(
+ l10n_util::GetStringUTF8(IDS_COOKIE_SHOW_DETAILS_LABEL).c_str());
+ gtk_box_pack_start(GTK_BOX(GTK_DIALOG(dialog)->action_area),
+ details_button, FALSE, FALSE, 0);
+ gtk_widget_set_sensitive(details_button, FALSE);
+ gtk_button_box_set_child_secondary(
+ GTK_BUTTON_BOX(GTK_DIALOG(dialog)->action_area),
+ details_button,
+ TRUE);
+
+ // TODO(erg): http://crbug.com/35178 : Needs to implement the cookie details
+ // box here.
+
+ gtk_dialog_set_default_response(GTK_DIALOG(dialog), GTK_RESPONSE_ACCEPT);
+ g_signal_connect(dialog, "response",
+ G_CALLBACK(AppModalDialog::OnDialogResponse),
+ reinterpret_cast<AppModalDialog*>(this));
+
+ gtk_util::MakeAppModalWindowGroup();
+
+ return dialog;
+}
+
+void CookiePromptModalDialog::HandleDialogResponse(GtkDialog* dialog,
+ gint response_id) {
+ bool remember_radio = gtk_toggle_button_get_active(
+ GTK_TOGGLE_BUTTON(remember_radio_));
+ if (response_id == GTK_RESPONSE_REJECT) {
+ BlockSiteData(remember_radio);
+ } else if (response_id == GTK_RESPONSE_ACCEPT) {
+ // TODO(erg): Needs to use |session_expire_| instead of true.
+ AllowSiteData(remember_radio, true);
+ } else {
+ BlockSiteData(false);
+ }
+ gtk_widget_destroy(GTK_WIDGET(dialog));
+
+ CompleteDialog();
+
+ gtk_util::AppModalDismissedUngroupWindows();
+ delete this;
+}
diff --git a/chrome/browser/js_modal_dialog_gtk.cc b/chrome/browser/js_modal_dialog_gtk.cc
index bf42fb6..01aff6e 100644
--- a/chrome/browser/js_modal_dialog_gtk.cc
+++ b/chrome/browser/js_modal_dialog_gtk.cc
@@ -10,8 +10,6 @@
#include "app/message_box_flags.h"
#include "base/logging.h"
#include "base/string_util.h"
-#include "chrome/browser/browser_list.h"
-#include "chrome/browser/browser_window.h"
#include "chrome/browser/tab_contents/tab_contents.h"
#include "chrome/browser/tab_contents/tab_contents_view.h"
#include "chrome/common/gtk_util.h"
@@ -82,13 +80,7 @@ void JavaScriptAppModalDialog::HandleDialogResponse(GtkDialog* dialog,
// Now that the dialog is gone, we can put all the windows into separate
// window groups so other dialogs are no longer app modal.
- for (BrowserList::const_iterator it = BrowserList::begin();
- it != BrowserList::end(); ++it) {
- GtkWindowGroup* window_group = gtk_window_group_new();
- gtk_window_group_add_window(window_group,
- (*it)->window()->GetNativeHandle());
- g_object_unref(window_group);
- }
+ gtk_util::AppModalDismissedUngroupWindows();
delete this;
}
@@ -151,13 +143,7 @@ NativeDialog JavaScriptAppModalDialog::CreateNativeDialog() {
// We want the alert to be app modal so put all the browser windows into the
// same window group.
- GtkWindowGroup* window_group = gtk_window_group_new();
- for (BrowserList::const_iterator it = BrowserList::begin();
- it != BrowserList::end(); ++it) {
- gtk_window_group_add_window(window_group,
- (*it)->window()->GetNativeHandle());
- }
- g_object_unref(window_group);
+ gtk_util::MakeAppModalWindowGroup();
gfx::NativeWindow window = client_->GetMessageBoxRootWindow();
NativeDialog dialog = gtk_message_dialog_new(window, GTK_DIALOG_MODAL,
diff --git a/chrome/browser/message_box_handler.cc b/chrome/browser/message_box_handler.cc
index a92bbf7..280472b 100644
--- a/chrome/browser/message_box_handler.cc
+++ b/chrome/browser/message_box_handler.cc
@@ -63,15 +63,9 @@ void RunCookiePrompt(TabContents* tab_contents,
const GURL& origin,
const std::string& cookie_line,
CookiePromptModalDialogDelegate* delegate) {
-#if defined(OS_WIN) || defined(OS_MACOSX)
Singleton<AppModalDialogQueue>()->AddDialog(
new CookiePromptModalDialog(tab_contents, host_content_settings_map,
origin, cookie_line, delegate));
-#else
- // Linux: http://crbug.com/35178
- NOTIMPLEMENTED();
- delegate->BlockSiteData();
-#endif
}
void RunLocalStoragePrompt(
@@ -81,15 +75,9 @@ void RunLocalStoragePrompt(
const string16& key,
const string16& value,
CookiePromptModalDialogDelegate* delegate) {
-#if defined(OS_WIN) || defined(OS_MACOSX)
Singleton<AppModalDialogQueue>()->AddDialog(
new CookiePromptModalDialog(tab_contents, host_content_settings_map,
origin, key, value, delegate));
-#else
- // Linux: http://crbug.com/35178
- NOTIMPLEMENTED();
- delegate->BlockSiteData();
-#endif
}
void RunDatabasePrompt(
@@ -98,13 +86,7 @@ void RunDatabasePrompt(
const GURL& origin,
const string16& database_name,
CookiePromptModalDialogDelegate* delegate) {
-#if defined(OS_WIN) || defined(OS_MACOSX)
Singleton<AppModalDialogQueue>()->AddDialog(
new CookiePromptModalDialog(tab_contents, host_content_settings_map,
origin, database_name, delegate));
-#else
- // Linux: http://crbug.com/35178
- NOTIMPLEMENTED();
- delegate->BlockSiteData();
-#endif
}
diff --git a/chrome/chrome_browser.gypi b/chrome/chrome_browser.gypi
index f0e0038..7d43fc1 100755
--- a/chrome/chrome_browser.gypi
+++ b/chrome/chrome_browser.gypi
@@ -714,6 +714,7 @@
'browser/cookie_modal_dialog.cc',
'browser/cookie_modal_dialog.h',
'browser/cookie_modal_dialog_mac.mm',
+ 'browser/cookie_modal_dialog_gtk.cc',
'browser/cookie_modal_dialog_views.cc',
'browser/cookie_prompt_modal_dialog_delegate.h',
'browser/cookies_tree_model.cc',
@@ -2711,7 +2712,6 @@
['include', '^browser/printing/print_dialog_gtk.h'],
['exclude', '^browser/browser_list_stub.cc'],
['exclude', '^browser/bookmarks/bookmark_drop_info.cc'],
- ['exclude', '^browser/cookie_modal_dialog.cc'],
['exclude', '^browser/views/autocomplete/autocomplete_popup_gtk.cc'],
['exclude', '^browser/views/autocomplete/autocomplete_popup_gtk.h'],
],
diff --git a/chrome/common/gtk_util.cc b/chrome/common/gtk_util.cc
index a1537c0..66971b5 100644
--- a/chrome/common/gtk_util.cc
+++ b/chrome/common/gtk_util.cc
@@ -14,6 +14,8 @@
#include "app/resource_bundle.h"
#include "base/linux_util.h"
#include "base/logging.h"
+#include "chrome/browser/browser_list.h"
+#include "chrome/browser/browser_window.h"
#include "chrome/browser/gtk/cairo_cached_surface.h"
#include "chrome/browser/gtk/gtk_theme_provider.h"
#include "chrome/common/renderer_preferences.h"
@@ -295,6 +297,80 @@ void CenterOverWindow(GtkWindow* window, GtkWindow* parent) {
}
}
+void MakeAppModalWindowGroup() {
+#if GTK_CHECK_VERSION(2, 14, 0)
+ // Older versions of GTK+ don't give us gtk_window_group_list() which is what
+ // we need to add current non-browser modal dialogs to the list. If
+ // we have 2.14+ we can do things the correct way.
+ GtkWindowGroup* window_group = gtk_window_group_new();
+ for (BrowserList::const_iterator it = BrowserList::begin();
+ it != BrowserList::end(); ++it) {
+ // List all windows in this current group
+ GtkWindowGroup* old_group =
+ gtk_window_get_group((*it)->window()->GetNativeHandle());
+
+ GList* all_windows = gtk_window_group_list_windows(old_group);
+ for (GList* window = all_windows; window; window = window->next) {
+ gtk_window_group_add_window(window_group, GTK_WINDOW(window->data));
+ }
+ g_list_free(all_windows);
+ }
+ g_object_unref(window_group);
+#else
+ // Otherwise just grab all browser windows and be slightly broken.
+ GtkWindowGroup* window_group = gtk_window_group_new();
+ for (BrowserList::const_iterator it = BrowserList::begin();
+ it != BrowserList::end(); ++it) {
+ gtk_window_group_add_window(window_group,
+ (*it)->window()->GetNativeHandle());
+ }
+ g_object_unref(window_group);
+#endif
+}
+
+void AppModalDismissedUngroupWindows() {
+#if GTK_CHECK_VERSION(2, 14, 0)
+ if (BrowserList::begin() != BrowserList::end()) {
+ std::vector<GtkWindow*> transient_windows;
+
+ // All windows should be part of one big modal group right now.
+ GtkWindowGroup* window_group = gtk_window_get_group(
+ (*BrowserList::begin())->window()->GetNativeHandle());
+ GList* windows = gtk_window_group_list_windows(window_group);
+
+ for (GList* item = windows; item; item = item->next) {
+ GtkWindow* window = GTK_WINDOW(item->data);
+ GtkWindow* transient_for = gtk_window_get_transient_for(window);
+ if (transient_for) {
+ transient_windows.push_back(window);
+ } else {
+ GtkWindowGroup* window_group = gtk_window_group_new();
+ gtk_window_group_add_window(window_group, window);
+ g_object_unref(window_group);
+ }
+ }
+
+ // Put each transient window in the same group as its transient parent.
+ for (std::vector<GtkWindow*>::iterator it = transient_windows.begin();
+ it != transient_windows.end(); ++it) {
+ GtkWindow* transient_parent = gtk_window_get_transient_for(*it);
+ GtkWindowGroup* group = gtk_window_get_group(transient_parent);
+ gtk_window_group_add_window(group, *it);
+ }
+ }
+#else
+ // This is slightly broken in the case where a different window had a dialog,
+ // but its the best we can do since we don't have newer gtk stuff.
+ for (BrowserList::const_iterator it = BrowserList::begin();
+ it != BrowserList::end(); ++it) {
+ GtkWindowGroup* window_group = gtk_window_group_new();
+ gtk_window_group_add_window(window_group,
+ (*it)->window()->GetNativeHandle());
+ g_object_unref(window_group);
+ }
+#endif
+}
+
void RemoveAllChildren(GtkWidget* container) {
gtk_container_foreach(GTK_CONTAINER(container), RemoveWidget, container);
}
diff --git a/chrome/common/gtk_util.h b/chrome/common/gtk_util.h
index 1caf748..40cab80 100644
--- a/chrome/common/gtk_util.h
+++ b/chrome/common/gtk_util.h
@@ -59,7 +59,7 @@ const int kFormControlSpacing = 10;
// be NULL to get the system default.
//
// For example:
-// controls = CreateLabeledControlsGroup(NULL, &gfx::kGdkBlack,
+// controls = CreateLabeledControlsGroup(NULL,
// "Name:", title_entry_,
// "Folder:", folder_combobox_,
// NULL);
@@ -106,6 +106,14 @@ void SetWindowSizeFromResources(GtkWindow* window,
// transient_for.
void CenterOverWindow(GtkWindow* window, GtkWindow* parent);
+// Puts all browser windows in one window group; this will make any dialog
+// spawned app modal.
+void MakeAppModalWindowGroup();
+
+// Called after an app modal dialog that used MakeAppModalWindowGroup() was
+// dismissed. Returns each browser window to its own window group.
+void AppModalDismissedUngroupWindows();
+
// Remove all children from this container.
void RemoveAllChildren(GtkWidget* container);