2014-02-16 8 views
5

Ich habe Aktivität und Pager mit 3 Fragmenten. Ich benutze Tabs zum Umschalten. Wenn ich auf eine Schaltfläche klicke, möchte ich Fragment0 durch eine neue ersetzen. Es funktioniert nur, wenn Fragment0 leeres Layout hat. Wenn ich einige Inhalte in dem Layout fragment0 gesetzt (es hat Listenansicht sein) Ausnahme ausgelöst:habe "java.lang.IllegalStateException: Fragment bereits aktiv" wenn das Layout nicht leer ist

java.lang.IllegalStateException: Fragment already active 
    at android.support.v4.app.Fragment.setInitialSavedState(Fragment.java:503) 
    at android.support.v4.app.FragmentStatePagerAdapter.instantiateItem(FragmentStatePagerAdapter.java:110) 
    at android.support.v4.view.ViewPager.addNewItem(ViewPager.java:649) 

Ich verwende folgendes Layout:

<?xml version="1.0" encoding="utf-8"?> 
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" 
      android:orientation="vertical" 
      android:id="@+id/all_exp_frag" 
      android:layout_width="fill_parent" 
      android:layout_height="fill_parent"> 

<ListView 
     android:layout_width="fill_parent" 
     android:layout_height="fill_parent" 
     android:id="@+id/all_expenses"/> 

</LinearLayout> 

Aktivität:

public class Activity extends FragmentActivity { 

    private List<Fragment> fragments; 
    private MyPagerAdapter pagerAdapter; 

    @Override 
    protected void onCreate(Bundle savedInstanceState) { 
     fragments = asList(new Fragment0(), new Fragment1(), new Fragment2()); 
     // initialize pager, etc. 
     pagerAdapter = new MyPagerAdapter(getSupportFragmentManager(), pager); 
    } 

    // handle add new fragment button 
    @Override 
    public boolean onOptionsItemSelected(MenuItem item) { 
     pagerAdapter.replaceCurrentFragment(new Fragment3()); 
    } 

    public class MyPagerAdapter extends FragmentStatePagerAdapter { 

     final ViewPager pager; 

     public MyPagerAdapter(FragmentManager fm, ViewPager pager) { 
      super(fm); 
      this.pager = pager; 
     } 

     @Override 
     public CharSequence getPageTitle(int position) { 
      return fragments.get(position).getFragmentTitle(); 
     } 

     @Override 
     public int getCount() { 
      return fragments.size(); 
     } 

     @Override 
     public Fragment getItem(int position) { 
      return fragments.get(position); 
     } 

     @Override 
     public int getItemPosition(Object object) { 
      if (object instanceof ExpensesFragment) { 
       return POSITION_NONE; 
      } 
      return POSITION_UNCHANGED; 
     } 

     public void replaceCurrentFragment(BaseFragment fragment) { 
      final int currentPosition = pager.getCurrentItem(); 
      final BaseFragment old_fragment = fragments.get(currentPosition); 
      if (old_fragment == null) { 
       return; 
      } 
      this.startUpdate(pager); 
      getSupportFragmentManager() 
        .beginTransaction() 
        .setTransition(FragmentTransaction.TRANSIT_FRAGMENT_OPEN) 
        .remove(old_fragment) 
        .add(pager.getId(), fragment) 
        .commitAllowingStateLoss(); 
      fragments.set(currentPosition, fragment); 
      this.finishUpdate(pager); 
      this.notifyDataSetChanged(); //IN THIS LINE EXCEPTION IS THROWN WHEN LAYOUT IS NOT EMPTY (contains listview). IF EMPTY - IT WORKS FINE. 
      listener.onPageSelected(0); 
     } 

    } 
} 

Anwendung wirft Ausnahme in Zeile

this.notifyDataSetChanged();

Wenn das Layout nicht leer ist.

Ich kann keine Lösung finden, wie diese Ausnahme zu vermeiden und Fragment korrekt zu ersetzen.

EDITED

https://android.googlesource.com/platform/frameworks/support/+/jb-mr1-dev/v4/java/android/support/v4/app/Fragment.java

als I enthält Fragment Klasse folgende Methode geprüft:

public void setArguments(Bundle args) { 
    if (mIndex >= 0) { 
     throw new IllegalStateException("Fragment already active"); 
    } 
    mArguments = args; 
} 

vielleicht die Art, wie ich bin Fragmente Zugabe ist nicht korrekt ..

+0

genannt annehmen wurde Did u got Lösung für dieses Problem .. bitte Antwort aktualisieren?. – CoDe

Antwort

3

Es war nur falsche Logik, Fragmente hinzuzufügen. Gute Arbeits Lösung könnte hier: correct answer

+1

Wenn es wirklich ein doppeltes Problem ist, dann markieren Sie dies als eine doppelte Lösung und gehen Sie diese Route. Ansonsten gib bitte ein Beispiel, keinen Link zu einer anderen Seite. So werden die Dinge hier verwirrend. :) –

1

Überprüfen Sie, ob das Fragment bereits hinzugefügt wurde oder nicht mit dem Fragment Klasse #isAdded() Methode. Dann ersetzen oder das Fragment hinzufügen entsprechend:

Lassen Sie uns Ihr Fragment fragment

// Fragment object 
Fragment fragment; 

// Check to see if it's added or not like this 
if (!fragment.isAdded()) { 
    // Things you could do here: 
    // -- Set argument 
    // -- Begin a transaction 
    // -- etc... 
} 
Verwandte Themen