passando l'argomento a DialogFragment


Risposte:


299

utilizzando newInstance

public static MyDialogFragment newInstance(int num) {
    MyDialogFragment f = new MyDialogFragment();

    // Supply num input as an argument.
    Bundle args = new Bundle();
    args.putInt("num", num);
    f.setArguments(args);

    return f;
}

E prendi gli Args in questo modo

@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    mNum = getArguments().getInt("num");
    ...
}

Guarda l'esempio completo qui
http://developer.android.com/reference/android/app/DialogFragment.html


Puoi semplicemente impostare variabili private su MyDialogFragment invece di usare bundle?
SIr Codealot

10
@SIrCodealot l'effetto sarebbe lo stesso dell'impostazione delle variabili su Activity o Fragment. Se affronti qualcosa che distrugge e ricrea il DialogDragment come il cambio di rotazione, perderai tutte le variabili.
inmyth

2
Per tutti coloro che chiedono il motivo per cui un costruttore di sovraccarico non viene utilizzato in questo caso, vedere un altro discussione sul tema che è molto istruttivo: stackoverflow.com/questions/14011808/...
HondaGuy

Mi ci è voluto un minuto per notare che il valore savedInstanceState non viene utilizzato.
Odys

25

Ho usato per inviare alcuni valori dal mio listview

Come spedire

mListview.setOnItemLongClickListener(new AdapterView.OnItemLongClickListener() {
        @Override
        public boolean onItemLongClick(AdapterView<?> parent, View view, int position, long id) {
            Favorite clickedObj = (Favorite) parent.getItemAtPosition(position);

            Bundle args = new Bundle();
            args.putString("tar_name", clickedObj.getNameTarife());
            args.putString("fav_name", clickedObj.getName());

            FragmentManager fragmentManager = getSupportFragmentManager();
            TarifeDetayPopup userPopUp = new TarifeDetayPopup();
            userPopUp.setArguments(args);
            userPopUp.show(fragmentManager, "sam");

            return false;
        }
    });

Come ricevere all'interno del metodo onCreate () di DialogFragment

    Bundle mArgs = getArguments();
    String nameTrife = mArgs.getString("tar_name");
    String nameFav = mArgs.getString("fav_name");
    String name = "";

// Caricamento di Kotlin

 val fm = supportFragmentManager
        val dialogFragment = AddProgFargmentDialog() // my custom FargmentDialog
        var args: Bundle? = null
        args?.putString("title", model.title);
        dialogFragment.setArguments(args)
        dialogFragment.show(fm, "Sample Fragment")

// ricevere

 override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        if (getArguments() != null) {
            val mArgs = arguments
            var myDay= mArgs.getString("title")
        }
    }

1
La risposta migliore!
user55924

1
Grazie ! La versione di Kotlin ha aiutato.
ArdenDev

6

Quindi ci sono due modi per passare valori da frammento / attività a frammento di dialogo: -

  1. Crea un oggetto frammento di dialogo con il metodo make setter e passa valore / argomento.

  2. Passa valore / argomento attraverso il bundle.

Metodo 1:

// Fragment or Activity 
@Override
public void onClick(View v) {
     DialogFragmentWithSetter dialog = new DialogFragmentWithSetter();
     dialog.setValue(header, body);
     dialog.show(getSupportFragmentManager(), "DialogFragmentWithSetter");         
}


//  your dialog fragment
public class MyDialogFragment extends DialogFragment {
    String header; 
    String body;
    public void setValue(String header, String body) {   
          this.header = header;
          this.body = body;
    }
    // use above variable into your dialog fragment
}

Nota: - Questo non è il modo migliore per farlo

Metodo 2:

// Fragment or Activity 
@Override
public void onClick(View v) {
     DialogFragmentWithSetter dialog = new DialogFragmentWithSetter();
     
     Bundle bundle = new Bundle();
     bundle.putString("header", "Header");
     bundle.putString("body", "Body");  
     dialog.setArguments(bundle);
     dialog.show(getSupportFragmentManager(), "DialogFragmentWithSetter");         
}


//  your dialog fragment
public class MyDialogFragment extends DialogFragment {
    String header; 
    String body;
    
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        if (getArguments() != null) {
             header = getArguments().getString("header","");
             body = getArguments().getString("body","");
        }
    }
    // use above variable into your dialog fragment
}

Nota: - Questo è il modo migliore per farlo.


Puoi persino utilizzare la libreria Gson per passare oggetti o ArrayList <Objects> come stringhe nel bundle.
Jeffrey

@duggu, perché getter e setter non sono il modo migliore per farlo?
sky91

5

come modo generale di lavorare con i frammenti, come notato da JafarKhQ, non dovresti passare i parametri nel costruttore ma con un file Bundle.

il metodo integrato per quello nella Fragmentclasse è setArguments(Bundle)e getArguments().

in pratica, quello che fai è impostare un pacchetto con tutti i tuoi Parcelablearticoli e inviarli.
a sua volta, il tuo frammento riceverà quegli oggetti onCreatee farà loro la magia.

