Вопрос по fragment, android, android-viewpager, crash – Приложение Android сбоит через некоторое время с использованием фрагментов и ViewPager

8

У меня проблема с аварийным завершением работы моего приложения для Android при попытке восстановить мои фрагменты. Я не добавил никаких пользовательских переменных в комплект, который я пытаюсь восстановить, все это по умолчанию. Я использую Fragments и ViewPager. Смотрите мои фрагменты кода ниже:

public static class MyAdapter extends FragmentStatePagerAdapter {
    public MyAdapter(FragmentManager fm) {
        super(fm);
    }

    @Override
    public int getCount() {
        return NUM_ITEMS;
    }

    public int getCurrentItemPosition(Fragment fragment){
        return getItemPosition(fragment);
    }

    @Override
    public Fragment getItem(int position) {
        return ContentFragment.newInstance(position);
    }
}

public class MyActivity extends FragmentActivity {

static final int NUM_ITEMS = 100000;
public int currentSelectedPage;
private int changeToFragmentIndex;
public DateTime midDate;
MyAdapter mAdapter;
ViewPager mPager;

/** Called when the activity is first created. */
@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.diary);
    MyApplication application = (MyApplication)getApplication();
    application.dataController.myActivity = this;
    mAdapter = new MyAdapter(getSupportFragmentManager());
    mPager = (ViewPager)findViewById(R.id.pager);
    mPager.setAdapter(mAdapter);
    int newDay = application.daysBetween(DateTime.now(), DateTime.parse(application.day.dateToShortString()));

    this.currentSelectedPage = NUM_ITEMS/2+newDay;
    mPager.setCurrentItem(NUM_ITEMS/2+newDay);
    mPager.setOnPageChangeListener(new SimpleOnPageChangeListener(){
        public void onPageSelected(int position){
            currentSelectedPage = position;
            ContentFragment fragment = (ContentFragment) mAdapter.instantiateItem(mPager, currentSelectedPage);
            fragment.loadData();
        }
    });
}

}

public class ContentFragment extends Fragment {
private View v;
static final int NUM_ITEMS = 100000;

static ContentFragment newInstance(int num) {
    ContentFragment f = new ContentFragment();

    return f;
}

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
        Bundle savedInstanceState) {
    if (container == null)
        return null;
    v = inflater.inflate(R.layout.diarycontent, container, false);
    return v;
}

@Override
public void onActivityCreated(Bundle savedInstanceState) {
    super.onActivityCreated(savedInstanceState);

}

@Override
public void onSaveInstanceState(Bundle savedInstanceState){
    super.onSaveInstanceState(savedInstanceState);
    setUserVisibleHint(true);
}
}

Я получаю эту стековую трассу:

Caused by: java.lang.NullPointerException
at android.support.v4.app.FragmentManagerImpl.getFragment(FragmentManager.java:519)
at android.support.v4.app.FragmentStatePagerAdapter.restoreState(FragmentStatePagerAdapter.java:1 55)
at android.support.v4.view.ViewPager.onRestoreInstanceState(ViewPager.java:522)

Как я понял, это может быть известной проблемой с пакетом поддержки, и одним из возможных решений будет использование setUserVisibleHint (true) в onSaveInstanceState. Но это не помогло.

Кто-нибудь знает другое решение проблемы или что я сделал не так?

hi @xteci ты решил эту проблему? Я также сталкиваюсь с такой ошибкой и все еще не могу найти решени hakim
Ты можешь использовать этот ответ, он работает для меня / Stackoverflow.com вопросы / 18642890 / ... Medo Elkamaly
Я тоже, ребята, вы нашли что-нибудь? @ Хаким henrikpersson

Ваш Ответ

3   ответа
1

предложенное @Lalit Kumar Sahoo. Однако я заметил серьезную проблему: каждый раз, когда я поворачивал устройство, Менеджер фрагментов добавил новые фрагменты, не удаляя старые. Поэтому я продолжил поиск и нашел отчет об ошибке с предложением обходного пути post # 1). Я использовал это исправление и протестировал с моим приложением, проблема, кажется, решена без каких-либо побочных эффектов:

Workaround: Создайте пользовательский FragmentStatePagerAdapter в папке проекта src / android / support / v4 / app и используйте его.

package android.support.v4.app;

import android.os.Bundle;
import android.view.ViewGroup;

public abstract class FixedFragmentStatePagerAdapter extends FragmentStatePagerAdapter {

  public FixedFragmentStatePagerAdapter(FragmentManager fm) {
    super(fm);
  }

  @Override
  public Object instantiateItem(ViewGroup container, int position) {
    Fragment f = (Fragment)super.instantiateItem(container, position);
    Bundle savedFragmentState = f.mSavedFragmentState;
    if (savedFragmentState != null) {
      savedFragmentState.setClassLoader(f.getClass().getClassLoader());
    }
    return f;
  }
}
Но "mSavedFragmentState" недоступно ... android developer
-1

mPager.setOnPageChangeListener(new SimpleOnPageChangeListener(){
    public void onPageSelected(int position){
        currentSelectedPage = position;
        ContentFragment fragment = (ContentFragment) mAdapter.instantiateItem(mPager, currentSelectedPage);
        fragment.loadData();
    }
});

Это

@Override
public Fragment getItem(int position) {
    return ContentFragment.newInstance(position);
}

Создает фрагмент.

Вы можете загрузить данные в виде фрагмента:

@Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
loadData();
}
Это решило это для меня или спрятало на самом деле / Stackoverflow.com вопросы / 18642890 / ... Martin Seal
Я делал это, потому что у меня были проблемы с корректным обновлением фрагментов. Я проверил ваш код, и сбой все еще происходит. xteci
ты смог решить это? Я застрял с этой проблемой Preethi
23

как только начал использовать ViewPager с FragmentStatePagerAdapter внутри Tab.

Затем я играл на всех форумах, связанных с этой проблемой, и два дня ломал голову, чтобы выяснить, почему эта проблема возникла и как ее решить, но не нашел идеального решения, которое отвечало бы моим требованиям.

Я получил решение, так как во избежание сбоя NPE используйте FragmentPagerAdapter вместо FragmentStatePagerAdapter. Когда я заменяю FragmentPagerAdapter вместо FragmentStatePagerAdapter, то не сталкивался с проблемой сбоя NPE, но эта же страница не обновлялась сама для дальнейшей навигации (что является моим требованием).

Наконец переопределите метод saveState для FragmentStatePagerAdapter, и все работает нормально, как и ожидалось.

@Override
public Parcelable saveState() {
    // Do Nothing
    return null;
}


Как легко воспроизвести эту проблему:
Я использую устройство более высокой версии (4.1) и выполнил следующие действия:
1. Зайдите в Настройки -> Параметры разработчика.
2. Нажмите на опцию «Не сохранять активность».

Теперь я играл с моим приложением.

Перед тем как переопределить метод saveState () каждый раз, когда происходит сбой приложения из-за NPE по адресу android.support.v4.app.FragmentManagerImpl.getFragment (Unknown Source). Но после переопределения saveState () сбой не регистрируется.

Надеюсь, у тебя не возникнет никаких проблем.

Спасибо за это! A.S.
Оно работает! Кто-нибудь знает почему? Archit
Большое спасибо! Работает отлично Arnaldo Ignacio Gaspar Véjar
Спасибо большое. Это сработал moDev
Это решение полностью уничтожит состояние просмотра, и каждый фрагмент снова создается без восстановления состояния просмотра. Полезно только если вы не хотите восстанавливать состояние просмотра. Не полезно для всех случаев Ashok Koyi

Похожие вопросы