LoaderManager.java revision 2707d6026240bcca6f0e35e2e1138958882e90ce
1c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn/* 2c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * Copyright (C) 2010 The Android Open Source Project 3c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * 4c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * Licensed under the Apache License, Version 2.0 (the "License"); 5c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * you may not use this file except in compliance with the License. 6c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * You may obtain a copy of the License at 7c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * 8c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * http://www.apache.org/licenses/LICENSE-2.0 9c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * 10c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * Unless required by applicable law or agreed to in writing, software 11c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * distributed under the License is distributed on an "AS IS" BASIS, 12c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * See the License for the specific language governing permissions and 14c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * limitations under the License. 15c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn */ 16c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn 17c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackbornpackage android.app; 18c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn 19c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackbornimport android.content.Loader; 20c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackbornimport android.content.Loader.OnLoadCompleteListener; 21c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackbornimport android.os.Bundle; 22c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackbornimport android.util.SparseArray; 23c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn 24c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn/** 25c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * Object associated with an {@link Activity} or {@link Fragment} for managing 26c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * one or more {@link android.content.Loader} instances associated with it. 27c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn */ 28c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackbornpublic class LoaderManager { 292707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn final SparseArray<LoaderInfo> mLoaders = new SparseArray<LoaderInfo>(); 302707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn final SparseArray<LoaderInfo> mInactiveLoaders = new SparseArray<LoaderInfo>(); 312707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn boolean mStarted; 322707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn boolean mRetaining; 332707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn boolean mRetainingStarted; 342707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn 35c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn /** 36c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * Callback interface for a client to interact with the manager. 37c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn */ 38c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn public interface LoaderCallbacks<D> { 39c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn public Loader<D> onCreateLoader(int id, Bundle args); 40c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn public void onLoadFinished(Loader<D> loader, D data); 41c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn } 42c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn 43c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn final class LoaderInfo implements Loader.OnLoadCompleteListener<Object> { 442707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn final int mId; 452707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn final Bundle mArgs; 462707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn LoaderManager.LoaderCallbacks<Object> mCallbacks; 472707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn Loader<Object> mLoader; 482707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn Object mData; 492707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn boolean mStarted; 502707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn boolean mRetaining; 512707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn boolean mRetainingStarted; 522707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn boolean mDestroyed; 532707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn boolean mListenerRegistered; 542707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn 552707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn public LoaderInfo(int id, Bundle args, LoaderManager.LoaderCallbacks<Object> callbacks) { 562707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mId = id; 572707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mArgs = args; 582707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mCallbacks = callbacks; 592707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 602707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn 612707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn void start() { 622707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn if (mRetaining && mRetainingStarted) { 632707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // Our owner is started, but we were being retained from a 642707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // previous instance in the started state... so there is really 652707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // nothing to do here, since the loaders are still started. 662707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mStarted = true; 672707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn return; 682707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 692707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn 702707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn if (mLoader == null && mCallbacks != null) { 712707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mLoader = mCallbacks.onCreateLoader(mId, mArgs); 722707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 732707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn if (mLoader != null) { 742707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mLoader.registerListener(mId, this); 752707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mListenerRegistered = true; 762707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mLoader.startLoading(); 772707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mStarted = true; 782707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 792707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 802707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn 812707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn void retain() { 822707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mRetaining = true; 832707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mRetainingStarted = mStarted; 842707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mStarted = false; 852707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mCallbacks = null; 862707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 872707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn 882707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn void finishRetain() { 892707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn if (mRetaining) { 902707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mRetaining = false; 912707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn if (mStarted != mRetainingStarted) { 922707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn if (!mStarted) { 932707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // This loader was retained in a started state, but 942707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // at the end of retaining everything our owner is 952707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // no longer started... so make it stop. 962707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn stop(); 972707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 982707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 992707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn if (mStarted && mData != null && mCallbacks != null) { 1002707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // This loader was retained, and now at the point of 1012707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // finishing the retain we find we remain started, have 1022707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // our data, and the owner has a new callback... so 1032707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // let's deliver the data now. 1042707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mCallbacks.onLoadFinished(mLoader, mData); 1052707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 1062707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 1072707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 1082707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn 1092707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn void stop() { 1102707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mStarted = false; 1112707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn if (mLoader != null && mListenerRegistered) { 1122707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // Let the loader know we're done with it 1132707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mListenerRegistered = false; 1142707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mLoader.unregisterListener(this); 1152707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 1162707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 1172707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn 1182707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn void destroy() { 1192707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mDestroyed = true; 1202707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mCallbacks = null; 1212707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn if (mLoader != null) { 1222707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn if (mListenerRegistered) { 1232707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mListenerRegistered = false; 1242707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mLoader.unregisterListener(this); 1252707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 1262707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mLoader.destroy(); 1272707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 1282707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 129c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn 130c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn @Override public void onLoadComplete(Loader<Object> loader, Object data) { 1312707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn if (mDestroyed) { 1322707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn return; 1332707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 1342707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn 135c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn // Notify of the new data so the app can switch out the old data before 136c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn // we try to destroy it. 1372707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mData = data; 1382707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn if (mCallbacks != null) { 1392707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mCallbacks.onLoadFinished(loader, data); 1402707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 141c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn 142c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn // Look for an inactive loader and destroy it if found 1432707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn LoaderInfo info = mInactiveLoaders.get(mId); 144c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn if (info != null) { 1452707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn Loader<Object> oldLoader = info.mLoader; 146c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn if (oldLoader != null) { 1472707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn oldLoader.unregisterListener(info); 148c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn oldLoader.destroy(); 149c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn } 1502707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mInactiveLoaders.remove(mId); 151c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn } 152c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn } 153c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn } 154c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn 155c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn LoaderManager(boolean started) { 156c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn mStarted = started; 157c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn } 158c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn 1592707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn private LoaderInfo createLoader(int id, Bundle args, 1602707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn LoaderManager.LoaderCallbacks<Object> callback) { 1612707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn LoaderInfo info = new LoaderInfo(id, args, (LoaderManager.LoaderCallbacks<Object>)callback); 1622707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mLoaders.put(id, info); 1632707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn Loader<Object> loader = callback.onCreateLoader(id, args); 1642707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn info.mLoader = (Loader<Object>)loader; 1652707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn if (mStarted) { 1662707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // The activity will start all existing loaders in it's onStart(), so only start them 1672707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // here if we're past that point of the activitiy's life cycle 1682707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn loader.registerListener(id, info); 1692707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn loader.startLoading(); 1702707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 1712707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn return info; 1722707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 1732707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn 1742707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn /** 1752707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn * Ensures a loader is initialized an active. If the loader doesn't 1762707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn * already exist, one is created and started. Otherwise the last created 1772707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn * loader is re-used. 1782707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn * 1792707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn * <p>In either case, the given callback is associated with the loader, and 1802707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn * will be called as the loader state changes. If at the point of call 1812707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn * the caller is in its started state, and the requested loader 1822707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn * already exists and has generated its data, then 1832707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn * callback.{@link LoaderCallbacks#onLoadFinished(Loader, Object)} will 1842707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn * be called immediately (inside of this function), so you must be prepared 1852707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn * for this to happen. 1862707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn */ 1872707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn @SuppressWarnings("unchecked") 1882707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn public <D> Loader<D> initLoader(int id, Bundle args, LoaderManager.LoaderCallbacks<D> callback) { 1892707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn LoaderInfo info = mLoaders.get(id); 1902707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn 1912707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn if (info == null) { 1922707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // Loader doesn't already exist; create. 1932707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn info = createLoader(id, args, (LoaderManager.LoaderCallbacks<Object>)callback); 1942707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } else { 1952707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn info.mCallbacks = (LoaderManager.LoaderCallbacks<Object>)callback; 1962707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 1972707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn 1982707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn if (info.mData != null && mStarted) { 1992707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // If the loader has already generated its data, report it now. 2002707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn info.mCallbacks.onLoadFinished(info.mLoader, info.mData); 2012707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 2022707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn 2032707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn return (Loader<D>)info.mLoader; 2042707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 2052707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn 206c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn /** 2072707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn * Create a new loader in this manager, registers the callbacks to it, 208c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * and starts it loading. If a loader with the same id has previously been 209c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * started it will automatically be destroyed when the new loader completes 210c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * its work. The callback will be delivered before the old loader 211c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * is destroyed. 212c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn */ 213c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn @SuppressWarnings("unchecked") 2142707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn public <D> Loader<D> restartLoader(int id, Bundle args, LoaderManager.LoaderCallbacks<D> callback) { 215c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn LoaderInfo info = mLoaders.get(id); 216c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn if (info != null) { 2172707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn if (mInactiveLoaders.get(id) != null) { 2182707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // We already have an inactive loader for this ID that we are 2192707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // waiting for! Now we have three active loaders... let's just 2202707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // drop the one in the middle, since we are still waiting for 2212707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // its result but that result is already out of date. 2222707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn info.destroy(); 2232707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } else { 2242707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // Keep track of the previous instance of this loader so we can destroy 2252707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn // it when the new one completes. 2262707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mInactiveLoaders.put(id, info); 2272707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 228c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn } 229c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn 2302707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn info = createLoader(id, args, (LoaderManager.LoaderCallbacks<Object>)callback); 2312707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn return (Loader<D>)info.mLoader; 232c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn } 233c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn 234c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn /** 235c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * Stops and removes the loader with the given ID. 236c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn */ 2372707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn public void stopLoader(int id) { 2382707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn int idx = mLoaders.indexOfKey(id); 2392707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn if (idx >= 0) { 2402707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn LoaderInfo info = mLoaders.valueAt(idx); 2412707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mLoaders.removeAt(idx); 2422707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn Loader<Object> loader = info.mLoader; 2432707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn if (loader != null) { 2442707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn loader.unregisterListener(info); 2452707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn loader.destroy(); 246c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn } 247c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn } 248c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn } 249c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn 250c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn /** 25153c67c8dfd4fe089bae2ab28cf6eae02ab1066c1Dianne Hackborn * Return the Loader with the given id or null if no matching Loader 252c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn * is found. 253c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn */ 254c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn @SuppressWarnings("unchecked") 255c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn public <D> Loader<D> getLoader(int id) { 256c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn LoaderInfo loaderInfo = mLoaders.get(id); 257c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn if (loaderInfo != null) { 2582707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn return (Loader<D>)mLoaders.get(id).mLoader; 259c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn } 260c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn return null; 261c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn } 262c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn 263c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn void doStart() { 264c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn // Call out to sub classes so they can start their loaders 265c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn // Let the existing loaders know that we want to be notified when a load is complete 266c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn for (int i = mLoaders.size()-1; i >= 0; i--) { 2672707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mLoaders.valueAt(i).start(); 268c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn } 269c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn mStarted = true; 270c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn } 271c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn 272c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn void doStop() { 273c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn for (int i = mLoaders.size()-1; i >= 0; i--) { 2742707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mLoaders.valueAt(i).stop(); 275c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn } 276c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn mStarted = false; 277c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn } 278c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn 2792707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn void doRetain() { 2802707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mRetaining = true; 2812707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mStarted = false; 2822707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn for (int i = mLoaders.size()-1; i >= 0; i--) { 2832707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mLoaders.valueAt(i).retain(); 2842707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 2852707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 2862707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn 2872707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn void finishRetain() { 2882707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mRetaining = false; 2892707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn for (int i = mLoaders.size()-1; i >= 0; i--) { 2902707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mLoaders.valueAt(i).finishRetain(); 2912707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 2922707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 2932707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn 294c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn void doDestroy() { 2952707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn if (!mRetaining) { 296c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn for (int i = mLoaders.size()-1; i >= 0; i--) { 2972707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mLoaders.valueAt(i).destroy(); 298c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn } 299c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn } 3002707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn 3012707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn for (int i = mInactiveLoaders.size()-1; i >= 0; i--) { 3022707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mInactiveLoaders.valueAt(i).destroy(); 3032707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn } 3042707d6026240bcca6f0e35e2e1138958882e90ceDianne Hackborn mInactiveLoaders.clear(); 305c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn } 306c801768e4d29667a2608695449ebc2833ba0f200Dianne Hackborn} 307