Как говорится в названии, я начинаю с Loader
нажатием кнопки, а затем меняю ориентацию. В воссозданной деятельности onLoadFinished
не вызывается автоматически при запуске. Мое подозрение состоит в том, что LoaderManager
не имеет представления об этом недавно созданном экземпляре активности, поскольку я не думаю, что это связано с жизненным циклом активности. Но я могу ошибаться ...Android-загрузчик начался с щелчка, а затем изменилась ориентация - данные больше не предоставлены
Это загрузчик, предоставляющий массив строк и имитирующий его затягивание данных с помощью 3 секунд. Реализация представляет собой упрощенную версию AsyncTaskLoader
sample code.
import android.content.Context;
import android.support.v4.content.AsyncTaskLoader;
public class ContentAsyncLoader extends AsyncTaskLoader<String[]> {
private String[] data;
public ContentAsyncLoader(Context context) {
super(context);
}
@Override
protected void onStartLoading() {
if (data != null) {
deliverResult(data);
} else {
forceLoad();
}
}
@Override
public String[] loadInBackground() {
synchronized (this) {
try {
wait(3000);
} catch (InterruptedException e) {
}
}
final String[] result = { "Dell Inspiron", "HTC One X", "HTC Wildfire S", "HTC Sense", "HTC Sensation XE", "iPhone 4S", "Samsung Galaxy Note 800", "Samsung Galaxy S3", "MacBook Air",
"Mac Mini", "MacBook Pro" };
return result;
}
@Override
protected void onStopLoading() {
cancelLoad();
}
@Override
protected void onReset() {
super.onReset();
onStopLoading();
data = null;
}
@Override
public void deliverResult(String[] data) {
if (isReset()) {
return;
}
this.data = data;
if (isStarted()) {
super.deliverResult(data);
}
}
}
И ниже деятельность, которая запускает загрузчик на кнопку мыши - это ListView
и Button
:
public class MainActivity extends FragmentActivity implements OnClickListener, LoaderCallbacks<String[]> {
private static final int LOADER_ID = 1;
private ListView lv;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
lv = (ListView) findViewById(R.id.list_view);
findViewById(R.id.btnSomeAction).setOnClickListener(this);
}
@Override
public void onClick(View v) {
getSupportLoaderManager().initLoader(LOADER_ID, null, this);
}
@Override
public Loader<String[]> onCreateLoader(int id, Bundle bundle) {
ContentAsyncLoader loader = new ContentAsyncLoader(this);
return loader;
}
@Override
public void onLoaderReset(Loader<String[]> loader) {
}
@Override
public void onLoadFinished(Loader<String[]> loader, String[] data) {
if (data != null) {
ArrayAdapter<String> adapter = new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1, android.R.id.text1, data);
lv.setAdapter(adapter);
}
}
}
Если кто-то хочет четкий вопрос: как правильно сделать использование Loader
что запускается нажатием кнопки, чтобы данные автоматически повторно предоставлялись при воссоздании активности?
У меня есть некоторые грязную работу вокруг, чтобы исправить это, держа флаг установлен в верно, когда кнопка нажата, сохранить его, когда onSaveInstanceState
называется, а затем в onCreate
проверить, если присутствует, и если это так назвать initLoader
; но я не хочу иметь это в таких случаях, и когда я начинаю разные загрузчики от деятельности мне нужно держать флаг для каждого такого загрузчика, как я, как правило, ленив ... Например:
private boolean loaderCreated;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
lv = (ListView) findViewById(R.id.list_view);
findViewById(R.id.btnSomeAction).setOnClickListener(this);
if (savedInstanceState != null) {
loaderCreated = savedInstanceState.getBoolean("TEMP", false);
if(loaderCreated) {
getSupportLoaderManager().initLoader(LOADER_ID, null, this);
}
}
}
@Override
protected void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
outState.putBoolean("TEMP", loaderCreated);
}
@Override
public void onClick(View v) {
loaderCreated = true;
getSupportLoaderManager().initLoader(LOADER_ID, null, this);
}
Isn» Есть ли лучший способ сделать это?
Да, я знаю ... Но, как говорится, я ненавижу делать это каждый раз, не лучший способ сделать это? Почему «LoaderManager» не знает об этой воссозданной деятельности? – gunar
LoaderManager ничего не знает. Это задание по работе, чтобы спросить о данных, и Activity должна спросить только, есть ли такая необходимость (что означает, что нажата кнопка). Вы не должны называть эту переменную 'loaderCreated', а' dataWasLoaded' или что-то вроде 'iWantToSeeData';), потому что реальная информация заключается в том, что вы хотите отображать данные, нажимая кнопку –
Действительно, это единственный метод. Я бы любил, однако, что «LoaderManager» должен делать это от моего имени. – gunar