2014-01-14 4 views
5

Итак, вот мой код. «currentFragment» - это просто поле, которое отслеживает отображаемое в данный момент. Это в классе, который сам является фрагментом (так что у меня есть фрагмент, показывающий фрагмент).Как предотвратить вызов функции onCreateView() фрагмента?

private void selectNavBarItem(NavbarItem v) 
{ 
    Fragment fragmentToUse = null; 

    if (v == setpointsNavItem) 
    { 
     fragmentToUse = setpointsFragment; 
    } 
    else if (v == rapidSetupNavItem) 
    { 
     fragmentToUse = rapidSetupFragment; 
    } 
    else if (v == outdoorResetNavItem) 
    { 
     fragmentToUse = outdoorResetFragment; 
    } 
    else if (v == rampDelayNavItem) 
    { 
     fragmentToUse = rampDelayFragment; 
    } 

    if (fragmentToUse != null) 
    { 
     FragmentManager fm = getFragmentManager(); 
     FragmentTransaction ft = fm.beginTransaction(); 

     if (currentFragment != null) 
     { 
      ft.detach(currentFragment); 
     } 

     currentFragment = fragmentToUse; 

     if (currentFragment.isDetached()) 
     { 
      ft.attach(currentFragment); 
     } 
     else 
     { 
      ft.add(R.id.setup_content_holder, currentFragment); 
     } 

     ft.addToBackStack(null); 
     ft.commit(); 
    } 

Все выглядит замечательно, но взгляды становятся воссозданы для всех фрагментов (onCreateView() и onViewCreated()). Я надеялся, что установка и отсоединение будут работать, но это не так. Причина, по которой я хочу поддерживать представление, заключается в том, что выбор пользователя по-прежнему существует, когда они перемещаются назад.

Другой вариант показывает и скрывает, но я не знаю, как это сделать, потому что фрагмент, который владеет этим кодом, имеет FrameLayout (R.id.setup_content_holder), который содержит фрагмент, который я хочу добавить, и я не может просто добавить к нему четыре фрагмента, но скрыть три из них. Есть возможность добавить фрагмент без контейнера, но я не знаю, как это должно работать.

Итак, любые идеи?

ответ

1

Методы OnCreateView всегда вызываются внутри фрагмента.

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

например. (в рамках данного фрагментного класса):

@Override 
public void onSaveInstanceState(Bundle savedInstanceState) { 
    super.onSaveInstanceState(savedInstanceState); 
    savedInstanceStatePutString("userString", someTextView.getText().toString()); 
    savedInstanceStatePutInt("userInt", userInt); 
    // etc... 
} 

@Override 
public void onRestoreInstanceState(Bundle savedInstanceState) { 
    super.onRestoreInstanceState(savedInstanceState); 
    someTextView.setText(savedInstanceState.getString("userString")); 
    userInt = savedInstanceState.getInt("userInt"); 
} 

Это должно решить вашу проблему при перескоке между фрагментами; приложение будет вызывать onSaveInstanceState и onRestoreInstanceState, когда фрагмент вставляется или вытаскивается из стека.

Это не спасет их навсегда, однако! Если вам требуется более постоянное хранилище, изучите другие параметры, такие как сохранение базы данных sqlite.

+1

Ugh, я не хочу использовать Bundles - они очень полезны, если я изменяю поля, не говоря уже о отсутствии проверки времени компиляции. Не обижайтесь на свой ответ - я уверен, что Android хочет, чтобы я это сделал.Знаете ли вы, что мой новый подход (см. Мой новый ответ) - хорошая идея? –

1

OP здесь.

Итак, я тут что-то взломал, и мне интересно, хорошая ли это идея. У меня есть фрагмент с изображением. В представлении содержится все, что я хочу сохранить (в краткосрочной перспективе, конечно же, это не должно быть более стойким, чем ОЗУ). Когда фрагмент вызывает onCreateView(), я просто возвращаю уже созданный View.

Теперь у меня возникла проблема, когда диспетчер фрагментов не удалялся. Я добавил вызов в onPause(), чтобы убедиться, что он удален из родителя.

Все работает нормально, но я хочу убедиться, что я не делаю что-то действительно плохое. Я знаю, что Android действительно очень хочет управлять своими жизненными циклами зрения, но я не хочу, чтобы он воссоздавал их каждое проклятое время. Они сложны, и я не хочу иметь дело с повторной инициализацией всего содержимого subview text/image /. Будут ли я сталкиваться с проблемами при попытке выполнить обычную рабочую процедуру Android?

EDIT: забыл код:

public class OutdoorResetFragment extends Fragment 
{ 
private OutdoorResetView view; 

public OutdoorResetFragment() 
{ 

} 

public void onAttach(Activity activity) 
{ 
    if (view == null || view.getContext() != activity) 
    { 
     view = new OutdoorResetView(activity); 
    } 

    super.onAttach(activity); 
} 

public void onPause() 
{ 
    super.onPause(); 

    ViewGroup container = (ViewGroup) view.getParent(); 

    if (container != null) 
    { 
     container.removeAllViews(); 
    } 
} 

@Override 
public View onCreateView(final LayoutInflater inflater, final ViewGroup container, 
     final Bundle savedInstanceState) 
{ 
    return view; 
} 

public OutdoorResetView getView() 
{ 
    return view; 
} 
} 
8

Попробуйте это, это будет решать ваш взгляд frgment г-создание вопроса;

@Override 
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { 
     if (mFragmentView != null) { 
      ((ViewGroup) mFragmentView.getParent()).removeView(mFragmentView); 
      return mFragmentView; 
     } 

     mFragmentView = inflater.inflate(R.layout.home_fragment, container, false); 

     ..... // your remaining code 
} 
+3

Это что-то, что обычно делают разработчики Android? – Eyeball

Смежные вопросы