0

I have two fragments sitting side by side in the same activity. When I touch a button in the right fragment (fragment B), I need a TextView in the left fragment to update (fragment A). I have looked all over for the best way to do this, but nothing seems to work for my needs. Could someone possibly give me an example of how I would code this? Fragment A is set through the XML layout, and fragment B gets loaded programmatically into a container. I have tried accomplishing this by using a method in fragment A to update the text, and calling on that method from a method in the parent activity. I then call on the method in the parent activity from fragment B.

This is the code in fragment B that declares the interface and calls a method in the interface

AttackCards attackCards; 

public interface AttackCards {
    public void deckSize();
}

public void onAttach(DeckBuilder deckBuilder) {
    super.onAttach(deckBuilder);

        attackCards = (AttackCards) deckBuilder;
        }

attackCards.deckSize(); //this is in my onclick methods

This is the code in the activity that implements the interface and calls the method in fragment A

public class DeckBuilder extends Activity implements AttackCards{

public void deckSize() {
    DeckBuilderFragment deckBuilderFragment = (DeckBuilderFragment)getFragmentManager().
            findFragmentById(R.id.deckbuilder_fragment);
    deckBuilderFragment.deckSize();
}

This is the method in fragment A that appends the textview with the contents of a shared preferences value

public void deckSize() {
deckSize = (TextView) getView().findViewById(R.id.decksize);  
final SharedPreferences defaultDeck = getActivity()
        .getSharedPreferences("defaultDeck", Context.MODE_PRIVATE);
deckSize.setText(String.valueOf(defaultDeck.getInt("decksize", 0)));
}

Sadly this attempt simply brings me a nullpointer when touching a button. I am getting a null pointer at

attackCards.deckSize(); //this is in my onclick methods

Could someone please help me out with an example of how to do this correctly?

Trent
  • 105
  • 2
  • 8

2 Answers2

3

One fragment should not communicate to another fragment directly. It should do so through attached activity. The detail explanation with code example is available here

Android Developer site

Declare an interface in Fragment B, and implement the interface in the activity. Call the interface through callback in Fragment B when button is clicked. You can have a public function in Fragment A to update the TextView, so activity directly call the function to update the text.

sjdutta
  • 376
  • 1
  • 5
  • Ok I am now using interfaces as explained on the developer site. However I am still getting a null pointer. I am updating my question now to reflect the new code. – Trent Oct 03 '13 at 03:56
  • What is showing in the null pointer exception? Did you initialize the callback in onAttach() function? – sjdutta Oct 03 '13 at 04:02
  • Sorry, I have added my onAttach code in my edit. I can post the logcat nullpointer info if you would like. – Trent Oct 03 '13 at 04:44
1

You can define an interface in Fragment B and implement it on the MainActivity. Then on the callback method (onClickOnB in this case) set the text on the TextView. You should obtain a reference of the TextView in the Activity's onCreate() after setContentView(). This works because Fragment A is static. Otherwise, you can create a public method inside Fragment A so you can set the text from inside the callback by getting a reference of Fragment A and calling such method.

Fragment B

public class FragmentB extends Fragment implements onClickListener{
ClickOnB listener;
public void setOnFragmentBClickListener(ClickOnB listener){
this.listener = listener;

}

@Override

public void onClick(View v){
//stringMessage is a `String` you will pass to `Fragment` A to update its `TextView`
listener.onClickOnB(stringMessage);
}

interface ClickOnB{
public void onClickOnB(String message);
}

}

MainActivity

public class MainActivity extends Activity implements ClickOnB{
@Override   
protected onCreate(Bundle savedInstanceState){

//Get a reference of `Fragment` B somewhere in your code after you added it dynamically and set the listener.
((FragmentB)getFragmentManager().findFragmentByTag("FragmentB")).setOnFragmentBClickListener(this);

}

@Override
public void onClickOnB(String message){

//Set the text to the `TextView` here (I am assuming you get a reference of the `TextView` in onCreate() after inflating your layout.

mTextView.setText(message);

}
}
Emmanuel
  • 13,083
  • 4
  • 39
  • 53
  • I tried implementing the interface in fragment A that I declared in fragment B, but I still got a null pointer. I have changed my code to use interfaces but communicate through the activity as sjdutta suggested, but I am still getting the null pointer. Do you see anything in my updated code that could be causing this? – Trent Oct 03 '13 at 04:24
  • Thank you so much Emmanuel! It was pointing me in the direction of editting the TextView from the activity that solved my problem. – Trent Oct 03 '13 at 04:59