diff options
Diffstat (limited to 'java/com/android/dialer/contactsfragment/ContactsFragment.java')
-rw-r--r-- | java/com/android/dialer/contactsfragment/ContactsFragment.java | 138 |
1 files changed, 117 insertions, 21 deletions
diff --git a/java/com/android/dialer/contactsfragment/ContactsFragment.java b/java/com/android/dialer/contactsfragment/ContactsFragment.java index ea662fc89..a996a4fad 100644 --- a/java/com/android/dialer/contactsfragment/ContactsFragment.java +++ b/java/com/android/dialer/contactsfragment/ContactsFragment.java @@ -16,63 +16,125 @@ package com.android.dialer.contactsfragment; +import android.Manifest.permission; import android.app.Fragment; import android.app.LoaderManager.LoaderCallbacks; import android.content.Loader; +import android.content.pm.PackageManager; import android.database.Cursor; import android.os.Bundle; +import android.provider.ContactsContract.Contacts; import android.support.annotation.Nullable; +import android.support.v13.app.FragmentCompat; import android.support.v7.widget.LinearLayoutManager; import android.support.v7.widget.RecyclerView; +import android.support.v7.widget.RecyclerView.Recycler; +import android.support.v7.widget.RecyclerView.State; import android.view.LayoutInflater; import android.view.View; import android.view.View.OnScrollChangeListener; import android.view.ViewGroup; import android.widget.TextView; +import com.android.contacts.common.preference.ContactsPreferences; +import com.android.dialer.common.Assert; +import com.android.dialer.util.DialerUtils; +import com.android.dialer.util.IntentUtil; import com.android.dialer.util.PermissionsUtil; +import com.android.dialer.widget.EmptyContentView; +import com.android.dialer.widget.EmptyContentView.OnEmptyViewActionButtonClickedListener; /** Fragment containing a list of all contacts. */ public class ContactsFragment extends Fragment - implements LoaderCallbacks<Cursor>, OnScrollChangeListener { + implements LoaderCallbacks<Cursor>, + OnScrollChangeListener, + OnEmptyViewActionButtonClickedListener { + public static final int READ_CONTACTS_PERMISSION_REQUEST_CODE = 1; + + private FastScroller fastScroller; private TextView anchoredHeader; private RecyclerView recyclerView; private LinearLayoutManager manager; private ContactsAdapter adapter; + private EmptyContentView emptyContentView; + + private ContactsPreferences contactsPrefs; + + private final ContactsPreferences.ChangeListener preferencesChangeListener = + () -> getLoaderManager().restartLoader(0, null, this); + + @Override + public void onCreate(Bundle savedState) { + super.onCreate(savedState); + contactsPrefs = new ContactsPreferences(getContext()); + contactsPrefs.registerChangeListener(preferencesChangeListener); + } @Nullable @Override public View onCreateView( LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { View view = inflater.inflate(R.layout.fragment_contacts, container, false); + fastScroller = (FastScroller) view.findViewById(R.id.fast_scroller); anchoredHeader = (TextView) view.findViewById(R.id.header); - manager = new LinearLayoutManager(getContext()); - - // TODO: Handle contacts permission denied view - // TODO: Handle 0 contacts layout recyclerView = (RecyclerView) view.findViewById(R.id.recycler_view); - recyclerView.setLayoutManager(manager); - getLoaderManager().initLoader(0, null, this); + + emptyContentView = (EmptyContentView) view.findViewById(R.id.empty_list_view); + emptyContentView.setImage(R.drawable.empty_contacts); + emptyContentView.setActionClickedListener(this); if (PermissionsUtil.hasContactsReadPermissions(getContext())) { getLoaderManager().initLoader(0, null, this); + } else { + emptyContentView.setDescription(R.string.permission_no_contacts); + emptyContentView.setActionLabel(R.string.permission_single_turn_on); + emptyContentView.setVisibility(View.VISIBLE); } return view; } + /** @return a loader according to sort order and display order. */ @Override public Loader<Cursor> onCreateLoader(int id, Bundle args) { - return new ContactsCursorLoader(getContext()); + boolean sortOrderPrimary = + (contactsPrefs.getSortOrder() == ContactsPreferences.SORT_ORDER_PRIMARY); + boolean displayOrderPrimary = + (contactsPrefs.getDisplayOrder() == ContactsPreferences.DISPLAY_ORDER_PRIMARY); + + String sortKey = sortOrderPrimary ? Contacts.SORT_KEY_PRIMARY : Contacts.SORT_KEY_ALTERNATIVE; + return displayOrderPrimary + ? ContactsCursorLoader.createInstanceDisplayNamePrimary(getContext(), sortKey) + : ContactsCursorLoader.createInstanceDisplayNameAlternative(getContext(), sortKey); } @Override public void onLoadFinished(Loader<Cursor> loader, Cursor cursor) { - // TODO setup fast scroller. - adapter = new ContactsAdapter(getContext(), cursor); - recyclerView.setAdapter(adapter); - if (adapter.getItemCount() > 1) { - recyclerView.setOnScrollChangeListener(this); + if (cursor.getCount() == 0) { + emptyContentView.setDescription(R.string.all_contacts_empty); + emptyContentView.setActionLabel(R.string.all_contacts_empty_add_contact_action); + emptyContentView.setVisibility(View.VISIBLE); + } else { + emptyContentView.setVisibility(View.GONE); + adapter = new ContactsAdapter(getContext(), cursor); + manager = + new LinearLayoutManager(getContext()) { + @Override + public void onLayoutChildren(Recycler recycler, State state) { + super.onLayoutChildren(recycler, state); + int itemsShown = findLastVisibleItemPosition() - findFirstVisibleItemPosition() + 1; + if (adapter.getItemCount() > itemsShown) { + fastScroller.setVisibility(View.VISIBLE); + recyclerView.setOnScrollChangeListener(ContactsFragment.this); + } else { + fastScroller.setVisibility(View.GONE); + } + } + }; + + recyclerView.setLayoutManager(manager); + recyclerView.setAdapter(adapter); + fastScroller.setup(adapter, manager); } } @@ -81,6 +143,7 @@ public class ContactsFragment extends Fragment recyclerView.setAdapter(null); recyclerView.setOnScrollChangeListener(null); adapter = null; + contactsPrefs.unregisterChangeListener(); } /* @@ -95,8 +158,10 @@ public class ContactsFragment extends Fragment */ @Override public void onScrollChange(View v, int scrollX, int scrollY, int oldScrollX, int oldScrollY) { + fastScroller.updateContainerAndScrollBarPosition(recyclerView); int firstVisibleItem = manager.findFirstVisibleItemPosition(); int firstCompletelyVisible = manager.findFirstCompletelyVisibleItemPosition(); + String anchoredHeaderString = adapter.getHeaderString(firstCompletelyVisible); // If the user swipes to the top of the list very quickly, there is some strange behavior // between this method updating headers and adapter#onBindViewHolder updating headers. @@ -104,15 +169,46 @@ public class ContactsFragment extends Fragment if (firstVisibleItem == firstCompletelyVisible && firstVisibleItem == 0) { adapter.refreshHeaders(); anchoredHeader.setVisibility(View.INVISIBLE); + } else if (adapter.getHeaderString(firstVisibleItem).equals(anchoredHeaderString)) { + anchoredHeader.setText(anchoredHeaderString); + anchoredHeader.setVisibility(View.VISIBLE); + getContactHolder(firstVisibleItem).getHeaderView().setVisibility(View.INVISIBLE); + getContactHolder(firstCompletelyVisible).getHeaderView().setVisibility(View.INVISIBLE); } else { - boolean showAnchor = - adapter.getHeader(firstVisibleItem).equals(adapter.getHeader(firstCompletelyVisible)); - anchoredHeader.setText(adapter.getHeader(firstCompletelyVisible)); - anchoredHeader.setVisibility(showAnchor ? View.VISIBLE : View.INVISIBLE); - - int rowHeaderVisibility = showAnchor ? View.INVISIBLE : View.VISIBLE; - adapter.setHeaderVisibility(firstVisibleItem, rowHeaderVisibility); - adapter.setHeaderVisibility(firstCompletelyVisible, rowHeaderVisibility); + anchoredHeader.setVisibility(View.INVISIBLE); + getContactHolder(firstVisibleItem).getHeaderView().setVisibility(View.VISIBLE); + getContactHolder(firstCompletelyVisible).getHeaderView().setVisibility(View.VISIBLE); + } + } + + private ContactViewHolder getContactHolder(int position) { + return ((ContactViewHolder) recyclerView.findViewHolderForAdapterPosition(position)); + } + + @Override + public void onEmptyViewActionButtonClicked() { + if (emptyContentView.getActionLabel() == R.string.permission_single_turn_on) { + FragmentCompat.requestPermissions( + this, new String[] {permission.READ_CONTACTS}, READ_CONTACTS_PERMISSION_REQUEST_CODE); + } else if (emptyContentView.getActionLabel() + == R.string.all_contacts_empty_add_contact_action) { + // Add new contact + DialerUtils.startActivityWithErrorToast( + getContext(), IntentUtil.getNewContactIntent(), R.string.add_contact_not_available); + } else { + throw Assert.createIllegalStateFailException("Invalid empty content view action label."); + } + } + + @Override + public void onRequestPermissionsResult( + int requestCode, String[] permissions, int[] grantResults) { + if (requestCode == READ_CONTACTS_PERMISSION_REQUEST_CODE) { + if (grantResults.length >= 1 && PackageManager.PERMISSION_GRANTED == grantResults[0]) { + // Force a refresh of the data since we were missing the permission before this. + emptyContentView.setVisibility(View.GONE); + getLoaderManager().initLoader(0, null, this); + } } } } |