2

It is possible to get reference to element(like button) defined in xml layout of fragment and use it in another activity?

I tried to do that but have null object reference.

fragment_date_picker.xml

<TimePicker
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:id="@+id/timePicker"
    android:layout_gravity="center_horizontal|top" />

<Button
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:text="ok"
    android:id="@+id/bt_ok"
    android:layout_gravity="center" />

MainActivity.java

btPickTime=(Button)findViewById(R.id.bt_pickTime);
    AlarmManager alarmManager=(AlarmManager)getSystemService(ALARM_SERVICE);
    final DatePickerFragment dp=new DatePickerFragment();

    btOk=(Button)findViewById(R.id.bt_ok);
    btOk.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            FragmentManager fm = getFragmentManager();
            FragmentTransaction ft = fm.beginTransaction();
            ft.remove(dp);
            ft.commit();
        }
    });
    btPickTime.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {

            FragmentManager fm = getFragmentManager();
            FragmentTransaction ft = fm.beginTransaction();
            ft.add(R.id.ll_main
                    ,dp);
            ft.commit();

        }
    });
Pavel Poley
  • 5,307
  • 4
  • 35
  • 66
  • How do you tried? Can you put some code? – ARP Apr 01 '16 at 14:16
  • Why would you want to do that? You can always inflate the view giving it the fragment's xml and then find that object in that view like `view.findViewById(R.id.myButton)` but I cannot see the point, why wouldn't you just do the things you need to do in your Fragment? – Vucko Apr 01 '16 at 14:26
  • You should read the documentation on [communication between Fragments](http://developer.android.com/training/basics/fragments/communicating.html) – OneCricketeer Apr 01 '16 at 14:34
  • I guess that you can only get some reference (not null) from layout you're using added with **setContentView()** at the currently activity, **UPDATED** I think that you can try with http://inthecheesefactory.com/blog/how-to-fix-nested-fragment-onactivityresult-issue/en Could it be? – M. Mariscal Apr 01 '16 at 14:35
  • Use a getter inside your `Fragment`, and communicate with the `Fragment` in the usual way: `getFragmentManager().findFragmentById(R.id.fragment_container).getButtonOrAnyOtherView()` – PPartisan Apr 01 '16 at 14:41
  • Yes i can use view.findViewById() in fragment class, but how i remove() the fragment from my activity when i press bt_ok? the reference to DatePickerFragment is in activity. – Pavel Poley Apr 01 '16 at 14:52
  • Ok - that isn't what your question asks, but now you've clarified I've answered with a few solutions – PPartisan Apr 01 '16 at 15:27

1 Answers1

5

For removing a Fragment, via a button press inside said Fragment.

Method One (Potentially the simplest)

I haven't tested this, so it may not be possible...but you could try and access the FragmentManager from inside this fragment, and then have it remove itself. In this case, you would call this inside your onClick(). You may need to place getActivity() in front of getFragmentManager() here.

getFragmentManager().beginTransaction().remove(this).commit();

Method Two (Almost as simple, but bad practice)

Place the above logic inside a public method in the Activity class your Fragment is attached to, and access it inside your Fragment onClick() like so:

((MyActivityName)getActivity()).nameOfPublicMethodToRemoveFragment();

Method Three (Recommended way for a Fragment to Communicate with its Activity)

Use an interface (Example pulled from here):

    public class BlankFragment extends Fragment implements View.OnClickListener{

    private View rootView;
    private Button button;

    private OnFragmentInteractionListener mListener;

    public static BlankFragment newInstance() {
        return new BlankFragment();
    }

    @Override
    public void onAttach(Activity activity) {
        super.onAttach(activity);
        try {
            mListener = (OnFragmentInteractionListener) activity;
        } catch (ClassCastException e) {
            throw new ClassCastException(activity.toString()
                    + " must implement OnFragmentInteractionListener");
        }
    }

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {

        rootView = inflater.inflate(R.layout.fragment_blank, container, false);
        button = (Button) rootView.findViewById(R.id.fragment_button);
        button.setOnClickListener(this);

        return rootView;
    }

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

    @Override
    public void onClick(View v) {
        mListener.onFragmentInteraction();
    }

    public interface OnFragmentInteractionListener {
        void onFragmentInteraction();
    }

}

Main Activity

public class MainActivity extends AppCompatActivity implements BlankFragment.OnFragmentInteractionListener{

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

        if (getFragmentManager().findFragmentById(R.id.fragment_container) == null) {
            getFragmentManager()
                    .beginTransaction()
                    .add(R.id.fragment_container, BlankFragment.newInstance())
                    .commit();
        }
    }

    @Override
    public void onFragmentInteraction() {
        //Remove Fragment Here
    }
}

Method Four (Alternative)

Use an EventBus to communicate from the Fragment to the Activity

PPartisan
  • 8,173
  • 4
  • 29
  • 48
  • What mean mListener = (OnFragmentInteractionListener) activity; ? and why onAttach is deprecated when you use onAttach(Activity activity) ? – Pavel Poley Apr 01 '16 at 16:15
  • @PavelPalei You may want to use `public void onAttach(Context context)` instead of `public void onAttach(Activity activity)`. There's more on it [here](http://stackoverflow.com/questions/32083053/android-fragment-onattach-deprecated) – PPartisan Apr 01 '16 at 16:20