2013-02-22 14 views
30

Mam ListFragment w mojej MainActivity. Oto, w jaki sposób ustawiam obiekt fragmentu.Czy istnieje sposób na pobranie fragmentu z góry stosu?

FragmentManager fragmentManager = activity.getSupportFragmentManager(); 
FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction(); 
Fragment newFragment = new MyFragment(); 
fragmentTransaction.replace(R.id.framecontainer, newFragment, "tag"); 
fragmentTransaction.addToBackStack(null); 
fragmentTransaction.commit(); 

Problemem jest to, kiedy nacisnąć przycisk użytkownika z powrotem, muszę przynajmniej zmienić pasek działań i menu poprzez wywołanie

getActionBar().setTitle(title); 
getActionBar().setDisplayHomeAsUpEnabled(isEnabled); 
invalidateOptionsMenu(); 

muszę wiedzieć, jaki rodzaj fragment pokazuje aktualnie , dzięki czemu wiem, jak ustawić pasek akcji. Przechowuję opcję ustawienia w fragmencie jako argumenty.

String title = fragment.getArguments().getString("KEY_TITLE"); 
boolean isEnabled = fragment.getArguments().getBoolean("KEY_ISENABLED"); 

zrobić przeszukać powiązane pytanie, i zdałem sobie sprawę, mogę dostać fragment wywołując

MyFragment fragment = (MyFragment) getSupportFragmentManager() 
     .findFragmentByTag("tag"); 

Jednak muszę przechowywać wszystkie tag w niestandardowym stosu i zadzwonić pop () za każdym razem, gdy użytkownik nacisnął przycisk Wstecz w onBackPressed().

Moje pytanie brzmi, czy jest dla mnie sposobem na pobranie bieżącego widocznego fragmentu ze stosu bezpośrednio?

Uwaga: Proszę pamiętać, że typy fragmentów są różne, nie tylko MyFragment.

Odpowiedz

52

Niektóre rzeczy jak to powinno pomóc postać tę działalność na backpress:

private Fragment getCurrentFragment(){ 
    FragmentManager fragmentManager = getSupportFragmentManager(); 
    String fragmentTag = fragmentManager.getBackStackEntryAt(fragmentManager.getBackStackEntryCount() - 1).getName(); 
    Fragment currentFragment = fragmentManager.findFragmentByTag(fragmentTag); 
    return currentFragment; 
} 

@Override 
public void onBackPressed() { 
    Fragment fragmentBeforeBackPress = getCurrentFragment(); 
    // Perform the usual back action 
    super.onBackPressed(); 
    Fragment fragmentAfterBackPress = getCurrentFragment(); 
} 

nadzieję, że to pomaga.

+6

Wydaje się, że jeśli to zrobić w sposób, muszę ustawić * * fragmentTransaction.addToBackStack (tag) ** również; W przeciwnym razie uzyskałabym wyjątek NullPointerException. Więc ** fragmentManager.getBackStackEntryAt (fragmentManager.getBackStackEntryCount() - 1) .getName(); ** nie odnosi się do nazwy znacznika –

+1

Tak ... będziesz musiał sprawdzić, czy są null i zła matematyka ((getBackStackEntryCount-1)> 0 i takie).Pisałem to zbyt szybko. Ponadto dodawanie tagów bez tagu będzie miało wartość NULL. – petey

+0

będzie nadal działać, jeśli używam addToBackStack (null)? – umerk44

20
FragmentManager.findFragmentById(fragmentsContainerId) 

function powraca odwołują się do góry Fragment w backstack. Przykład użycia:

fragmentManager.addOnBackStackChangedListener(new OnBackStackChangedListener() { 
     @Override 
     public void onBackStackChanged() { 
      Fragment fr = fragmentManager.findFragmentById(R.id.fragmentsContainer); 
      if(fr!=null){ 
       Log.e("fragment=", f.getClass().getSimpleName()); 
      } 
     } 
    }); 
+0

Wydaje się to trochę dziwne ... ale działa dobrze dla mnie :). Dokumenty mówią, że przeszukuje backstack, więc mam nadzieję, że zawsze wyszukuje od góry stosu, we wszystkich wersjach Androida (kciuki). – delrocco

+0

Szukałem tego od tak dawna. Dzięki za wyjaśnienie, jak działa ten słuchacz – mikebertiean

1

Jest już odpowiedź oznaczone jako poprawne i moja dodatkowa informacja nie będzie, że różni się. ALE, mam kłopoty z korzystaniem z odbiornika próbującego dowiedzieć się, czy fragment, z którego pochodzi odbiornik, jest bieżącym topowym fragmentem na stosie. Możesz łatwo uruchomić wiele NPE i indeks poza granicami. Dlatego napisałem to, może to pomaga komuś.

private boolean isFragmentOnTop(Activity parentActivity, final String fragmentName){ 
     FragmentManager fmManager = parentActivity.getFragmentManager(); 
     if(fmManager.getBackStackEntryCount() == 0){ 
      LOG.i("BackStack entry count is 0: " + this); 
      return false; 
     } 
     String fragmentNameOnStackTop = ""; 
     final FragmentManager.BackStackEntry topEntry = fmManager.getBackStackEntryAt(fmManager.getBackStackEntryCount() -1); 
     if(topEntry != null) { 
      fragmentNameOnStackTop = topEntry.getName(); 
     } 
     LOG.d("Got fragments name: " + fragmentNameOnStackTop); 
     return fragmentNameOnStackTop != null ? fragmentNameOnStackTop.equals(fragmentName) : false; 
    } 

Zauważ, że działa to dobrze w przypadku aktywności mającej pewne fragmenty. Bądź świadomy, jeśli jesteś przy użyciu ViewPager childfragmentmanager.

I nie zapomnij, aby ustawić fragmentName w FragmentTransaction.addToBackStack(fragmentName)

0

ta metoda pomocnika dostać fragment z wierzchu stosu:

public Fragment getTopFragment() { 
    if (getSupportFragmentManager().getBackStackEntryCount() == 0) { 
     return null; 
    } 
    String fragmentTag = getSupportFragmentManager().getBackStackEntryAt(getSupportFragmentManager().getBackStackEntryCount() - 1).getName(); 
    return getSupportFragmentManager().findFragmentByTag(fragmentTag); 
} 
Powiązane problemy