7

現在、1 つのアクティビティがあり、それにフラグメントが追加されています (検索、曲の詳細、設定など)。サイド ベースのメニュー ナビゲーションを実装したので、副作用として、バックスタックに追加されるフラグメントの数に制限がなくなりました。フラグメントの数を制限したり、古いエントリを削除したりする方法はありますか? たとえば、各曲の詳細フラグメントには推奨曲リストがあり、それを介して別の曲の詳細フラグメントに移動できます。バックスタックに 30 個のフラグメントを持つことは簡単に可能です。DDMS を開いている場合、ヒープ サイズがゆっくりと (しかし確実に) 増加していることがわかります。

編集:私がやろうとしたことの1つは、ユーザーがサイドメニューオプションの1つをクリックした場合、そのフラグメントがすでにバックスタックにある場合、新しいフラグメントをインスタンス化する代わりにそのフラグメントに戻ろうとすることですが、もちろん、ユーザーがが曲の詳細ページにある場合、[戻る] を押すとそのフラグメントに移動すると予想されるため、機能しません。

編集2:これは私のaddFragmentメソッドです(Philの提案とともに):

public void addFragment(Fragment fragment) { 

        FragmentManager fm = getSupportFragmentManager();
        if(fm.getBackStackEntryCount() > 2) {

              fm.popBackStack();
            }
        fm.beginTransaction()                 
                  .replace(R.id.fragment_container, fragment).addToBackStack("")
                  .commit();
}

試してみたところ、Fragment の履歴が A->B->C->D で、D から戻って B->A->exit と仮定しました。

テストするために 8 レベルの深さを調べました: A->B->C->D->E->F->G->H、そして H から戻ると、同じことが起こりました: H->B->A- >終了します。

すべてのフラグメントは、上記の方法で追加されます。私が見たいのは、H->G->F->exit です。

4

2 に答える 2

12

BackStack 内の Fragment の数をプログラムで制御できます。

FragmentManager fm = getActivity().getSupportFragmentManager();

if(fm.getBackStackEntryCount() > 10) {

   fm.popBackStack(); // remove one (you can also remove more)
}

バックスタックにあるフラグメントの数を確認し、「オーバーフロー」がある場合は削除してください。

特定のフラグメントを BackStack から削除したい場合は、独自の BackStack を実装してonBackPressed() をオーバーライドする必要があります。Fragment BackStack は (名前が示すように) スタックであるため、最上位の要素 (最後に追加された要素) のみを削除でき、間にある Fragment を削除する可能性はありません。

たとえば、使用できます

ArrayList<Fragment>

独自のスタックを実現するために。onBackPressed() メソッドをオーバーライドすることで、以前のフラグメントの読み込みを希望するときはいつでも、その「スタック」にフラグメントを追加および削除するだけです(実際にはスタックではなくなりました)。

于 2013-08-17T21:47:39.923 に答える
3

これは古い質問ですが、私の答えは誰かを助けるかもしれません。

フラグメントがスタックにあるかどうかを確認してポップしないのはなぜですか? この方法では、バック スタックのサイズを気にする必要はありません (フラグメントが多数ある場合を除きます)。

    String backStateName = fragment.getClass().getName();
    boolean fragmentPopped = false;
    try {
        // true if fragment is in the stack
        fragmentPopped = fragmentManager.popBackStackImmediate(backStateName, 0);
    } catch (Exception e) {
        e.printStackTrace();
    }

    FragmentTransaction ft = fragmentManager.beginTransaction();

    if ( !fragmentPopped ) { //fragment not in back stack, add it...            
        ft.setTransition( FragmentTransaction.TRANSIT_FRAGMENT_FADE );
        ft.replace(R.id.main, fragment);
        ft.addToBackStack( backStateName );

        try {
            ft.commit();
        } catch (Exception e) {
            e.printStackTrace();
        }           
    }
于 2014-08-23T12:38:00.803 に答える