10

ローダーの問題に直面しています。

ローカル DB から取得したレコードのリストを表示するアクティビティがあります。アクティビティが開始されると、レコードは LoaderManager.initLoader() メソッドによって自動的にロードされます。

ActionBarSherlock の更新ボタンを使用してリストを手動で更新することもできます。ただし、DB にレコードを追加する別のアクティビティが終了した後、onLoadFinished は呼び出されません。

私はSimpleCursorLoaderを使用しています。アクティビティのコード スニペットは次のとおりです。

@Override
public void onStart() {
   ...
   getSupportLoaderManager().initLoader(0, null, this);
}

@Override
public void onPause() {
   ...
   getSupportLoaderManager().destroyLoader(0);
}

public void refreshRecords() {
   getSupportLoaderManager().restartLoader(0, null, this);
}

@Override
public Loader<Cursor> onCreateLoader(int id, final Bundle args) {
Loader<Cursor> l = new SimpleCursorLoader(this) {
    @Override
    public Cursor loadInBackground() {
        return recordDAO.getCursor();
    }
};
l.forceLoad();
return l;
}

@Override
public void onLoadFinished(Loader<Cursor> loader, Cursor c) {
   // updateUI
}

@Override
public void onLoaderReset(Loader<Cursor> loader) {
}

問題は、他のアクティビティを終了した後、呼び出されますonLoaderCreateが、onLoaderFinished呼び出されないことです。

いくつかのデバッグの後、それSimpleCursorAdapter.deliverResults()も呼び出されていることがわかりました。つぼみは最終的に.. if (isReset()) { ..

何か不足していますか?データのリロードを強制する方法は?

前もって感謝します

4

5 に答える 5

16

に関する議論のおかげで、私は最終的にこの問題の解決策を見つけました

https://groups.google.com/forum/#!topic/android-developers/DbKL6PVyhLI

public static <T> void initLoader(final int loaderId, final Bundle args, final LoaderCallbacks<T> callbacks,
        final LoaderManager loaderManager) {
    final Loader<T> loader = loaderManager.getLoader(loaderId);
    if (loader != null && loader.isReset()) {
        loaderManager.restartLoader(loaderId, args, callbacks);
    } else {
        loaderManager.initLoader(loaderId, args, callbacks);
    }
}

さらに、サポート ライブラリ 28 以降では、 initLoader を 内から呼び出さないようにしてくださいFragment.onCreate()。更新されたドキュメントの状態として

通常、ローダーはアクティビティのonCreate()メソッド内またはフラグメントのonActivityCreated()メソッド内で初期化します。

https://developer.android.com/guide/components/loadersを参照してください

于 2013-07-04T18:16:28.540 に答える
4

RaB ソリューションがうまくいかない

私の働いていたソリューションは、再起動する前に常にローダーを破壊していました

Loader<Cursor> loader = mLoaderManager.getLoader(mKeyLoader);
if (loader != null)
{
    mLoaderManager.destroyLoader(mKeyLoader);
}
mLoaderManager.restartLoader(mKeyLoader, args, this);
于 2016-03-24T11:48:00.657 に答える
2

RaB の回答に加えて、カスタムを使用している場合は、上書きするLoader場合に呼び出す場合は次のことを確認してください。superdeliverResult()

@Override
public void deliverResult(D data) {
    super.deliverResult(data); // <--onLoadFinished() will not be called if you don't call this
    ...
}
于 2016-04-07T08:12:40.320 に答える
1

fwiw、最初の onLoadFinished が呼び出される前に、ローダーをもう一度すぐに再起動しようとすると、同様の問題が発生し、どちらも呼び出されませんでした。

これは私のために働いた:

if( loader == null )
    loader = loaderMngr.initLoader(
        0, null, myLoaderCallbacks
        ); 
else if( loader.isAbandoned() )
    return;
else
    loaderMngr.restartLoader(
        0, null, myLoaderCallbacks
        );    
于 2014-07-11T20:22:21.467 に答える