103 votes

Comment regrouper les boutons radio de différents LinearLayouts?

Je me demandais s'il est possible de regrouper chaque RadioButton individuel dans un unique RadioGroup en conservant la même structure. Ma structure ressemble à ceci :

  • LinearLayout_principal
    • LinearLayout_1
      • RadioButton1
    • LinearLayout_2
      • RadioButton2
    • LinearLayout_3
      • RadioButton3

Comme vous pouvez le constater, chaque RadioButton est actuellement un enfant d'un LinearLayout différent. J'ai essayé d'utiliser la structure ci-dessous, mais cela ne fonctionne pas :

  • RadioGroup
    • LinearLayout_principal
      • LinearLayout_1
        • RadioButton1
      • LinearLayout_2
        • RadioButton2
      • LinearLayout_3
        • RadioButton3

0voto

Mayhem Points 168

Alors que cela peut être un sujet plus ancien, je voudrais rapidement partager le code bricolage que j'ai écrit.. Ce n'est pas pour tout le monde et pourrait être amélioré..

La situation pour utiliser ce code ??
Ce code est pour les personnes qui ont une mise en page de la question d'origine ou similaire, dans mon cas, c'était comme ci-dessous. C'était personnellement pour une boîte de dialogue que j'utilisais.

  • LinLayout_Main
    • LinLayout_Row1
      • ImageView
      • RadioButton
    • LinLayout_Row2
      • ImageView
      • RadioButton
    • LinLayout_Row3
      • ImageView
      • RadioButton

Que fait le code lui-même ??
Ce code va énumérer chaque enfant de "LinLayout_Main" et pour chaque enfant qui est un "LinearLayout", il énumérera ensuite cette vue pour trouver des boutons radio.

Simplement, il cherchera le parent "LinLayout_Main" et trouvera les boutons radio dans les LinearLayouts enfants.

MyMethod_ShowDialog
Affichera une boîte de dialogue avec un fichier de mise en page XML tout en essayant de définir le "setOnClickListener" pour chaque RadioButton trouvé

MyMethod_ClickRadio
Parcourra chaque RadioButton de la même manière que "MyMethod_ShowDialog" le fait mais au lieu de définir le "setOnClickListener", il "setChecked(false)" pour effacer chaque RadioButton et ensuite, comme dernière étape, "setChecked(false)" à l'RadioButton ayant déclenché l'événement de clic.

public void MyMethod_ShowDialog(final double tmpLat, final double tmpLng) {
        final Dialog dialog = new Dialog(actMain);
        dialog.requestWindowFeature(Window.FEATURE_NO_TITLE);
        dialog.setContentView(R.layout.layout_dialogXML);

        final LinearLayout tmpLayMain = (LinearLayout)dialog.findViewById(R.id.LinLayout_Main);
        if (tmpLayMain!=null) {
            // Effectuer une recherche pour chaque enfant du LinearLayout principal
            int iChildCount1 = tmpLayMain.getChildCount();
            for (int iLoop1=0; iLoop1 < iChildCount1; iLoop1++){
                View tmpChild1 = tmpLayMain.getChildAt(iLoop1);
                if (tmpChild1 instanceof LinearLayout) {
                    // Effectuer une recherche pour chaque enfant LinearLayout du LinearLayout principal
                    int iChildCount2 = ((LinearLayout) tmpChild1).getChildCount();
                    for (int iLoop2=0; iLoop2 < iChildCount2; iLoop2++){
                        View tmpChild2 = ((LinearLayout) tmpChild1).getChildAt(iLoop2);
                        if (tmpChild2 instanceof RadioButton) {
                            ((RadioButton) tmpChild2).setOnClickListener(new RadioButton.OnClickListener() {
                                public void onClick(View v) {
                                    MyMethod_ClickRadio(v, dialog);
                                }
                            });
                        }
                    }
                }
            }

            Button dialogButton = (Button)dialog.findViewById(R.id.LinLayout_Save);
            dialogButton.setOnClickListener(new Button.OnClickListener() {
                public void onClick(View v) {
                    dialog.dismiss();
                }
            });
        }
       dialog.show();
}

public void MyMethod_ClickRadio(View vRadio, final Dialog dDialog) {

        final LinearLayout tmpLayMain = (LinearLayout)dDialog.findViewById(R.id.LinLayout_Main);
        if (tmpLayMain!=null) {
            int iChildCount1 = tmpLayMain.getChildCount();
            for (int iLoop1=0; iLoop1 < iChildCount1; iLoop1++){
                View tmpChild1 = tmpLayMain.getChildAt(iLoop1);
                if (tmpChild1 instanceof LinearLayout) {
                    int iChildCount2 = ((LinearLayout) tmpChild1).getChildCount();
                    for (int iLoop2=0; iLoop2 < iChildCount2; iLoop2++){
                        View tmpChild2 = ((LinearLayout) tmpChild1).getChildAt(iLoop2);
                        if (tmpChild2 instanceof RadioButton) {
                            ((RadioButton) tmpChild2).setChecked(false);
                        }
                    }
                }
            }
        }

        ((RadioButton) vRadio).setChecked(true);
}

