title: AlphabetIndexer with Custom Adapter managed by LoaderManager
body: <p>I am trying to implement <code>AlphabetIndexer</code> with Custom Adapter like this</p>
  
  <p><a href="https://stackoverflow.com/questions/4115920/alphabetindexer-with-custom-adapter">AlphabetIndexer with Custom Adapter</a></p>
  
  <p>My class ContactsCursorAdapter extends <code>SimpleCursorAdapter</code> and implements <code>SectionIndexer</code>
  and I am using a <code>LoaderManager</code> to manage my adapter's cursor so i have overridden the <code>swapCursor()</code> method like the second answer to the example above indicates.  </p>
  
  <pre><code>public class ContactsCursorAdapter extends SimpleCursorAdapter 
      implements SectionIndexer{
  
      private LayoutInflater mInflater;
      private Context mContext; 
  
      private AlphabetIndexer mAlphaIndexer;
  
      public ContactsCursorAdapter(Context context, int layout, Cursor c,
          String[] from, int[] to) {
          super(context, layout, c, from, to);
  
          mInflater = LayoutInflater.from(context);
          mContext = context;
      }
  
      public View getView(final int position, View convertView, ViewGroup parent) {
          ...
      }
  
      @Override
      public int getPositionForSection(int section) {
          return mAlphaIndexer.getPositionForSection(section);
      }
  
      @Override
      public int getSectionForPosition(int position) {
          return mAlphaIndexer.getSectionForPosition(position);
      }
  
      @Override
      public Object[] getSections() {
          return mAlphaIndexer.getSections();
      }
  
      public Cursor swapCursor(Cursor c) {
          // Create our indexer
          if (c != null) {
              mAlphaIndexer = new AlphabetIndexer(c, c.getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME),
                  " ABCDEFGHIJKLMNOPQRSTUVWXYZ");
          }
          return super.swapCursor(c);
      }
  }
  </code></pre>
  
  <p>However, this errors out if I set my listview to fastScrollEnabled = true </p>
  
  <p>getListView().setFastScrollEnabled(true); </p>
  
  <p>in my class ContactsCursorLoaderListFragment which extends <code>ListFragment</code> and implements LoaderManager.LoaderCallbacks .</p>
  
  <p>Here is the stack trace:</p>
  
  <pre><code>04-25 01:37:23.280: E/AndroidRuntime(711): FATAL EXCEPTION: main
  04-25 01:37:23.280: E/AndroidRuntime(711): java.lang.RuntimeException: Unable to start activity ComponentInfo{com.sendit/com.sendit.ContactManager}: java.lang.NullPointerException
  04-25 01:37:23.280: E/AndroidRuntime(711):  at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:1956)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:1981)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at android.app.ActivityThread.access$600(ActivityThread.java:123)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1147)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at android.os.Handler.dispatchMessage(Handler.java:99)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at android.os.Looper.loop(Looper.java:137)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at android.app.ActivityThread.main(ActivityThread.java:4424)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at java.lang.reflect.Method.invokeNative(Native Method)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at java.lang.reflect.Method.invoke(Method.java:511)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:784)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:551)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at dalvik.system.NativeStart.main(Native Method)
  04-25 01:37:23.280: E/AndroidRuntime(711): Caused by: java.lang.NullPointerException
  04-25 01:37:23.280: E/AndroidRuntime(711):  at com.sendit.ContactsCursorAdapter.getSections(ContactsCursorAdapter.java:222)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at android.widget.FastScroller.getSectionsFromIndexer(FastScroller.java:507)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at android.widget.FastScroller.init(FastScroller.java:269)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at android.widget.FastScroller.&lt;init&gt;(FastScroller.java:155)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at android.widget.AbsListView.setFastScrollEnabled(AbsListView.java:1144)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at com.sendit.LoaderCursor$ContactsCursorLoaderListFragment.onActivityCreated(LoaderCursor.java:107)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at android.app.FragmentManagerImpl.moveToState(FragmentManager.java:847)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at android.app.FragmentManagerImpl.moveToState(FragmentManager.java:1032)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at android.app.BackStackRecord.run(BackStackRecord.java:622)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at android.app.FragmentManagerImpl.execPendingActions(FragmentManager.java:1382)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at android.app.Activity.performStart(Activity.java:4474)
  04-25 01:37:23.280: E/AndroidRuntime(711):  at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:1929)
  04-25 01:37:23.280: E/AndroidRuntime(711):  ... 11 more
  </code></pre>
  
  <p>after the <code>setFastScrollEnabled()</code> method gets called it calls the custom adapter's <code>getSections()</code> method which is where it crashes.</p>
  
  <pre><code>public class LoaderCursor extends Activity {
  
      @Override
      protected void onCreate(Bundle savedInstanceState) {
          super.onCreate(savedInstanceState);
  
          FragmentManager fm = getFragmentManager();
  
          // Create the list fragment and add it as our sole content.
          if (fm.findFragmentById(android.R.id.content) == null) {
              ContactsCursorLoaderListFragment list = new ContactsCursorLoaderListFragment();
              fm.beginTransaction().add(android.R.id.content, list).commit();
          }
      }
  
      public static class ContactsCursorLoaderListFragment extends ListFragment
          implements LoaderManager.LoaderCallbacks&lt;Cursor&gt; {
  
          ContactsCursorAdapter mAdapter;
          Cursor mCursor;
          String mCurFilter;
  
          @Override
          public void onActivityCreated(Bundle savedInstanceState) {
              super.onActivityCreated(savedInstanceState);
  
              populateContactList();
  
              // Prepare the loader. Either re-connect with an existing one,
              // or start a new one.
              getLoaderManager().initLoader(0, null, this);
  
              ListView lv = getListView();
              lv.setFastScrollEnabled(true);
              //lv.setScrollingCacheEnabled(true);
              lv.setDivider(getResources().getDrawable(R.drawable.list_divider));
  
          }       
  
          // These are the Contacts rows that we will retrieve.
          final String[] CONTACTS_SUMMARY_PROJECTION = new String[] {
              ContactsContract.Contacts._ID,
              ContactsContract.Contacts.DISPLAY_NAME,
              ContactsContract.Contacts.PHOTO_ID, };
  
          public Loader&lt;Cursor&gt; onCreateLoader(int id, Bundle args) {
              // This is called when a new Loader needs to be created. This
              // sample only has one Loader, so we don't care about the ID.
              // First, pick the base URI to use depending on whether we are
              // currently filtering.
              Uri baseUri;
              if (mCurFilter != null) {
                  baseUri = Uri.withAppendedPath(ContactsContract.Contacts.CONTENT_FILTER_URI,Uri.encode(mCurFilter));
              } else {
                  baseUri = ContactsContract.Contacts.CONTENT_URI;
              }
  
              // Now create and return a CursorLoader that will take care of
              // creating a Cursor for the data being displayed.
              String selection = "((" + ContactsContract.Contacts.DISPLAY_NAME + 
                  " NOTNULL) AND (" + ContactsContract.Contacts.HAS_PHONE_NUMBER + "=1) 
                  AND (" + ContactsContract.Contacts.DISPLAY_NAME + " != '' ))";
              String sortOrder = ContactsContract.Contacts.DISPLAY_NAME
                  + " COLLATE LOCALIZED ASC";
  
              return new CursorLoader(getActivity(), baseUri,
                  CONTACTS_SUMMARY_PROJECTION, selection, null, sortOrder);
  
          }
  
          public void onLoadFinished(Loader&lt;Cursor&gt; loader, Cursor data) { 
              // Swap the new cursor in.  (The framework will take care of closing the
              // old cursor once we return.)
              mAdapter.swapCursor(data);
          }
  
          public void onLoaderReset(Loader&lt;Cursor&gt; loader) {
              // This is called when the last Cursor provided to onLoadFinished()
              // above is about to be closed. We need to make sure we are no
              // longer using it.
              mAdapter.swapCursor(null);
          }
  
          /**
          * Populate the contact list
          */
          private void populateContactList() {
  
              // start mappings
              String[] from = new String[] { ContactsContract.Contacts.DISPLAY_NAME };
              int[] to = new int[] { R.id.contactInfo };
  
              // Create an empty adapter we will use to display the loaded data.
              mAdapter = new ContactsCursorAdapter(getActivity().getApplicationContext(),    
                  R.layout.contact_manager, null, from, to);
              setListAdapter(mAdapter);
          }   
  
      }
  }
  </code></pre>
  
  <p>And if I comment the <code>setFastScrollEnabled()</code> call, then it does not error out, but I do not see the <code>AlphabetIndexer</code> working.  </p>
  
  <p>Does this need to be implemented differently because my custom adapter is set in a <code>ListFragment</code> and not a <code>ListActivity</code>?</p>
  
  <p>Does anyone have suggestions about how to make this all work?</p>