I am just starting to play with the new cursorLoader and I am running into problems. The following code is just to understand how the cursorLoader works but I keep getting:
I don't believe that capturing the Cursor from loader.loadInBackground() is what you want. The implementation for loadInBackground() basically does a query and returns you the cursor on the UI thread, which is what your trying to avoid.
Be cautious anytime you are waiting on the UI thread for a return value. It should be a good indicator that this is not something you want.
What I did to fix this issue was to restart the loader. In my case, I'm trying to use the action bar to search my content. My class extends ListFragment and implements LoaderManager.LoaderCallbacks The Activity that houses this implements OnQueryTextListener and is calling into the fragment here is the code that I'm doing in the fragment.
public void doSearch(String query) {
Bundle bundle = new Bundle();
bundle.putString("query", query);
getLoaderManager().restartLoader(LoaderMangerIdHelper.INVENTORY, bundle, this);
}
Note that you must restart the loader. The loaders are all managed by the system. This will cause your onCreateLoader to get re-called. So you'll have to check for query string in there to set your selection.
@Override
public Loader onCreateLoader(int id, Bundle bundle) {
String SELECTION = "someColumn=?";
List selectionArgs = new ArrayList();
selectionArgs.add("someArgs");
if (bundle != null && bundle.containsKey("query")) {
SELECTION += " AND columnTitle LIKE ?";
selectionArgs.add(bundle.getString("query") + "%");
}
final String[] SELECTION_ARGS = new String[selectionArgs.size()];
selectionArgs.toArray(SELECTION_ARGS);
mLoader = new CursorLoader(getActivity(), RoamPay.Product.CONTENT_URI, null, SELECTION,
SELECTION_ARGS, null);
return mLoader;
}
This starts the cursorLoading in the background. And the callbacks should be the same as usual.
@Override
public void onLoadFinished(Loader loader, Cursor data) {
// Swap the new cursor in. (The framework will take care of closing the
// old cursor once we return.)
mAdapter.swapCursor(data);
// The list should now be shown.
if (isResumed()) {
setListShown(true);
} else {
setListShownNoAnimation(true);
}
}
@Override
public void onLoaderReset(Loader 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);
}