Adding the "Edit" mode to aggregation suggestion.
Now if you are creating a new contact and enter
the name of an existing editable contact, the
UI will show an identity card for that other contact
and an Edit button. Tapping on the Edit button
simply switches the editor to the suggested contact.
The data you may have entered will be transferred to
the suggested contact in another CL.
Change-Id: Ic0af5d883efb17d30dfea052b911e0a5f02d0e91
diff --git a/res/layout-xlarge/aggregation_suggestions_item.xml b/res/layout-xlarge/aggregation_suggestions_item.xml
index abda55e..865c492 100644
--- a/res/layout-xlarge/aggregation_suggestions_item.xml
+++ b/res/layout-xlarge/aggregation_suggestions_item.xml
@@ -18,7 +18,7 @@
-->
<view xmlns:android="http://schemas.android.com/apk/res/android"
- class="com.android.contacts.quickcontact.widget.AggregationSuggestionView"
+ class="com.android.contacts.views.editor.AggregationSuggestionView"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
@@ -34,6 +34,15 @@
android:layout_alignParentRight="true"
/>
+ <Button
+ android:id="@+id/aggregation_suggestion_edit_button"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:text="@string/aggregation_suggestion_edit_button"
+ android:layout_centerInParent="true"
+ android:layout_alignParentRight="true"
+ />
+
<ImageView
android:id="@+id/aggregation_suggestion_photo"
android:layout_width="@dimen/aggregation_suggestion_icon_size"
diff --git a/res/layout/aggregation_suggestions_item.xml b/res/layout/aggregation_suggestions_item.xml
index bda9e1d..988508b 100644
--- a/res/layout/aggregation_suggestions_item.xml
+++ b/res/layout/aggregation_suggestions_item.xml
@@ -18,7 +18,7 @@
-->
<view xmlns:android="http://schemas.android.com/apk/res/android"
- class="com.android.contacts.quickcontact.widget.AggregationSuggestionView"
+ class="com.android.contacts.views.editor.AggregationSuggestionView"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
@@ -34,6 +34,15 @@
android:layout_alignParentRight="true"
/>
+ <Button
+ android:id="@+id/aggregation_suggestion_edit_button"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:text="@string/aggregation_suggestion_edit_button"
+ android:layout_centerInParent="true"
+ android:layout_alignParentRight="true"
+ />
+
<ImageView
android:id="@+id/aggregation_suggestion_photo"
android:layout_width="@dimen/aggregation_suggestion_icon_size"
diff --git a/res/values/strings.xml b/res/values/strings.xml
index 7267d62..cd39508 100644
--- a/res/values/strings.xml
+++ b/res/values/strings.xml
@@ -1305,11 +1305,13 @@
indicating the contact that will be joined with the current contact. [CHAR LIMIT=128]-->
<string name="aggregation_suggestion_joined_title">Joined contact:</string>
- <!-- The button next to a contact aggregation suggestion in Contact editor. [CHAR LIMIT=12]-->
+ <!-- The button next to a contact aggregation suggestion in Contact editor. Causes a logical
+ join with the suggested contact. [CHAR LIMIT=12]-->
<string name="aggregation_suggestion_join_button">Join</string>
- <!-- The button next to the message about multiple contact aggregation suggestions in Contact editor. [CHAR LIMIT=12]-->
- <string name="aggregation_suggestion_view_button">View</string>
+ <!-- The button next to a contact aggregation suggestion in Contact editor. Causes the UI
+ to switch to the suggested contact in the editor. [CHAR LIMIT=12]-->
+ <string name="aggregation_suggestion_edit_button">Edit</string>
<!-- The menu item (or button) that creates a local copy of a corporate contact. [CHAR LIMIT=40]-->
<string name="menu_copyContact">Copy to my contacts</string>
diff --git a/src/com/android/contacts/views/editor/AggregationSuggestionEngine.java b/src/com/android/contacts/views/editor/AggregationSuggestionEngine.java
index bf1f7ac..9b95aee 100644
--- a/src/com/android/contacts/views/editor/AggregationSuggestionEngine.java
+++ b/src/com/android/contacts/views/editor/AggregationSuggestionEngine.java
@@ -36,6 +36,7 @@
import android.provider.ContactsContract.Contacts.AggregationSuggestions;
import android.provider.ContactsContract.Contacts.AggregationSuggestions.Builder;
import android.provider.ContactsContract.Data;
+import android.provider.ContactsContract.RawContacts;
import android.text.TextUtils;
import java.util.ArrayList;
@@ -70,19 +71,31 @@
void onAggregationSuggestionChange();
}
+ public static final class RawContact {
+ public long rawContactId;
+ public String accountType;
+ public String accountName;
+
+ @Override
+ public String toString() {
+ return "ID: " + rawContactId + " account: " + accountType + "/" + accountName;
+ }
+ }
+
public static final class Suggestion {
+
public long contactId;
- public List<Long> rawContactIds;
public String lookupKey;
public String name;
public String phoneNumber;
public String emailAddress;
public String nickname;
public byte[] photo;
+ public List<RawContact> rawContacts;
@Override
public String toString() {
- return "ID: " + contactId + " rawContactIds: " + rawContactIds + " name: " + name
+ return "ID: " + contactId + " rawContacts: " + rawContacts + " name: " + name
+ " phone: " + phoneNumber + " email: " + emailAddress + " nickname: "
+ nickname + (photo != null ? " [has photo]" : "");
}
@@ -227,6 +240,8 @@
Data.DATA1,
Data.IS_SUPER_PRIMARY,
Photo.PHOTO,
+ RawContacts.ACCOUNT_TYPE,
+ RawContacts.ACCOUNT_NAME,
};
public static final int ID = 0;
@@ -239,6 +254,8 @@
public static final int DATA1 = 7;
public static final int IS_SUPERPRIMARY = 8;
public static final int PHOTO = 9;
+ public static final int ACCOUNT_TYPE = 10;
+ public static final int ACCOUNT_NAME = 11;
}
private void loadAggregationSuggestions(Uri uri) {
@@ -326,14 +343,19 @@
suggestion = new Suggestion();
suggestion.contactId = contactId;
suggestion.name = mDataCursor.getString(DataQuery.DISPLAY_NAME);
- suggestion.rawContactIds = Lists.newArrayList();
+ suggestion.lookupKey = mDataCursor.getString(DataQuery.LOOKUP_KEY);
+ suggestion.rawContacts = Lists.newArrayList();
list.add(suggestion);
currentContactId = contactId;
}
- Long rawContactId = Long.valueOf(mDataCursor.getLong(DataQuery.RAW_CONTACT_ID));
- if (!suggestion.rawContactIds.contains(rawContactId)) {
- suggestion.rawContactIds.add(rawContactId);
+ long rawContactId = mDataCursor.getLong(DataQuery.RAW_CONTACT_ID);
+ if (!containsRawContact(suggestion, rawContactId)) {
+ RawContact rawContact = new RawContact();
+ rawContact.rawContactId = rawContactId;
+ rawContact.accountName = mDataCursor.getString(DataQuery.ACCOUNT_NAME);
+ rawContact.accountType = mDataCursor.getString(DataQuery.ACCOUNT_TYPE);
+ suggestion.rawContacts.add(rawContact);
}
String mimetype = mDataCursor.getString(DataQuery.MIMETYPE);
@@ -367,4 +389,16 @@
}
return list;
}
+
+ public boolean containsRawContact(Suggestion suggestion, long rawContactId) {
+ if (suggestion.rawContacts != null) {
+ int count = suggestion.rawContacts.size();
+ for (int i = 0; i < count; i++) {
+ if (suggestion.rawContacts.get(i).rawContactId == rawContactId) {
+ return true;
+ }
+ }
+ }
+ return false;
+ }
}
diff --git a/src/com/android/contacts/views/editor/AggregationSuggestionView.java b/src/com/android/contacts/views/editor/AggregationSuggestionView.java
index 8880e67..367ed52 100644
--- a/src/com/android/contacts/views/editor/AggregationSuggestionView.java
+++ b/src/com/android/contacts/views/editor/AggregationSuggestionView.java
@@ -17,10 +17,17 @@
package com.android.contacts.views.editor;
import com.android.contacts.R;
+import com.android.contacts.model.ContactsSource;
+import com.android.contacts.model.Sources;
+import com.android.contacts.views.editor.AggregationSuggestionEngine.RawContact;
import com.android.contacts.views.editor.AggregationSuggestionEngine.Suggestion;
+import com.google.android.collect.Lists;
+import android.content.ContentUris;
import android.content.Context;
import android.graphics.BitmapFactory;
+import android.net.Uri;
+import android.provider.ContactsContract.Contacts;
import android.util.AttributeSet;
import android.view.View;
import android.view.View.OnClickListener;
@@ -29,6 +36,7 @@
import android.widget.RelativeLayout;
import android.widget.TextView;
+import java.util.ArrayList;
import java.util.List;
/**
@@ -44,11 +52,18 @@
* for those.
*/
public void onJoinAction(long contactId, List<Long> rawContacIds);
+
+ /**
+ * Callback that passes the contact ID to edit instead of the current contact.
+ */
+ public void onEditAction(Uri contactLookupUri);
}
private Listener mListener;
private long mContactId;
- private List<Long> mRawContactIds;
+ private String mLookupKey;
+ private List<RawContact> mRawContacts = Lists.newArrayList();
+ private boolean mNewContact;
public AggregationSuggestionView(Context context) {
super(context);
@@ -62,9 +77,14 @@
super(context, attrs, defStyle);
}
+ public void setNewContact(boolean flag) {
+ mNewContact = flag;
+ }
+
public void bindSuggestion(Suggestion suggestion) {
mContactId = suggestion.contactId;
- mRawContactIds = suggestion.rawContactIds;
+ mLookupKey = suggestion.lookupKey;
+ mRawContacts = suggestion.rawContacts;
ImageView photo = (ImageView) findViewById(R.id.aggregation_suggestion_photo);
if (suggestion.photo != null) {
photo.setImageBitmap(BitmapFactory.decodeByteArray(
@@ -87,9 +107,38 @@
}
data.setText(dataText);
+ boolean canEdit = canEditSuggestedContact();
Button join = (Button) findViewById(R.id.aggregation_suggestion_join_button);
join.setOnClickListener(this);
- join.setVisibility(View.VISIBLE);
+ join.setVisibility(canEdit ? View.GONE : View.VISIBLE);
+
+ Button edit = (Button) findViewById(R.id.aggregation_suggestion_edit_button);
+ edit.setOnClickListener(this);
+ edit.setVisibility(canEdit ? View.VISIBLE : View.GONE);
+ }
+
+ /**
+ * Returns true if the suggested contact can be edited.
+ */
+ private boolean canEditSuggestedContact() {
+ if (!mNewContact) {
+ return false;
+ }
+
+ Sources sources = Sources.getInstance(getContext());
+ for (RawContact rawContact : mRawContacts) {
+ String accountType = rawContact.accountType;
+ if (accountType == null) {
+ return true;
+ }
+ ContactsSource source = sources.getInflatedSource(
+ accountType, ContactsSource.LEVEL_SUMMARY);
+ if (!source.readOnly) {
+ return true;
+ }
+ }
+
+ return false;
}
public void setListener(Listener listener) {
@@ -99,7 +148,15 @@
@Override
public void onClick(View v) {
if (mListener != null) {
- mListener.onJoinAction(mContactId, mRawContactIds);
+ if (v.getId() == R.id.aggregation_suggestion_join_button) {
+ ArrayList<Long> rawContactIds = Lists.newArrayList();
+ for (RawContact rawContact : mRawContacts) {
+ rawContactIds.add(rawContact.rawContactId);
+ }
+ mListener.onJoinAction(mContactId, rawContactIds);
+ } else {
+ mListener.onEditAction(Contacts.getLookupUri(mContactId, mLookupKey));
+ }
}
}
}
diff --git a/src/com/android/contacts/views/editor/ContactEditorFragment.java b/src/com/android/contacts/views/editor/ContactEditorFragment.java
index d7b1f18..2deab0d 100644
--- a/src/com/android/contacts/views/editor/ContactEditorFragment.java
+++ b/src/com/android/contacts/views/editor/ContactEditorFragment.java
@@ -1196,6 +1196,7 @@
suggestionView.setLayoutParams(
new LinearLayout.LayoutParams(
LayoutParams.MATCH_PARENT, LayoutParams.WRAP_CONTENT));
+ suggestionView.setNewContact(mState.size() == 1 && mState.get(0).isContactInsert());
suggestionView.setListener(new AggregationSuggestionView.Listener() {
@Override
@@ -1205,6 +1206,15 @@
// join the suggested contact, save all changes, and stay in the editor.
doSaveAction(SaveMode.RELOAD);
}
+
+ @Override
+ public void onEditAction(Uri contactLookupUri) {
+ // Abandon the currently inserted contact and load the suggested one
+ mState = null;
+ load(Intent.ACTION_EDIT, contactLookupUri, Contacts.CONTENT_TYPE, null);
+ mStatus = Status.LOADING;
+ getLoaderManager().restartLoader(LOADER_DATA, null, mDataLoaderListener);
+ }
});
suggestionView.bindSuggestion(suggestion);
itemList.addView(suggestionView);