1

Из всех поисков я нашел на SO о том, что вы должны сохранить состояние экземпляра в @Override public void onSaveInstanceState(Bundle outState)Сохранение фрагментов экземпляра состояния между транзакциями

Однако этот тесно связан с образом жизни деятельности.

Как сохранить состояние моего списка в фрагменте, который будет заменен другим фрагментом. У меня есть одно основное действие, в которое загружаются все фрагменты.

Я попытался это до сих пор:

@Override 
public void onSaveInstanceState(Bundle outState) { 
    super.onSaveInstanceState(outState); 
    //Save adapter data so that when the fragment is returned to it can be resused. 
    ArrayList<CategoryMobileDto> categories = new ArrayList<CategoryMobileDto>(); 
    for(int i=0; i < adapter.getCount();i++) 
    { 
     categories.add(adapter.getItem(i)); 
    } 
    String persistData = new Gson().toJson(categories); 
    outState.putString("Categories", persistData);   
} 

, а затем в моем OnCreate();

if(savedInstanceState!=null) 
    { 
     String data =savedInstanceState.getString("Categories"); 
     Type collectionType = new TypeToken<ArrayList<CategoryMobileDto>>() { 
     }.getType(); 
     adapter.addAll(gson.<Collection<CategoryMobileDto>>fromJson(data, collectionType)); 
     adapter.notifyDataSetChanged(); 
    }else{ 
     // Make request to server 
    } 

однако savedInstanceState всегда null. Но это имеет смысл, поскольку моя деятельность не разрушается и не воссоздается.

Это, как я переход от одного фрагмента к другому:

fragment.setArguments(args); 
    FragmentManager fragmentManager = getFragmentManager(); 
    FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction(); 
    fragmentTransaction.replace(R.id.container, fragment, "ProductListFragment"); 
    fragmentTransaction.addToBackStack(null); 
    fragmentTransaction.commit(); 

Есть ли способ я могу сохранить состояние моего ListView, когда фрагмент будет удален, а затем восстановить его снова, когда фрагмент извлекается из back-stack?

ответ

0

Переместить этот код из OnCreate() в onActivityCreated() из фрагмента

if(savedInstanceState!=null) 
    { 
     String data =savedInstanceState.getString("Categories"); 
     Type collectionType = new TypeToken<ArrayList<CategoryMobileDto>>() { 
     }.getType(); 
     adapter.addAll(gson.<Collection<CategoryMobileDto>>fromJson(data, collectionType)); 
     adapter.notifyDataSetChanged(); 
    }else{ 
     // Make request to server 
    } 

Если у вас есть запрос, пожалуйста, дайте мне знать.

+0

ли моя деятельность получить воссозданы каждый раз, когда я выгрузить фрагмент? – Zapnologica

+0

Я рекомендую это решение для фрагмента. – droidd

+0

Кажется не работает для меня. Сохраненный экземпляр всегда равен нулю. И '@Override public void onSaveInstanceState (Bundle outState)' не вызывается при замене фрагмента на другой? (только на экране вращаются). Все мысли. Я не могу каким-то образом связать его с фрагментатором? – Zapnologica

0

Вы можете использовать Аргументы с Фрагментом (Только если у вас есть данные, чтобы показать их фрагмент до того, как фрагмент загружен, означает прикрепленный). Вы можете установить аргументы в фрагмент, который будет сохраняться при переходе на другой фрагмент по транзакции фрагмента, а когда вы вернетесь, загрузите фрагмент из функции getArguments.

общественных пустот setArguments (Bundle арг)

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

общественные конечные Bundle getArguments()

Добавлено уровня API 11 возвращенной аргументы, переданные когда фрагмент был экземпляр, если таковые имеются.

Вы можете найти пример кода ниже для передачи данных между фрагментами:

main.xml

<?xml version="1.0" encoding="utf-8"?> 
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android" 
android:id="@+id/flContainer" 
android:layout_width="match_parent" 
android:layout_height="match_parent" > 

</FrameLayout> 

MainActivity.java

