Como passar valores entre fragmentos

109

Eu sou muito novo no uso de Fragments.

Estou apenas tentando construir um aplicativo de amostra simples que usa Fragments. Meu cenário é, tenho duas atividades com um fragmento dentro de cada atividade. O primeiro fragmento possui um texto de edição e um botão. O segundo fragmento tem um textview. Quando eu insiro um nome no texto de edição e clico no botão, a visualização de texto no segundo fragmento deve exibir o nome inserido no texto de edição do primeiro fragmento.

Consegui enviar o valor do primeiro fragmento para sua atividade e, em seguida, dessa atividade para a segunda atividade. Agora, como faço para usar esse valor dentro do segundo fragmento.

Aqui está o código Java :::

package com.example.fragmentexample;

import android.app.Activity;
import android.app.Fragment;
import android.app.FragmentManager;
import android.content.Intent;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.ViewGroup;
import android.widget.Button;
import android.widget.EditText;
import android.widget.Toast;

public class Fragment_1 extends Fragment{

    OnFragmentChangedListener mCallback;

    // Container Activity must implement this interface
    public interface OnFragmentChangedListener {
        public void onButtonClicked(String name);
    }

    @Override
    public void onAttach(Activity activity) {
        super.onAttach(activity);

        // This makes sure that the container activity has implemented
        // the callback interface. If not, it throws an exception
        try {
            mCallback = (OnFragmentChangedListener) activity;
        } catch (ClassCastException e) {
            throw new ClassCastException(activity.toString()
                    + " must implement OnHeadlineSelectedListener");
        }
    }


    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
            Bundle savedInstanceState) {
        // TODO Auto-generated method stub      

        View view = inflater.inflate(R.layout.fragment_fragment_1, container, false);

        final EditText edtxtPersonName_Fragment = (EditText) view.findViewById(R.id.edtxtPersonName);
        Button btnSayHi_Fragment = (Button) view.findViewById(R.id.btnSayHi);

        btnSayHi_Fragment.setOnClickListener(new OnClickListener() {

            @Override
            public void onClick(View v) {
                // TODO Auto-generated method stub

                String name = edtxtPersonName_Fragment.getText().toString();

                FragmentManager fm = getFragmentManager();
                Fragment_2 f2 = (Fragment_2) fm.findFragmentById(R.id.fragment_content_2);

                Activity activity = getActivity();

                if(activity != null)
                {
                    Toast.makeText(activity, "Say&ing Hi in Progress...", Toast.LENGTH_LONG).show();
                }


                if(f2 != null && f2.isInLayout())
                {
                    f2.setName(name);
                }
                else
                {
                    mCallback.onButtonClicked(name);
                }
            }
        });

        return view;


    }

}

MainActivity.Java

package com.example.fragmentexample;

import android.os.Bundle;
import android.app.Activity;
import android.content.Intent;

import android.view.Choreographer.FrameCallback;
import android.view.Menu;

public class MainActivity extends Activity implements Fragment_1.OnFragmentChangedListener {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);     
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        getMenuInflater().inflate(R.menu.activity_main, menu);
        return true;
    }

    @Override
    public void onButtonClicked(String name) {
        // TODO Auto-generated method stub

        Intent i = new Intent(this, SecondActivity.class);
        i.putExtra("", name);
        startActivity(i);
    }

}

SecondActivity.Java

package com.example.fragmentexample;

import android.app.Activity;
import android.os.Bundle;

public class SecondActivity extends Activity{

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        // TODO Auto-generated method stub
        super.onCreate(savedInstanceState);

        setContentView(R.layout.activity_second);

        Bundle b = getIntent().getExtras();

        Fragment_2 f2 = new Fragment_2();
        f2.setArguments(b);
    }
}

Fragment_2.Java

package com.example.fragmentexample;

import android.app.Activity;
import android.app.Fragment;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.TextView;

public class Fragment_2 extends Fragment{

    View view;
    TextView txtName;


    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
            Bundle savedInstanceState) {
        // TODO Auto-generated method stub

        view = inflater.inflate(R.layout.fragment_fragment_2, container, false);

            // Exception at this line
        String name = getArguments().getString("message");
        txtName = (TextView) view.findViewById(R.id.txtViewResult);
        txtName.setText(name);

        return view;
    }

    @Override
    public void onAttach(Activity activity) {
        // TODO Auto-generated method stub
        super.onAttach(activity);       
    }

    public void setName(String name)
    {   
        txtName.setText("Hi " + name);
    }

}

