5

問題は次のとおりです。フラグメント3つのタブがあります:同じフラグメントの異なるインスタンス間で通信する

  • タブ1(フラグメントA)。タブ2にデータを送信する必要があります。
  • タブ2(フラグメントB)。タブ1からデータを受信する必要があります。
  • タブ3(フラグメントB)。すでにデータが含まれています。

タブ3とタブ2には、同じフラグメントが含まれていますが、異なるインスタンスが含まれています。

データを(引数ではなく)正確にタブ2に送信するにはどうすればよいですか?

私が試したもの:

  1. それらが作成されたときの引数を経由してフラグメントBの一意のIDを設定します。
  2. 断片B
  3. の両方のインスタンスの同じLocal Broadcast Receiver登録recevied IDがフラグメント

しかし残念ながら放送のIDと等しい場合、フラグメントB onReceive()チェックでは、そのID

  • と断片Bに断片Aからのデータを送信しますタブ3のみに送信されました。


    EDIT:いくつかのより多くの情報。

    これらのタブは、ViewPagerという別のフラグメント内にホストされています。これは、のフラグメントを有するNavigationDrawerと問題のタブとの組み合わせによるものである。

  • +0

    フラグメントAがあなたのアクティビティにデータを送信し、アクティビティでフラグメントBを送信させるのはなぜですか? –

    +0

    あなたは、データの送信に問題はないことがわかります。問題は、フラグメントBの最初のインスタンスにデータを正確に送信することです。 – AnZ

    +0

    BroadcastReceiverはあまりにも多くのメモリを必要とし、非同期プロセスであると思います。そして、解決するセキュリティ問題があります。 –

    答えて

    5

    フラグメントは1つのアクティビティでホストされていますか?次に、ホスティング活動のインターフェースを実装することができます。

    YourActivity implements MyInterface { 
    ... 
    } 
    

    そして、あなたの断片にあなたはこの定義:

    @Override 
    public void onAttach(final Activity context) { 
        myInterface = (MyInterface) context; 
    } 
    

    を、あなたのフラグメントで何かをクリックすると、その後myInterface.doSomething(parameter);を呼び出します。そしてあなたの活動は別の断片に委譲することができます。

    +0

    これは正しい方法です! – Skynet

    +0

    すぐにお返事ありがとうございます。これらのフラグメントは1つのフラグメントでホストされています(NavigationDrawerにはViewPagerとそのタブが含まれているフラグメントがあるためです)。しかし、とにかく、私はあなたのポイントを持っています。試してみよう。 – AnZ

    +0

    申し訳ありませんが、このアプローチのように見える断片の中でホストされているフラグメントのためには動作しません。私は 'OnAttach()'に 'ClassCastException'を受け取りました。質問 – AnZ

    6

    あなたのアプリにEventBusを紹介することをお勧めします。

    依存関係を追加するには、依存関係リストにcompile 'de.greenrobot:eventbus:2.4.0'を追加します。

    次に、3番目のタブのフラグメントを購読して、最初のフラグメントからイベントを聴くだけです。

    このような何か:断片Bで

    @Override 
    public void onAttach(Activity activity) { 
        super.onAttach(activity); 
        eventBus.register(this); 
    } 
    
    @Override 
    public void onDetach() { 
        eventBus.unregister(this); 
        super.onDetach(); 
    } 
    
    @SuppressWarnings("unused") // invoked by EventBus 
    public void onEventMainThread(NewDataEvent event) { 
        // Handle new data 
    } 
    

    NewDataEvent。

    public class NewDataEvent extends EventBase { 
        public NewDataEvent() {} 
    } 
    

    とフラグメントAでのJava

    はちょうどイベントを送信:

    protected EventBus eventBus; 
    .... 
    eventBus = EventBus.getDefault(); 
    .... 
    eventBus.post(new NewDataEvent()); 
    

    (および第二のタブでイベントを処理避けるために - それはを聞くために持っている場合だけ、フラグメントのインスタンス化の際に追加のパラメータを渡しますイベント)

    +0

    イベント駆動型開発ですか?それは面白いアプローチです。試してみることにしました。ありがとうございました! – AnZ

    0

    実行時にフラグメントを追加する方法は書かれていませんでした。

    ... 
    fragmentTransaction.replace(R.id.layoutTab2, fragment, "F-B-2"); 
    ... 
    fragmentTransaction.replace(R.id.layoutTab3, fragment, "F-B-3"); 
    ... 
    

    ので、後であなたがそのタグでフラグメントを識別したり、見つけることができます:実行時にそれを追加し、このように、各フラグメントにタグを割り当てることが良いでしょう。たとえば:

    FragmentManager.findFragmentByTag("F-B-2") 
    

    か、フラグメントB 3が必要な場合:

    FragmentManager.findFragmentByTag("F-B-3") 
    

    はそれに役立つことを願っています。

    0

    フラグメントの間でデータを渡すためにバンドルのアイデアを使用できます。前の投稿でこのアイデアの提案が間違っていることがわかりました。 フラグメントがデータを受け取るサンプルコードを次に示します。 Fragment2:別のフラグメントまたは活性に対する

    public static Fragment2 newInstance(long param1, String param2) { 
        MediaFragment fragment = new Fragment2(); 
        Bundle args = new Bundle(); 
    
        args.putLong(ARG_PARAM1, param1); 
        args.putString(ARG_PARAM2, param2); 
    
        fragment.setArguments(args); 
        return fragment; 
    } 
    
    @Override 
    public void onCreate(Bundle savedInstanceState) { 
        super.onCreate(savedInstanceState); 
        if (getArguments() != null) { 
         Bundle bundle = getArguments(); 
         audioId = bundle.getLong(ARG_PARAM1); 
         audioName = bundle.getString(ARG_PARAM2); 
        } 
    } 
    

    、Fragment2を呼び出す:

    Fragment2 recvfragment = Fragment2.newInstance(itemId, itemName); 
    

    注:バンドルに

    • 、あなたに値を使用して特定のデータ型を渡すことができますあなたが必要とする断片の異なるインスタンス。
    • この場合、コードはLongおよびString型をFragment2に渡しています。あなたは、フラグメントAからフラグメントBに移動する場合は、すべての3つのフラグメントに使用するデータの同じセットが必要な場合、あなたは、単にフラグメントB.

      または他のコンストラクタに値を渡すことができ

    +0

    私の質問が慎重に表示されている場合は、フラグメントがすでに作成されているときに実行時にデータを渡す必要があるため、引数を使用して渡すデータが満足できないことがわかります – AnZ

    +0

    @AnZ、私の例では、パラメータは "newInstance(long param1 ...")になります。どちらのフラグメントが呼び出し元であっても、メインアクティビティは値をフラグメントに渡すことができ、そのフラグメントはその値を受信フラグメントに渡すことができます。 –

    0

    共有設定を使用することもできます。

    +0

    データは実行時と数回に渡ってtransfreredされます。イベントトリガーの解決策がいくつかあります – AnZ

    関連する問題