public class MainActivity extends Activity implements IFragContainer { 

private static final String FRAG_TAG = "FragTag"; 
private FragBase mFrag; 
private String dataToBePassedBack; 

@Override 
protected void onCreate(Bundle savedInstanceState) { 
    super.onCreate(savedInstanceState); 
    setContentView(R.layout.main); 
    changeFragment(FragA.class, "Data to Frag A"); 
} 

@Override 
public void changeFragment(Class<? extends FragBase> fragClass, String data) { 
    try { 
     FragmentTransaction ft = getFragmentManager().beginTransaction(); 
     mFrag = fragClass.newInstance(); 
     Bundle args = new Bundle(); 
     args.putString("DATA", data); 
     mFrag.setArguments(args); 
     ft.replace(R.id.flContainer, mFrag, FRAG_TAG); 
     ft.addToBackStack(mFrag.toString()); 
     ft.commit(); 
    } catch (Exception e) { 
     e.printStackTrace(); 
    } 
} 

@Override 
public void onBackPressed() { 
    dataToBePassedBack = mFrag.getDataToPassBack(); 
    FragmentManager mgr = getFragmentManager(); 
    mgr.executePendingTransactions(); 

    boolean doCheckAndExit = true; 

    for (int i = mgr.getBackStackEntryCount() - 1; i > 0; i--) { 
     BackStackEntry entry = mgr.getBackStackEntryAt(i); 

     if (!TextUtils.isEmpty(entry.getName())) { 
      mgr.popBackStackImmediate(entry.getId(), 
        FragmentManager.POP_BACK_STACK_INCLUSIVE); 
      doCheckAndExit = false; 
      break; 
     } 
    } 

    if (doCheckAndExit) { 
     finish(); 
    } else { 
     mFrag = (FragBase) mgr.findFragmentByTag(FRAG_TAG); 
    } 
} 

@Override 
public String getDataToBePassedBack() { 
    return dataToBePassedBack; 
} 

} 

IFragContainer.Java

public interface IFragContainer { 
void changeFragment(Class<? extends FragBase> fragClass, String data); 

String getDataToBePassedBack(); 
} 

FragBase.java

public abstract class FragBase extends Fragment { 

public String getDataToPassBack(){ 
    return null; 
} 

} 

FragA.java

public class FragA extends FragBase { 

@Override 
public View onCreateView(LayoutInflater inflater, ViewGroup container, 
     Bundle savedInstanceState) { 
    Button btn = new Button(getActivity()); 
    final IFragContainer fragContainer = (IFragContainer) getActivity(); 
    if (TextUtils.isEmpty(fragContainer.getDataToBePassedBack())) { 
     btn.setText(getArguments().getString("DATA")); 
    } else { 
     btn.setText(fragContainer.getDataToBePassedBack()); 
    } 
    btn.setLayoutParams(new LayoutParams(LayoutParams.WRAP_CONTENT, 
      LayoutParams.WRAP_CONTENT)); 
    btn.setOnClickListener(new OnClickListener() { 

     @Override 
     public void onClick(View v) { 
      fragContainer.changeFragment(FragB.class, "Data to Frag B"); 
     } 
    }); 
    return btn; 
} 

} 

FragB.java

public class FragB extends FragBase { 
@Override 
public View onCreateView(LayoutInflater inflater, ViewGroup container, 
     Bundle savedInstanceState) { 
    Button btn = new Button(getActivity()); 
    btn.setText(getArguments().getString("DATA")); 
    btn.setLayoutParams(new LayoutParams(LayoutParams.WRAP_CONTENT, 
      LayoutParams.WRAP_CONTENT)); 
    btn.setOnClickListener(new OnClickListener() { 

     @Override 
     public void onClick(View v) { 
      getActivity().onBackPressed(); 
     } 
    }); 
    return btn; 
} 

@Override 
public String getDataToPassBack() { 
    return "Data from Frag B to A"; 
} 
} 
+0

Итак, вы говорите, что я должен передать аргументы из frag1 => frag2 и передать их обратно, когда вы нажимаете кнопку назад от frag2 => frag1? – Zapnologica

+0

@ Zapnologica Нет, если вам нужно передать некоторые значения фрагменту во время его создания, вы можете использовать setArguments и внутренний фрагмент, вы можете использовать getArguments. Таким образом, для передачи некоторой даты от frag A до frag B вы можете создать объект frag B и вызвать setArguments на объекте frag B с передаваемыми данными. Когда вы вернетесь, если вам нужны данные, которые нужно вернуть, вам необходимо обратиться за помощью к своей родительской деятельности, связав ее. Например, у вас есть контекст (означает вашу родительскую активность) в вашем фрагменте B, установите данные в этот cntext с интерфейсом, а затем вернитесь к фрагменту A, получите данные из cntext в A. –

+0

Мне нужен фрагмент a для сохранения данных, а затем отправьте его обратно в frag A, когда фрагмент A снова появится в стеке. Я не пытаюсь передать данные между любыми двумя фрагментами. Он должен вращаться вокруг одного жизненного цикла фрагментов. – Zapnologica

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