Eu recebo a seguinte exceção :::

04-16 18:10:24.573: E/AndroidRuntime(713): FATAL EXCEPTION: main
04-16 18:10:24.573: E/AndroidRuntime(713): java.lang.RuntimeException: Unable to start activity ComponentInfo{com.example.fragmentexample/com.example.fragmentexample.SecondActivity}: android.view.InflateException: Binary XML file line #8: Error inflating class fragment
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:1815)
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:1831)
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.app.ActivityThread.access$500(ActivityThread.java:122)
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1024)
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.os.Handler.dispatchMessage(Handler.java:99)
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.os.Looper.loop(Looper.java:132)
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.app.ActivityThread.main(ActivityThread.java:4123)
04-16 18:10:24.573: E/AndroidRuntime(713):  at java.lang.reflect.Method.invokeNative(Native Method)
04-16 18:10:24.573: E/AndroidRuntime(713):  at java.lang.reflect.Method.invoke(Method.java:491)
04-16 18:10:24.573: E/AndroidRuntime(713):  at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:841)
04-16 18:10:24.573: E/AndroidRuntime(713):  at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:599)
04-16 18:10:24.573: E/AndroidRuntime(713):  at dalvik.system.NativeStart.main(Native Method)
04-16 18:10:24.573: E/AndroidRuntime(713): Caused by: android.view.InflateException: Binary XML file line #8: Error inflating class fragment
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:688)
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.view.LayoutInflater.rInflate(LayoutInflater.java:724)
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.view.LayoutInflater.inflate(LayoutInflater.java:479)
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.view.LayoutInflater.inflate(LayoutInflater.java:391)
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.view.LayoutInflater.inflate(LayoutInflater.java:347)
04-16 18:10:24.573: E/AndroidRuntime(713):  at com.android.internal.policy.impl.PhoneWindow.setContentView(PhoneWindow.java:223)
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.app.Activity.setContentView(Activity.java:1786)
04-16 18:10:24.573: E/AndroidRuntime(713):  at com.example.fragmentexample.SecondActivity.onCreate(SecondActivity.java:13)
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.app.Activity.performCreate(Activity.java:4397)
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1048)
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:1779)
04-16 18:10:24.573: E/AndroidRuntime(713):  ... 11 more
04-16 18:10:24.573: E/AndroidRuntime(713): Caused by: java.lang.NullPointerException
04-16 18:10:24.573: E/AndroidRuntime(713):  at com.example.fragmentexample.Fragment_2.onCreateView(Fragment_2.java:24)
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.app.FragmentManagerImpl.moveToState(FragmentManager.java:754)
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.app.FragmentManagerImpl.moveToState(FragmentManager.java:956)
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.app.FragmentManagerImpl.addFragment(FragmentManager.java:1035)
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.app.Activity.onCreateView(Activity.java:4177)
04-16 18:10:24.573: E/AndroidRuntime(713):  at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:664)
04-16 18:10:24.573: E/AndroidRuntime(713):  ... 21 more

Como obtenho o valor do pacote em SecondActivity.java para Fragment_2.Java?

Vamsi Challa
fonte
Destaque a parte em que está tendo o problema
Nikhil Agrawal
solução de trabalho de maneira fácil: stackoverflow.com/a/59332751/10201722
Adil Siddiqui

Respostas:

203

etapa 1. para enviar dados do fragmento para a atividade

Intent intent = new Intent(getActivity().getBaseContext(),
                        TargetActivity.class);
                intent.putExtra("message", message);
                getActivity().startActivity(intent);

etapa 2. para receber esses dados na atividade:

Intent intent = getIntent();
String message = intent.getStringExtra("message");

passo 3 . para enviar dados de uma atividade para outra, siga a abordagem normal

Intent intent = new Intent(MainActivity.this,
                        TargetActivity.class);
                intent.putExtra("message", message);
                startActivity(intent);

etapa 4 para receber esses dados em atividade

     Intent intent = getIntent();
  String message = intent.getStringExtra("message");

