Loaders,获取数据的东西。
总体流程是:通过getLoaderManager().initLoader(0,null,this)获得Loader,如果没有,那么就会调用接口函数获取,注意:有ID,所以要在获取的接口函数里进行相应的选择。
会自动更新数据;
一个主要依赖Activity或者Fragment存在的。
通过getLoaderManager().initLoader(0,null,this)方法初始化LOADER。
要继承LoaderManager.LoaderCallbacks,包括:
LoaderManager.LoaderCallbacks
includes these methods:
onCreateLoader()
— Instantiate and return a newLoader
for the given ID.
onLoadFinished()
— Called when a previously created loader has finished its load.
onLoaderReset()
— Called when a previously created loader is being reset, thus making its data unavailable.These methods are described in more detail in the following sections.
第一个用于创建LOADER,一般来说,只有init的时候ID对应的LOADER不在的时候才会运行该方法。
第二个一般用来获取数据后的填充适配器。
第三个用于重置。
Loader可以自定义,一般使用继承AsyncTaskLoader的类。
/*** A custom Loader that loads all of the installed applications.*/ public static class AppListLoader extends AsyncTaskLoader<List<AppEntry>> {final InterestingConfigChanges mLastConfig = new InterestingConfigChanges();final PackageManager mPm;List<AppEntry> mApps;PackageIntentReceiver mPackageObserver;public AppListLoader(Context context) {super(context);// Retrieve the package manager for later use; note we don't// use 'context' directly but instead the save global application// context returned by getContext().mPm = getContext().getPackageManager();}/*** This is where the bulk of our work is done. This function is* called in a background thread and should generate a new set of* data to be published by the loader.*/@Override public List<AppEntry> loadInBackground() {// Retrieve all known applications.List<ApplicationInfo> apps = mPm.getInstalledApplications(PackageManager.GET_UNINSTALLED_PACKAGES |PackageManager.GET_DISABLED_COMPONENTS);if (apps == null) {apps = new ArrayList<ApplicationInfo>();}final Context context = getContext();// Create corresponding array of entries and load their labels.List<AppEntry> entries = new ArrayList<AppEntry>(apps.size());for (int i=0; i<apps.size(); i++) {AppEntry entry = new AppEntry(this, apps.get(i));entry.loadLabel(context);entries.add(entry);}// Sort the list. Collections.sort(entries, ALPHA_COMPARATOR);// Done!return entries;}/*** Called when there is new data to deliver to the client. The* super class will take care of delivering it; the implementation* here just adds a little more logic.*/@Override public void deliverResult(List<AppEntry> apps) {if (isReset()) {// An async query came in while the loader is stopped. We// don't need the result.if (apps != null) {onReleaseResources(apps);}}List<AppEntry> oldApps = mApps;mApps = apps;if (isStarted()) {// If the Loader is currently started, we can immediately// deliver its results.super.deliverResult(apps);}// At this point we can release the resources associated with// 'oldApps' if needed; now that the new result is delivered we// know that it is no longer in use.if (oldApps != null) {onReleaseResources(oldApps);}}/*** Handles a request to start the Loader.*/@Override protected void onStartLoading() {if (mApps != null) {// If we currently have a result available, deliver it// immediately. deliverResult(mApps);}// Start watching for changes in the app data.if (mPackageObserver == null) {mPackageObserver = new PackageIntentReceiver(this);}// Has something interesting in the configuration changed since we// last built the app list?boolean configChange = mLastConfig.applyNewConfig(getContext().getResources());if (takeContentChanged() || mApps == null || configChange) {// If the data has changed since the last time it was loaded// or is not currently available, start a load. forceLoad();}}/*** Handles a request to stop the Loader.*/@Override protected void onStopLoading() {// Attempt to cancel the current load task if possible. cancelLoad();}/*** Handles a request to cancel a load.*/@Override public void onCanceled(List<AppEntry> apps) {super.onCanceled(apps);// At this point we can release the resources associated with 'apps'// if needed. onReleaseResources(apps);}/*** Handles a request to completely reset the Loader.*/@Override protected void onReset() {super.onReset();// Ensure the loader is stopped onStopLoading();// At this point we can release the resources associated with 'apps'// if needed.if (mApps != null) {onReleaseResources(mApps);mApps = null;}// Stop monitoring for changes.if (mPackageObserver != null) {getContext().unregisterReceiver(mPackageObserver);mPackageObserver = null;}}/*** Helper function to take care of releasing resources associated* with an actively loaded data set.*/protected void onReleaseResources(List<AppEntry> apps) {// For a simple List<> there is nothing to do. For something// like a Cursor, we would close it here. } }
上面是官方的代码。
构造方法传入context。
loadInBackground是后台真正获取数据的代码。
deliverResult提交数据给客户端,可以直接返回。
onStartLoading处理要开始的请求,官方在这里进行了更新的监听。
onStopLoading要求停止,官方直接使用cancelLoad()。
onCanceled()取消的操作,官方建议对资源进行释放。
onReset,重置,详细看代码。
这样的话,就能从头到尾自定义和使用一个Loader了。