summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorjhawkins@chromium.org <jhawkins@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2010-04-09 22:56:34 +0000
committerjhawkins@chromium.org <jhawkins@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2010-04-09 22:56:34 +0000
commitcf28ec5f4f485d4758de3817cd116e47fdc3edeb (patch)
treee69ea0cac56aaabe71901a1f2bce2e33061dc88a
parent5b6699d3ed74c9382c5f9a2aa8c8f2500900c7f8 (diff)
downloadchromium_src-cf28ec5f4f485d4758de3817cd116e47fdc3edeb.zip
chromium_src-cf28ec5f4f485d4758de3817cd116e47fdc3edeb.tar.gz
chromium_src-cf28ec5f4f485d4758de3817cd116e47fdc3edeb.tar.bz2
AutoFill: Fill the default profile when the AutoFill accelerator combo is pressed (ctrl-shift-a).
BUG=39491 TEST=none Review URL: http://codereview.chromium.org/1521020 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@44149 0039d316-1c4b-4281-b951-d872f2087c98
-rw-r--r--chrome/app/chrome_dll.rc1
-rw-r--r--chrome/app/chrome_dll_resource.h1
-rw-r--r--chrome/browser/autofill/autofill_manager.cc52
-rw-r--r--chrome/browser/autofill/autofill_manager.h5
-rw-r--r--chrome/browser/autofill/form_structure.cc51
-rw-r--r--chrome/browser/autofill/form_structure.h16
-rw-r--r--chrome/browser/autofill/form_structure_unittest.cc108
-rw-r--r--chrome/browser/browser.cc16
-rw-r--r--chrome/browser/browser.h1
-rw-r--r--chrome/browser/gtk/accelerators_gtk.cc4
-rw-r--r--chrome/browser/renderer_host/render_view_host.cc5
-rw-r--r--chrome/browser/renderer_host/render_view_host.h3
-rw-r--r--chrome/browser/tab_contents/tab_contents.cc10
-rw-r--r--chrome/browser/tab_contents/tab_contents.h3
-rw-r--r--chrome/browser/views/accelerator_table_gtk.cc3
-rw-r--r--chrome/common/render_messages_internal.h3
-rw-r--r--chrome/renderer/form_manager.cc7
-rw-r--r--chrome/renderer/form_manager.h3
-rw-r--r--chrome/renderer/render_view.cc6
-rw-r--r--chrome/renderer/render_view.h3
-rw-r--r--webkit/glue/form_data.h10
21 files changed, 277 insertions, 34 deletions
diff --git a/chrome/app/chrome_dll.rc b/chrome/app/chrome_dll.rc
index 00c87f7..c9322d3 100644
--- a/chrome/app/chrome_dll.rc
+++ b/chrome/app/chrome_dll.rc
@@ -136,6 +136,7 @@ BEGIN
VK_OEM_PLUS, IDC_ZOOM_PLUS, VIRTKEY, CONTROL
VK_OEM_PLUS, IDC_ZOOM_PLUS, VIRTKEY, CONTROL, SHIFT
VK_ADD, IDC_ZOOM_PLUS, VIRTKEY, CONTROL
+ "A", IDC_AUTOFILL_DEFAULT, VIRTKEY, CONTROL, SHIFT
END
IDR_CHROMEFRAME ACCELERATORS
diff --git a/chrome/app/chrome_dll_resource.h b/chrome/app/chrome_dll_resource.h
index ed5bc03..917cb01 100644
--- a/chrome/app/chrome_dll_resource.h
+++ b/chrome/app/chrome_dll_resource.h
@@ -216,6 +216,7 @@
#define IDC_SHOW_PAGE_MENU 40021
#define IDC_SHOW_EXTENSION_SHELF 40022
#define IDC_MANAGE_EXTENSIONS 40023
+#define IDC_AUTOFILL_DEFAULT 40024
// Spell-check
// Insert any additional suggestions before _LAST; these have to be consecutive.
diff --git a/chrome/browser/autofill/autofill_manager.cc b/chrome/browser/autofill/autofill_manager.cc
index e4d4aae..bcac2ed 100644
--- a/chrome/browser/autofill/autofill_manager.cc
+++ b/chrome/browser/autofill/autofill_manager.cc
@@ -449,6 +449,58 @@ bool AutoFillManager::IsAutoFillEnabled() {
return prefs->GetBoolean(prefs::kAutoFillEnabled);
}
+void AutoFillManager::FillDefaultProfile() {
+ if (!IsAutoFillEnabled())
+ return;
+
+ RenderViewHost* host = tab_contents_->render_view_host();
+ if (!host)
+ return;
+
+ // TODO(jhawkins): Do we need to wait for the profiles to be loaded?
+ const std::vector<AutoFillProfile*>& profiles = personal_data_->profiles();
+ const std::vector<CreditCard*>& credit_cards = personal_data_->credit_cards();
+ if (profiles.empty() && credit_cards.empty())
+ return;
+
+ AutoFillProfile* profile = NULL;
+ int default_profile = personal_data_->DefaultProfile();
+ if (default_profile != -1)
+ profile = profiles[default_profile];
+
+ CreditCard* credit_card = NULL;
+ int default_credit_card = personal_data_->DefaultCreditCard();
+ if (default_credit_card != -1)
+ credit_card = credit_cards[default_credit_card];
+
+ // We'll have either one or the other at this point.
+ DCHECK(profile || credit_card);
+
+ std::vector<FormData> forms;
+ for (std::vector<FormStructure*>::const_iterator iter =
+ form_structures_.begin();
+ iter != form_structures_.end(); ++iter) {
+ const FormStructure* form_structure = *iter;
+ FormData form = form_structure->ConvertToFormData();
+ DCHECK_EQ(form_structure->field_count(), form.fields.size());
+
+ for (size_t i = 0; i < form_structure->field_count(); ++i) {
+ const AutoFillField* field = form_structure->field(i);
+
+ AutoFillType type(field->type());
+ if (credit_card && type.group() == AutoFillType::CREDIT_CARD) {
+ form.fields[i].set_value(credit_card->GetFieldText(type));
+ } else if (profile) {
+ form.fields[i].set_value(profile->GetFieldText(type));
+ }
+ }
+
+ forms.push_back(form);
+ }
+
+ host->AutoFillForms(forms);
+}
+
AutoFillManager::AutoFillManager()
: tab_contents_(NULL),
personal_data_(NULL),
diff --git a/chrome/browser/autofill/autofill_manager.h b/chrome/browser/autofill/autofill_manager.h
index e765bd3..a8fe529 100644
--- a/chrome/browser/autofill/autofill_manager.h
+++ b/chrome/browser/autofill/autofill_manager.h
@@ -95,6 +95,11 @@ class AutoFillManager : public RenderViewHostDelegate::AutoFill,
// Returns the value of the AutoFillEnabled pref.
bool IsAutoFillEnabled();
+ // Fills all the forms in the page with the default profile.
+ // TODO(jhawkins): Do we really want to fill all of the forms on the page?
+ // Check how toolbar handles this case.
+ void FillDefaultProfile();
+
protected:
// For AutoFillInfoBarDelegateTest.
AutoFillManager();
diff --git a/chrome/browser/autofill/form_structure.cc b/chrome/browser/autofill/form_structure.cc
index bb91ec9..0c28609 100644
--- a/chrome/browser/autofill/form_structure.cc
+++ b/chrome/browser/autofill/form_structure.cc
@@ -12,7 +12,6 @@
#include "chrome/browser/autofill/field_types.h"
#include "chrome/browser/autofill/form_field.h"
#include "third_party/libjingle/files/talk/xmllite/xmlelement.h"
-#include "webkit/glue/form_data.h"
#include "webkit/glue/form_field.h"
using webkit_glue::FormData;
@@ -60,22 +59,24 @@ static std::string Hash64Bit(const std::string& str) {
FormStructure::FormStructure(const FormData& form)
: form_name_(UTF16ToUTF8(form.name)),
source_url_(form.origin),
- target_url_(form.action) {
+ target_url_(form.action),
+ autofill_count_(0) {
// Copy the form fields.
std::vector<webkit_glue::FormField>::const_iterator field;
for (field = form.fields.begin();
field != form.fields.end(); field++) {
- // We currently only handle text and select fields. This prevents us from
- // thinking we can autofill other types of controls, e.g., password, hidden,
- // submit.
- if (!LowerCaseEqualsASCII(field->form_control_type(), kControlTypeText) &&
- !LowerCaseEqualsASCII(field->form_control_type(), kControlTypeSelect))
- continue;
-
- // Add all form fields (including with empty names) to signature.
- // This is a requirement for AutoFill servers.
- form_signature_field_names_.append("&");
- form_signature_field_names_.append(UTF16ToUTF8(field->name()));
+ // We currently only handle text and select fields; however, we need to
+ // store all fields in order to match the fields stored in the FormManager.
+ // We don't append other field types to the form signature though in order
+ // to match the form signature of the AutoFill servers.
+ if (LowerCaseEqualsASCII(field->form_control_type(), kControlTypeText) ||
+ LowerCaseEqualsASCII(field->form_control_type(), kControlTypeSelect)) {
+ // Add all supported form fields (including with empty names) to
+ // signature. This is a requirement for AutoFill servers.
+ form_signature_field_names_.append("&");
+ form_signature_field_names_.append(UTF16ToUTF8(field->name()));
+ ++autofill_count_;
+ }
// Generate a unique name for this field by appending a counter to the name.
string16 unique_name = field->name() + IntToString16(fields_.size() + 1);
@@ -198,7 +199,7 @@ std::string FormStructure::FormSignature() const {
}
bool FormStructure::IsAutoFillable() const {
- if (field_count() < kRequiredFillableFields)
+ if (autofill_count() < kRequiredFillableFields)
return false;
// Rule out http(s)://*/search?...
@@ -230,6 +231,27 @@ size_t FormStructure::field_count() const {
return (field_size == 0) ? 0 : field_size - 1;
}
+FormData FormStructure::ConvertToFormData() const {
+ FormData form;
+ form.name = UTF8ToUTF16(form_name_);
+ form.origin = source_url_;
+ form.action = target_url_;
+
+ if (method_ == GET)
+ form.method = ASCIIToUTF16("GET");
+ else if (method_ == POST)
+ form.method = ASCIIToUTF16("POST");
+ else
+ NOTREACHED();
+
+ for (std::vector<AutoFillField*>::const_iterator iter = fields_.begin();
+ iter != fields_.end() && *iter; ++iter) {
+ form.fields.push_back(static_cast<webkit_glue::FormField>(**iter));
+ }
+
+ return form;
+}
+
bool FormStructure::operator==(const FormData& form) const {
// TODO(jhawkins): Is this enough to differentiate a form?
if (UTF8ToUTF16(form_name_) == form.name &&
@@ -289,4 +311,3 @@ bool FormStructure::EncodeFormRequest(
}
return true;
}
-
diff --git a/chrome/browser/autofill/form_structure.h b/chrome/browser/autofill/form_structure.h
index 4028117..c2a25a9 100644
--- a/chrome/browser/autofill/form_structure.h
+++ b/chrome/browser/autofill/form_structure.h
@@ -13,15 +13,12 @@
#include "chrome/browser/autofill/autofill_type.h"
#include "chrome/browser/autofill/field_types.h"
#include "googleurl/src/gurl.h"
+#include "webkit/glue/form_data.h"
namespace buzz {
class XmlElement;
} // namespace buzz
-namespace webkit_glue {
-struct FormData;
-} // namespace webkit_glue
-
enum RequestMethod {
GET,
POST
@@ -69,6 +66,12 @@ class FormStructure {
const AutoFillField* field(int index) const;
size_t field_count() const;
+ // Returns the number of fields that are able to be autofilled.
+ size_t autofill_count() const { return autofill_count_; }
+
+ // Converts this object to a FormData object.
+ webkit_glue::FormData ConvertToFormData() const;
+
// Used for iterating over the fields.
std::vector<AutoFillField*>::const_iterator begin() const {
return fields_.begin();
@@ -108,6 +111,9 @@ class FormStructure {
bool has_autofillable_field_;
bool has_password_fields_;
+ // The number of fields able to be autofilled.
+ size_t autofill_count_;
+
// A vector of all the input fields in the form. The vector is terminated by
// a NULL entry.
ScopedVector<AutoFillField> fields_;
@@ -119,6 +125,8 @@ class FormStructure {
// GET or POST.
RequestMethod method_;
+
+ DISALLOW_COPY_AND_ASSIGN(FormStructure);
};
#endif // CHROME_BROWSER_AUTOFILL_FORM_STRUCTURE_H_
diff --git a/chrome/browser/autofill/form_structure_unittest.cc b/chrome/browser/autofill/form_structure_unittest.cc
index 4dc4818..2bd5328 100644
--- a/chrome/browser/autofill/form_structure_unittest.cc
+++ b/chrome/browser/autofill/form_structure_unittest.cc
@@ -4,17 +4,39 @@
#include "base/scoped_ptr.h"
#include "base/string_util.h"
+#include "base/utf_string_conversions.h"
#include "chrome/browser/autofill/form_structure.h"
#include "googleurl/src/gurl.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "third_party/WebKit/WebKit/chromium/public/WebInputElement.h"
#include "webkit/glue/form_data.h"
+#include "webkit/glue/form_field.h"
using webkit_glue::FormData;
using WebKit::WebInputElement;
namespace {
+std::ostream& operator<<(std::ostream& os, const FormData& form) {
+ os << UTF16ToUTF8(form.name)
+ << " "
+ << UTF16ToUTF8(form.method)
+ << " "
+ << form.origin.spec()
+ << " "
+ << form.action.spec()
+ << " ";
+
+ for (std::vector<webkit_glue::FormField>::const_iterator iter =
+ form.fields.begin();
+ iter != form.fields.end(); ++iter) {
+ os << *iter
+ << " ";
+ }
+
+ return os;
+}
+
TEST(FormStructureTest, FieldCount) {
FormData form;
form.method = ASCIIToUTF16("post");
@@ -32,8 +54,58 @@ TEST(FormStructureTest, FieldCount) {
ASCIIToUTF16("submit")));
FormStructure form_structure(form);
- // Only text fields are counted.
- EXPECT_EQ(1U, form_structure.field_count());
+ // All fields are counted.
+ EXPECT_EQ(3U, form_structure.field_count());
+}
+
+TEST(FormStructureTest, AutoFillCount) {
+ FormData form;
+ form.method = ASCIIToUTF16("post");
+ form.fields.push_back(webkit_glue::FormField(ASCIIToUTF16("username"),
+ ASCIIToUTF16("username"),
+ string16(),
+ ASCIIToUTF16("text")));
+ form.fields.push_back(webkit_glue::FormField(ASCIIToUTF16("password"),
+ ASCIIToUTF16("password"),
+ string16(),
+ ASCIIToUTF16("password")));
+ form.fields.push_back(webkit_glue::FormField(ASCIIToUTF16("state"),
+ ASCIIToUTF16("state"),
+ string16(),
+ ASCIIToUTF16("select-one")));
+ form.fields.push_back(webkit_glue::FormField(string16(),
+ ASCIIToUTF16("Submit"),
+ string16(),
+ ASCIIToUTF16("submit")));
+ FormStructure form_structure(form);
+
+ // Only text and select fields are counted.
+ EXPECT_EQ(2U, form_structure.autofill_count());
+}
+
+TEST(FormStructureTest, ConvertToFormData) {
+ FormData form;
+ form.method = ASCIIToUTF16("post");
+ form.fields.push_back(webkit_glue::FormField(ASCIIToUTF16("username"),
+ ASCIIToUTF16("username"),
+ string16(),
+ ASCIIToUTF16("text")));
+ form.fields.push_back(webkit_glue::FormField(ASCIIToUTF16("password"),
+ ASCIIToUTF16("password"),
+ string16(),
+ ASCIIToUTF16("password")));
+ form.fields.push_back(webkit_glue::FormField(ASCIIToUTF16("state"),
+ ASCIIToUTF16("state"),
+ string16(),
+ ASCIIToUTF16("select")));
+ form.fields.push_back(webkit_glue::FormField(string16(),
+ ASCIIToUTF16("Submit"),
+ string16(),
+ ASCIIToUTF16("submit")));
+ FormStructure form_structure(form);
+
+ FormData converted = form_structure.ConvertToFormData();
+ EXPECT_EQ(form, converted);
}
TEST(FormStructureTest, IsAutoFillable) {
@@ -131,7 +203,7 @@ TEST(FormStructureTest, HeuristicsContactInfo) {
EXPECT_TRUE(form_structure->IsAutoFillable());
// Expect the correct number of fields.
- ASSERT_EQ(8UL, form_structure->field_count());
+ ASSERT_EQ(9UL, form_structure->field_count());
// Check that heuristics are initialized as UNKNOWN_TYPE.
std::vector<AutoFillField*>::const_iterator iter;
@@ -150,7 +222,7 @@ TEST(FormStructureTest, HeuristicsContactInfo) {
// Compute heuristic types.
form_structure->GetHeuristicAutoFillTypes();
- ASSERT_EQ(8U, form_structure->field_count());
+ ASSERT_EQ(9U, form_structure->field_count());
// Check that heuristics are no longer UNKNOWN_TYPE.
// First name.
@@ -170,6 +242,8 @@ TEST(FormStructureTest, HeuristicsContactInfo) {
EXPECT_EQ(ADDRESS_HOME_CITY, form_structure->field(6)->heuristic_type());
// Zip.
EXPECT_EQ(ADDRESS_HOME_ZIP, form_structure->field(7)->heuristic_type());
+ // Submit.
+ EXPECT_EQ(UNKNOWN_TYPE, form_structure->field(8)->heuristic_type());
}
TEST(FormStructureTest, HeuristicsSample8) {
@@ -247,7 +321,7 @@ TEST(FormStructureTest, HeuristicsSample8) {
// Compute heuristic types.
form_structure->GetHeuristicAutoFillTypes();
- ASSERT_EQ(9U, form_structure->field_count());
+ ASSERT_EQ(10U, form_structure->field_count());
// Check that heuristics are no longer UNKNOWN_TYPE.
// First name.
@@ -269,6 +343,8 @@ TEST(FormStructureTest, HeuristicsSample8) {
// Phone.
EXPECT_EQ(PHONE_HOME_WHOLE_NUMBER,
form_structure->field(8)->heuristic_type());
+ // Submit.
+ EXPECT_EQ(UNKNOWN_TYPE, form_structure->field(9)->heuristic_type());
}
TEST(FormStructureTest, HeuristicsSample6) {
@@ -333,7 +409,7 @@ TEST(FormStructureTest, HeuristicsSample6) {
// Compute heuristic types.
form_structure->GetHeuristicAutoFillTypes();
- ASSERT_EQ(6U, form_structure->field_count());
+ ASSERT_EQ(7U, form_structure->field_count());
// Check that heuristics are no longer UNKNOWN_TYPE.
// Email.
@@ -348,6 +424,8 @@ TEST(FormStructureTest, HeuristicsSample6) {
EXPECT_EQ(ADDRESS_HOME_CITY, form_structure->field(4)->heuristic_type());
// Zip.
EXPECT_EQ(ADDRESS_HOME_ZIP, form_structure->field(5)->heuristic_type());
+ // Submit.
+ EXPECT_EQ(UNKNOWN_TYPE, form_structure->field(6)->heuristic_type());
}
// Tests a sequence of FormFields where only labels are supplied to heuristics
@@ -398,7 +476,7 @@ TEST(FormStructureTest, HeuristicsLabelsOnly) {
EXPECT_TRUE(form_structure->IsAutoFillable());
// Expect the correct number of fields.
- ASSERT_EQ(8UL, form_structure->field_count());
+ ASSERT_EQ(9UL, form_structure->field_count());
// Check that heuristics are initialized as UNKNOWN_TYPE.
std::vector<AutoFillField*>::const_iterator iter;
@@ -417,7 +495,7 @@ TEST(FormStructureTest, HeuristicsLabelsOnly) {
// Compute heuristic types.
form_structure->GetHeuristicAutoFillTypes();
- ASSERT_EQ(8U, form_structure->field_count());
+ ASSERT_EQ(9U, form_structure->field_count());
// Check that heuristics are no longer UNKNOWN_TYPE.
// First name.
@@ -437,6 +515,8 @@ TEST(FormStructureTest, HeuristicsLabelsOnly) {
EXPECT_EQ(ADDRESS_HOME_LINE2, form_structure->field(6)->heuristic_type());
// Zip.
EXPECT_EQ(ADDRESS_HOME_ZIP, form_structure->field(7)->heuristic_type());
+ // Submit.
+ EXPECT_EQ(UNKNOWN_TYPE, form_structure->field(8)->heuristic_type());
}
TEST(FormStructureTest, HeuristicsCreditCardInfo) {
@@ -472,7 +552,7 @@ TEST(FormStructureTest, HeuristicsCreditCardInfo) {
EXPECT_TRUE(form_structure->IsAutoFillable());
// Expect the correct number of fields.
- ASSERT_EQ(5UL, form_structure->field_count());
+ ASSERT_EQ(6UL, form_structure->field_count());
// Check that heuristics are initialized as UNKNOWN_TYPE.
std::vector<AutoFillField*>::const_iterator iter;
@@ -491,7 +571,7 @@ TEST(FormStructureTest, HeuristicsCreditCardInfo) {
// Compute heuristic types.
form_structure->GetHeuristicAutoFillTypes();
- ASSERT_EQ(5U, form_structure->field_count());
+ ASSERT_EQ(6U, form_structure->field_count());
// Credit card name.
EXPECT_EQ(CREDIT_CARD_NAME, form_structure->field(0)->heuristic_type());
@@ -505,6 +585,8 @@ TEST(FormStructureTest, HeuristicsCreditCardInfo) {
// Credit card cvc.
EXPECT_EQ(CREDIT_CARD_VERIFICATION_CODE,
form_structure->field(4)->heuristic_type());
+ // Submit.
+ EXPECT_EQ(UNKNOWN_TYPE, form_structure->field(5)->heuristic_type());
}
TEST(FormStructureTest, HeuristicsCreditCardInfoWithUnknownCardField) {
@@ -546,7 +628,7 @@ TEST(FormStructureTest, HeuristicsCreditCardInfoWithUnknownCardField) {
EXPECT_TRUE(form_structure->IsAutoFillable());
// Expect the correct number of fields.
- ASSERT_EQ(6UL, form_structure->field_count());
+ ASSERT_EQ(7UL, form_structure->field_count());
// Check that heuristics are initialized as UNKNOWN_TYPE.
std::vector<AutoFillField*>::const_iterator iter;
@@ -565,7 +647,7 @@ TEST(FormStructureTest, HeuristicsCreditCardInfoWithUnknownCardField) {
// Compute heuristic types.
form_structure->GetHeuristicAutoFillTypes();
- ASSERT_EQ(6UL, form_structure->field_count());
+ ASSERT_EQ(7UL, form_structure->field_count());
// Credit card name.
EXPECT_EQ(CREDIT_CARD_NAME, form_structure->field(0)->heuristic_type());
@@ -581,6 +663,8 @@ TEST(FormStructureTest, HeuristicsCreditCardInfoWithUnknownCardField) {
// Credit card cvc.
EXPECT_EQ(CREDIT_CARD_VERIFICATION_CODE,
form_structure->field(5)->heuristic_type());
+ // Submit.
+ EXPECT_EQ(UNKNOWN_TYPE, form_structure->field(6)->heuristic_type());
}
} // namespace
diff --git a/chrome/browser/browser.cc b/chrome/browser/browser.cc
index dffd1cd..09eee48 100644
--- a/chrome/browser/browser.cc
+++ b/chrome/browser/browser.cc
@@ -18,6 +18,7 @@
#include "base/thread.h"
#include "gfx/point.h"
#include "chrome/app/chrome_dll_resource.h"
+#include "chrome/browser/autofill/autofill_manager.h"
#include "chrome/browser/bookmarks/bookmark_model.h"
#include "chrome/browser/bookmarks/bookmark_utils.h"
#include "chrome/browser/browser_list.h"
@@ -1562,6 +1563,14 @@ void Browser::OpenInternetOptionsDialog() {
}
#endif
+void Browser::AutoFillDefaultProfile() {
+ TabContents* current_tab = GetSelectedTabContents();
+ if (!current_tab) // May be NULL during tab restore.
+ return;
+
+ current_tab->GetAutoFillManager()->FillDefaultProfile();
+}
+
///////////////////////////////////////////////////////////////////////////////
// static
@@ -1812,6 +1821,9 @@ void Browser::ExecuteCommandWithDisposition(
case IDC_INTERNET_OPTIONS: OpenInternetOptionsDialog(); break;
#endif
+ // AutoFill
+ case IDC_AUTOFILL_DEFAULT: AutoFillDefaultProfile(); break;
+
default:
LOG(WARNING) << "Received Unimplemented Command: " << id;
break;
@@ -2851,6 +2863,10 @@ void Browser::InitCommandState() {
command_updater_.UpdateCommandEnabled(IDC_FIND_NEXT, non_devtools_window);
command_updater_.UpdateCommandEnabled(IDC_FIND_PREVIOUS, non_devtools_window);
+ // AutoFill
+ command_updater_.UpdateCommandEnabled(IDC_AUTOFILL_DEFAULT,
+ non_devtools_window);
+
// Show various bits of UI
command_updater_.UpdateCommandEnabled(IDC_CLEAR_BROWSING_DATA, normal_window);
diff --git a/chrome/browser/browser.h b/chrome/browser/browser.h
index c82c01c..9d81731 100644
--- a/chrome/browser/browser.h
+++ b/chrome/browser/browser.h
@@ -492,6 +492,7 @@ class Browser : public TabStripModelDelegate,
void OpenSystemOptionsDialog();
void OpenInternetOptionsDialog();
#endif
+ void AutoFillDefaultProfile();
virtual void UpdateDownloadShelfVisibility(bool visible);
diff --git a/chrome/browser/gtk/accelerators_gtk.cc b/chrome/browser/gtk/accelerators_gtk.cc
index 42ff3a1..c93d8f0 100644
--- a/chrome/browser/gtk/accelerators_gtk.cc
+++ b/chrome/browser/gtk/accelerators_gtk.cc
@@ -140,6 +140,10 @@ const struct AcceleratorMapping {
{ GDK_x, IDC_CUT, GDK_CONTROL_MASK },
{ GDK_v, IDC_PASTE, GDK_CONTROL_MASK },
+ // AutoFill.
+ { GDK_a, IDC_AUTOFILL_DEFAULT,
+ GdkModifierType(GDK_CONTROL_MASK | GDK_SHIFT_MASK) },
+
// Miscellany.
{ GDK_d, IDC_BOOKMARK_ALL_TABS,
GdkModifierType(GDK_CONTROL_MASK | GDK_SHIFT_MASK) },
diff --git a/chrome/browser/renderer_host/render_view_host.cc b/chrome/browser/renderer_host/render_view_host.cc
index 91ffc97..81a9cd2 100644
--- a/chrome/browser/renderer_host/render_view_host.cc
+++ b/chrome/browser/renderer_host/render_view_host.cc
@@ -1610,6 +1610,11 @@ void RenderViewHost::AutoFillSuggestionsReturned(
routing_id(), query_id, names, labels, default_suggestion_index));
}
+void RenderViewHost::AutoFillForms(
+ const std::vector<webkit_glue::FormData>& forms) {
+ Send(new ViewMsg_AutoFillForms(routing_id(), forms));
+}
+
void RenderViewHost::AutocompleteSuggestionsReturned(
int query_id, const std::vector<string16>& suggestions,
int default_suggestion_index) {
diff --git a/chrome/browser/renderer_host/render_view_host.h b/chrome/browser/renderer_host/render_view_host.h
index 3492603..fb86e94 100644
--- a/chrome/browser/renderer_host/render_view_host.h
+++ b/chrome/browser/renderer_host/render_view_host.h
@@ -393,6 +393,9 @@ class RenderViewHost : public RenderWidgetHost {
const std::vector<string16>& labels,
int default_suggestion_index);
+ // Called by the AutoFillManager to fill out all the forms in the renderer.
+ void AutoFillForms(const std::vector<webkit_glue::FormData>& forms);
+
// Called by the AutocompleteHistoryManager when the list of suggestions is
// ready.
void AutocompleteSuggestionsReturned(
diff --git a/chrome/browser/tab_contents/tab_contents.cc b/chrome/browser/tab_contents/tab_contents.cc
index 4054816f..b783b2c 100644
--- a/chrome/browser/tab_contents/tab_contents.cc
+++ b/chrome/browser/tab_contents/tab_contents.cc
@@ -468,6 +468,12 @@ bool TabContents::HostsExtension() const {
return GetURL().SchemeIs(chrome::kExtensionScheme);
}
+AutoFillManager* TabContents::GetAutoFillManager() {
+ if (autofill_manager_.get() == NULL)
+ autofill_manager_.reset(new AutoFillManager(this));
+ return autofill_manager_.get();
+}
+
PasswordManager* TabContents::GetPasswordManager() {
if (password_manager_.get() == NULL)
password_manager_.reset(new PasswordManager(this));
@@ -2117,9 +2123,7 @@ RenderViewHostDelegate::Autocomplete* TabContents::GetAutocompleteDelegate() {
}
RenderViewHostDelegate::AutoFill* TabContents::GetAutoFillDelegate() {
- if (autofill_manager_.get() == NULL)
- autofill_manager_.reset(new AutoFillManager(this));
- return autofill_manager_.get();
+ return GetAutoFillManager();
}
AutomationResourceRoutingDelegate*
diff --git a/chrome/browser/tab_contents/tab_contents.h b/chrome/browser/tab_contents/tab_contents.h
index 902e61e..97f688a 100644
--- a/chrome/browser/tab_contents/tab_contents.h
+++ b/chrome/browser/tab_contents/tab_contents.h
@@ -152,6 +152,9 @@ class TabContents : public PageNavigator,
// Returns true if contains content rendered by an extension.
bool HostsExtension() const;
+ // Returns the AutoFillManager, creating it if necessary.
+ AutoFillManager* GetAutoFillManager();
+
// Returns the PasswordManager, creating it if necessary.
PasswordManager* GetPasswordManager();
diff --git a/chrome/browser/views/accelerator_table_gtk.cc b/chrome/browser/views/accelerator_table_gtk.cc
index 02f996f..9e1f6c9 100644
--- a/chrome/browser/views/accelerator_table_gtk.cc
+++ b/chrome/browser/views/accelerator_table_gtk.cc
@@ -109,6 +109,9 @@ const AcceleratorMapping kAcceleratorMap[] = {
{ base::VKEY_F2, false, false, false, IDC_FORWARD },
#endif
+ // AutoFill.
+ { base::VKEY_A, true, true, false, IDC_AUTOFILL_DEFAULT },
+
// Miscellany.
{ base::VKEY_D, false, true, false, IDC_BOOKMARK_PAGE },
{ base::VKEY_D, true, true, false, IDC_BOOKMARK_ALL_TABS },
diff --git a/chrome/common/render_messages_internal.h b/chrome/common/render_messages_internal.h
index 93b1a76..24cda62 100644
--- a/chrome/common/render_messages_internal.h
+++ b/chrome/common/render_messages_internal.h
@@ -637,6 +637,9 @@ IPC_BEGIN_MESSAGES(View)
std::vector<string16> /* labels */,
int /* index of default suggestion */)
+ IPC_MESSAGE_ROUTED1(ViewMsg_AutoFillForms,
+ std::vector<webkit_glue::FormData> /* forms */)
+
// Reply to the ViewHostMsg_QueryFormFieldAutofill message with the
// autocomplete suggestions.
IPC_MESSAGE_ROUTED3(ViewMsg_AutocompleteSuggestionsReturned,
diff --git a/chrome/renderer/form_manager.cc b/chrome/renderer/form_manager.cc
index d2c80b8..0d202ab 100644
--- a/chrome/renderer/form_manager.cc
+++ b/chrome/renderer/form_manager.cc
@@ -404,6 +404,13 @@ bool FormManager::FillForm(const FormData& form) {
return true;
}
+void FormManager::FillForms(const std::vector<webkit_glue::FormData>& forms) {
+ for (std::vector<webkit_glue::FormData>::const_iterator iter = forms.begin();
+ iter != forms.end(); ++iter) {
+ FillForm(*iter);
+ }
+}
+
void FormManager::Reset() {
for (WebFrameFormElementMap::iterator iter = form_elements_map_.begin();
iter != form_elements_map_.end(); ++iter) {
diff --git a/chrome/renderer/form_manager.h b/chrome/renderer/form_manager.h
index e1176bc..c35da84 100644
--- a/chrome/renderer/form_manager.h
+++ b/chrome/renderer/form_manager.h
@@ -85,6 +85,9 @@ class FormManager {
// store multiple forms with the same names from different frames.
bool FillForm(const webkit_glue::FormData& form);
+ // Fills all of the forms in the cache with form data from |forms|.
+ void FillForms(const std::vector<webkit_glue::FormData>& forms);
+
// Resets the stored set of forms.
void Reset();
diff --git a/chrome/renderer/render_view.cc b/chrome/renderer/render_view.cc
index 9dc6442..7b81bd9 100644
--- a/chrome/renderer/render_view.cc
+++ b/chrome/renderer/render_view.cc
@@ -602,6 +602,7 @@ void RenderView::OnMessageReceived(const IPC::Message& message) {
OnDisassociateFromPopupCount)
IPC_MESSAGE_HANDLER(ViewMsg_AutoFillSuggestionsReturned,
OnAutoFillSuggestionsReturned)
+ IPC_MESSAGE_HANDLER(ViewMsg_AutoFillForms, OnAutoFillForms)
IPC_MESSAGE_HANDLER(ViewMsg_AutocompleteSuggestionsReturned,
OnAutocompleteSuggestionsReturned)
IPC_MESSAGE_HANDLER(ViewMsg_AutoFillFormDataFilled,
@@ -1452,6 +1453,11 @@ void RenderView::OnAutoFillSuggestionsReturned(
autofill_query_node_.reset();
}
+void RenderView::OnAutoFillForms(
+ const std::vector<webkit_glue::FormData>& forms) {
+ form_manager_.FillForms(forms);
+}
+
void RenderView::OnAutocompleteSuggestionsReturned(
int query_id,
const std::vector<string16>& suggestions,
diff --git a/chrome/renderer/render_view.h b/chrome/renderer/render_view.h
index 6f67b4d..c3a0190 100644
--- a/chrome/renderer/render_view.h
+++ b/chrome/renderer/render_view.h
@@ -750,6 +750,9 @@ class RenderView : public RenderWidget,
const std::vector<string16>& labels,
int default_suggestions_index);
+ // Fills all the forms in this RenderView with the form data in |forms|.
+ void OnAutoFillForms(const std::vector<webkit_glue::FormData>& forms);
+
// Notification that we have received Autocomplete suggestions.
void OnAutocompleteSuggestionsReturned(
int query_id,
diff --git a/webkit/glue/form_data.h b/webkit/glue/form_data.h
index 6af9b28..033cac3 100644
--- a/webkit/glue/form_data.h
+++ b/webkit/glue/form_data.h
@@ -7,6 +7,7 @@
#include <vector>
+#include "base/string_util.h"
#include "googleurl/src/gurl.h"
#include "webkit/glue/form_field.h"
@@ -24,6 +25,15 @@ struct FormData {
GURL action;
// A vector of all the input fields in the form.
std::vector<FormField> fields;
+
+ // Used by FormStructureTest.
+ inline bool operator==(const FormData& form) const {
+ return (name == form.name &&
+ StringToLowerASCII(method) == StringToLowerASCII(form.method) &&
+ origin == form.origin &&
+ action == form.action &&
+ fields == form.fields);
+ }
};
} // namespace webkit_glue