Etapa 5. Na atividade, você pode enviar dados para o Fragment com a intenção de:

Bundle bundle=new Bundle();
bundle.putString("message", "From Activity");
  //set Fragmentclass Arguments
Fragmentclass fragobj=new Fragmentclass();
fragobj.setArguments(bundle);

e para receber em fragmento no método Fragment onCreateView:

@Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
    Bundle savedInstanceState) {
          String strtext=getArguments().getString("message");

    return inflater.inflate(R.layout.fragment, container, false);
    }
Shiv
fonte
2
Tentei a etapa 5, Estou chamando de listactivity do fragmento e, após selecionar o item dessa atividade, quero voltar no fragmento com o nome do arquivo selecionado. Mas não está funcionando, está me dando Nullpointer Exception em onCreateView. Alguma solução para isso, por favor? Esta é a minha pergunta stackoverflow.com/questions/18208771/…
OnkarDhane
como faço para colocar um POJO aqui? bundle.putString("message", "From Activity");
jeet.chanchawat
31
Alguém está enojado com o quão complicado fazer algo assim é
Ed Lee
1
Exatamente Eddie, esse não é o caminho correto. Eles devem usar interfaces para se comunicar entre fragmentos por meio da atividade do contêiner.
Kaveesh Kanwal,
Em relação ao uso de interfaces para comunicação entre fragmentos: developer.android.com/training/basics/fragments/…
Andre L Torres
49

Conforme observado no site do desenvolvedor

Freqüentemente, você desejará que um fragmento se comunique com outro, por exemplo, para alterar o conteúdo com base em um evento do usuário. Toda a comunicação fragmento a fragmento é feita por meio da atividade associada. Dois fragmentos nunca devem se comunicar diretamente.

a comunicação entre fragmentos deve ser feita por meio da atividade associada.

Vamos ter os seguintes componentes:

Uma atividade hospeda fragmentos e permite a comunicação de fragmentos

Fragmento Um primeiro fragmento que enviará dados

FragmentB segundo fragmento que receberá dados do FragmentA

A implementação do FragmentA é:

public class FragmentA extends Fragment 
{
    DataPassListener mCallback;
    
    public interface DataPassListener{
        public void passData(String data);
    }

    @Override
    public void onAttach(Context context) 
    {
        super.onAttach(context);
        // This makes sure that the host activity has implemented the callback interface
        // If not, it throws an exception
        try 
        {
            mCallback = (OnImageClickListener) context;
        }
        catch (ClassCastException e) 
        {
            throw new ClassCastException(context.toString()+ " must implement OnImageClickListener");
        }
    }
    
    public View onCreateView(LayoutInflater inflater, ViewGroup container,Bundle savedInstanceState) 
    {
        // Suppose that when a button clicked second FragmentB will be inflated
        // some data on FragmentA will pass FragmentB
        // Button passDataButton = (Button).........
        
        passDataButton.setOnClickListener(new OnClickListener() {
            @Override
            public void onClick(View v) {
                if (view.getId() == R.id.passDataButton) {
                    mCallback.passData("Text to pass FragmentB");
                }
            }
        });
    }
}

A implementação de MainActivity é:

public class MainActivity extends ActionBarActivity implements DataPassListener{
    
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        
        if (findViewById(R.id.container) != null) {
            if (savedInstanceState != null) {
                return;
            }
            getFragmentManager().beginTransaction()
                    .add(R.id.container, new FragmentA()).commit();
        }
    }
    
    @Override
    public void passData(String data) {
        FragmentB fragmentB = new FragmentB ();
        Bundle args = new Bundle();
        args.putString(FragmentB.DATA_RECEIVE, data);
        fragmentB .setArguments(args);
        getFragmentManager().beginTransaction()
            .replace(R.id.container, fragmentB )
            .commit();
    }
}

A implementação do FragmentB é:

public class FragmentB extends Fragment{
    final static String DATA_RECEIVE = "data_receive";
    TextView showReceivedData;
    
    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
            Bundle savedInstanceState) {
        View view = inflater.inflate(R.layout.fragment_B, container, false);
        showReceivedData = (TextView) view.findViewById(R.id.showReceivedData);
    }
    
    @Override
    public void onStart() {
        super.onStart();
        Bundle args = getArguments();
        if (args != null) {
            showReceivedData.setText(args.getString(DATA_RECEIVE));
        }
    }
}

