0

J'ai un bouton d'action flottante (FAB) dans l'activité principale avec 4 onglets de fragmentation en dessous.Android: Actualiser l'onglet du fragment ViewPager actuellement affiché après avoir saisi des données dans l'invite de l'activité principale

J'ai une boîte de dialogue séparée pour la saisie de données lorsque je clique sur le FAB en fonction de l'onglet affiché.

Maintenant, pour le premier onglet, je suis en mesure d'actualiser le contenu du fragment immédiatement après avoir entré des données et en cliquant sur OK dans l'invite de boîte de dialogue en utilisant Interface. Toutefois, pour les onglets 2 à 4, je ne suis pas en mesure d'actualiser les données immédiatement après avoir cliqué sur OK dans la boîte de dialogue respective pour chacun des onglets 2 à 4. Je dois cliquer sur le premier onglet puis revenir à l'onglet précédemment affiché pour pouvoir actualiser les vues.

Ce que je veux faire est:

De deuxième/troisième/quatrième onglet, après la saisie des données et en cliquant sur l'invite de dialogue d'entrée pour l'onglet correspondant, l'onglet affiché doit immédiatement mettre à jour les vues à l'intérieur il en fonction de ce que j'ai entré dans la boîte de dialogue et enregistré dans la base de données.

Veuillez noter que je sauvegarde les entrées dans la base de données après avoir cliqué sur le bouton OK dans les invites.

Comment est-ce que je peux faire ceci? Merci d'avance et j'apprécie toute votre aide!:)

