How can I transfer data from one fragment to another fragment android

前端 未结 5 1427
梦如初夏
梦如初夏 2020-12-16 23:41

One way I know that is through activity.We can send data from fragment to activity and activity to fragment Is there any other way.

5条回答
  •  我在风中等你
    2020-12-17 00:12

    There are two methods I'd consider viable:

    A.Communicate with your owning activity and forward messages to other fragments via that owning activity, details on that can be found int he official android documentation here:

    http://developer.android.com/guide/components/fragments.html#CommunicatingWithActivity

    Quote:

    In some cases, you might need a fragment to share events with the activity. A good way to do that is to define a callback interface inside the fragment and require that the host activity implement it. When the activity receives a callback through the interface, it can share the information with other fragments in the layout as necessary.

    The Communication interface could look something like this:

    public interface IActionListener{
    
      //You can also add parameters to pass along etc
      public void doSomething();
    }
    

    The fragment would look something like this:

    public class MyFragment extends Fragment{
    
    private WeakReference actionCallback;
    
        @Override
        public void onAttach(Activity activity) {
            super.onAttach(activity);
            try {
                // This makes sure that the container activity has implemented
                // the callback interface. If not, it throws an exception
                actionCallback = new WeakReference((IActionListener) activity);
            } catch (ClassCastException e) {
                throw new ClassCastException(activity.toString() + " must implement IActionListener.");
            }
        }
    }
    

    I am using a WeakReference here but that's really up to you. You can now use actionCallback to communicate with the owning activity and call the methods defined in IActionListener.

    The owning Activity would look like this:

    public class MyActivity extends ActionBarActivity implements IActionListener {
    
    public void doSomething(){ //Here you can forward information to other fragments }
    
    }
    

    B. Now as for the second method - you can have fragments directly communicate with each other using interfaces as well - this way you don't have to know the exact class of the fragment you are talking to, which ensures loose coupling.

    The setup is as follows: You have two fragments (or more) and an activity (to start the second fragment). We have an interface that lets Fragment 2 send a response to Fragment 1 once it has completed it's task. For the sake of simplicity we just re-use the interface I defined in A.

    Here is our Fragment 1 :

    public class FragmentOne extends Fragment implements IActionListener {
    
     public void doSomething() {//The response from Fragment 2 will be processed here}
    
    }
    

    Using the method described in A. Fragment 1 asks it's owning Activity to start Fragment 2. However, the Activity will pass along Fragment 1 as an argument to Fragment 2, so Fragment 2 can later indirectly access Fragment 1 and send the reply. Let's look at how the Activity preps Fragment 2:

        public class MyActivity extends ActionBarActivity {
    
        // The number is pretty random, we just need a request code to identify our request later
        public final int REQUEST_CODE = 10;
        //We use this to identify a fragment by tag
        public final String FRAGMENT_TAG = "MyFragmentTag";
    
            @Override
            public void onStartFragmentTwo() {
                FragmentManager manager = getSupportFragmentManager();
                FragmentTransaction transaction = manager.beginTransaction();
    
                        // The requesting fragment (you must have originally added Fragment 1 using 
                        //this Tag !)
                Fragment requester = manager.findFragmentByTag(FRAGMENT_TAG);   
                        // Prepare the target fragment
                Fragment target = new FragmentTwo();
                        //Here we set the Fragment 1 as the target fragment of Fragment 2's       
                        //communication endeavors
                target.getSelf().setTargetFragment(requester, REQUEST_CODE);
    
                        // Hide the requesting fragment, so we can go fullscreen on the target
                transaction.hide(requester);
                transaction.add(R.id.fragment_container, target.getSelf(), FRAGMENT_TAG);
                transaction.addToBackStack(null);
    
                transaction.commit();
            }
        }
    

    Hint: I am using the Support-Framework, so if you develop solely for > Android 3.0 you can simply use FragmentActivity instead of ActionBarActivity.

    Now FragmentTwo is being started, let's look at how FragmentTwo would communicate with FragmentOne:

    public class FragmentTwo extends Fragment {
        @Override
        public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
            if(savedInstanceState != null){
                // Restore our target fragment that we previously saved in onSaveInstanceState
                setTargetFragment(getActivity().getSupportFragmentManager().getFragment(savedInstanceState, TAG),
                        MyActivity.REQUEST_CODE);           
            }
    
            return super.onCreateView(inflater, container, savedInstanceState);
        }
    
        @Override
        public void onSaveInstanceState(Bundle outState) {
            super.onSaveInstanceState(outState);
            // Retain our callback fragment, the TAG is just a key by which we later access the fragment
            getActivity().getSupportFragmentManager().putFragment(outState, TAG, getTargetFragment());
        }
    
        public void onSave(){
            //This gets called, when the fragment has done all its work and is ready to send the reply to Fragment 1
            IActionListener callback = (IActionListener) getTargetFragment();
            callback.doSomething();
        }
    
    }
    

    Now the implementation of doSomething() in Fragment 1 will be called.

提交回复
热议问题