Espero que isso ajude..

Ozhanli
fonte
4
O que é OnImageClickListener aqui? e como ele é convertido em uma variável DataPassListener?
Harsha
Descobri que é o "DataPassListener". Consegui fazer funcionar, mas só para descobrir devido a cada vez que o botão é clicado os dados são enviados. Quando é enviado, ele substitui o fragmento. O que significa que a lista é renovada todas as vezes. Portanto, não mantendo a lista de itens na memória.
wesley franks
44

// Em Fragment_1.java

Bundle bundle = new Bundle();
bundle.putString("key","abc"); // Put anything what you want

Fragment_2 fragment2 = new Fragment_2();
fragment2.setArguments(bundle);

getFragmentManager()
      .beginTransaction()
      .replace(R.id.content, fragment2)
      .commit();

// Em Fragment_2.java

Bundle bundle = this.getArguments();

if(bundle != null){
     // handle your code here.
}

Espero que isso ajude você.

nguyencse
fonte
1
Resposta clara para mostrar o ponto principal. usando putString(ou putInt) é a resposta!
Mehdi Dehghani
22

Do site dos desenvolvedores :

Freqüentemente, você desejará que um fragmento se comunique com outro, por exemplo, para alterar o conteúdo com base em um evento do usuário. Toda a comunicação fragmento a fragmento é feita por meio da atividade associada. Dois fragmentos nunca devem se comunicar diretamente.

Você pode se comunicar entre fragmentos com a ajuda de sua atividade. Você pode se comunicar entre a atividade e o fragmento usando esta abordagem.

Por favor, verifique este link também.

Jainendra
fonte
O segundo link que você forneceu mostra como se comunicar entre fragmentos quando eles estão na mesma atividade. Como faço para me comunicar quando ambos estão em atividades diferentes?
Vamsi Challa
5

Em primeiro lugar, todas as respostas estão corretas, você pode passar os dados, exceto objetos personalizados usando Intent. Se você deseja passar os objetos personalizados, você deve implementar Serialazableou Parcelablepara sua classe de objeto personalizado. Achei muito complicado ...

Portanto, se seu projeto é simples, tente usar DataCache. Isso fornece uma maneira super simples de passar dados. Ref: CachePot do projeto Github

1- Defina como Exibir ou Atividade ou Fragmento que enviará dados

DataCache.getInstance().push(obj);

2- Obtenha dados em qualquer lugar como abaixo

public class MainFragment extends Fragment
{
    private YourObject obj;

    @Override
    public void onCreate(Bundle savedInstanceState)
    {
        super.onCreate(savedInstanceState);

        obj = DataCache.getInstance().pop(YourObject.class);

    }//end onCreate()
}//end class MainFragment
Kimkevin
fonte
Não seria mais fácil usar uma classe extra com valores estáticos dentro? Esses valores podem ser acessados ​​por ambos os fragmentos, portanto, não há necessidade de usar uma biblioteca extra para armazenar objetos personalizados em cache.
Neph
4

A solução mais recente para a passagem de dados entre fragmentos pode ser implementada usando componentes de arquitetura Android, como ViewModel e LiveData. Com esta solução, você não precisa definir a interface para comunicação e pode obter as vantagens de usar viewmodel como sobrevivência de dados devido a alterações de configuração.

Nesta solução, os fragmentos envolvidos na comunicação compartilham o mesmo objeto viewmodel que está vinculado ao seu ciclo de vida de atividade. O objeto do modelo de visualização contém o objeto liveata. Um fragmento define os dados a serem transmitidos ao objeto liveata e os observadores do segundo fragmento mudam e recebem os dados.

Aqui está o exemplo completo http://www.zoftino.com/passing-data-between-android-fragments-using-viewmodel

Arnav Rao
fonte
3

Passando argumentos entre fragmentos. É um pouco tarde para responder a esta pergunta, mas pode ajudar alguém! Fragment_1.java

Bundle i = new Bundle(); 
            i.putString("name", "Emmanuel");

            Fragment_1 frag = new Fragment_1();
            frag.setArguments(i);
            FragmentManager fragmentManager = getFragmentManager();
            fragmentManager.beginTransaction()
                    .replace(R.id.content_frame
                            , new Fragment_2())
                    .commit();