Voici mon code (je suis en utilisant l'interface):

public class MyActivity extends AppCompatActivity { 
 

 
    private PopupListener popupListener; 
 

 
    @Override 
 
    protected void onCreate(@Nullable Bundle savedInstanceState) { 
 
    super.onCreate(savedInstanceState); 
 
    //Your dialog code. 
 
    setPositiveButton("Ok", new DialogInterface.OnClickListener() { 
 
     @Override 
 
     public void onClick(DialogInterface dialog, int which) { 
 
     popupListener.onDialogClick("first_tab"); //"second_tab" for second tab, and so on... 
 
     } 
 
    }) 
 
    } 
 

 
    public void setPopupListener(PopupListener popupListener) { 
 
    this.popupListener = popupListener; 
 
    } 
 

 
    public interface PopupListener { 
 
    void onDialogClick(String value); 
 
    } 
 
}

code en 2ème onglet:

public class MyFragment extends Fragment { 
 

 
    @Override 
 
    public void onViewCreated(final View view, @Nullable Bundle savedInstanceState) { 
 
    super.onViewCreated(view, savedInstanceState); 
 
    ((MyActivity) getActivity()).setPopupListener(new MyActivity.PopupListener() { 
 
     @Override 
 
     public void onDialogClick(String value) { 
 
     //After clicking dialog ok button in Activity 
 
     setUserVisibleHint(true, view); // get value from the database here. 
 
     } 
 
    }); 
 
    } 
 
}

Code pour mettre à jour cu fragment rrently affichée (échantillon est inférieure à deuxièmeonglet):

@Override 
 
public void setUserVisibleHint(boolean isVisibleToUser, final View view) { 
 
    super.setUserVisibleHint(isVisibleToUser); 
 
    if (isVisibleToUser) { 
 
    //get data from database and refresh view. 
 
    viewFunds(view) //method is for updating 2nd tab 
 
    } 
 
}

OnCreate intérieur() de l'ensemble des 4 fragments:

public void onCreate(@Nullable Bundle savedInstanceState) { 
 
    setUserVisibleHint(false); 
 
}

premier code onglet: (ajouté selon la demande de commentaire)

@Override 
 
public void onViewCreated(final View view, @Nullable Bundle savedInstanceState) { 
 
    super.onViewCreated(view, savedInstanceState); 
 
    ((Main2Activity) getActivity()).setPopupListener(new Main2Activity.PopupListener() { 
 
    @Override 
 
    public void onDialogClick(String value) { 
 
     //After clicking dialog ok button in Activity 
 
     // you will get value here. 
 
     viewBudget(view); //method to updated views inside first tab 
 
    } 
 
    }); 
 
}

FAB Surclic Listener:

FloatingActionButton fab = (FloatingActionButton) findViewById(R.id.floatingActionButton_main2); 
 
fab.setOnClickListener(new View.OnClickListener() { 
 
     @Override 
 
     public void onClick(View view) { 
 
      int position = tabLayout.getSelectedTabPosition(); 
 

 
      switch (position) { 
 
      case 0: 
 

 
       // first tab is selected 
 

 
       //Toast.makeText(context,"0",Toast.LENGTH_LONG).show(); 
 

 

 
       break; 
 
      case 1: 
 
       // second tab is selected 
 
       //Toast.makeText(getApplicationContext(),"1",Toast.LENGTH_LONG).show(); 
 

 
       break; 
 
      case 2: 
 
       // third tab is selected 
 
       //Toast.makeText(getApplicationContext(),"2",Toast.LENGTH_LONG).show(); 
 
       UpdateableFragment.showDialog(); //ERROR: non static method onDialogClick cannot be referenced from static context 
 
       break; 
 
      case 3: 
 
       // third tab is selected 
 
       //Toast.makeText(getApplicationContext(),"3",Toast.LENGTH_LONG).show(); 
 
       break; 
 
      }

+0

J'utilise déjà 'Interface' comme mentionné dans la question. Vous avez mentionné 'broadcast', pouvez-vous donner plus de détails en ajoutant une réponse? Je vous remercie. –

+0

Code pour le premier onglet ajouté (voir la question mise à jour ci-dessus). Merci :) –

+0

Premier fragment intérieur, onViewCreated. –

Répondre

0

En regardant votre code, je crois que ton problème je s que votre activité a un écouteur il peut invoquer en cliquant sur OK dans la boîte de dialogue, mais vous avez quatre fragments. Donc seul le un actuellement enregistré en tant qu'auditeur recevra le rappel.

Étant donné que votre logique communique d'une activité jusqu'à Fragments, il n'y a pas besoin d'un rappel ici (généralement vous utilisez callbacks pour communiquer de Fragments jusqu'à l'activité possédante).

Ainsi, vous pouvez remplacer votre interface avec un appel explicite au fragment concerné:

// Your dialog code. 
setPositiveButton("Ok", new DialogInterface.OnClickListener() { 
    @Override 
    public void onClick(DialogInterface dialog, int which) { 
     figureOutWhichFragmentIsSelectedAndCallExplicitUpdateMethodOnIt(); 
    } 
}) 

Maintenant, c'est une option. Je ne sais pas à quoi ressemble votre code ou application au-delà de votre échantillon, mais il semble que la boîte de dialogue affichée soit spécifique à chaque fragment. Dans ce cas, je pense qu'il est plus logique que le fragment en question montre le dialogue et gère l'interaction elle-même.

Vous pourriez avoir une interface/base pour tous vos fragments:

public interface UpdateableFragment { 
    void showDialog(); 
} 

Ensuite implémenter cette interface pour chaque fragment:

public TabOneFragment extends Fragment implements UpdateableFragment { 
    @Override 
    public void showDialog() { 
     // Show dialog for tab one data, register listener, save specific data 
    } 

Même idée pour les autres. Ensuite, dans votre activité, il se résume à:

myFabButton.setOnClickListener(new OnClickListener() { 
    @Override 
    public void onClick(View view) { 
     UpdateableFragment fragment = getCurrentlySelectedFragment(); // You define this method to return the current fragment 
     fragment.showDialog(); 
    } 
} 

Cela signifie que 1) l'activité a moins de logique à faire pour comprendre quel fragment est choisi et la méthode sur elle doit être appelé, car il va à travers une interface commune et 2) vos fragments n'ont pas besoin de savoir à quel type d'activité ils sont attachés (pour le moment, chaque fragment est explicitement converti en MyActivity et en appelant une méthode connue, ce qui interrompt l'encapsulation).

Espérons que ça aide!

+0

Merci @dominicoder, j'ai étudié votre réponse et les codes fournis. Je vais le tester et revenir à vous si j'ai des questions. Merci de votre aide! :) –

+0

@dominiicoder: Oui, vous avez raison, la boîte de dialogue affichée est spécifique à chaque fragment lorsque je clique sur l'activité principale FAB. –

+0

Bonjour @dominicoder, j'ai implémenté vos codes. Mon FAB OnClickListener est un peu différent car j'utilise 'tabLayout.getSelectedTabPosition()' puis 'switch' et' case'. J'ai ajouté votre code 'UpdateableFragment.showDialog()' dans le cas 2 et j'ai rencontré une erreur _non static method onDialogClick ne peut pas être référencé à partir du contexte statique. S'il vous plaît voir mon code FAB dans la question mise à jour ci-dessus. Comment dois-je procéder? Merci pour l'aide. –