il modo mostrato nel DialogFragmentcollegamento era un modo per farlo in un frammento che appare più volte con un tipo specifico di dati e funziona bene la maggior parte del tempo, ma puoi anche farlo manualmente.


0

Nel mio caso, nessuno dei codici sopra con bundle-operatefunziona; Ecco la mia decisione (non so se sia un codice corretto o meno, ma funziona nel mio caso):

public class DialogMessageType extends DialogFragment {
    private static String bodyText;

    public static DialogMessageType addSomeString(String temp){
        DialogMessageType f = new DialogMessageType();
        bodyText = temp;
        return f;
    };

    @Override
    public Dialog onCreateDialog(Bundle savedInstanceState) {
        final String[] choiseArray = {"sms", "email"};
        String title = "Send text via:";
        final AlertDialog.Builder builder = new AlertDialog.Builder(getActivity());
        builder.setTitle(title).setItems(choiseArray, itemClickListener);
        builder.setCancelable(true);
        return builder.create();
    }

    DialogInterface.OnClickListener itemClickListener = new DialogInterface.OnClickListener() {
        @Override
        public void onClick(DialogInterface dialog, int which) {
            switch (which){
                case 0:
                    prepareToSendCoordsViaSMS(bodyText);
                    dialog.dismiss();
                    break;
                case 1:
                    prepareToSendCoordsViaEmail(bodyText);
                    dialog.dismiss();
                    break;
                default:
                    break;
            }
        }
    };
[...]
}

public class SendObjectActivity extends FragmentActivity {
[...]

DialogMessageType dialogMessageType = DialogMessageType.addSomeString(stringToSend);
dialogMessageType.show(getSupportFragmentManager(),"dialogMessageType");

[...]
}

1) Memorizzando staticamente il bodyText, si rende effettivamente impossibile avere due istanze di questa classe contemporaneamente, con body text differenti. Non c'è motivo di non memorizzarlo invece come variabile di istanza. 2) L'intero scopo dell'invio di argomenti utilizzando setArguments (Bundle) è che il sistema operativo può quindi ricreare il frammento nel caso in cui venga perso in una situazione di memoria insufficiente ecc. Con la tua soluzione il frammento verrà ricreato e il corpo del testo verrà essere qualunque sia l'ultima istanza della finestra di dialogo utilizzata (poiché è statica). La soluzione corretta è impostare il corpo del testo come parametro bundle.
JHH

0

Solo che voglio mostrare come fare ciò che ha detto @JafarKhQ in Kotlin per coloro che usano kotlin che potrebbe aiutarli e risparmiare tempo sul tema:

quindi devi creare un oggetto companion per creare una nuova funzione newInstance

puoi impostare il parametro della funzione come preferisci. utilizzando

 val args = Bundle()

puoi impostare i tuoi argomenti.

Ora puoi usare args.putSomthingper aggiungere gli argomenti che fornisci come prameter nella tua funzione newInstance. putString(key:String,str:String)per aggiungere una stringa ad esempio e così via

Ora per ottenere l'argomento puoi usare arguments.getSomthing(Key:String)=> likearguments.getString("1")

ecco un esempio completo

class IntervModifFragment : DialogFragment(), ModContract.View
{
    companion object {
        fun newInstance(  plom:String,type:String,position: Int):IntervModifFragment {
            val fragment =IntervModifFragment()
            val args = Bundle()
            args.putString( "1",plom)
            args.putString("2",type)
            args.putInt("3",position)
            fragment.arguments = args
            return fragment
        }
    }

...
    override fun onViewCreated(view: View?, savedInstanceState: Bundle?) {
        super.onViewCreated(view, savedInstanceState)
        fillSpinerPlom(view,arguments.getString("1"))
         fillSpinerType(view, arguments.getString("2"))
        confirmer_virme.setOnClickListener({on_confirmClick( arguments.getInt("3"))})


        val dateSetListener = object : DatePickerDialog.OnDateSetListener {
            override fun onDateSet(view: DatePicker, year: Int, monthOfYear: Int,
                                   dayOfMonth: Int) {
                val datep= DateT(year,monthOfYear,dayOfMonth)
                updateDateInView(datep.date)
            }
        }

    }
  ...
}

Ora come creare il tuo dialogo puoi fare qualcosa di simile in un'altra classe

  val dialog = IntervModifFragment.newInstance(ListInter.list[position].plom,ListInter.list[position].type,position)

come questo per esempio

class InterListAdapter(private val context: Context, linkedList: LinkedList<InterItem> ) : RecyclerView.Adapter<InterListAdapter.ViewHolder>()
{
   ... 
    override fun onBindViewHolder(holder: ViewHolder, position: Int) {

        ...
        holder.btn_update!!.setOnClickListener {
           val dialog = IntervModifFragment.newInstance(ListInter.list[position].plom,ListInter.list[position].type,position)
           val ft = (context as AppCompatActivity).supportFragmentManager.beginTransaction()
            dialog.show(ft, ContentValues.TAG)
        }
        ...
    }
..

}
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.