Multi select remove from group members list (1/2)
Bug 18641067
Change-Id: I8968ce992615e2b64ada7caa8b9ce7ea08ee0048
diff --git a/AndroidManifest.xml b/AndroidManifest.xml
index c2c4eab..16bd38a 100644
--- a/AndroidManifest.xml
+++ b/AndroidManifest.xml
@@ -245,7 +245,7 @@
<!-- Displays the members of a group in a list -->
<activity android:name=".activities.GroupMembersActivity"
- android:theme="@style/ContactPickerTheme"/>
+ android:theme="@style/PeopleActivityTheme"/>
<!-- Views the details of a single group -->
<activity android:name=".activities.GroupDetailActivity"
diff --git a/res/layout/group_members_activity.xml b/res/layout/group_members_activity.xml
index e8cc594..387fdd2 100644
--- a/res/layout/group_members_activity.xml
+++ b/res/layout/group_members_activity.xml
@@ -19,4 +19,10 @@
android:id="@+id/fragment_container"
android:orientation="vertical"
android:layout_width="match_parent"
- android:layout_height="match_parent"/>
\ No newline at end of file
+ android:layout_height="match_parent">
+
+ <include
+ layout="@layout/people_activity_toolbar"
+ android:id="@+id/toolbar_parent" />
+
+</LinearLayout>
\ No newline at end of file
diff --git a/res/menu/view_group.xml b/res/menu/view_group.xml
index 669f401..6c5979e 100644
--- a/res/menu/view_group.xml
+++ b/res/menu/view_group.xml
@@ -14,13 +14,20 @@
limitations under the License.
-->
-<menu xmlns:android="http://schemas.android.com/apk/res/android">
+<menu xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:contacts="http://schemas.android.com/apk/res-auto">
+
<item
android:id="@+id/menu_edit_group"
+ android:icon="@drawable/ic_create_24dp"
android:title="@string/menu_editGroup"
- android:alphabeticShortcut="e" />
+ contacts:showAsAction="ifRoom" />
<item
android:id="@+id/menu_delete_group"
android:title="@string/menu_deleteGroup" />
+
+ <item
+ android:id="@+id/menu_remove_from_group"
+ android:title="@string/menu_removeFromGroup" />
</menu>
diff --git a/res/values/strings.xml b/res/values/strings.xml
index 37e276f..e3c5146 100644
--- a/res/values/strings.xml
+++ b/res/values/strings.xml
@@ -135,7 +135,10 @@
<string name="menu_editGroup">Edit</string>
<!-- Menu item that deletes the currently selected label [CHAR LIMIT=30] -->
- <string name="menu_deleteGroup">Delete</string>
+ <string name="menu_deleteGroup">Delete label</string>
+
+ <!-- Menu item to remove the currently selected contacts from the currently selected label. [CHAR LIMIT=60] -->
+ <string name="menu_removeFromGroup">Remove from label</string>
<!-- Menu item (in the action bar) that creates a new contact [CHAR LIMIT=30] -->
<string name="menu_new_contact_action_bar">Add Contact</string>
diff --git a/src/com/android/contacts/activities/GroupMembersActivity.java b/src/com/android/contacts/activities/GroupMembersActivity.java
index e13bcd6..5a1f8e2 100644
--- a/src/com/android/contacts/activities/GroupMembersActivity.java
+++ b/src/com/android/contacts/activities/GroupMembersActivity.java
@@ -15,25 +15,34 @@
*/
package com.android.contacts.activities;
-import android.app.ActionBar;
import android.app.FragmentManager;
import android.content.Intent;
import android.net.Uri;
import android.os.Bundle;
+import android.support.v7.widget.Toolbar;
+import android.widget.Toast;
-import com.android.contacts.ContactsActivity;
+import com.android.contacts.AppCompatContactsActivity;
import com.android.contacts.R;
import com.android.contacts.common.util.ImplicitIntentsUtil;
import com.android.contacts.group.GroupMembersListFragment;
import com.android.contacts.group.GroupMembersListFragment.GroupMembersListCallbacks;
+import com.android.contacts.list.ContactsRequest;
+import com.android.contacts.list.MultiSelectContactsListFragment;
import com.android.contacts.quickcontact.QuickContactActivity;
/** Displays the members of a group. */
-public class GroupMembersActivity extends ContactsActivity implements GroupMembersListCallbacks {
+public class GroupMembersActivity extends AppCompatContactsActivity implements
+ ActionBarAdapter.Listener,
+ MultiSelectContactsListFragment.OnCheckBoxListActionListener,
+ GroupMembersListCallbacks {
private static final String TAG_GROUP_MEMBERS = "group_members";
+ public static final String ACTION_SAVE_COMPLETED = "saveCompleted";
+
private GroupMembersListFragment mFragment;
+ private ActionBarAdapter mActionBarAdapter;
@Override
public void onCreate(Bundle savedState) {
@@ -41,13 +50,7 @@
setContentView(R.layout.group_members_activity);
- final ActionBar actionBar = getActionBar();
- if (actionBar != null) {
- actionBar.setDisplayShowHomeEnabled(true);
- actionBar.setDisplayHomeAsUpEnabled(true);
- actionBar.setDisplayShowTitleEnabled(true);
- }
-
+ // Add the group members list fragment
final FragmentManager fragmentManager = getFragmentManager();
mFragment = (GroupMembersListFragment) fragmentManager.findFragmentByTag(TAG_GROUP_MEMBERS);
if (mFragment == null) {
@@ -58,6 +61,55 @@
}
mFragment.setGroupUri(getIntent().getData());
mFragment.setCallbacks(this);
+ mFragment.setCheckBoxListListener(this);
+
+ // Set up the action bar
+ final Toolbar toolbar = getView(R.id.toolbar);
+ setSupportActionBar(toolbar);
+ final ContactsRequest contactsRequest = new ContactsRequest();
+ contactsRequest.setActionCode(ContactsRequest.ACTION_GROUP);
+ mActionBarAdapter = new ActionBarAdapter(this, this, getSupportActionBar(),
+ /* portraitTabs */ null, /* landscapeTabs */ null, toolbar);
+ mActionBarAdapter.setShowHomeIcon(true);
+ mActionBarAdapter.setShowHomeAsUp(true);
+ mActionBarAdapter.initialize(savedState, contactsRequest);
+ }
+
+ @Override
+ protected void onNewIntent(Intent newIntent) {
+ super.onNewIntent(newIntent);
+ if (mFragment != null && ACTION_SAVE_COMPLETED.equals(newIntent.getAction())) {
+ final Uri groupUri = newIntent.getData();
+ Toast.makeText(this,
+ groupUri == null ? R.string.groupSavedErrorToast :R.string.groupSavedToast,
+ Toast.LENGTH_SHORT).show();
+
+ if (groupUri != null) {
+ final Intent intent = new Intent(this, GroupMembersActivity.class);
+ intent.setData(groupUri);
+ intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
+ startActivity(intent);
+ }
+
+ finish();
+ }
+ }
+
+ /** Whether the ActionBar is currently in selection mode. */
+ public boolean isSelectionMode() {
+ return mActionBarAdapter.isSelectionMode();
+ }
+
+ @Override
+ public void onBackPressed() {
+ if (mActionBarAdapter.isSelectionMode()) {
+ mActionBarAdapter.setSelectionMode(false);
+ mFragment.displayCheckBoxes(false);
+ } else if (mActionBarAdapter.isSearchMode()) {
+ mActionBarAdapter.setSearchMode(false);
+ } else {
+ super.onBackPressed();
+ }
}
@Override
@@ -67,7 +119,7 @@
@Override
public void onGroupNameLoaded(String groupName) {
- setTitle(groupName);
+ getSupportActionBar().setTitle(groupName);
}
@Override
@@ -83,4 +135,62 @@
intent.setAction(Intent.ACTION_EDIT);
startActivity(intent);
}
+
+ @Override
+ public void onAction(int action) {
+ switch (action) {
+ case ActionBarAdapter.Listener.Action.CHANGE_SEARCH_QUERY:
+ // TODO(wjang)
+ break;
+ case ActionBarAdapter.Listener.Action.START_SEARCH_MODE:
+ mActionBarAdapter.setSearchMode(true);
+ invalidateOptionsMenu();
+ showFabWithAnimation(/* showFabWithAnimation = */ false);
+ break;
+ case ActionBarAdapter.Listener.Action.START_SELECTION_MODE:
+ mFragment.displayCheckBoxes(true);
+ invalidateOptionsMenu();
+ break;
+ case ActionBarAdapter.Listener.Action.STOP_SEARCH_AND_SELECTION_MODE:
+ mActionBarAdapter.setSearchMode(false);
+ mFragment.displayCheckBoxes(false);
+ invalidateOptionsMenu();
+ showFabWithAnimation(/* showFabWithAnimation */ true);
+ break;
+ case ActionBarAdapter.Listener.Action.BEGIN_STOPPING_SEARCH_AND_SELECTION_MODE:
+ showFabWithAnimation(/* showFabWithAnimation */ true);
+ break;
+ }
+ }
+
+ private void showFabWithAnimation(boolean showFab) {
+ // TODO(wjang): b/28497108
+ }
+
+ @Override
+ public void onSelectedTabChanged() {
+ }
+
+ @Override
+ public void onUpButtonPressed() {
+ onBackPressed();
+ }
+
+ @Override
+ public void onStartDisplayingCheckBoxes() {
+ mActionBarAdapter.setSelectionMode(true);
+ invalidateOptionsMenu();
+ }
+
+ @Override
+ public void onSelectedContactIdsChanged() {
+ mActionBarAdapter.setSelectionCount(mFragment.getSelectedContactIds().size());
+ invalidateOptionsMenu();
+ }
+
+ @Override
+ public void onStopDisplayingCheckBoxes() {
+ mActionBarAdapter.setSelectionMode(false);
+ invalidateOptionsMenu();
+ }
}
diff --git a/src/com/android/contacts/group/GroupMembersListAdapter.java b/src/com/android/contacts/group/GroupMembersListAdapter.java
index f208fc8..167c014 100644
--- a/src/com/android/contacts/group/GroupMembersListAdapter.java
+++ b/src/com/android/contacts/group/GroupMembersListAdapter.java
@@ -39,6 +39,7 @@
private static final String[] PROJECTION_PRIMARY = new String[] {
Data.CONTACT_ID,
+ Data.RAW_CONTACT_ID,
Data.PHOTO_ID,
Data.LOOKUP_KEY,
Data.CONTACT_PRESENCE,
@@ -48,6 +49,7 @@
private static final String[] PROJECTION_ALTERNATIVE = new String[] {
Data.CONTACT_ID,
+ Data.RAW_CONTACT_ID,
Data.PHOTO_ID,
Data.LOOKUP_KEY,
Data.CONTACT_PRESENCE,
@@ -56,18 +58,19 @@
};
public static final int CONTACT_ID = 0;
- public static final int CONTACT_PHOTO_ID = 1;
- public static final int CONTACT_LOOKUP_KEY = 2;
- public static final int CONTACT_PRESENCE = 3;
- public static final int CONTACT_STATUS = 4;
- public static final int CONTACT_DISPLAY_NAME = 5;
+ public static final int RAW_CONTACT_ID = 1;
+ public static final int CONTACT_PHOTO_ID = 2;
+ public static final int CONTACT_LOOKUP_KEY = 3;
+ public static final int CONTACT_PRESENCE = 4;
+ public static final int CONTACT_STATUS = 5;
+ public static final int CONTACT_DISPLAY_NAME = 6;
}
private final CharSequence mUnknownNameText;
private long mGroupId;
public GroupMembersListAdapter(Context context) {
- super(context, GroupMembersQuery.CONTACT_ID);
+ super(context, GroupMembersQuery.RAW_CONTACT_ID);
mUnknownNameText = context.getText(android.R.string.unknownName);
setIndexedPartition(0);
}
@@ -116,6 +119,13 @@
return ((Cursor) getItem(position)).getString(GroupMembersQuery.CONTACT_DISPLAY_NAME);
}
+ public Uri getContactUri(int position) {
+ final Cursor cursor = (Cursor) getItem(position);
+ final long contactId = cursor.getLong(GroupMembersQuery.CONTACT_ID);
+ final String lookupKey = cursor.getString(GroupMembersQuery.CONTACT_LOOKUP_KEY);
+ return Contacts.getLookupUri(contactId, lookupKey);
+ }
+
@Override
protected ContactListItemView newView(Context context, int partition, Cursor cursor,
int position, ViewGroup parent) {
diff --git a/src/com/android/contacts/group/GroupMembersListFragment.java b/src/com/android/contacts/group/GroupMembersListFragment.java
index 6fe206d..fa3de1b 100644
--- a/src/com/android/contacts/group/GroupMembersListFragment.java
+++ b/src/com/android/contacts/group/GroupMembersListFragment.java
@@ -18,6 +18,7 @@
import android.app.Activity;
import android.app.LoaderManager.LoaderCallbacks;
import android.content.CursorLoader;
+import android.content.Intent;
import android.content.Loader;
import android.database.Cursor;
import android.net.Uri;
@@ -34,10 +35,11 @@
import android.view.ViewGroup;
import android.widget.TextView;
+import com.android.contacts.ContactSaveService;
import com.android.contacts.GroupListLoader;
import com.android.contacts.GroupMetaDataLoader;
import com.android.contacts.R;
-import com.android.contacts.common.list.ContactEntryListFragment;
+import com.android.contacts.activities.GroupMembersActivity;
import com.android.contacts.common.model.AccountTypeManager;
import com.android.contacts.common.model.account.AccountType;
import com.android.contacts.interactions.GroupDeletionDialogFragment;
@@ -270,10 +272,18 @@
@Override
public void onPrepareOptionsMenu(Menu menu) {
final MenuItem editMenu = menu.findItem(R.id.menu_edit_group);
- editMenu.setVisible(isGroupEditable());
+ editMenu.setVisible(!isSelectionMode() && isGroupEditable());
final MenuItem deleteMenu = menu.findItem(R.id.menu_delete_group);
- deleteMenu.setVisible(isGroupDeletable());
+ deleteMenu.setVisible(!isSelectionMode() && isGroupDeletable());
+
+ final MenuItem removeFromGroupMenu = menu.findItem(R.id.menu_remove_from_group);
+ removeFromGroupMenu.setVisible(isSelectionMode());
+ }
+
+ private boolean isSelectionMode() {
+ final GroupMembersActivity activity = (GroupMembersActivity) getActivity();
+ return activity != null && activity.isSelectionMode();
}
private boolean isGroupEditable() {
@@ -304,10 +314,26 @@
mGroupMetadata.groupName, /* endActivity */ true);
return true;
}
+ case R.id.menu_remove_from_group: {
+ removeSelectedContacts();
+ return true;
+ }
}
return false;
}
+ private void removeSelectedContacts() {
+ final Activity activity = getActivity();
+ if (activity != null) {
+ final long[] rawContactsToRemove = getAdapter().getSelectedContactIdsArray();
+ final Intent intent = ContactSaveService.createGroupUpdateIntent(
+ activity, mGroupMetadata.groupId, /* groupName */ null,
+ /* rawContactsToAdd */ null, rawContactsToRemove, activity.getClass(),
+ GroupMembersActivity.ACTION_SAVE_COMPLETED);
+ activity.startService(intent);
+ }
+ }
+
private void onGroupMetadataLoaded() {
final Activity activity = getActivity();
if (activity != null) activity.invalidateOptionsMenu();
@@ -368,6 +394,14 @@
@Override
protected void onItemClick(int position, long id) {
+ final Uri uri = getAdapter().getContactUri(position);
+ if (uri == null) {
+ return;
+ }
+ if (getAdapter().isDisplayingCheckBoxes()) {
+ super.onItemClick(position, id);
+ return;
+ }
if (mCallbacks != null) {
final Uri contactLookupUri = getAdapter().getContactLookupUri(position);
mCallbacks.onGroupMemberClicked(contactLookupUri);