Então em seu Fragment_2.javavocê pode obter os paramaters normalmente dentro de seu onActivityCreated ex

 Intent intent = getActivity().getIntent();
    if (intent.getExtras() != null) {
        String name =intent.getStringExtra("name");
    }
Emmanuel R
fonte
3

Acho que uma boa maneira de resolver esse problema é usar uma interface personalizada.

Digamos que você tenha dois fragmentos (A e B) que estão dentro da mesma atividade e você deseja enviar dados de A para B.

Interface:

public interface OnDataSentListener{
    void onDataSent(Object data);
}

Atividade:

    public class MyActivity extends AppCompatActivity{

            private OnDataSentListener onDataSentListener;

            @Override
            protected void onCreate(Bundle savedInstanceState) {
                super.onCreate(savedInstanceState);
                setContentView(R.layout.activity_activity);

                FragmentTransaction trans = getFragmentManager().beginTransaction();

                FragmentA fa = new FragmentA();
                FragmentB fb = new FragmentB();

               fa.setOnDataSentListener(new Listeners.OnDataSentListener() {
                    @Override
                    public void onDataSent(Object data) {
                         if(onDataSentListener != null)  onDataSentListener.onDataSent(data);
                    }
               });

                transaction.add(R.id.frame_a, fa);
                transaction.add(R.id.frame_b, fb);

                transaction.commit();
            }

            public void setOnDataSentListener(OnDataSentListener listener){
                this.onDataSentListener = listener;
            }
        }

Fragmento A:

public class FragmentA extends Fragment{

    private OnDataSentListener onDataSentListener;

    private void sendDataToFragmentB(Object data){
        if(onDataSentListener != null) onDataSentListener.onDataSent(data);
    }

    public void setOnDataSentListener(OnDataSentListener listener){
        this.onDataSentListener = listener;
    }
}

Fragmento B:

public class FragmentB extends Fragment{

    private void initReceiver(){
        ((MyActivity) getActivity()).setOnDataSentListener(new OnDataSentListener() {
            @Override
            public void onDataSent(Object data) {
                //Here you receive the data from fragment A
            }
        });
    }
}
simpleApps
fonte
2

A comunicação entre fragmentos é bastante complicada (acho o conceito de ouvintes um pouco desafiador de implementar).

É comum usar um 'Event Bus "para abstrair essas comunicações. Esta é uma biblioteca de terceiros que cuida dessa comunicação para você.

'Otto' é aquele que é usado frequentemente para fazer isso e pode valer a pena dar uma olhada em: http://square.github.io/otto/

Booger
fonte
2

Passando dados de Fragment para outro Fragment

  • Do primeiro fragmento

    // Set data to pass
    MyFragment fragment = new MyFragment(); //Your Fragment
    Bundle bundle = new Bundle();
    bundle.putInt("year", 2017)  // Key, value
    fragment.setArguments(bundle); 
    // Pass data to other Fragment
    getFragmentManager()
     .beginTransaction()
     .replace(R.id.content, fragment)
     .commit(); 
  • No Segundo Fragmento

    @Override
    public void onCreate(@Nullable Bundle savedInstanceState) {
         super.onCreate(savedInstanceState);
    
         Bundle bundle = this.getArguments();
         if (bundle != null) {
             Int receivedYear = bundle.getInt("year", ""); // Key, default value
         } 
    }
Espírito de Solução
fonte
1

Essa implementação simples ajuda a passar dados entre fragmentos de uma maneira simples. Acha que deseja passar dados de 'Frgment1' para 'Fragment2'

Em Fragment1 (definir dados para enviar)

 Bundle bundle = new Bundle();
 bundle.putString("key","Jhon Doe"); // set your parameteres

 Fragment2 nextFragment = new Fragment2();
 nextFragment.setArguments(bundle);

 FragmentManager fragmentManager = getActivity().getSupportFragmentManager();
 fragmentManager.beginTransaction().replace(R.id.content_drawer, nextFragment).commit();

No método Fragment2 onCreateView (Get Parameteres)

