diff options
-rw-r--r-- | chrome/browser/autocomplete_history_manager.h | 5 | ||||
-rw-r--r-- | chrome/browser/autocomplete_history_manager_unittest.cc | 7 | ||||
-rw-r--r-- | chrome/browser/autofill/autofill_external_delegate.cc | 10 | ||||
-rw-r--r-- | chrome/browser/autofill/autofill_external_delegate.h | 14 | ||||
-rw-r--r-- | chrome/browser/autofill/autofill_external_delegate_gtk.cc | 86 | ||||
-rw-r--r-- | chrome/browser/autofill/autofill_external_delegate_gtk.h | 66 | ||||
-rw-r--r-- | chrome/browser/autofill/autofill_external_delegate_unittest.cc | 106 | ||||
-rw-r--r-- | chrome/browser/autofill/autofill_manager_unittest.cc | 22 | ||||
-rw-r--r-- | chrome/browser/autofill/autofill_popup_view.cc | 32 | ||||
-rw-r--r-- | chrome/browser/autofill/autofill_popup_view.h | 54 | ||||
-rw-r--r-- | chrome/browser/autofill/autofill_popup_view_browsertest.cc | 87 | ||||
-rw-r--r-- | chrome/browser/ui/gtk/autofill/autofill_popup_view_gtk.cc | 62 | ||||
-rw-r--r-- | chrome/browser/ui/gtk/autofill/autofill_popup_view_gtk.h | 38 | ||||
-rw-r--r-- | chrome/chrome_browser.gypi | 6 | ||||
-rw-r--r-- | chrome/chrome_tests.gypi | 2 |
15 files changed, 572 insertions, 25 deletions
diff --git a/chrome/browser/autocomplete_history_manager.h b/chrome/browser/autocomplete_history_manager.h index 8f5eabc..c4c02d6 100644 --- a/chrome/browser/autocomplete_history_manager.h +++ b/chrome/browser/autocomplete_history_manager.h @@ -1,4 +1,4 @@ -// Copyright (c) 2011 The Chromium Authors. All rights reserved. +// Copyright (c) 2012 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. @@ -57,7 +57,8 @@ class AutocompleteHistoryManager : public content::WebContentsObserver, friend class AutocompleteHistoryManagerTest; friend class AutofillManagerTest; FRIEND_TEST_ALL_PREFIXES(AutocompleteHistoryManagerTest, ExternalDelegate); - FRIEND_TEST_ALL_PREFIXES(AutofillManagerTest, TestTabContents); + FRIEND_TEST_ALL_PREFIXES(AutofillManagerTest, + TestTabContentsWithExternalDelegate); // For tests. AutocompleteHistoryManager(TabContents* tab_contents, diff --git a/chrome/browser/autocomplete_history_manager_unittest.cc b/chrome/browser/autocomplete_history_manager_unittest.cc index d1086f1..94a7a9e 100644 --- a/chrome/browser/autocomplete_history_manager_unittest.cc +++ b/chrome/browser/autocomplete_history_manager_unittest.cc @@ -1,4 +1,4 @@ -// Copyright (c) 2011 The Chromium Authors. All rights reserved. +// Copyright (c) 2012 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. @@ -142,7 +142,7 @@ namespace { class MockAutofillExternalDelegate : public AutofillExternalDelegate { public: explicit MockAutofillExternalDelegate(TabContentsWrapper* wrapper) - : AutofillExternalDelegate(wrapper) {} + : AutofillExternalDelegate(wrapper, NULL) {} virtual ~MockAutofillExternalDelegate() {} virtual void OnQuery(int query_id, @@ -171,7 +171,8 @@ class MockAutofillExternalDelegate : public AutofillExternalDelegate { virtual void OnQueryPlatformSpecific( int query_id, const webkit::forms::FormData& form, - const webkit::forms::FormField& field) OVERRIDE {} + const webkit::forms::FormField& field, + const gfx::Rect& bounds) OVERRIDE {} private: DISALLOW_COPY_AND_ASSIGN(MockAutofillExternalDelegate); diff --git a/chrome/browser/autofill/autofill_external_delegate.cc b/chrome/browser/autofill/autofill_external_delegate.cc index 6d0a6f3..8c0bcdd 100644 --- a/chrome/browser/autofill/autofill_external_delegate.cc +++ b/chrome/browser/autofill/autofill_external_delegate.cc @@ -1,4 +1,4 @@ -// Copyright (c) 2011 The Chromium Authors. All rights reserved. +// Copyright (c) 2012 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. @@ -17,8 +17,10 @@ AutofillExternalDelegate::~AutofillExternalDelegate() { } AutofillExternalDelegate::AutofillExternalDelegate( - TabContentsWrapper* tab_contents_wrapper) + TabContentsWrapper* tab_contents_wrapper, + AutofillManager* autofill_manager) : tab_contents_wrapper_(tab_contents_wrapper), + autofill_manager_(autofill_manager), autofill_query_id_(0), display_warning_if_disabled_(false), has_shown_autofill_popup_for_current_edit_(false) { @@ -41,7 +43,7 @@ void AutofillExternalDelegate::OnQuery(int query_id, display_warning_if_disabled_ = display_warning_if_disabled; autofill_query_id_ = query_id; - OnQueryPlatformSpecific(query_id, form, field); + OnQueryPlatformSpecific(query_id, form, field, bounds); } void AutofillExternalDelegate::DidEndTextFieldEditing() { @@ -134,7 +136,7 @@ void AutofillExternalDelegate::OnSuggestionsReturned( // in an autofill_external_delegate_YOUROS.cc. Currently there are // none, so all platforms use the default. -#if !defined(OS_ANDROID) +#if !defined(OS_ANDROID) && !defined(TOOLKIT_GTK) AutofillExternalDelegate* AutofillExternalDelegate::Create( TabContentsWrapper*, AutofillManager*) { diff --git a/chrome/browser/autofill/autofill_external_delegate.h b/chrome/browser/autofill/autofill_external_delegate.h index 4890565..20d15bb 100644 --- a/chrome/browser/autofill/autofill_external_delegate.h +++ b/chrome/browser/autofill/autofill_external_delegate.h @@ -1,4 +1,4 @@ -// Copyright (c) 2011 The Chromium Authors. All rights reserved. +// Copyright (c) 2012 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. @@ -76,7 +76,8 @@ class AutofillExternalDelegate { void DidEndTextFieldEditing(); protected: - explicit AutofillExternalDelegate(TabContentsWrapper* tab_contents_wrapper); + explicit AutofillExternalDelegate(TabContentsWrapper* tab_contents_wrapper, + AutofillManager* autofill_manager); // Displays the the Autofill results to the user with an external // Autofill popup that lives completely in the browser. The suggestions @@ -89,13 +90,14 @@ class AutofillExternalDelegate { int separator_index) = 0; // Handle instance specific OnQueryCode. - virtual void OnQueryPlatformSpecific( - int query_id, - const webkit::forms::FormData& form, - const webkit::forms::FormField& field) = 0; + virtual void OnQueryPlatformSpecific(int query_id, + const webkit::forms::FormData& form, + const webkit::forms::FormField& field, + const gfx::Rect& bounds) = 0; private: TabContentsWrapper* tab_contents_wrapper_; // weak; owns me. + AutofillManager* autofill_manager_; // weak. // The ID of the last request sent for form field Autofill. Used to ignore // out of date responses. diff --git a/chrome/browser/autofill/autofill_external_delegate_gtk.cc b/chrome/browser/autofill/autofill_external_delegate_gtk.cc new file mode 100644 index 0000000..e39b72e --- /dev/null +++ b/chrome/browser/autofill/autofill_external_delegate_gtk.cc @@ -0,0 +1,86 @@ +// Copyright (c) 2012 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/autofill/autofill_external_delegate_gtk.h" + +#include "chrome/browser/ui/gtk/autofill/autofill_popup_view_gtk.h" +#include "chrome/browser/ui/tab_contents/tab_contents_wrapper.h" +#include "content/browser/tab_contents/tab_contents.h" +#include "content/browser/tab_contents/tab_contents_view.h" +#include "content/public/browser/web_contents.h" + +AutofillExternalDelegate* AutofillExternalDelegate::Create( + TabContentsWrapper* tab_contents_wrapper, + AutofillManager* autofill_manager) { + return new AutofillExternalDelegateGtk(tab_contents_wrapper, + autofill_manager); +} + +AutofillExternalDelegateGtk::AutofillExternalDelegateGtk( + TabContentsWrapper* tab_contents_wrapper, + AutofillManager* autofill_manager) + : AutofillExternalDelegate(tab_contents_wrapper, autofill_manager), + web_contents_(tab_contents_wrapper->web_contents()) { + tab_native_view_ = web_contents_->GetView()->GetNativeView(); +} + +AutofillExternalDelegateGtk::~AutofillExternalDelegateGtk() { +} + +void AutofillExternalDelegateGtk::OnQueryPlatformSpecific( + int query_id, + const webkit::forms::FormData& form, + const webkit::forms::FormField& field, + const gfx::Rect& bounds) { + CreateViewIfNeeded(); + view_->set_element_bounds(bounds); +} + +void AutofillExternalDelegateGtk::ApplyAutofillSuggestions( + const std::vector<string16>& autofill_values, + const std::vector<string16>& autofill_labels, + const std::vector<string16>& autofill_icons, + const std::vector<int>& autofill_unique_ids, + int separator_index) { + view_->Show(autofill_values, + autofill_labels, + autofill_icons, + autofill_unique_ids, + separator_index); +} + +void AutofillExternalDelegateGtk::HideAutofillPopup() { + if (!view_.get()) + return; + + view_->Hide(); + view_.reset(); + + GtkWidget* toplevel = gtk_widget_get_toplevel(tab_native_view_); + g_signal_handler_disconnect(toplevel, event_handler_id_); +} + +void AutofillExternalDelegateGtk::CreateViewIfNeeded() { + if (view_.get()) + return; + + view_.reset(new AutofillPopupViewGtk(web_contents_, + tab_native_view_)); + + GtkWidget* toplevel = gtk_widget_get_toplevel(tab_native_view_); + if (!g_signal_handler_is_connected(toplevel, event_handler_id_)) { + event_handler_id_ = g_signal_connect( + toplevel, + "focus-out-event", + G_CALLBACK(HandleViewFocusOutThunk), + this); + } +} + +gboolean AutofillExternalDelegateGtk::HandleViewFocusOut(GtkWidget* sender, + GdkEventFocus* event) { + HideAutofillPopup(); + + return TRUE; +} diff --git a/chrome/browser/autofill/autofill_external_delegate_gtk.h b/chrome/browser/autofill/autofill_external_delegate_gtk.h new file mode 100644 index 0000000..31e2fd0 --- /dev/null +++ b/chrome/browser/autofill/autofill_external_delegate_gtk.h @@ -0,0 +1,66 @@ +// Copyright (c) 2012 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. + +#ifndef CHROME_BROWSER_AUTOFILL_AUTOFILL_EXTERNAL_DELEGATE_GTK_H_ +#define CHROME_BROWSER_AUTOFILL_AUTOFILL_EXTERNAL_DELEGATE_GTK_H_ +#pragma once + +#include <gtk/gtk.h> + +#include "base/memory/scoped_ptr.h" +#include "chrome/browser/autofill/autofill_external_delegate.h" +#include "ui/base/gtk/gtk_signal.h" +#include "ui/gfx/native_widget_types.h" + +class AutofillPopupViewGtk; + +namespace content { +class WebContents; +} + +class AutofillExternalDelegateGtk : public AutofillExternalDelegate { + public: + AutofillExternalDelegateGtk(TabContentsWrapper* tab_contents_wrapper, + AutofillManager* autofill_manager); + + virtual ~AutofillExternalDelegateGtk(); + + // AutofillExternalDelegate implementation. + virtual void HideAutofillPopup() OVERRIDE; + + protected: + // AutofillExternalDelegate implementations. + virtual void OnQueryPlatformSpecific( + int query_id, + const webkit::forms::FormData& form, + const webkit::forms::FormField& field, + const gfx::Rect& bounds) OVERRIDE; + virtual void ApplyAutofillSuggestions( + const std::vector<string16>& autofill_values, + const std::vector<string16>& autofill_labels, + const std::vector<string16>& autofill_icons, + const std::vector<int>& autofill_unique_ids, + int separator_index) OVERRIDE; + + private: + // Create a valid view to display the autofill results if one doesn't + // currently exist. + void CreateViewIfNeeded(); + + CHROMEGTK_CALLBACK_1(AutofillExternalDelegateGtk, gboolean, + HandleViewFocusOut, GdkEventFocus*); + + scoped_ptr<AutofillPopupViewGtk> view_; + + content::WebContents* web_contents_; // Weak reference. + gfx::NativeView tab_native_view_; // Weak reference. + + // The handler value for the focus out event, allows us to block and unblock + // it as needed. + gulong event_handler_id_; + + DISALLOW_COPY_AND_ASSIGN(AutofillExternalDelegateGtk); +}; + +#endif // CHROME_BROWSER_AUTOFILL_AUTOFILL_EXTERNAL_DELEGATE_GTK_H_ diff --git a/chrome/browser/autofill/autofill_external_delegate_unittest.cc b/chrome/browser/autofill/autofill_external_delegate_unittest.cc new file mode 100644 index 0000000..f9e6f6c --- /dev/null +++ b/chrome/browser/autofill/autofill_external_delegate_unittest.cc @@ -0,0 +1,106 @@ +// Copyright (c) 2012 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 <vector> + +#include "base/compiler_specific.h" +#include "base/memory/ref_counted.h" +#include "base/string16.h" +#include "chrome/browser/autofill/autofill_external_delegate.h" +#include "chrome/browser/autofill/autofill_manager.h" +#include "chrome/browser/ui/tab_contents/test_tab_contents_wrapper.h" +#include "chrome/test/base/testing_profile.h" +#include "content/test/test_browser_thread.h" +#include "testing/gmock/include/gmock/gmock.h" +#include "testing/gtest/include/gtest/gtest.h" +#include "ui/gfx/rect.h" +#include "webkit/forms/form_data.h" +#include "webkit/forms/form_field.h" + +using content::BrowserThread; +using testing::_; +using webkit::forms::FormData; +using webkit::forms::FormField; + +namespace { + +class MockAutofillExternalDelegate : public AutofillExternalDelegate { + public: + explicit MockAutofillExternalDelegate(TabContentsWrapper* wrapper, + AutofillManager* autofill_manager) + : AutofillExternalDelegate(wrapper, autofill_manager) {} + virtual ~MockAutofillExternalDelegate() {} + + virtual void HideAutofillPopup() OVERRIDE {} + + MOCK_METHOD5(ApplyAutofillSuggestions, void( + const std::vector<string16>& autofill_values, + const std::vector<string16>& autofill_labels, + const std::vector<string16>& autofill_icons, + const std::vector<int>& autofill_unique_ids, + int separator_index)); + + MOCK_METHOD4(OnQueryPlatformSpecific, + void(int query_id, + const webkit::forms::FormData& form, + const webkit::forms::FormField& field, + const gfx::Rect& bounds)); + + private: + DISALLOW_COPY_AND_ASSIGN(MockAutofillExternalDelegate); +}; + +} // namespace + +class AutofillExternalDelegateTest : public TabContentsWrapperTestHarness { + public: + AutofillExternalDelegateTest() + : ui_thread_(BrowserThread::UI, &message_loop_) {} + virtual ~AutofillExternalDelegateTest() {} + + virtual void SetUp() OVERRIDE { + TabContentsWrapperTestHarness::SetUp(); + autofill_manager_ = new AutofillManager(contents_wrapper()); + } + + protected: + scoped_refptr<AutofillManager> autofill_manager_; + + private: + content::TestBrowserThread ui_thread_; + + DISALLOW_COPY_AND_ASSIGN(AutofillExternalDelegateTest); +}; + +// Test that our external delegate called the virtual methods at the right time. +TEST_F(AutofillExternalDelegateTest, TestExternalDelegateVirtualCalls) { + MockAutofillExternalDelegate external_delegate(contents_wrapper(), + autofill_manager_); + const int kQueryId = 5; + const FormData form; + FormField field; + field.is_focusable = true; + field.should_autocomplete = true; + const gfx::Rect bounds; + + EXPECT_CALL(external_delegate, + OnQueryPlatformSpecific(kQueryId, form, field, bounds)); + + // This should call OnQueryPlatform specific. + external_delegate.OnQuery(kQueryId, form, field, bounds, false); + + + EXPECT_CALL(external_delegate, ApplyAutofillSuggestions(_, _, _, _, _)); + + // This should call ApplyAutofillSuggestions. + std::vector<string16> autofill_item; + autofill_item.push_back(string16()); + std::vector<int> autofill_ids; + autofill_ids.push_back(1); + external_delegate.OnSuggestionsReturned(kQueryId, + autofill_item, + autofill_item, + autofill_item, + autofill_ids); +} diff --git a/chrome/browser/autofill/autofill_manager_unittest.cc b/chrome/browser/autofill/autofill_manager_unittest.cc index 22abbf0..ee42ca3 100644 --- a/chrome/browser/autofill/autofill_manager_unittest.cc +++ b/chrome/browser/autofill/autofill_manager_unittest.cc @@ -1,4 +1,4 @@ -// Copyright (c) 2011 The Chromium Authors. All rights reserved. +// Copyright (c) 2012 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. @@ -2864,8 +2864,9 @@ namespace { class MockAutofillExternalDelegate : public AutofillExternalDelegate { public: - explicit MockAutofillExternalDelegate(TabContentsWrapper* wrapper) - : AutofillExternalDelegate(wrapper) {} + explicit MockAutofillExternalDelegate(TabContentsWrapper* wrapper, + AutofillManager* autofill_manager) + : AutofillExternalDelegate(wrapper, autofill_manager) {} virtual ~MockAutofillExternalDelegate() {} MOCK_METHOD5(OnQuery, void(int query_id, @@ -2883,10 +2884,10 @@ class MockAutofillExternalDelegate : public AutofillExternalDelegate { const std::vector<int>& autofill_unique_ids, int separator_index) OVERRIDE {} - virtual void OnQueryPlatformSpecific( - int query_id, - const webkit::forms::FormData& form, - const webkit::forms::FormField& field) OVERRIDE {} + virtual void OnQueryPlatformSpecific(int query_id, + const webkit::forms::FormData& form, + const webkit::forms::FormField& field, + const gfx::Rect& bounds) OVERRIDE {} private: DISALLOW_COPY_AND_ASSIGN(MockAutofillExternalDelegate); @@ -2896,7 +2897,8 @@ class MockAutofillExternalDelegate : public AutofillExternalDelegate { // Test our external delegate is called at the right time. TEST_F(AutofillManagerTest, TestExternalDelegate) { - MockAutofillExternalDelegate external_delegate(contents_wrapper()); + MockAutofillExternalDelegate external_delegate(contents_wrapper(), + autofill_manager_); EXPECT_CALL(external_delegate, OnQuery(_, _, _, _, _)); autofill_manager_->SetExternalDelegate(&external_delegate); @@ -2910,8 +2912,8 @@ TEST_F(AutofillManagerTest, TestExternalDelegate) { autofill_manager_->SetExternalDelegate(NULL); } -#if defined(OS_ANDROID) -// Only OS_ANDROID defines an external delegate, but prerequisites for +#if defined(OS_ANDROID) || defined(TOOLKIT_GTK) +// OS_ANDROID defines an external delegate, but prerequisites for // landing autofill_external_delegate_android.cc in the Chromium tree // have not themselves landed. diff --git a/chrome/browser/autofill/autofill_popup_view.cc b/chrome/browser/autofill/autofill_popup_view.cc new file mode 100644 index 0000000..9a2ea79 --- /dev/null +++ b/chrome/browser/autofill/autofill_popup_view.cc @@ -0,0 +1,32 @@ +// Copyright (c) 2012 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/autofill/autofill_popup_view.h" + +#include "content/public/browser/web_contents.h" +#include "content/public/browser/navigation_controller.h" +#include "content/public/browser/notification_service.h" +#include "content/public/browser/notification_source.h" +#include "content/public/browser/notification_types.h" + +AutofillPopupView::AutofillPopupView(content::WebContents* web_contents) { + registrar_.Add(this, + content::NOTIFICATION_WEB_CONTENTS_HIDDEN, + content::Source<content::WebContents>(web_contents)); + registrar_.Add( + this, + content::NOTIFICATION_NAV_ENTRY_COMMITTED, + content::Source<content::NavigationController>( + &(web_contents->GetController()))); +} + +AutofillPopupView::~AutofillPopupView() {} + +void AutofillPopupView::Observe(int type, + const content::NotificationSource& source, + const content::NotificationDetails& details) { + if (type == content::NOTIFICATION_WEB_CONTENTS_HIDDEN + || type == content::NOTIFICATION_NAV_ENTRY_COMMITTED) + Hide(); +} diff --git a/chrome/browser/autofill/autofill_popup_view.h b/chrome/browser/autofill/autofill_popup_view.h new file mode 100644 index 0000000..bde5cd2 --- /dev/null +++ b/chrome/browser/autofill/autofill_popup_view.h @@ -0,0 +1,54 @@ +// Copyright (c) 2012 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. + +#ifndef CHROME_BROWSER_AUTOFILL_AUTOFILL_POPUP_VIEW_H_ +#define CHROME_BROWSER_AUTOFILL_AUTOFILL_POPUP_VIEW_H_ +#pragma once + +#include "base/compiler_specific.h" +#include "base/string16.h" +#include "content/public/browser/notification_registrar.h" +#include "content/public/browser/notification_observer.h" +#include "ui/gfx/rect.h" + +namespace content { +class WebContents; +} + +class AutofillPopupView : public content::NotificationObserver { + public: + explicit AutofillPopupView(content::WebContents* web_contents); + virtual ~AutofillPopupView(); + + // Hide the popup from view. + virtual void Hide() = 0; + + // Display the autofill popup and fill it in with the values passed in. + virtual void Show(const std::vector<string16>& autofill_values, + const std::vector<string16>& autofill_labels, + const std::vector<string16>& autofill_icons, + const std::vector<int>& autofill_unique_ids, + int separator_index) = 0; + + + void set_element_bounds(const gfx::Rect& bounds) { + element_bounds_ = bounds; + } + + const gfx::Rect& element_bounds() { return element_bounds_; } + + private: + // content::NotificationObserver method override. + virtual void Observe(int type, + const content::NotificationSource& source, + const content::NotificationDetails& details) OVERRIDE; + + // A scoped container for notification registries. + content::NotificationRegistrar registrar_; + + // The bounds of the text element that is the focus of the Autofill. + gfx::Rect element_bounds_; +}; + +#endif // CHROME_BROWSER_AUTOFILL_AUTOFILL_POPUP_VIEW_H_ diff --git a/chrome/browser/autofill/autofill_popup_view_browsertest.cc b/chrome/browser/autofill/autofill_popup_view_browsertest.cc new file mode 100644 index 0000000..52f6421 --- /dev/null +++ b/chrome/browser/autofill/autofill_popup_view_browsertest.cc @@ -0,0 +1,87 @@ +// Copyright (c) 2012 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/autofill/autofill_popup_view.h" + +#include "base/memory/scoped_ptr.h" +#include "chrome/browser/ui/browser.h" +#include "chrome/test/base/ui_test_utils.h" +#include "content/browser/tab_contents/tab_contents.h" +#include "content/public/browser/navigation_controller.h" +#include "content/public/browser/notification_service.h" +#include "content/public/browser/notification_types.h" +#include "content/public/browser/page_navigator.h" +#include "content/public/common/url_constants.h" +#include "content/test/browser_test.h" +#include "testing/gmock/include/gmock/gmock.h" +#include "testing/gtest/include/gtest/gtest.h" + +class TestAutofillPopupView : public AutofillPopupView { + public: + explicit TestAutofillPopupView(content::WebContents* web_contents) + : AutofillPopupView(web_contents) {} + virtual ~TestAutofillPopupView() {} + + MOCK_METHOD0(Hide, void()); + + virtual void Show(const std::vector<string16>& autofill_values, + const std::vector<string16>& autofill_labels, + const std::vector<string16>& autofill_icons, + const std::vector<int>& autofill_unique_ids, + int separator_index) OVERRIDE {} +}; + +class AutofillPopupViewBrowserTest : public InProcessBrowserTest { + public: + AutofillPopupViewBrowserTest() {} + virtual ~AutofillPopupViewBrowserTest() {} + + protected: + scoped_ptr<TestAutofillPopupView> autofill_popup_view_; +}; + + +#if defined(OS_WIN) +// http://crbug.com/109269 +#define MAYBE_SwitchTabAndHideAutofillPopup \ + DISABLED_SwitchTabAndHideAutofillPopup +#else +#define MAYBE_SwitchTabAndHideAutofillPopup SwitchTabAndHideAutofillPopup +#endif +IN_PROC_BROWSER_TEST_F(InProcessBrowserTest, + MAYBE_SwitchTabAndHideAutofillPopup) { + content::WebContents* web_contents = browser()->GetSelectedWebContents(); + TestAutofillPopupView autofill_popup_view(web_contents); + EXPECT_CALL(autofill_popup_view, Hide()); + + ui_test_utils::WindowedNotificationObserver observer( + content::NOTIFICATION_WEB_CONTENTS_HIDDEN, + content::Source<content::WebContents>(web_contents)); + browser()->AddSelectedTabWithURL(GURL(chrome::kAboutBlankURL), + content::PAGE_TRANSITION_START_PAGE); + observer.Wait(); + + // The mock verifies that the call was made. +} + +IN_PROC_BROWSER_TEST_F(InProcessBrowserTest, + TestPageNavigationHidingAutofillPopup) { + content::WebContents* web_contents = browser()->GetSelectedWebContents(); + TestAutofillPopupView autofill_popup_view(web_contents); + EXPECT_CALL(autofill_popup_view, Hide()); + + ui_test_utils::WindowedNotificationObserver observer( + content::NOTIFICATION_NAV_ENTRY_COMMITTED, + content::Source<content::NavigationController>( + &(web_contents->GetController()))); + browser()->OpenURL(content::OpenURLParams( + GURL(chrome::kAboutBlankURL), content::Referrer(), + CURRENT_TAB, content::PAGE_TRANSITION_TYPED, false)); + browser()->OpenURL(content::OpenURLParams( + GURL(chrome::kAboutCrashURL), content::Referrer(), + CURRENT_TAB, content::PAGE_TRANSITION_TYPED, false)); + observer.Wait(); + + // The mock verifies that the call was made. +} diff --git a/chrome/browser/ui/gtk/autofill/autofill_popup_view_gtk.cc b/chrome/browser/ui/gtk/autofill/autofill_popup_view_gtk.cc new file mode 100644 index 0000000..5df1bdc --- /dev/null +++ b/chrome/browser/ui/gtk/autofill/autofill_popup_view_gtk.cc @@ -0,0 +1,62 @@ +// Copyright (c) 2012 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 "autofill_popup_view_gtk.h" + +#include "base/logging.h" +#include "ui/base/gtk/gtk_windowing.h" + +AutofillPopupViewGtk::AutofillPopupViewGtk(content::WebContents* web_contents, + GtkWidget* parent) + : AutofillPopupView(web_contents), + parent_(parent), + window_(gtk_window_new(GTK_WINDOW_POPUP)) { + CHECK(parent != NULL); + gtk_window_set_resizable(GTK_WINDOW(window_), FALSE); + gtk_widget_set_app_paintable(window_, TRUE); + gtk_widget_set_double_buffered(window_, TRUE); + + // Setup the window to ensure it recieves the expose event. + gtk_widget_add_events(window_, GDK_EXPOSURE_MASK); + g_signal_connect(window_, "expose-event", + G_CALLBACK(HandleExposeThunk), this); +} + +AutofillPopupViewGtk::~AutofillPopupViewGtk() { + gtk_widget_destroy(window_); +} + +void AutofillPopupViewGtk::Hide() { + gtk_widget_hide(window_); +} + +// TODO(csharp): Actually show the values. +void AutofillPopupViewGtk::Show(const std::vector<string16>& autofill_values, + const std::vector<string16>& autofill_labels, + const std::vector<string16>& autofill_icons, + const std::vector<int>& autofill_unique_ids, + int separator_index) { + gint origin_x, origin_y; + gdk_window_get_origin(gtk_widget_get_window(parent_), &origin_x, &origin_y); + + gtk_window_move(GTK_WINDOW(window_), + origin_x + element_bounds().x(), + origin_y + element_bounds().y() + element_bounds().height()); + + gtk_widget_set_size_request( + window_, + element_bounds().width(), + element_bounds().height() * autofill_values.size()); + + gtk_widget_show(window_); + + GtkWidget* toplevel = gtk_widget_get_toplevel(parent_); + CHECK(gtk_widget_is_toplevel(toplevel)); + ui::StackPopupWindow(window_, toplevel); +} + +gboolean AutofillPopupViewGtk::HandleExpose(GtkWidget* widget, + GdkEventExpose* event) { + return TRUE; +} diff --git a/chrome/browser/ui/gtk/autofill/autofill_popup_view_gtk.h b/chrome/browser/ui/gtk/autofill/autofill_popup_view_gtk.h new file mode 100644 index 0000000..d45b0a4 --- /dev/null +++ b/chrome/browser/ui/gtk/autofill/autofill_popup_view_gtk.h @@ -0,0 +1,38 @@ +// Copyright (c) 2012 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. + +#ifndef CHROME_BROWSER_UI_GTK_AUTOFILL_AUTOFILL_POPUP_VIEW_GTK_H_ +#define CHROME_BROWSER_UI_GTK_AUTOFILL_AUTOFILL_POPUP_VIEW_GTK_H_ +#pragma once + +#include <gtk/gtk.h> + +#include "base/string16.h" +#include "chrome/browser/autofill/autofill_popup_view.h" +#include "ui/base/gtk/gtk_signal.h" + +#include <vector> + +class AutofillPopupViewGtk : public AutofillPopupView { + public: + AutofillPopupViewGtk(content::WebContents* web_contents, GtkWidget* parent); + virtual ~AutofillPopupViewGtk(); + + // AutofillPopupView implementations. + virtual void Hide() OVERRIDE; + virtual void Show(const std::vector<string16>& autofill_values, + const std::vector<string16>& autofill_labels, + const std::vector<string16>& autofill_icons, + const std::vector<int>& autofill_unique_ids, + int separator_index) OVERRIDE; + + private: + CHROMEGTK_CALLBACK_1(AutofillPopupViewGtk, gboolean, HandleExpose, + GdkEventExpose*); + + GtkWidget* parent_; // Weak reference. + GtkWidget* window_; // Strong refence. +}; + +#endif // CHROME_BROWSER_UI_GTK_AUTOFILL_AUTOFILL_POPUP_VIEW_GTK_H_ diff --git a/chrome/chrome_browser.gypi b/chrome/chrome_browser.gypi index bc1ff6d..acb765b 100644 --- a/chrome/chrome_browser.gypi +++ b/chrome/chrome_browser.gypi @@ -151,6 +151,8 @@ 'browser/autofill/autofill_download.h', 'browser/autofill/autofill_external_delegate.cc', 'browser/autofill/autofill_external_delegate.h', + 'browser/autofill/autofill_external_delegate_gtk.cc', + 'browser/autofill/autofill_external_delegate_gtk.h', 'browser/autofill/autofill_feedback_infobar_delegate.cc', 'browser/autofill/autofill_feedback_infobar_delegate.h', 'browser/autofill/autofill_field.cc', @@ -161,6 +163,8 @@ 'browser/autofill/autofill_manager.h', 'browser/autofill/autofill_metrics.cc', 'browser/autofill/autofill_metrics.h', + 'browser/autofill/autofill_popup_view.cc', + 'browser/autofill/autofill_popup_view.h', 'browser/autofill/autofill_profile.cc', 'browser/autofill/autofill_profile.h', 'browser/autofill/autofill_regex_constants.cc.utf8', @@ -2987,6 +2991,8 @@ 'browser/ui/gtk/about_chrome_dialog.h', 'browser/ui/gtk/accelerators_gtk.cc', 'browser/ui/gtk/accelerators_gtk.h', + 'browser/ui/gtk/autofill/autofill_popup_view_gtk.cc', + 'browser/ui/gtk/autofill/autofill_popup_view_gtk.h', 'browser/ui/gtk/avatar_menu_bubble_gtk.cc', 'browser/ui/gtk/avatar_menu_bubble_gtk.h', 'browser/ui/gtk/avatar_menu_button_gtk.cc', diff --git a/chrome/chrome_tests.gypi b/chrome/chrome_tests.gypi index bb4c46a..c506fd2 100644 --- a/chrome/chrome_tests.gypi +++ b/chrome/chrome_tests.gypi @@ -1255,6 +1255,7 @@ 'browser/autofill/address_unittest.cc', 'browser/autofill/autofill_country_unittest.cc', 'browser/autofill/autofill_download_unittest.cc', + 'browser/autofill/autofill_external_delegate_unittest.cc', 'browser/autofill/autofill_field_unittest.cc', 'browser/autofill/autofill_ie_toolbar_import_win_unittest.cc', 'browser/autofill/autofill_manager_unittest.cc', @@ -2460,6 +2461,7 @@ 'browser/accessibility/dump_accessibility_tree_browsertest.cc', 'browser/autocomplete/autocomplete_browsertest.cc', 'browser/autofill/form_structure_browsertest.cc', + 'browser/autofill/autofill_popup_view_browsertest.cc', 'browser/automation/automation_tab_helper_browsertest.cc', 'browser/bookmarks/bookmark_extension_apitest.cc', 'browser/bookmarks/bookmark_manager_extension_apitest.cc', |