FragmentのFragments間の通信(3)


  • これらの多重化可能なFragmentsを定義すると、Activityと関連付けることができ、アプリケーションの論理と関連付けることで総合的なUIを実現することができます.
  • ユーザーの行動に応じてコンテンツを変更するなど、Fragmentが他のFragmentと通信できることを望んでいる可能性があります.すべてのFragment間の通信は、それに関連付けられたActivityによって行われる.2つのFragmentの間では、直接通信することはありません.

  • インタフェースの定義

  • FragmentとActivityが通信できるようにする.Fragmentクラスでインタフェースを定義し、Activityで実装できます.Fragmentは、onAttach()中にインタフェースの実装を取得します.その後、インタフェースのメソッドを呼び出してActivityと通信します.次にFragmentとActivity通信の例:
  • public class HeadlinesFragment extends ListFragment { 
        OnHeadlineSelectedListener mCallback;
    
        // Container Activity must implement this interface 
        public interface OnHeadlineSelectedListener { 
            public void onArticleSelected(int position);
        } 
    
        @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 = (OnHeadlineSelectedListener) activity;
            } catch (ClassCastException e) {
                throw new ClassCastException(activity.toString()
                        + " must implement OnHeadlineSelectedListener"); 
            } 
        } 
    
        ... 
    } 

    fragmentは、mCallbackインスタンスのonArticleSelected()関数(またはインタフェース内の他の方法)を介してactivityに情報を伝達することができるようになった.たとえば、ユーザーがリスト項目をクリックすると、以下のfragmentのメソッドが呼び出されます.fragmentはcallbackインタフェースを介してイベントをactivityに渡す
    @Override 
        public void onListItemClick(ListView l, View v, int position, long id) {
            // Send the event to the host activity 
            mCallback.onArticleSelected(position);
        } 

    実装インタフェース


    fragmentのイベントコールバックを受信できるように、fragmentを持つactivityは、fragmentクラスに定義されたインタフェース、例えば、以下のactivityが上記のインスタンスを実装するインタフェースを実装する必要がある.
    public static class MainActivity extends Activity implements HeadlinesFragment.OnHeadlineSelectedListener{ 
        ... 
    
        public void onArticleSelected(int position) {
            // The user selected the headline of an article from the HeadlinesFragment 
            // Do something here to display that article 
        } 
    } 

    fragmentへのメッセージの転送

  • プライマリactivityは、findFragmentById()関数によってFragmentインスタンスを取得することによってfragmentにメッセージを伝達することを想定し、上記のactivityは、コールバック関数が返す特定のデータを示す別のfragmentを含む可能性がある.この場合、activityは、コールバック関数から受信した情報を、示すための別のfragment:
  • に伝えることができる.
    public static class MainActivity extends Activity implements HeadlinesFragment.OnHeadlineSelectedListener{ 
        ... 
    
        public void onArticleSelected(int position) {
            // The user selected the headline of an article from the HeadlinesFragment 
            // Do something here to display that article 
    
            ArticleFragment articleFrag = (ArticleFragment)
                    getSupportFragmentManager().findFragmentById(R.id.article_fragment);
    
            if (articleFrag != null) {
                // If article frag is available, we're in two-pane layout... 
    
                // Call a method in the ArticleFragment to update its content 
                articleFrag.updateArticleView(position);
            } else { 
                // Otherwise, we're in the one-pane layout and must swap frags... 
    
                // Create fragment and give it an argument for the selected article 
                ArticleFragment newFragment = new ArticleFragment();
                Bundle args = new Bundle();
                args.putInt(ArticleFragment.ARG_POSITION, position);
                newFragment.setArguments(args);
    
                FragmentTransaction transaction = getSupportFragmentManager().beginTransaction(); 
    
                // Replace whatever is in the fragment_container view with this fragment, 
                // and add the transaction to the back stack so the user can navigate back 
                transaction.replace(R.id.fragment_container, newFragment);
                transaction.addToBackStack(null); 
    
                // Commit the transaction 
                transaction.commit(); 
            } 
        } 
    }