String value = this.getArguments().getString("key");//get your parameters
Toast.makeText(getActivity(), value+" ", Toast.LENGTH_LONG).show();//show data in tost
Janaka
fonte
Em meu aplicativo, estou tentando fazer isso funcionar, mas de alguma forma, embora o valor esteja sendo passado, ele não está sendo exibido no fragmento 2, acho que estou cometendo um erro ao definir R.id.content_drawer. Alguém pode me orientar qual poderia ser o identificador correto para R.id.content_drawer com exemplo .xml.
falcon
1

Maneira Kotlin

Use uma SharedViewModelproposta na documentação oficial do ViewModel

É muito comum que dois ou mais fragmentos em uma atividade precisem se comunicar entre si. Imagine um caso comum de fragmentos de detalhes mestres, onde você tem um fragmento no qual o usuário seleciona um item de uma lista e outro fragmento que exibe o conteúdo do item selecionado. Este caso nunca é trivial, pois ambos os fragmentos precisam definir alguma descrição de interface e a atividade do proprietário deve vincular os dois. Além disso, ambos os fragmentos devem lidar com o cenário em que o outro fragmento ainda não foi criado ou visível.

Esse ponto comum pode ser resolvido usando objetos ViewModel. Esses fragmentos podem compartilhar um ViewModel usando seu escopo de atividade para lidar com essa comunicação

Primeiro implemente o fragment-ktx para instanciar seu modelo de visão mais facilmente

dependencies {
    implementation "androidx.fragment:fragment-ktx:1.2.2"
} 

Então, você só precisa colocar dentro do viewmodel os dados que você irá compartilhar com o outro fragmento

class SharedViewModel : ViewModel() {
    val selected = MutableLiveData<Item>()

    fun select(item: Item) {
        selected.value = item
    }
}

Então, para terminar, apenas instancie seu viewModel em cada fragmento e defina o valor de selecteddo fragmento que você deseja definir os dados

Fragmento A

class MasterFragment : Fragment() {

    private val model: SharedViewModel by activityViewModels()

    override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
        super.onViewCreated(view, savedInstanceState)
        itemSelector.setOnClickListener { item ->
        model.select(item)
      }

    }
}

E então, apenas ouça esse valor no destino do Fragment

Fragmento B

 class DetailFragment : Fragment() {

        private val model: SharedViewModel by activityViewModels()

        override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
            super.onViewCreated(view, savedInstanceState)
            model.selected.observe(viewLifecycleOwner, Observer<Item> { item ->
                // Update the UI
            })
        }
    }

Você também pode fazer isso da maneira oposta

Gastón Saillén
fonte
0

Solução de trabalho 100%: (se ajudar você, não se esqueça de acertar o voto positivo)

Em seu primeiro fragmento, coloque este trecho de código:

    editprofile.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {

                    Fragment_editprofile Fragment = new Fragment_editprofile();
.
.
.
.
.


                Fragment.getintentdetails(tv_name.getText().toString(),
                            tv_mob.getText().toString(), tv_email.getText().toString(), tv_dob.getText().toString(),
                            tv_gender.getText().toString(), photointent);

                }
            });

No segundo fragmento, faça o método como abaixo:

public void getintentdetails(String name, String mobile, String email, String dob, String gender,
                                 String photointent) {

        this.name_str= name;
        this.mob_str= mobile;
        this.email_str= email;
        this.dob_str= dob;
        this.gender_str= gender;
        this.photo_str= photointent;

    }

em seguida, defina uma variável no nível da classe:

String name_str, mob_str, dob_str, photo_str, email_str, gender_str;

em seguida, faça outro método no segundo fragmento para definir o valor:

  setexistingdetails();


private void setexistingdetails() {

        if(!name_str.equalsIgnoreCase(""))
            (et_name).setText(name_str);
        if(!mob_str.equalsIgnoreCase(""))
            et_mobile.setText(mob_str);
        if(!email_str.equalsIgnoreCase(""))
            email_et.setText(email_str);
        if(!dob_str.equalsIgnoreCase(""))
            dob_et.setText(dob_str);
        if(!gender_str.equalsIgnoreCase("")){
            if (gender_str.equalsIgnoreCase("m")){
                male_radio.setChecked(true);
            }else {
                female_radio.setChecked(true);
            }
        }
        if(!photo_str.equalsIgnoreCase("")){
            try {
                Picasso.get().load(Const.BASE_PATH+"include/sub-domain/GENIUS/"+photo_str).into(adminpropic_edit);
            } catch (Exception e) {            }
        }
    }
