3

のアクティビティと2つのフラグメントは、viewpagerを含んでいます。 これで、Googleのガイドコールバックインターフェイスを実装して、フラグメントからアクティビティに通信できます。しかし、他の方法でをアクティビティからフラグメントにどのように伝えることができますか?アクティビティ(外部イベント)で何かが発生した場合、私はフラグメントを更新したいと思います。私はアクティビティからViewPagerでのフラグメントへの通信

MyFragmentPagerAdapter a = (MyFragmentPagerAdapter) viewPager.getAdapter(); 
Frag1 frag = (Frag1) a.getItem(0); 

でFrag1フラグメントを得ることができたが、私はFRAGのパブリックメソッドを呼び出すとき、私はIllegalStateExceptionが取得:フラグメントは、おそらく活動に付着していないのgetItem(0)Frag1の新しいインスタンスを返し、これが取り付けられていないので、しかし、この全体のViewpager - > Activity to Fragment通信にクリーンなソリューションを提供できる人は誰ですか?

あなたのためのいくつかのコード:活動中

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

     ViewPager viewPager = (ViewPager) findViewById(R.id.viewpager); 
     if (viewPager != null) { 
      viewPager.setAdapter(new MyFragmentPagerAdapter(getSupportFragmentManager())); 
     } 

     TabLayout tabLayout = (TabLayout) findViewById(R.id.sliding_tabs); 
     if (tabLayout != null) { 
      tabLayout.setupWithViewPager(viewPager); 
     } 
} 

アクティビティのレイアウト:

<?xml version="1.0" encoding="utf-8"?> 
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" 
    xmlns:tools="http://schemas.android.com/tools" 
    android:layout_width="match_parent" 
    android:layout_height="match_parent" 
    xmlns:app="http://schemas.android.com/apk/res-auto" 
    android:orientation="vertical" 
    tools:context="com.MainActivity"> 

    <android.support.design.widget.TabLayout 
     android:id="@+id/sliding_tabs" 
     android:layout_width="match_parent" 
     android:layout_height="wrap_content"/> 

    <android.support.v4.view.ViewPager 
     android:id="@+id/viewpager" 
     android:layout_width="match_parent" 
     android:layout_height="0px" 
     android:layout_weight="1"/> 
</LinearLayout> 

MyFragmentPagerAdapter:

public class MyFragmentPagerAdapter extends FragmentPagerAdapter { 

    final int PAGE_COUNT = 2; 
    private String tabTitles[] = new String[] { "tab1", "tab2" }; 

    public MyFragmentPagerAdapter(FragmentManager fm) { 
     super(fm); 
    } 

    @Override 
    public Fragment getItem(int position) { 
     switch (position) { 
      case 0: 
       return Frag1.newInstance(position + 1); 
      case 1: 
       return Frag2.newInstance(position + 1); 
      default: 
       return null; 
     } 
    } 

    @Override 
    public int getCount() { 
     return PAGE_COUNT; 
    } 

    @Override 
    public CharSequence getPageTitle(int position) { 
     return tabTitles[position]; 
    } 
} 

Frag1:

public class Frag1 extends Fragment { 
    public static final String ARG_PAGE = "ARG_PAGE"; 

    private int mPage; 

    private onFrag1InteractionListener mListener; 

    public Frag1() { 
     // Required empty public constructor 
    } 

    /** 
    * Use this factory method to create a new instance of 
    * this fragment using the provided parameters. 
    * 
    * @return A new instance of fragment Frag1. 
    */ 
    public static Frag1 newInstance(int page) { 
     Frag1 fragment = new Frag1(); 
     Bundle args = new Bundle(); 
     args.putInt(ARG_PAGE, page); 
     fragment.setArguments(args); 
     return fragment; 
    } 

    @Override 
    public void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     if (getArguments() != null) { 
      mPage = getArguments().getInt(ARG_PAGE); 
     } 
    } 

    @Override 
    public View onCreateView(LayoutInflater inflater, ViewGroup container, 
          Bundle savedInstanceState) { 
     View view = inflater.inflate(R.layout.fragment_1, container, false); 
     return view; 
    } 


    @Override 
    public void onAttach(Context context) { 
     super.onAttach(context); 
     if (context instanceof onFrag1InteractionListener) { 
      mListener = (onFrag1InteractionListener) context; 
     } else { 
      throw new RuntimeException(context.toString() 
        + " must implement onFrag1InteractionListener"); 
     } 
    } 

    @Override 
    public void onDetach() { 
     super.onDetach(); 
     mListener = null; 
    } 

    public interface onFrag1InteractionListener { 
     // TODO: Update argument type and name 
     void onFrag1Interaction(Action action); 
    } 
+0

アクティビティの代わりにAppCompatActivityを拡張して何が起きているのかを確認しますか? – Nitesh

+0

アクティビティは既に拡張されていますAppCompatActivity – Zuop

+0

外部イベントはどういう意味ですか?タブをスワイプしたときにフラグメントを更新したいとします。そのように – Nitesh

答えて

1

あなたはフラグメントが、それは望んでいるイベントのために活動して登録するいくつかのイベントリスナーのロジックを設定する必要があります。フラグメントは作成時に登録し、破棄時に登録解除する必要があります。

イベントが発生すると、アクティビティは登録されたリスナーのリストを通過し、イベントを通知します。

this answerに詳細な例を示します。

イベントバスライブラリを使用して、アクティビティとフラグメント間の配線を簡素化できます。

+0

私はあなたの答えのリンクの指示に従って、それを解決しました。 。私はそれが奇妙な部分からの通信を実装するインターフェイスを実装することを見つける - >アクティビティとさらに別のインターフェイスから通信するアクティビティ - >フラグメント – Zuop

+0

私の例は、アクティビティのインターフェイスを実装していませんでしたユニットテストと再利用。ナビゲーション・ドロワーのようなものに関するGoogleの例がたくさんあります。 –

+0

オハイオ州オハイオ州..私はあなたの答えを誤解する必要がありますが、それは今働いているnvm。 「リスナインターフェイスを定義します。私は通常、リンク内のアクティビティ内の内部インターフェイスとしてこれを行います。」 – Zuop

関連する問題