0

I am working in android app, have designed a generic adapter and parameterized adapter will inherit this.

public abstract class CarAdapter<T> extends RecyclerView.Adapter<CarAdapter<T>.BaseCarViewHolder> {
    protected DialogMakerCar<T> dialogMaker;
    protected Context context;
......

child class

public class CarItemAdapter extends CarDialogAdapter<Item> {

    public CarItemAdapter(Context context, DialogMakerCar<Item> dialogMaker) {
        super(dialogMaker, context);
    }

I am calling this adapter in a fragment and that fragment is also need to be generic so that i can call this fragment and adapter for custom objects from activity.

//Fragment to call adapter but its not letting me to use <T> generic 
 adapter = new CarItemAdapter(getContext(),dialogMaker);
        gridRecycler.setHasFixedSize(true);
        gridRecycler.setLayoutManager(adapter.getLayoutManager());

Please let me know if you need more details, Thanks

alainlompo
  • 4,414
  • 4
  • 32
  • 41
ghufranne
  • 849
  • 2
  • 9
  • 18
  • 1
    You are in fact using T when you defined in CarItemAdapter that T is Item. You can change CardItemAdapter for CarDialogAdapter and define the T at that point, if that is what you are looking for. – MissingSemiColon Jun 29 '20 at 08:59
  • @MissingSemiColon please let me know what exactly are you saying, basically, I want the adapter to have generic list of objects which I will initialize in activity but i will call this adapter NOT from activity rather from a fragment, that fragment class was called from Activity, so i can initialise with exact type in activity class but fragment dont know about it which does not letting me use generic for the adapter call. Activity --> Fragment --> Adapter – ghufranne Jun 29 '20 at 10:17
  • 1
    The thing is that CarItemAdapter is not generic, you are defining that it uses Item. You could define a generic in CarItemAdapter, or if what you want to accomplish is that the fragment create an Adapter depending on what Activity needs, you would have to define an interface. I don't fully understand what you really want, but I would guess your are trying to create some kind of factory, where fragment should return the correct adapter, and activity should not care what the real adapter is. This is done by using an interface. Read about the List intercace, its an interface and uses generics. – MissingSemiColon Jun 30 '20 at 11:03
  • yes @MissingSemiColon you understand correctly what i want, i just want to know more about the approach you are suggesting. – ghufranne Jun 30 '20 at 12:04

1 Answers1

1

I'm not an Android dev, so can't really give you a real example. Lets define the interface as following ( I don't know the real method you need so just made a simple example)

public interface ICarAdapter {

    public <T> DialogMakerCar<T> getDialogMaker();

    public Context getContext();

}

You can defined what the T extends from to avoid warnings when used in the other classes.

Now you need to use this interface in the classes you defined:

public class CarItemAdapter extends DialogMakerCar<Item> implements ICarAdapter{
  private DialogMakerCar<Item> dialogMakerCar;
  private Context context;

  public CarItemAdapter(Context cntxt, DialogMakerCar<Item> dialogMaker) {
    dialogMakerCar = dialogMaker;
    context = cntxt;
  }

  /** This will give you a warning, can be avoided 
      if you define in the interface that T extendes 
      an interface that Item implements.*/
  @Override
  public DialogMakerCar<Item> getDialogMaker() {
    return dialogMakerCar;
  }

  @Override
  public Context getContext() {
    return context;
  }
}

In the fragment class:

public class Fragment {
   
  public <T> ICarAdapter createAdapter(T item) {
    //You can manage this as you want, 
    //with a switch, defining an Enum or passing the Class that you want. 
    if (item instanceof Item) {
        return new CarItemAdapter(getContext(),dialogMaker);
    }
    return null;
}

An then when you want to use it:

public class Activity {

    Fragment fragment;

    ICarAdapter adapter;

    public Activity() {
        fragment = new Fragment();
        Item item = new Item();
        adapter = fragment.createAdapter(item);
        adapter.getContext();
        adapter.getDialogMaker();
    }

Hope at least it helps you a bit.

Other ways to do this:

https://dzone.com/articles/java-generic-factory

https://stackoverflow.com/a/47464801/6708879

Generic factory with unknown implementation classes

MissingSemiColon
  • 346
  • 3
  • 14