2011-03-11 3 views
16

Pouvez-vous placer des fragments à l'intérieur du fragment pour un onglet dans la barre d'actions?Fragments dans l'action Barre de fragments de tabulation?

J'ai une application Android (3.0/Honeycomb) avec une activité principale qui a une barre d'action avec 3 onglets. Les onglets sont ajoutés dans la méthode onCreate() de mon activité et les fragments de tabulation sont ajoutés/supprimés avec TabListener. Le code est presque identique à l'échantillon à http://developer.android.com/guide/topics/ui/actionbar.html#Tabs.

Le TabListener ressemble à ceci:

public class SwapOutTabListener implements ActionBar.TabListener { 
    public SwapOutTabListener(Fragment fragment) { 
     _fragment = fragment; 
    } 

    @Override 
    public void onTabSelected(Tab tab, FragmentTransaction ft) { 
     ft.add(R.id.fragment_container, _fragment, null); 
    } 

    @Override 
    public void onTabUnselected(Tab tab, FragmentTransaction ft) { 
     ft.remove(_fragment); 
    } 

    @Override 
    public void onTabReselected(Tab tab, FragmentTransaction ft) { 
     // do nothing 
    } 

    private Fragment _fragment; 
} 

Deux de mes onglets sont simples fragments, ils ne contiennent qu'un seul TextView en eux, un peu comme celui-ci (la plupart des attributs supprimés pour plus de clarté):

<LinearLayout> 
    <TextView android:text="Tab 1" /> 
</LinearLayout> 

Mais le fragment pour un de mes onglets est plus complexe, et contient deux fragments intégrés, un peu comme celui-ci:

<LinearLayout> 
    <fragment 
     android:name="...Fragment_1" 
     android:id="@+id/frag1" 
    /> 
    <fragment 
     android:name="...Fragment_2" 
     android:id="@+id/frag2" 
    /> 
</LinearLayout> 

Lorsque l'utilisateur sélectionne l'onglet pour ce fragment, toutes les méthodes du cycle de vie de démarrage (onStart(), onResume()) sont appelées pour les trois fragments (le fragment de tabulation, plus les deux fragments incorporés). Mais lorsque l'utilisateur sélectionne un autre onglet, seul le fragment de tabulation obtient l'une des méthodes de fin de cycle (onPause(), onStop(), etc.). Les deux fragments incorporés n'obtiennent jamais aucun de ces appels et ne sont jamais fermés.

Cela provoque des problèmes lorsque l'onglet est à nouveau sélectionné, comme le moteur d'exécution se plaint d'un ID de fragment en double lors du chargement du fragment onglet:

Binary XML file line #7: Duplicate id 0x7f05000a, tag null, or parent id 0x7f050009 with another fragment for ...Fragment_1 

Est-il ma responsabilité de supprimer ces fragments incorporés lorsque le fragment onglet est retiré? Si oui, quand, exactement, est-ce que je fais ça?

+0

Pouvez-vous poster votre code TabListener qui exécute le commutateur onglet? Sont également les doublons 'android: id =" @ + id/frag2 "lignes ci-dessus intentionnel ou juste une erreur de transcription dans la question posté ici? – adamp

+0

@adamp, oui, l'ID en double était une erreur de transcription ... J'ai édité la question pour corriger cela. J'ai également ajouté mon code TabListener à la question. –

Répondre

18

Non, les fragments ne font actuellement pas partie d'une hiérarchie. J'ai envisagé de le faire, mais à ce stade, tous les cas d'utilisation ont été principalement motivés par une surutilisation extrême de fragments où chaque élément d'interface utilisateur séparé est implémenté en tant que fragment. Ce n'est pas ainsi qu'ils sont destinés à être utilisés, ils sont destinés à encapsuler les principales pièces de haut niveau d'une application. Si vous avez une hiérarchie de choses, c'est ce que votre mise en page et vos vues sont pour.

+0

Voici un cas d'utilisation à considérer. Prenez l'application Google I/O 2012, installez-la sur une tablette de 10 pouces. Aller à la vue des sessions. Vous avez des "Sessions" et "Sandbox" comme onglets en haut, mais je ne pense pas que vous pourriez utiliser PageViewer ici parce que vous avez déjà des fragments. Je pense que ce serait bien d'utiliser PageViewer et de toujours utiliser Fragments pour l'onglet que vous utilisez actuellement. – Justin