Il peut y avoir des bugs, copié depuis le projet et renommé Voids/XML/ID

Vous pouvez également exécuter le même type de boucle pour trouver les éléments cochés

0voto

Qamar4P Points 39

Ceci est une version modifiée de la solution de @Infografnet. C'est simple et facile à utiliser.

RadioGroupHelper group = new RadioGroupHelper(this,R.id.radioButton1,R.id.radioButton2); group.radioButtons.get(0).performClick(); //programmatiquement

Il suffit de copier et coller

package com.qamar4p.farmer.ui.custom;

import java.util.ArrayList;
import java.util.List;

import android.app.Activity;
import android.view.View;
import android.widget.CompoundButton;
import android.widget.RadioButton;

public class RadioGroupHelper {

    public List radioButtons = new ArrayList<>();

    public RadioGroupHelper(RadioButton... radios) {
        super();
        for (RadioButton rb : radios) {
            add(rb);
        }
    }

    public RadioGroupHelper(Activity activity, int... radiosIDs) {
        this(activity.findViewById(android.R.id.content),radiosIDs);
    }

    public RadioGroupHelper(View rootView, int... radiosIDs) {
        super();
        for (int radioButtonID : radiosIDs) {
            add((RadioButton)rootView.findViewById(radioButtonID));
        }
    }

    private void add(CompoundButton button){
        this.radioButtons.add(button);
        button.setOnClickListener(onClickListener);
    }

    View.OnClickListener onClickListener = v -> {
        for (CompoundButton rb : radioButtons) {
            if(rb != v) rb.setChecked(false);
        }
    };
}

0voto

Edgar Khimich Points 89

Ceci est ma solution en Kotlin pour un layout personnalisé avec un RadioButton à l'intérieur.

tipInfoContainerFirst.radioButton.isChecked = true

var prevSelected = tipInfoContainerFirst.radioButton
prevSelected.isSelected = true

listOf(
    tipInfoContainerFirst.radioButton,
    tipInfoContainerSecond.radioButton,
    tipInfoContainerThird.radioButton,
    tipInfoContainerForth.radioButton,
    tipInfoContainerCustom.radioButton
).forEach {
    it.setOnClickListener { _it ->
    if(!it.isSelected) {
        prevSelected.isChecked = false
        prevSelected.isSelected = false
        it.radioButton.isSelected = true
        prevSelected = it.radioButton
    }
  }
}

0voto

Anupriya Points 773

Je rencontre le même problème, je dois utiliser un bouton radio pour le genre et tous étaient avec une image et un texte donc j'ai essayé de le résoudre de la manière suivante.

fichier xml:

Dans le fichier java: J'ai ajouté setOnCheckedChangeListener sur les 3 boutons radio et j'ai remplacé la méthode comme mentionné ci-dessous et ça fonctionne bien pour moi.

@Override
    public void onCheckedChanged(CompoundButton compoundButton, boolean b) {
   switch (compoundButton.getId()){
       case R.id.rbMale:
           if(rbMale.isChecked()){
               rbMale.setChecked(true);
               rbFemale.setChecked(false);
               rbOther.setChecked(false);
           }
           break;
       case R.id.rbFemale:
           if(rbFemale.isChecked()){
               rbMale.setChecked(false);
               rbFemale.setChecked(true);
               rbOther.setChecked(false);
           }
           break;
       case R.id.rbOthers:
           if(rbOther.isChecked()){
               rbMale.setChecked(false);
               rbFemale.setChecked(false);
               rbOther.setChecked(true);
           }
           break;

   }
    }

0voto

avisper Points 352

MixedCompoundButtonGroup le fait pour vous!

MixedCompoundButtonGroup gist

fun setAll() {
    for (i in 0 until childCount) {
        val child = getChildAt(i)
        setCompoundButtonListener(child)
    }
}  

private fun setCompoundButtonListener(view: View?) {
    if (view == null) return
    if (view is CompoundButton) {
        view.setOnCheckedChangeListener(compoundButtonCheckedChangedListener)
    } else if (view is ViewGroup && view !is RadioGroup) { // PAS RadioGroup!
        for (i in 0 until view.childCount) {
            setCompoundButtonListener(view.getChildAt(i))
        }
    }
}

private fun initCompoundButtonListener() {
    compoundButtonCheckedChangedListener = CompoundButton.OnCheckedChangeListener { compoundButton, isChecked ->
        setChecked(compoundButton, isChecked)
    }
}

private fun setChecked(compoundButton: CompoundButton, isChecked: Boolean) {
    if (isChecked.not()) return
    if (currentCompoundButton != null) {
        currentCompoundButton!!.isChecked = false
        currentCompoundButton = compoundButton
    } else {
        currentCompoundButton = compoundButton
    }
    checkedChangedListener?.onCheckedChanged(currentCompoundButton!!)
}

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X