Adil Siddiqui
fonte
0

Você pode atingir seu objetivo por ViewModel e Live Data, que é liberado por Arnav Rao . Agora coloquei um exemplo para esclarecê-lo com mais clareza.

Primeiro, o presumido ViewModelé nomeado SharedViewModel.java.

public class SharedViewModel extends ViewModel {
    private final MutableLiveData<Item> selected = new MutableLiveData<Item>();

    public void select(Item item) {
        selected.setValue(item);
    }
    public LiveData<Item> getSelected() {
        return selected;
    }
}

Então, o fragmento de origem é MasterFragment.javade onde queremos enviar os dados.

public class MasterFragment extends Fragment {
    private SharedViewModel model;

    public void onViewCreated(@NonNull View view, Bundle savedInstanceState) {
        super.onViewCreated(view, savedInstanceState);
        model = new ViewModelProvider(requireActivity()).get(SharedViewModel.class);
        itemSelector.setOnClickListener(item -> {

            // Data is sent

            model.select(item);
        });
    }
}

E, finalmente, o fragmento de destino é DetailFragment.javapara onde queremos receber os dados.

public class DetailFragment extends Fragment {

    public void onViewCreated(@NonNull View view, Bundle savedInstanceState) {
        super.onViewCreated(view, savedInstanceState);
        SharedViewModel model = new ViewModelProvider(requireActivity()).get(SharedViewModel.class);
        model.getSelected().observe(getViewLifecycleOwner(), { item ->

           // Data is received 

        });
    }
}
Gk Mohammad Emon
fonte
0

OK, depois de tanto cavar aqui, encontrei uma solução simples. Na verdade, você nunca deve passar os dados de um fragmento para outro, é sempre uma má ideia, você pode passar os dados do fragmento A para a atividade e obter os dados da atividade no fragmento B.

For Example
//fragment A
//your method that will be called in Main Activity for getting data from this fragment
public List<customDataModel> getlist(){
return mlist; //your custom list 
}
buttonopen.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            //before calling  your new fragment, send a Broadcast signal to your main activity
 mContext.sendBroadcast(new Intent("call.myfragment.action"));
//here you are now changing the fragment
Fragment fragment1 = new VolunteerListDetailsFragment();

            FragmentTransaction ft = getSupportFragmentManager().beginTransaction();
            ft.replace(R.id.content_frame, fragment1);
            ft.commit();
        }
    });

// na atividade principal

this.registerReceiver(mBroadcastReceiver, new IntentFilter("call.myfragment.action"));//this line should be in your onCreate method
   BroadcastReceiver mBroadcastReceiver = new BroadcastReceiver() {

    @Override
    public void onReceive(Context context, Intent intent) {
//init the fragment A
FragmenA fragment =
                (FragmentA) getSupportFragmentManager().findFragmentById(R.id.content_frame);
        mlistdetails = fragment.getlist();//this is my method in fragmentA which is retuning me a custom list, init this list type in top of on create fragment


    }
};
//here you are creating method that is returning the list that you just recieved From fragmentA
public List<customDataModel> getcustomlist(){
return mlistdetails; //you are returning the same list that you recived from fragmentA
}

// agora em FragmentB

 public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {

    View rootView = (View) inflater.inflate(R.layout.vol_listdetails, container, false);

    mlistdetails=((MainActivity)getActivity()).getcustomlist();//here you are calling the method that you have created in Main Activity

    Toast.makeText(getActivity().getApplicationContext(), mlistdetails.get(0).getItemqty(), Toast.LENGTH_SHORT).show();
    return rootView;

}
Mubashir Murtaza
fonte
-2

fiz algo realmente fácil para iniciantes como eu .. fiz um textview no meu activity_main.xml e coloquei

id=index
visibility=invisible

então eu recebo esta visualização de texto do primeiro fragmento

index= (Textview) getActivity().findviewbyid(R.id.index)
index.setText("fill me with the value")

e então no segundo fragmento eu obtenho o valor

index= (Textview) getActivity().findviewbyid(R.id.index)
String get_the_value= index.getText().toString();

espero que ajude!

user7933515
fonte
A resposta não está relacionada à pergunta feita
Kanagalingam