12

I have an activity that calls initLoader when it is created in order to load the data that the activity will display. Normally, this works fine. I have breakpoints set to see the order that everything happens. First I call initLoader, then I get the OnCreateLoader callback, then the OnLoadFinished callback, then everything is great.

However, I noticed that if I changed the orientation on my Android that I don't get the OnCreateLoader callback or the OnLoadFinished callback, resulting in no data displayed on the page. I still get my breakpoint on the initLoader call so I know that is happening, but I don't get an error and I can't find any documentation explaining why I wouldn't get a callback after calling initLoader.

Interestingly, I do get the callbacks if I return to the original orientation.

So, to summarize:

I start the activity in portrait orientation

  • I call initLoader
  • I get onCreateLoader and onLoadFinished callbacks

I then change to landscape

  • I call initLoader
  • no onCreateLoader or onLoadFinished callbacks

I change back to portrait

  • I call initLoader
  • I get onCreateLoader and onLoadFinished callbacks

Similarly, if I start the activity in landscape mode I get the callbacks. Then, if I switch to portrait, I don't. Then, if I switch back to landscape I get the callbacks again.

Does anyone have any idea what's going on?

casimps1
  • 1,749
  • 1
  • 11
  • 8

7 Answers7

10

We've seen this same problem with Fragments in a ViewPager. It appears that the loaders are not properly activated again when a fragment is resumed. In fact, when the fragment is paused, our CursorLoader no longer gets ContentObserver callbacks as I would expect.

Our workaround has been to call restartLoader() which dumps the previous contents and reloads the data. This would have the same net affect as destroyLoader(); initLoader(), but it will be more efficient.

jsmith
  • 4,847
  • 2
  • 32
  • 39
4

You'll need to call initLoader in your onCreate

For a similar issue and more info have a look at LoaderCallbacks.onLoadFinished not called if orientation change happens during AsyncTaskLoader run

Community
  • 1
  • 1
gnorsilva
  • 640
  • 6
  • 11
2

I've been tracing this problem

Initial create (OnActivityCreated)

initLoader -> OnCreateLoader -> OnOnStartLoading -> OnLoadFinished

Orientation change - OnActivityCreated called again

initLoader - OnLoadFinished (Without loading any data!) - bug.

The only workaround I've found is to call destroyLoader() just before the init. This forces the proper Create/Start/Finished sequence to happen.

What appears to be happening is the initLoader code is written to assume the fragment isn't destroyed during an orientation change, which is of course not how the rest of android works..

Tony Hoyle
  • 609
  • 6
  • 4
  • 2
    this is how its ment to work. If calling init on a loader that has already loaded its data it will just return that data via onLoadFinished. You should look at http://developer.android.com/reference/android/app/LoaderManager.html#restartLoader(int, android.os.Bundle, android.app.LoaderManager.LoaderCallbacks) to reload the data – Dori May 24 '12 at 10:11
2

I had something very similar thing happening with cursor adapters in fragments on orientation change. initloader was called in onCreateView (also tried onStart and onResume) but onCreatLoader as well as the other loader callback methods never were called. Also of note in my case the fragment was contained in a view pager.

So initially the activity and view pager and fragments were created and everything worked. On orientation change though the lists in my fragments would not get data. Changing orientation again and the data came back.

In my case the fix was changing this:

getActivity().getLoaderManager().initLoader( 0, null, this );

I changed it to this

getLoaderManager().initLoader( 0, null, this );
startoftext
  • 3,846
  • 7
  • 40
  • 49
1

I spent weeks on tracking this issue. It tired to put the previous fragment content to my new fragment. Finally fixed.

In my onCreate() method of which fragment implemented LoaderManager, I did this

  getLoaderManager().initLoader(0, null, this);
        if(!getLoaderManager().getLoader(0).isReset()) {
            getLoaderManager().restartLoader(0, null, this);
        }

It works when new loader was not actived properly.

Xin Zhang
  • 103
  • 1
  • 9
1

I had this problem recently, and would like to submit my solution.

I found it was simply enough to just do:

    Loader<Cursor> loader = getActivity().getLoaderManager().getLoader(LOADERID);

    if (loader == null) {
        getActivity().getLoaderManager().initLoader(LOADERID, null, this);
    } else {
        getActivity().getLoaderManager().restartLoader(LOADERID, null, this);
    }
Chad Mx
  • 1,266
  • 14
  • 17
0

This is an old question, but maybe someone might still cares... I had the same problem and was able to fix it. Here's the link: onCreateLoader not called when orientation changes

Community
  • 1
  • 1
Dude
  • 1,202
  • 21
  • 30