Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(95)

Unified Diff: chrome/android/java/src/org/chromium/chrome/browser/payments/PaymentRequestImpl.java

Issue 2165163002: Autofill cards at the bottom of the PaymentRequest UI (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Static comparator and faux-parameterized test Created 4 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « no previous file | chrome/android/java_sources.gni » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: chrome/android/java/src/org/chromium/chrome/browser/payments/PaymentRequestImpl.java
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/payments/PaymentRequestImpl.java b/chrome/android/java/src/org/chromium/chrome/browser/payments/PaymentRequestImpl.java
index c198b8c7b85a9e1095961f4f70e6be9111d7008a..b6a653d633b412da13326e5482981ba776773abc 100644
--- a/chrome/android/java/src/org/chromium/chrome/browser/payments/PaymentRequestImpl.java
+++ b/chrome/android/java/src/org/chromium/chrome/browser/payments/PaymentRequestImpl.java
@@ -53,6 +53,7 @@ import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Locale;
+import java.util.Map;
import java.util.Set;
/**
@@ -89,8 +90,14 @@ public class PaymentRequestImpl implements PaymentRequest, PaymentRequestUI.Clie
}
private static final String TAG = "cr_PaymentRequest";
-
private static final int SUGGESTIONS_LIMIT = 4;
+ private static final Comparator<Completable> COMPLETENESS_COMPARATOR =
+ new Comparator<Completable>() {
+ @Override
+ public int compare(Completable a, Completable b) {
+ return (b.isComplete() ? 1 : 0) - (a.isComplete() ? 1 : 0);
+ }
+ };
private static PaymentRequestServiceObserverForTest sObserverForTest;
@@ -127,12 +134,12 @@ public class PaymentRequestImpl implements PaymentRequest, PaymentRequestUI.Clie
*/
private SectionInformation mUiShippingOptions;
- private HashMap<String, JSONObject> mMethodData;
+ private Map<String, JSONObject> mMethodData;
private SectionInformation mShippingAddressesSection;
private SectionInformation mContactSection;
private List<PaymentApp> mPendingApps;
- private int mFirstCompletePendingInstrument;
private List<PaymentInstrument> mPendingInstruments;
+ private List<PaymentInstrument> mPendingAutofillInstruments;
private SectionInformation mPaymentMethodsSection;
private PaymentRequestUI mUI;
private Callback<PaymentInformation> mPaymentInformationCallback;
@@ -237,20 +244,6 @@ public class PaymentRequestImpl implements PaymentRequest, PaymentRequestUI.Clie
return;
}
- // Create a comparator to sort the suggestions by completeness.
- Comparator<Completable> completenessComparator = new Comparator<Completable>() {
- @Override
- public int compare(Completable a, Completable b) {
- if (a.isComplete() == b.isComplete()) {
- return 0;
- } else if (a.isComplete()) {
- return -1;
- } else {
- return 1;
- }
- }
- };
-
// If the merchant requests shipping and does not provide a selected shipping option, then
// the merchant needs the shipping address to calculate the shipping price and availability.
boolean requestShipping = options != null && options.requestShipping;
@@ -277,7 +270,7 @@ public class PaymentRequestImpl implements PaymentRequest, PaymentRequestUI.Clie
}
// Suggest complete addresses first.
- Collections.sort(addresses, completenessComparator);
+ Collections.sort(addresses, COMPLETENESS_COMPARATOR);
// Limit the number of suggestions.
addresses = addresses.subList(0, Math.min(addresses.size(), SUGGESTIONS_LIMIT));
@@ -324,7 +317,7 @@ public class PaymentRequestImpl implements PaymentRequest, PaymentRequestUI.Clie
}
// Suggest complete contact infos first.
- Collections.sort(contacts, completenessComparator);
+ Collections.sort(contacts, COMPLETENESS_COMPARATOR);
// Limit the number of suggestions.
contacts = contacts.subList(0, Math.min(contacts.size(), SUGGESTIONS_LIMIT));
@@ -351,11 +344,11 @@ public class PaymentRequestImpl implements PaymentRequest, PaymentRequestUI.Clie
if (mContactEditor != null) mContactEditor.setEditorView(mUI.getEditorView());
}
- private static HashMap<String, JSONObject> getValidatedMethodData(
+ private static Map<String, JSONObject> getValidatedMethodData(
PaymentMethodData[] methodData, CardEditor paymentMethodsCollector) {
// Payment methodData are required.
if (methodData == null || methodData.length == 0) return null;
- HashMap<String, JSONObject> result = new HashMap<>();
+ Map<String, JSONObject> result = new HashMap<>();
for (int i = 0; i < methodData.length; i++) {
JSONObject data = null;
if (!TextUtils.isEmpty(methodData[i].stringifiedData)) {
@@ -395,10 +388,11 @@ public class PaymentRequestImpl implements PaymentRequest, PaymentRequestUI.Clie
*/
private boolean getMatchingPaymentInstruments() {
mPendingApps = new ArrayList<>(mApps);
- mFirstCompletePendingInstrument = SectionInformation.NO_SELECTION;
mPendingInstruments = new ArrayList<>();
+ mPendingAutofillInstruments = new ArrayList<>();
boolean arePaymentMethodsSupported = false;
+ Map<PaymentApp, JSONObject> queryApps = new HashMap<>();
for (int i = 0; i < mApps.size(); i++) {
PaymentApp app = mApps.get(i);
Set<String> appMethods = app.getSupportedMethodNames();
@@ -407,11 +401,18 @@ public class PaymentRequestImpl implements PaymentRequest, PaymentRequestUI.Clie
mPendingApps.remove(app);
} else {
arePaymentMethodsSupported = true;
- mMerchantSupportsAutofillPaymentInstruments = app instanceof AutofillPaymentApp;
- app.getInstruments(mMethodData.get(appMethods.iterator().next()), this);
+ mMerchantSupportsAutofillPaymentInstruments |= app instanceof AutofillPaymentApp;
+ queryApps.put(app, mMethodData.get(appMethods.iterator().next()));
}
}
+ // Query instruments after mMerchantSupportsAutofillPaymentInstruments has been initialized,
+ // so a fast response from a non-autofill payment app at the front of the app list does not
+ // cause NOT_SUPPORTED payment rejection.
+ for (Map.Entry<PaymentApp, JSONObject> q : queryApps.entrySet()) {
+ q.getKey().getInstruments(q.getValue(), this);
+ }
+
return arePaymentMethodsSupported;
}
@@ -868,12 +869,13 @@ public class PaymentRequestImpl implements PaymentRequest, PaymentRequestUI.Clie
public void onInstrumentsReady(PaymentApp app, List<PaymentInstrument> instruments) {
mPendingApps.remove(app);
+ // Place the instruments into either "autofill" or "non-autofill" list to be displayed when
+ // all apps have responded.
if (instruments != null) {
for (int i = 0; i < instruments.size(); i++) {
PaymentInstrument instrument = instruments.get(i);
if (mMethodData.containsKey(instrument.getMethodName())) {
- checkForCompletePaymentInstrument(instrument, mPendingInstruments.size());
- mPendingInstruments.add(instrument);
+ addPendingInstrument(instrument);
} else {
instrument.dismiss();
}
@@ -893,25 +895,56 @@ public class PaymentRequestImpl implements PaymentRequest, PaymentRequestUI.Clie
return;
}
+ // List order:
+ // > Non-autofill instruments.
+ // > Complete autofill instruments.
+ // > Incomplete autofill instruments.
+ Collections.sort(mPendingAutofillInstruments, COMPLETENESS_COMPARATOR);
+ mPendingInstruments.addAll(mPendingAutofillInstruments);
+
+ mPendingAutofillInstruments.clear();
+ mPendingAutofillInstruments = null;
+
+ // Pre-select the first instrument on the list, if it is complete.
+ int selection = SectionInformation.NO_SELECTION;
+ if (!mPendingInstruments.isEmpty()) {
+ PaymentInstrument first = mPendingInstruments.get(0);
+ if (!(first instanceof AutofillPaymentInstrument)
+ || ((AutofillPaymentInstrument) first).isComplete()) {
+ selection = 0;
+ }
+ }
+
// The list of payment instruments is ready to display.
mPaymentMethodsSection = new SectionInformation(PaymentRequestUI.TYPE_PAYMENT_METHODS,
- mFirstCompletePendingInstrument, mPendingInstruments);
+ selection, mPendingInstruments);
+
mPendingInstruments.clear();
+ mPendingInstruments = null;
// UI has requested the full list of payment instruments. Provide it now.
if (mPaymentInformationCallback != null) providePaymentInformation();
}
- private void checkForCompletePaymentInstrument(PaymentInstrument instrument, int index) {
- boolean isComplete = true;
+ /**
+ * Saves the given instrument in either "autofill" or "non-autofill" list. The separation
+ * enables placing autofill instruments on the bottom of the list.
+ *
+ * Autofill instruments are also checked for completeness. A complete autofill instrument can be
+ * sent to the merchant as-is, without editing first. Such instruments should be displayed
+ * higher in the list.
+ *
+ * @param instrument The instrument to add to either "autofill" or "non-autofill" list.
+ */
+ private void addPendingInstrument(PaymentInstrument instrument) {
if (instrument instanceof AutofillPaymentInstrument) {
AutofillPaymentInstrument autofillInstrument = (AutofillPaymentInstrument) instrument;
- isComplete = mCardEditor.isCardComplete(autofillInstrument.getCard());
- if (isComplete) autofillInstrument.setIsComplete();
- }
-
- if (isComplete && mFirstCompletePendingInstrument == SectionInformation.NO_SELECTION) {
- mFirstCompletePendingInstrument = index;
+ if (mCardEditor.isCardComplete(autofillInstrument.getCard())) {
+ autofillInstrument.setIsComplete();
+ }
+ mPendingAutofillInstruments.add(instrument);
+ } else {
+ mPendingInstruments.add(instrument);
}
}
« no previous file with comments | « no previous file | chrome/android/java_sources.gni » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698