How to create an interface between a fragment and an adapter?

I have a snippet with a ListView , say MyListFragment and a custom CursorAdapter . I set onClickListener in this adapter for the button in the list bar.

 public class MyListAdapter extends CursorAdapter { public interface AdapterInterface { public void buttonPressed(); } ... @Override public void bindView(final View view, final Context context, final Cursor cursor) { ViewHolder holder = (ViewHolder) view.getTag(); ... holder.button.setOnClickListener(new OnClickListener() { @Override public void onClick(View v) { // some action // need to notify MyListFragment } }); } } public MyListFragment extends Fragment implements AdapterInterface { @Override public void buttonPressed() { // some action } } 

I need to notify the fragment when the button is clicked. How to call this interface?

Help me please.

+32
java android interface
Mar 16 '13 at 0:59
source share
4 answers

Create a new constructor and instance variable:

 AdapterInterface buttonListener; public MyListAdapter (Context context, Cursor c, int flags, AdapterInterface buttonListener) { super(context,c,flags); this.buttonListener = buttonListener; } 

When you create the adapter, the instance variable will be assigned the correct hold reference.

To call a fragment from a click:

 public void onClick(View v) { buttonListener.buttonPressed(); } 

When creating the Adapter you also need to transfer your fragment to the adapter. for example

 MyListAdapter adapter = new MyListAdapter (getActivity(), myCursor, myFlags, this); 

since this will refer to your fragment, which is now AdapterInterface .

Keep in mind that when orienting changes to the Fragment, it will most likely be recreated. If your adapter is not recreated, it could potentially refer to a non-existent object, causing errors.

+55
Mar 16 '13 at 1:03
source share

Using Eventbus:

Examples:

https://github.com/kaushikgopal/RxJava-Android-Samples/tree/master/app/src/main/java/com/morihacky/android/rxjava/rxbus

or

https://github.com/greenrobot/EventBus

Using Interfaces:

I understand the current answer, but I need a clearer example. Here is an example of what I used with Adapter (RecyclerView.Adapter) and Fragment .

Create Callback Interface:

 public interface AdapterCallback { void onMethodCallback(); } 

Callback / Fragment Transmission:

This will implement the interface that we have in our Adapter . In this example, it will be called when the user clicks on an item in the RecyclerView .

In your Fragment :

 public class MyFragment extends Fragment implements AdapterCallback { private MyAdapter mMyAdapter; @Override public void onMethodCallback() { // do something } @Override public void onCreate(final Bundle savedInstanceState) { super.onCreate(savedInstanceState); this.mMyAdapter = new MyAdapter(this); // this class implements callback } } 

Use Callback in your adapter:

In Fragment we initiated our Adapter and passed this as an argument to the constructor. This will call our interface for our callback method. You can see that we use our callback method for custom clicks.

 public class MyAdapter extends RecyclerView.Adapter<MyAdapter.ViewHolder> { private AdapterCallback mAdapterCallback; public MyAdapter(AdapterCallback callback) { this.mAdapterCallback = callback; } @Override public void onBindViewHolder(final MyAdapter.ViewHolder viewHolder, final int i) { // simple example, call interface here // not complete viewHolder.itemView.setOnClickListener(new OnClickListener() { @Override public void onClick(View v) { mAdapterCallback.onMethodCallback(); } }); } } 

or use Fragment in your adapter:

 public class MyAdapter extends RecyclerView.Adapter<MyAdapter.ViewHolder> { private AdapterCallback mAdapterCallback; public MyAdapter(Fragment fragment) { try { this.mAdapterCallback = ((AdapterCallback) fragment); } catch (ClassCastException e) { throw new ClassCastException("Fragment must implement AdapterCallback."); } } @Override public void onBindViewHolder(final MyAdapter.ViewHolder viewHolder, final int i) { // simple example, call interface here // not complete viewHolder.itemView.setOnClickListener(new OnClickListener() { @Override public void onClick(View v) { try { mAdapterCallback.onMethodCallback(); } catch (ClassCastException exception) { // do something } } }); } } 
+50
Dec 31 '15 at 5:48
source share

Follow the two steps below to get the adapter callback in Fragment (or Activity)

First: In Adapter

 public class ListAdapter extends RecyclerView.Adapter < RecyclerListAdapter.ItemViewHolder > { ... private ListAdapterListener mListener; public interface ListAdapterListener { // create an interface void onClickAtOKButton(int position); // create callback function } public RecyclerListAdapter(Context mContext, ArrayList < Items > listItems, ListAdapterListener mListener) { // add the interface to your adapter constructor ... this.mListener = mListener; // receive mListener from Fragment (or Activity) } ... public void onBindViewHolder(final ItemViewHolder holder, final int position) { holder.btnOK.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { // use callback function in the place you want mListener.onClickAtOKButton(position); } }); ... } ... } 

Second: In your Fragment (or Activity) there are 2 ways to implement a callback method

Path 1

  public MyListFragment extends Fragment { ... public void onViewCreated(View view, @Nullable Bundle savedInstanceState) { ... ListAdapter adapter = new ListAdapter(getActivity(), listItems, new ListAdapter.ListAdapterListener() { @Override public void onClickAtOKButton(int position) { Toast.makeText(getActivity(), "click ok button at" + position, Toast.LENGTH_SHORT).show(); } }); ... } } 

Way 2

 public MyListFragment extends Fragment implements ListAdapter.ListAdapterListener { ... public void onViewCreated(View view, @Nullable Bundle savedInstanceState) { ListAdapter adapter = new ListAdapter (getActivity(), listItems, this); ... } @Override public void onClickAtOKButton(int position) { Toast.makeText(getActivity(), "click ok button at" + position, Toast.LENGTH_SHORT).show(); } } 
+17
May 31 '16 at 12:24 a.m.
source share

This is very similar to the mode of interaction and the fragment. In the constructor of your adapter, pass the link of your fragment, drop it to your interface and just call yourReference.buttonPressed () method for your onClick method.

0
Mar 16 '13 at 1:05
source share



All Articles