Failing to load next data with android Paging library












1















I am trying to show call log list using Room-Paging-LiveData-ViewModel.
Without paging my code works perfectly. And I want to use paging also.



In my database I have total 25 call log record. The first 9 call log is showing in the list.



By debugging I found that while reading data in view model via Dao, it is returning list of size 25. But only first 9 of these are non null. All other entries in the list is null.




I am expecting the null data will refresh soon as this is a paged
list. But the problem is the null are never getting refreshed with
valid data.




And the observe method of view model is getting called only once, the first time only.



I think I am doing something wrong.



Here is the code below




The fragment




public class CallLogListFragment extends Fragment {
private static final String TAG = "RecentCallsFragment";

public static String getTAG() {
return TAG;
}

public static Fragment newInstance() {
return new CallLogListFragment();
}

public CallLogListFragment() {
}

@Override
public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
FragmentCallLogListBinding binding = DataBindingUtil.inflate(inflater, R.layout.fragment_call_log_list, container, false);
CallLogListAdapter adapter = new CallLogListAdapter();
binding.list.setAdapter(adapter);
CallLogListViewModel model = ViewModelProviders.of(this).get(CallLogListViewModel.class);
model.getCallLogList().observe(this, adapter::refreshData);
return binding.getRoot();
}

}



The Adapter




public class CallLogListAdapter extends PagedListAdapter<CallLogItem, CallLogListAdapter.ViewHolder> {
CallLogListAdapter() {
super(DIFF_CALLBACK);
}

void refreshData(List<CallLogItem> data) {
DiffUtil.DiffResult calculatedDiff = DiffUtil.calculateDiff(new CallLogListDiffUtilCallBack(this.data, data));
this.data.clear();
this.data.addAll(data);
calculatedDiff.dispatchUpdatesTo(this);
}

private List<CallLogItem> data = new ArrayList<>();

@NonNull
@Override
public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
return new ViewHolder(DataBindingUtil.inflate(
LayoutInflater.from(parent.getContext()),
R.layout.call_log_list_single_item,
parent, false
));
}

@Override
public void onBindViewHolder(@NonNull ViewHolder holder, int position) {
CallLogItem item = data.get(position);
holder.binding.setCallLog(item);
}

@Override
public int getItemCount() {
return data.size();
}

class ViewHolder extends RecyclerView.ViewHolder {
public CallLogListSingleItemBinding binding;
public ViewHolder(@NonNull CallLogListSingleItemBinding binding) {
super(binding.getRoot());
this.binding = binding;
}
}

private static DiffUtil.ItemCallback<CallLogItem> DIFF_CALLBACK =
new DiffUtil.ItemCallback<CallLogItem>() {
@Override
public boolean areItemsTheSame(CallLogItem oldItem, CallLogItem newItem) {
return oldItem.getHeaderDateVisibility() == newItem.getHeaderDateVisibility()
&& oldItem.getCallId().equals(newItem.getCallId());
}

@Override
public boolean areContentsTheSame(@NonNull CallLogItem oldItem, @NonNull CallLogItem newItem) {
return areItemsTheSame(oldItem, newItem);
}
};
}



The Dao




@Dao
public interface CallLogDao extends BaseDao<CallLog>{
@Query("SELECT * FROM log")
List<CallLog> getAll();

@Query("SELECT * FROM log WHERE number=:number")
CallLog findByName(String number);

@Query("SELECT * FROM log order by date desc")
LiveData<List<CallLog>> getAllLive();

@Query("SELECT * FROM log order by date desc")
DataSource.Factory<Integer, CallLog> getAllLivePaged();
}



The ViewModel




public class CallLogListViewModel extends ViewModel {
private LiveData<List<CallLogItem>> callLogList;

public CallLogListViewModel() {
callLogList = Transformations.map(new LivePagedListBuilder<>(AppDatabase.get().callLogDao().getAllLivePaged(), 3).build(), input -> {
List<CallLogItem> list = new ArrayList<>();
for (int i = 0; i < input.size(); i++) {
boolean isHeader = true;
CallLog callLog = input.get(i);
if(callLog!=null) {
if (i > 0) {
CallLog previousCallLog = input.get(i - 1);
if(previousCallLog!=null) {
isHeader = TimeFormat.isDifferentDate(callLog.date, previousCallLog.date);
}
}
list.add(CallLogItem.Companion.from(callLog, isHeader));
}
}
return list;
});
}

LiveData<List<CallLogItem>> getCallLogList() {
return callLogList;
}
}


Later I tried to make



private LiveData<List<CallLogItem>> callLogList; 


to Paged list like



private LiveData<PagedList<CallLogItem>> callLogList; 


But I found no proper way to transform into that.










share|improve this question





























    1















    I am trying to show call log list using Room-Paging-LiveData-ViewModel.
    Without paging my code works perfectly. And I want to use paging also.



    In my database I have total 25 call log record. The first 9 call log is showing in the list.



    By debugging I found that while reading data in view model via Dao, it is returning list of size 25. But only first 9 of these are non null. All other entries in the list is null.




    I am expecting the null data will refresh soon as this is a paged
    list. But the problem is the null are never getting refreshed with
    valid data.




    And the observe method of view model is getting called only once, the first time only.



    I think I am doing something wrong.



    Here is the code below




    The fragment




    public class CallLogListFragment extends Fragment {
    private static final String TAG = "RecentCallsFragment";

    public static String getTAG() {
    return TAG;
    }

    public static Fragment newInstance() {
    return new CallLogListFragment();
    }

    public CallLogListFragment() {
    }

    @Override
    public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
    FragmentCallLogListBinding binding = DataBindingUtil.inflate(inflater, R.layout.fragment_call_log_list, container, false);
    CallLogListAdapter adapter = new CallLogListAdapter();
    binding.list.setAdapter(adapter);
    CallLogListViewModel model = ViewModelProviders.of(this).get(CallLogListViewModel.class);
    model.getCallLogList().observe(this, adapter::refreshData);
    return binding.getRoot();
    }

    }



    The Adapter




    public class CallLogListAdapter extends PagedListAdapter<CallLogItem, CallLogListAdapter.ViewHolder> {
    CallLogListAdapter() {
    super(DIFF_CALLBACK);
    }

    void refreshData(List<CallLogItem> data) {
    DiffUtil.DiffResult calculatedDiff = DiffUtil.calculateDiff(new CallLogListDiffUtilCallBack(this.data, data));
    this.data.clear();
    this.data.addAll(data);
    calculatedDiff.dispatchUpdatesTo(this);
    }

    private List<CallLogItem> data = new ArrayList<>();

    @NonNull
    @Override
    public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
    return new ViewHolder(DataBindingUtil.inflate(
    LayoutInflater.from(parent.getContext()),
    R.layout.call_log_list_single_item,
    parent, false
    ));
    }

    @Override
    public void onBindViewHolder(@NonNull ViewHolder holder, int position) {
    CallLogItem item = data.get(position);
    holder.binding.setCallLog(item);
    }

    @Override
    public int getItemCount() {
    return data.size();
    }

    class ViewHolder extends RecyclerView.ViewHolder {
    public CallLogListSingleItemBinding binding;
    public ViewHolder(@NonNull CallLogListSingleItemBinding binding) {
    super(binding.getRoot());
    this.binding = binding;
    }
    }

    private static DiffUtil.ItemCallback<CallLogItem> DIFF_CALLBACK =
    new DiffUtil.ItemCallback<CallLogItem>() {
    @Override
    public boolean areItemsTheSame(CallLogItem oldItem, CallLogItem newItem) {
    return oldItem.getHeaderDateVisibility() == newItem.getHeaderDateVisibility()
    && oldItem.getCallId().equals(newItem.getCallId());
    }

    @Override
    public boolean areContentsTheSame(@NonNull CallLogItem oldItem, @NonNull CallLogItem newItem) {
    return areItemsTheSame(oldItem, newItem);
    }
    };
    }



    The Dao




    @Dao
    public interface CallLogDao extends BaseDao<CallLog>{
    @Query("SELECT * FROM log")
    List<CallLog> getAll();

    @Query("SELECT * FROM log WHERE number=:number")
    CallLog findByName(String number);

    @Query("SELECT * FROM log order by date desc")
    LiveData<List<CallLog>> getAllLive();

    @Query("SELECT * FROM log order by date desc")
    DataSource.Factory<Integer, CallLog> getAllLivePaged();
    }



    The ViewModel




    public class CallLogListViewModel extends ViewModel {
    private LiveData<List<CallLogItem>> callLogList;

    public CallLogListViewModel() {
    callLogList = Transformations.map(new LivePagedListBuilder<>(AppDatabase.get().callLogDao().getAllLivePaged(), 3).build(), input -> {
    List<CallLogItem> list = new ArrayList<>();
    for (int i = 0; i < input.size(); i++) {
    boolean isHeader = true;
    CallLog callLog = input.get(i);
    if(callLog!=null) {
    if (i > 0) {
    CallLog previousCallLog = input.get(i - 1);
    if(previousCallLog!=null) {
    isHeader = TimeFormat.isDifferentDate(callLog.date, previousCallLog.date);
    }
    }
    list.add(CallLogItem.Companion.from(callLog, isHeader));
    }
    }
    return list;
    });
    }

    LiveData<List<CallLogItem>> getCallLogList() {
    return callLogList;
    }
    }


    Later I tried to make



    private LiveData<List<CallLogItem>> callLogList; 


    to Paged list like



    private LiveData<PagedList<CallLogItem>> callLogList; 


    But I found no proper way to transform into that.










    share|improve this question



























      1












      1








      1


      0






      I am trying to show call log list using Room-Paging-LiveData-ViewModel.
      Without paging my code works perfectly. And I want to use paging also.



      In my database I have total 25 call log record. The first 9 call log is showing in the list.



      By debugging I found that while reading data in view model via Dao, it is returning list of size 25. But only first 9 of these are non null. All other entries in the list is null.




      I am expecting the null data will refresh soon as this is a paged
      list. But the problem is the null are never getting refreshed with
      valid data.




      And the observe method of view model is getting called only once, the first time only.



      I think I am doing something wrong.



      Here is the code below




      The fragment




      public class CallLogListFragment extends Fragment {
      private static final String TAG = "RecentCallsFragment";

      public static String getTAG() {
      return TAG;
      }

      public static Fragment newInstance() {
      return new CallLogListFragment();
      }

      public CallLogListFragment() {
      }

      @Override
      public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
      FragmentCallLogListBinding binding = DataBindingUtil.inflate(inflater, R.layout.fragment_call_log_list, container, false);
      CallLogListAdapter adapter = new CallLogListAdapter();
      binding.list.setAdapter(adapter);
      CallLogListViewModel model = ViewModelProviders.of(this).get(CallLogListViewModel.class);
      model.getCallLogList().observe(this, adapter::refreshData);
      return binding.getRoot();
      }

      }



      The Adapter




      public class CallLogListAdapter extends PagedListAdapter<CallLogItem, CallLogListAdapter.ViewHolder> {
      CallLogListAdapter() {
      super(DIFF_CALLBACK);
      }

      void refreshData(List<CallLogItem> data) {
      DiffUtil.DiffResult calculatedDiff = DiffUtil.calculateDiff(new CallLogListDiffUtilCallBack(this.data, data));
      this.data.clear();
      this.data.addAll(data);
      calculatedDiff.dispatchUpdatesTo(this);
      }

      private List<CallLogItem> data = new ArrayList<>();

      @NonNull
      @Override
      public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
      return new ViewHolder(DataBindingUtil.inflate(
      LayoutInflater.from(parent.getContext()),
      R.layout.call_log_list_single_item,
      parent, false
      ));
      }

      @Override
      public void onBindViewHolder(@NonNull ViewHolder holder, int position) {
      CallLogItem item = data.get(position);
      holder.binding.setCallLog(item);
      }

      @Override
      public int getItemCount() {
      return data.size();
      }

      class ViewHolder extends RecyclerView.ViewHolder {
      public CallLogListSingleItemBinding binding;
      public ViewHolder(@NonNull CallLogListSingleItemBinding binding) {
      super(binding.getRoot());
      this.binding = binding;
      }
      }

      private static DiffUtil.ItemCallback<CallLogItem> DIFF_CALLBACK =
      new DiffUtil.ItemCallback<CallLogItem>() {
      @Override
      public boolean areItemsTheSame(CallLogItem oldItem, CallLogItem newItem) {
      return oldItem.getHeaderDateVisibility() == newItem.getHeaderDateVisibility()
      && oldItem.getCallId().equals(newItem.getCallId());
      }

      @Override
      public boolean areContentsTheSame(@NonNull CallLogItem oldItem, @NonNull CallLogItem newItem) {
      return areItemsTheSame(oldItem, newItem);
      }
      };
      }



      The Dao




      @Dao
      public interface CallLogDao extends BaseDao<CallLog>{
      @Query("SELECT * FROM log")
      List<CallLog> getAll();

      @Query("SELECT * FROM log WHERE number=:number")
      CallLog findByName(String number);

      @Query("SELECT * FROM log order by date desc")
      LiveData<List<CallLog>> getAllLive();

      @Query("SELECT * FROM log order by date desc")
      DataSource.Factory<Integer, CallLog> getAllLivePaged();
      }



      The ViewModel




      public class CallLogListViewModel extends ViewModel {
      private LiveData<List<CallLogItem>> callLogList;

      public CallLogListViewModel() {
      callLogList = Transformations.map(new LivePagedListBuilder<>(AppDatabase.get().callLogDao().getAllLivePaged(), 3).build(), input -> {
      List<CallLogItem> list = new ArrayList<>();
      for (int i = 0; i < input.size(); i++) {
      boolean isHeader = true;
      CallLog callLog = input.get(i);
      if(callLog!=null) {
      if (i > 0) {
      CallLog previousCallLog = input.get(i - 1);
      if(previousCallLog!=null) {
      isHeader = TimeFormat.isDifferentDate(callLog.date, previousCallLog.date);
      }
      }
      list.add(CallLogItem.Companion.from(callLog, isHeader));
      }
      }
      return list;
      });
      }

      LiveData<List<CallLogItem>> getCallLogList() {
      return callLogList;
      }
      }


      Later I tried to make



      private LiveData<List<CallLogItem>> callLogList; 


      to Paged list like



      private LiveData<PagedList<CallLogItem>> callLogList; 


      But I found no proper way to transform into that.










      share|improve this question
















      I am trying to show call log list using Room-Paging-LiveData-ViewModel.
      Without paging my code works perfectly. And I want to use paging also.



      In my database I have total 25 call log record. The first 9 call log is showing in the list.



      By debugging I found that while reading data in view model via Dao, it is returning list of size 25. But only first 9 of these are non null. All other entries in the list is null.




      I am expecting the null data will refresh soon as this is a paged
      list. But the problem is the null are never getting refreshed with
      valid data.




      And the observe method of view model is getting called only once, the first time only.



      I think I am doing something wrong.



      Here is the code below




      The fragment




      public class CallLogListFragment extends Fragment {
      private static final String TAG = "RecentCallsFragment";

      public static String getTAG() {
      return TAG;
      }

      public static Fragment newInstance() {
      return new CallLogListFragment();
      }

      public CallLogListFragment() {
      }

      @Override
      public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
      FragmentCallLogListBinding binding = DataBindingUtil.inflate(inflater, R.layout.fragment_call_log_list, container, false);
      CallLogListAdapter adapter = new CallLogListAdapter();
      binding.list.setAdapter(adapter);
      CallLogListViewModel model = ViewModelProviders.of(this).get(CallLogListViewModel.class);
      model.getCallLogList().observe(this, adapter::refreshData);
      return binding.getRoot();
      }

      }



      The Adapter




      public class CallLogListAdapter extends PagedListAdapter<CallLogItem, CallLogListAdapter.ViewHolder> {
      CallLogListAdapter() {
      super(DIFF_CALLBACK);
      }

      void refreshData(List<CallLogItem> data) {
      DiffUtil.DiffResult calculatedDiff = DiffUtil.calculateDiff(new CallLogListDiffUtilCallBack(this.data, data));
      this.data.clear();
      this.data.addAll(data);
      calculatedDiff.dispatchUpdatesTo(this);
      }

      private List<CallLogItem> data = new ArrayList<>();

      @NonNull
      @Override
      public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
      return new ViewHolder(DataBindingUtil.inflate(
      LayoutInflater.from(parent.getContext()),
      R.layout.call_log_list_single_item,
      parent, false
      ));
      }

      @Override
      public void onBindViewHolder(@NonNull ViewHolder holder, int position) {
      CallLogItem item = data.get(position);
      holder.binding.setCallLog(item);
      }

      @Override
      public int getItemCount() {
      return data.size();
      }

      class ViewHolder extends RecyclerView.ViewHolder {
      public CallLogListSingleItemBinding binding;
      public ViewHolder(@NonNull CallLogListSingleItemBinding binding) {
      super(binding.getRoot());
      this.binding = binding;
      }
      }

      private static DiffUtil.ItemCallback<CallLogItem> DIFF_CALLBACK =
      new DiffUtil.ItemCallback<CallLogItem>() {
      @Override
      public boolean areItemsTheSame(CallLogItem oldItem, CallLogItem newItem) {
      return oldItem.getHeaderDateVisibility() == newItem.getHeaderDateVisibility()
      && oldItem.getCallId().equals(newItem.getCallId());
      }

      @Override
      public boolean areContentsTheSame(@NonNull CallLogItem oldItem, @NonNull CallLogItem newItem) {
      return areItemsTheSame(oldItem, newItem);
      }
      };
      }



      The Dao




      @Dao
      public interface CallLogDao extends BaseDao<CallLog>{
      @Query("SELECT * FROM log")
      List<CallLog> getAll();

      @Query("SELECT * FROM log WHERE number=:number")
      CallLog findByName(String number);

      @Query("SELECT * FROM log order by date desc")
      LiveData<List<CallLog>> getAllLive();

      @Query("SELECT * FROM log order by date desc")
      DataSource.Factory<Integer, CallLog> getAllLivePaged();
      }



      The ViewModel




      public class CallLogListViewModel extends ViewModel {
      private LiveData<List<CallLogItem>> callLogList;

      public CallLogListViewModel() {
      callLogList = Transformations.map(new LivePagedListBuilder<>(AppDatabase.get().callLogDao().getAllLivePaged(), 3).build(), input -> {
      List<CallLogItem> list = new ArrayList<>();
      for (int i = 0; i < input.size(); i++) {
      boolean isHeader = true;
      CallLog callLog = input.get(i);
      if(callLog!=null) {
      if (i > 0) {
      CallLog previousCallLog = input.get(i - 1);
      if(previousCallLog!=null) {
      isHeader = TimeFormat.isDifferentDate(callLog.date, previousCallLog.date);
      }
      }
      list.add(CallLogItem.Companion.from(callLog, isHeader));
      }
      }
      return list;
      });
      }

      LiveData<List<CallLogItem>> getCallLogList() {
      return callLogList;
      }
      }


      Later I tried to make



      private LiveData<List<CallLogItem>> callLogList; 


      to Paged list like



      private LiveData<PagedList<CallLogItem>> callLogList; 


      But I found no proper way to transform into that.







      android android-room android-livedata androidx android-paging






      share|improve this question















      share|improve this question













      share|improve this question




      share|improve this question








      edited Dec 2 '18 at 7:32







      Ifta

















      asked Nov 14 '18 at 10:14









      IftaIfta

      19339




      19339
























          2 Answers
          2






          active

          oldest

          votes


















          2














          In order to be able to return a mapped PagedList you should know that DataSource and DataSource.Factory has map() and mapByPage().
          You can map the DataSource Factory items with mapByPage() instead using Transformation, like this:



          DataSource.Factory<Integer, CallLog> dataSourceFactoryCallLog = AppDatabase.get().callLogDao().getAllLivePaged();

          DataSource.Factory<Integer, CallLogItem> dataSourceFactoryCallLogItem = dataSourceFactoryCallLog.mapByPage(input -> {
          List<CallLogItem> list = new ArrayList<>();
          for (int i = 0; i < input.size(); i++) {
          boolean isHeader = true;
          CallLog callLog = input.get(i);
          if(callLog!=null) {
          if (i > 0) {
          CallLog previousCallLog = input.get(i - 1);
          if(previousCallLog!=null) {
          isHeader = TimeFormat.isDifferentDate(callLog.date, previousCallLog.date);
          }
          }
          list.add(CallLogItem.Companion.from(callLog, isHeader));
          }
          }
          return list;
          });

          LiveData<PagedList<CallLogItem>> callLogItems = new LivePagedListBuilder<>(dataSourceFactoryCallLogItem, 3).build()


          EDIT



          According PagedList documentation




          With placeholders, the PagedList is always the full size of the data set. get(N) returns the Nth item in the data set, or null if its not yet loaded.



          Without null placeholders, the PagedList is the sublist of data that has already been loaded. The size of the PagedList is the number of currently loaded items, and get(N) returns the Nth loaded item. This is not necessarily the Nth item in the data set.



          Placeholders are enabled by default, but can be disabled in two ways. They are disabled if the DataSource does not count its data set in its initial load, or if false is passed to setEnablePlaceholders(boolean) when building a PagedList.Config.




          You just need to create a PagedList.Config and add this to LivePagedListBuilder instantiation.



          PagedList.Config pagedListConfig =
          (new PagedList.Config.Builder())
          .setEnablePlaceholders(false)
          .setPageSize(3).build();

          LiveData<PagedList<CallLogItem>> callLogItems = new LivePagedListBuilder<>(dataSourceFactoryCallLogItem, pagedListConfig).build()





          share|improve this answer


























          • I have tried and i found that, in my adapter refreshData method is called only once with full list size. List size is 25 but contains 9 actual data, others are null. How can I configure PagedList to load the next page in the data list?

            – Ifta
            Nov 15 '18 at 3:55











          • try to create a PagedList.Config and add this to LivePagedListBuilder instantiation. new LivePagedListBuilder<>(dataSourceFactoryCallLogItem, pagedListConfig).build()

            – haroldolivieri
            Nov 15 '18 at 8:55













          • change placeholders to false on PagedList.Config like this .setEnablePlaceholders(false)

            – haroldolivieri
            Nov 15 '18 at 9:02













          • thanks. that would help removing null elements, i know. but the problem was wrong implementation of my adapter class. I had edited your answer to make it correct answer and was waiting for the edit to approve by peer review. But now I see the edit is gone.

            – Ifta
            Nov 15 '18 at 10:56






          • 1





            I think you can edit your question to let the problem more clear and after this create the right answer for that.

            – haroldolivieri
            Nov 17 '18 at 21:01



















          0














          For paged list adapter there is 2 thing to note.
          1. Data will be handled internally and no need to declare any data structure to handle data manually.
          2. There is a default method called submitList in PagedListAdapter. It is necessary to submit paged list over that method to the adapter.




          Modified adapter




          public class CallLogListAdapter extends PagedListAdapter<CallLogItem, CallLogListAdapter.ViewHolder> {
          private Context context;
          CallLogListAdapter(Context context) {
          super(DIFF_CALLBACK);
          this.context = context;
          }

          @NonNull
          @Override
          public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
          return new ViewHolder(DataBindingUtil.inflate(
          LayoutInflater.from(parent.getContext()),
          R.layout.call_log_list_single_item,
          parent, false
          ));
          }

          @Override
          public void onBindViewHolder(@NonNull ViewHolder holder, int position) {
          CallLogItem item = getItem(position);
          if (item != null) {
          holder.binding.setCallLog(item);
          ImageUtil.setImage(holder.binding.ivProfileImage, item.getImageUrl(), item.getName());
          } else {
          holder.binding.invalidateAll();
          }
          }


          class ViewHolder extends RecyclerView.ViewHolder {
          public CallLogListSingleItemBinding binding;

          public ViewHolder(@NonNull CallLogListSingleItemBinding binding) {
          super(binding.getRoot());
          this.binding = binding;
          }
          }

          private static DiffUtil.ItemCallback<CallLogItem> DIFF_CALLBACK =
          new DiffUtil.ItemCallback<CallLogItem>() {
          @Override
          public boolean areItemsTheSame(CallLogItem oldItem, CallLogItem newItem) {
          return oldItem.getHeaderDateVisibility() == newItem.getHeaderDateVisibility()
          && oldItem.getCallId()!=null && oldItem.getCallId().equals(newItem.getCallId());
          }

          @Override
          public boolean areContentsTheSame(@NonNull CallLogItem oldItem, @NonNull CallLogItem newItem) {
          return areItemsTheSame(oldItem, newItem);
          }
          };
          }



          Modified Data passing to adapter




          CallLogListViewModel model = ViewModelProviders.of(this).get(CallLogListViewModel.class);
          model.getCallLogList().observe(this, adapter::submitList);





          share|improve this answer























            Your Answer






            StackExchange.ifUsing("editor", function () {
            StackExchange.using("externalEditor", function () {
            StackExchange.using("snippets", function () {
            StackExchange.snippets.init();
            });
            });
            }, "code-snippets");

            StackExchange.ready(function() {
            var channelOptions = {
            tags: "".split(" "),
            id: "1"
            };
            initTagRenderer("".split(" "), "".split(" "), channelOptions);

            StackExchange.using("externalEditor", function() {
            // Have to fire editor after snippets, if snippets enabled
            if (StackExchange.settings.snippets.snippetsEnabled) {
            StackExchange.using("snippets", function() {
            createEditor();
            });
            }
            else {
            createEditor();
            }
            });

            function createEditor() {
            StackExchange.prepareEditor({
            heartbeatType: 'answer',
            autoActivateHeartbeat: false,
            convertImagesToLinks: true,
            noModals: true,
            showLowRepImageUploadWarning: true,
            reputationToPostImages: 10,
            bindNavPrevention: true,
            postfix: "",
            imageUploader: {
            brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
            contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
            allowUrls: true
            },
            onDemand: true,
            discardSelector: ".discard-answer"
            ,immediatelyShowMarkdownHelp:true
            });


            }
            });














            draft saved

            draft discarded


















            StackExchange.ready(
            function () {
            StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53297726%2ffailing-to-load-next-data-with-android-paging-library%23new-answer', 'question_page');
            }
            );

            Post as a guest















            Required, but never shown

























            2 Answers
            2






            active

            oldest

            votes








            2 Answers
            2






            active

            oldest

            votes









            active

            oldest

            votes






            active

            oldest

            votes









            2














            In order to be able to return a mapped PagedList you should know that DataSource and DataSource.Factory has map() and mapByPage().
            You can map the DataSource Factory items with mapByPage() instead using Transformation, like this:



            DataSource.Factory<Integer, CallLog> dataSourceFactoryCallLog = AppDatabase.get().callLogDao().getAllLivePaged();

            DataSource.Factory<Integer, CallLogItem> dataSourceFactoryCallLogItem = dataSourceFactoryCallLog.mapByPage(input -> {
            List<CallLogItem> list = new ArrayList<>();
            for (int i = 0; i < input.size(); i++) {
            boolean isHeader = true;
            CallLog callLog = input.get(i);
            if(callLog!=null) {
            if (i > 0) {
            CallLog previousCallLog = input.get(i - 1);
            if(previousCallLog!=null) {
            isHeader = TimeFormat.isDifferentDate(callLog.date, previousCallLog.date);
            }
            }
            list.add(CallLogItem.Companion.from(callLog, isHeader));
            }
            }
            return list;
            });

            LiveData<PagedList<CallLogItem>> callLogItems = new LivePagedListBuilder<>(dataSourceFactoryCallLogItem, 3).build()


            EDIT



            According PagedList documentation




            With placeholders, the PagedList is always the full size of the data set. get(N) returns the Nth item in the data set, or null if its not yet loaded.



            Without null placeholders, the PagedList is the sublist of data that has already been loaded. The size of the PagedList is the number of currently loaded items, and get(N) returns the Nth loaded item. This is not necessarily the Nth item in the data set.



            Placeholders are enabled by default, but can be disabled in two ways. They are disabled if the DataSource does not count its data set in its initial load, or if false is passed to setEnablePlaceholders(boolean) when building a PagedList.Config.




            You just need to create a PagedList.Config and add this to LivePagedListBuilder instantiation.



            PagedList.Config pagedListConfig =
            (new PagedList.Config.Builder())
            .setEnablePlaceholders(false)
            .setPageSize(3).build();

            LiveData<PagedList<CallLogItem>> callLogItems = new LivePagedListBuilder<>(dataSourceFactoryCallLogItem, pagedListConfig).build()





            share|improve this answer


























            • I have tried and i found that, in my adapter refreshData method is called only once with full list size. List size is 25 but contains 9 actual data, others are null. How can I configure PagedList to load the next page in the data list?

              – Ifta
              Nov 15 '18 at 3:55











            • try to create a PagedList.Config and add this to LivePagedListBuilder instantiation. new LivePagedListBuilder<>(dataSourceFactoryCallLogItem, pagedListConfig).build()

              – haroldolivieri
              Nov 15 '18 at 8:55













            • change placeholders to false on PagedList.Config like this .setEnablePlaceholders(false)

              – haroldolivieri
              Nov 15 '18 at 9:02













            • thanks. that would help removing null elements, i know. but the problem was wrong implementation of my adapter class. I had edited your answer to make it correct answer and was waiting for the edit to approve by peer review. But now I see the edit is gone.

              – Ifta
              Nov 15 '18 at 10:56






            • 1





              I think you can edit your question to let the problem more clear and after this create the right answer for that.

              – haroldolivieri
              Nov 17 '18 at 21:01
















            2














            In order to be able to return a mapped PagedList you should know that DataSource and DataSource.Factory has map() and mapByPage().
            You can map the DataSource Factory items with mapByPage() instead using Transformation, like this:



            DataSource.Factory<Integer, CallLog> dataSourceFactoryCallLog = AppDatabase.get().callLogDao().getAllLivePaged();

            DataSource.Factory<Integer, CallLogItem> dataSourceFactoryCallLogItem = dataSourceFactoryCallLog.mapByPage(input -> {
            List<CallLogItem> list = new ArrayList<>();
            for (int i = 0; i < input.size(); i++) {
            boolean isHeader = true;
            CallLog callLog = input.get(i);
            if(callLog!=null) {
            if (i > 0) {
            CallLog previousCallLog = input.get(i - 1);
            if(previousCallLog!=null) {
            isHeader = TimeFormat.isDifferentDate(callLog.date, previousCallLog.date);
            }
            }
            list.add(CallLogItem.Companion.from(callLog, isHeader));
            }
            }
            return list;
            });

            LiveData<PagedList<CallLogItem>> callLogItems = new LivePagedListBuilder<>(dataSourceFactoryCallLogItem, 3).build()


            EDIT



            According PagedList documentation




            With placeholders, the PagedList is always the full size of the data set. get(N) returns the Nth item in the data set, or null if its not yet loaded.



            Without null placeholders, the PagedList is the sublist of data that has already been loaded. The size of the PagedList is the number of currently loaded items, and get(N) returns the Nth loaded item. This is not necessarily the Nth item in the data set.



            Placeholders are enabled by default, but can be disabled in two ways. They are disabled if the DataSource does not count its data set in its initial load, or if false is passed to setEnablePlaceholders(boolean) when building a PagedList.Config.




            You just need to create a PagedList.Config and add this to LivePagedListBuilder instantiation.



            PagedList.Config pagedListConfig =
            (new PagedList.Config.Builder())
            .setEnablePlaceholders(false)
            .setPageSize(3).build();

            LiveData<PagedList<CallLogItem>> callLogItems = new LivePagedListBuilder<>(dataSourceFactoryCallLogItem, pagedListConfig).build()





            share|improve this answer


























            • I have tried and i found that, in my adapter refreshData method is called only once with full list size. List size is 25 but contains 9 actual data, others are null. How can I configure PagedList to load the next page in the data list?

              – Ifta
              Nov 15 '18 at 3:55











            • try to create a PagedList.Config and add this to LivePagedListBuilder instantiation. new LivePagedListBuilder<>(dataSourceFactoryCallLogItem, pagedListConfig).build()

              – haroldolivieri
              Nov 15 '18 at 8:55













            • change placeholders to false on PagedList.Config like this .setEnablePlaceholders(false)

              – haroldolivieri
              Nov 15 '18 at 9:02













            • thanks. that would help removing null elements, i know. but the problem was wrong implementation of my adapter class. I had edited your answer to make it correct answer and was waiting for the edit to approve by peer review. But now I see the edit is gone.

              – Ifta
              Nov 15 '18 at 10:56






            • 1





              I think you can edit your question to let the problem more clear and after this create the right answer for that.

              – haroldolivieri
              Nov 17 '18 at 21:01














            2












            2








            2







            In order to be able to return a mapped PagedList you should know that DataSource and DataSource.Factory has map() and mapByPage().
            You can map the DataSource Factory items with mapByPage() instead using Transformation, like this:



            DataSource.Factory<Integer, CallLog> dataSourceFactoryCallLog = AppDatabase.get().callLogDao().getAllLivePaged();

            DataSource.Factory<Integer, CallLogItem> dataSourceFactoryCallLogItem = dataSourceFactoryCallLog.mapByPage(input -> {
            List<CallLogItem> list = new ArrayList<>();
            for (int i = 0; i < input.size(); i++) {
            boolean isHeader = true;
            CallLog callLog = input.get(i);
            if(callLog!=null) {
            if (i > 0) {
            CallLog previousCallLog = input.get(i - 1);
            if(previousCallLog!=null) {
            isHeader = TimeFormat.isDifferentDate(callLog.date, previousCallLog.date);
            }
            }
            list.add(CallLogItem.Companion.from(callLog, isHeader));
            }
            }
            return list;
            });

            LiveData<PagedList<CallLogItem>> callLogItems = new LivePagedListBuilder<>(dataSourceFactoryCallLogItem, 3).build()


            EDIT



            According PagedList documentation




            With placeholders, the PagedList is always the full size of the data set. get(N) returns the Nth item in the data set, or null if its not yet loaded.



            Without null placeholders, the PagedList is the sublist of data that has already been loaded. The size of the PagedList is the number of currently loaded items, and get(N) returns the Nth loaded item. This is not necessarily the Nth item in the data set.



            Placeholders are enabled by default, but can be disabled in two ways. They are disabled if the DataSource does not count its data set in its initial load, or if false is passed to setEnablePlaceholders(boolean) when building a PagedList.Config.




            You just need to create a PagedList.Config and add this to LivePagedListBuilder instantiation.



            PagedList.Config pagedListConfig =
            (new PagedList.Config.Builder())
            .setEnablePlaceholders(false)
            .setPageSize(3).build();

            LiveData<PagedList<CallLogItem>> callLogItems = new LivePagedListBuilder<>(dataSourceFactoryCallLogItem, pagedListConfig).build()





            share|improve this answer















            In order to be able to return a mapped PagedList you should know that DataSource and DataSource.Factory has map() and mapByPage().
            You can map the DataSource Factory items with mapByPage() instead using Transformation, like this:



            DataSource.Factory<Integer, CallLog> dataSourceFactoryCallLog = AppDatabase.get().callLogDao().getAllLivePaged();

            DataSource.Factory<Integer, CallLogItem> dataSourceFactoryCallLogItem = dataSourceFactoryCallLog.mapByPage(input -> {
            List<CallLogItem> list = new ArrayList<>();
            for (int i = 0; i < input.size(); i++) {
            boolean isHeader = true;
            CallLog callLog = input.get(i);
            if(callLog!=null) {
            if (i > 0) {
            CallLog previousCallLog = input.get(i - 1);
            if(previousCallLog!=null) {
            isHeader = TimeFormat.isDifferentDate(callLog.date, previousCallLog.date);
            }
            }
            list.add(CallLogItem.Companion.from(callLog, isHeader));
            }
            }
            return list;
            });

            LiveData<PagedList<CallLogItem>> callLogItems = new LivePagedListBuilder<>(dataSourceFactoryCallLogItem, 3).build()


            EDIT



            According PagedList documentation




            With placeholders, the PagedList is always the full size of the data set. get(N) returns the Nth item in the data set, or null if its not yet loaded.



            Without null placeholders, the PagedList is the sublist of data that has already been loaded. The size of the PagedList is the number of currently loaded items, and get(N) returns the Nth loaded item. This is not necessarily the Nth item in the data set.



            Placeholders are enabled by default, but can be disabled in two ways. They are disabled if the DataSource does not count its data set in its initial load, or if false is passed to setEnablePlaceholders(boolean) when building a PagedList.Config.




            You just need to create a PagedList.Config and add this to LivePagedListBuilder instantiation.



            PagedList.Config pagedListConfig =
            (new PagedList.Config.Builder())
            .setEnablePlaceholders(false)
            .setPageSize(3).build();

            LiveData<PagedList<CallLogItem>> callLogItems = new LivePagedListBuilder<>(dataSourceFactoryCallLogItem, pagedListConfig).build()






            share|improve this answer














            share|improve this answer



            share|improve this answer








            edited Nov 15 '18 at 9:23

























            answered Nov 14 '18 at 11:47









            haroldolivieriharoldolivieri

            329214




            329214













            • I have tried and i found that, in my adapter refreshData method is called only once with full list size. List size is 25 but contains 9 actual data, others are null. How can I configure PagedList to load the next page in the data list?

              – Ifta
              Nov 15 '18 at 3:55











            • try to create a PagedList.Config and add this to LivePagedListBuilder instantiation. new LivePagedListBuilder<>(dataSourceFactoryCallLogItem, pagedListConfig).build()

              – haroldolivieri
              Nov 15 '18 at 8:55













            • change placeholders to false on PagedList.Config like this .setEnablePlaceholders(false)

              – haroldolivieri
              Nov 15 '18 at 9:02













            • thanks. that would help removing null elements, i know. but the problem was wrong implementation of my adapter class. I had edited your answer to make it correct answer and was waiting for the edit to approve by peer review. But now I see the edit is gone.

              – Ifta
              Nov 15 '18 at 10:56






            • 1





              I think you can edit your question to let the problem more clear and after this create the right answer for that.

              – haroldolivieri
              Nov 17 '18 at 21:01



















            • I have tried and i found that, in my adapter refreshData method is called only once with full list size. List size is 25 but contains 9 actual data, others are null. How can I configure PagedList to load the next page in the data list?

              – Ifta
              Nov 15 '18 at 3:55











            • try to create a PagedList.Config and add this to LivePagedListBuilder instantiation. new LivePagedListBuilder<>(dataSourceFactoryCallLogItem, pagedListConfig).build()

              – haroldolivieri
              Nov 15 '18 at 8:55













            • change placeholders to false on PagedList.Config like this .setEnablePlaceholders(false)

              – haroldolivieri
              Nov 15 '18 at 9:02













            • thanks. that would help removing null elements, i know. but the problem was wrong implementation of my adapter class. I had edited your answer to make it correct answer and was waiting for the edit to approve by peer review. But now I see the edit is gone.

              – Ifta
              Nov 15 '18 at 10:56






            • 1





              I think you can edit your question to let the problem more clear and after this create the right answer for that.

              – haroldolivieri
              Nov 17 '18 at 21:01

















            I have tried and i found that, in my adapter refreshData method is called only once with full list size. List size is 25 but contains 9 actual data, others are null. How can I configure PagedList to load the next page in the data list?

            – Ifta
            Nov 15 '18 at 3:55





            I have tried and i found that, in my adapter refreshData method is called only once with full list size. List size is 25 but contains 9 actual data, others are null. How can I configure PagedList to load the next page in the data list?

            – Ifta
            Nov 15 '18 at 3:55













            try to create a PagedList.Config and add this to LivePagedListBuilder instantiation. new LivePagedListBuilder<>(dataSourceFactoryCallLogItem, pagedListConfig).build()

            – haroldolivieri
            Nov 15 '18 at 8:55







            try to create a PagedList.Config and add this to LivePagedListBuilder instantiation. new LivePagedListBuilder<>(dataSourceFactoryCallLogItem, pagedListConfig).build()

            – haroldolivieri
            Nov 15 '18 at 8:55















            change placeholders to false on PagedList.Config like this .setEnablePlaceholders(false)

            – haroldolivieri
            Nov 15 '18 at 9:02







            change placeholders to false on PagedList.Config like this .setEnablePlaceholders(false)

            – haroldolivieri
            Nov 15 '18 at 9:02















            thanks. that would help removing null elements, i know. but the problem was wrong implementation of my adapter class. I had edited your answer to make it correct answer and was waiting for the edit to approve by peer review. But now I see the edit is gone.

            – Ifta
            Nov 15 '18 at 10:56





            thanks. that would help removing null elements, i know. but the problem was wrong implementation of my adapter class. I had edited your answer to make it correct answer and was waiting for the edit to approve by peer review. But now I see the edit is gone.

            – Ifta
            Nov 15 '18 at 10:56




            1




            1





            I think you can edit your question to let the problem more clear and after this create the right answer for that.

            – haroldolivieri
            Nov 17 '18 at 21:01





            I think you can edit your question to let the problem more clear and after this create the right answer for that.

            – haroldolivieri
            Nov 17 '18 at 21:01













            0














            For paged list adapter there is 2 thing to note.
            1. Data will be handled internally and no need to declare any data structure to handle data manually.
            2. There is a default method called submitList in PagedListAdapter. It is necessary to submit paged list over that method to the adapter.




            Modified adapter




            public class CallLogListAdapter extends PagedListAdapter<CallLogItem, CallLogListAdapter.ViewHolder> {
            private Context context;
            CallLogListAdapter(Context context) {
            super(DIFF_CALLBACK);
            this.context = context;
            }

            @NonNull
            @Override
            public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
            return new ViewHolder(DataBindingUtil.inflate(
            LayoutInflater.from(parent.getContext()),
            R.layout.call_log_list_single_item,
            parent, false
            ));
            }

            @Override
            public void onBindViewHolder(@NonNull ViewHolder holder, int position) {
            CallLogItem item = getItem(position);
            if (item != null) {
            holder.binding.setCallLog(item);
            ImageUtil.setImage(holder.binding.ivProfileImage, item.getImageUrl(), item.getName());
            } else {
            holder.binding.invalidateAll();
            }
            }


            class ViewHolder extends RecyclerView.ViewHolder {
            public CallLogListSingleItemBinding binding;

            public ViewHolder(@NonNull CallLogListSingleItemBinding binding) {
            super(binding.getRoot());
            this.binding = binding;
            }
            }

            private static DiffUtil.ItemCallback<CallLogItem> DIFF_CALLBACK =
            new DiffUtil.ItemCallback<CallLogItem>() {
            @Override
            public boolean areItemsTheSame(CallLogItem oldItem, CallLogItem newItem) {
            return oldItem.getHeaderDateVisibility() == newItem.getHeaderDateVisibility()
            && oldItem.getCallId()!=null && oldItem.getCallId().equals(newItem.getCallId());
            }

            @Override
            public boolean areContentsTheSame(@NonNull CallLogItem oldItem, @NonNull CallLogItem newItem) {
            return areItemsTheSame(oldItem, newItem);
            }
            };
            }



            Modified Data passing to adapter




            CallLogListViewModel model = ViewModelProviders.of(this).get(CallLogListViewModel.class);
            model.getCallLogList().observe(this, adapter::submitList);





            share|improve this answer




























              0














              For paged list adapter there is 2 thing to note.
              1. Data will be handled internally and no need to declare any data structure to handle data manually.
              2. There is a default method called submitList in PagedListAdapter. It is necessary to submit paged list over that method to the adapter.




              Modified adapter




              public class CallLogListAdapter extends PagedListAdapter<CallLogItem, CallLogListAdapter.ViewHolder> {
              private Context context;
              CallLogListAdapter(Context context) {
              super(DIFF_CALLBACK);
              this.context = context;
              }

              @NonNull
              @Override
              public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
              return new ViewHolder(DataBindingUtil.inflate(
              LayoutInflater.from(parent.getContext()),
              R.layout.call_log_list_single_item,
              parent, false
              ));
              }

              @Override
              public void onBindViewHolder(@NonNull ViewHolder holder, int position) {
              CallLogItem item = getItem(position);
              if (item != null) {
              holder.binding.setCallLog(item);
              ImageUtil.setImage(holder.binding.ivProfileImage, item.getImageUrl(), item.getName());
              } else {
              holder.binding.invalidateAll();
              }
              }


              class ViewHolder extends RecyclerView.ViewHolder {
              public CallLogListSingleItemBinding binding;

              public ViewHolder(@NonNull CallLogListSingleItemBinding binding) {
              super(binding.getRoot());
              this.binding = binding;
              }
              }

              private static DiffUtil.ItemCallback<CallLogItem> DIFF_CALLBACK =
              new DiffUtil.ItemCallback<CallLogItem>() {
              @Override
              public boolean areItemsTheSame(CallLogItem oldItem, CallLogItem newItem) {
              return oldItem.getHeaderDateVisibility() == newItem.getHeaderDateVisibility()
              && oldItem.getCallId()!=null && oldItem.getCallId().equals(newItem.getCallId());
              }

              @Override
              public boolean areContentsTheSame(@NonNull CallLogItem oldItem, @NonNull CallLogItem newItem) {
              return areItemsTheSame(oldItem, newItem);
              }
              };
              }



              Modified Data passing to adapter




              CallLogListViewModel model = ViewModelProviders.of(this).get(CallLogListViewModel.class);
              model.getCallLogList().observe(this, adapter::submitList);





              share|improve this answer


























                0












                0








                0







                For paged list adapter there is 2 thing to note.
                1. Data will be handled internally and no need to declare any data structure to handle data manually.
                2. There is a default method called submitList in PagedListAdapter. It is necessary to submit paged list over that method to the adapter.




                Modified adapter




                public class CallLogListAdapter extends PagedListAdapter<CallLogItem, CallLogListAdapter.ViewHolder> {
                private Context context;
                CallLogListAdapter(Context context) {
                super(DIFF_CALLBACK);
                this.context = context;
                }

                @NonNull
                @Override
                public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
                return new ViewHolder(DataBindingUtil.inflate(
                LayoutInflater.from(parent.getContext()),
                R.layout.call_log_list_single_item,
                parent, false
                ));
                }

                @Override
                public void onBindViewHolder(@NonNull ViewHolder holder, int position) {
                CallLogItem item = getItem(position);
                if (item != null) {
                holder.binding.setCallLog(item);
                ImageUtil.setImage(holder.binding.ivProfileImage, item.getImageUrl(), item.getName());
                } else {
                holder.binding.invalidateAll();
                }
                }


                class ViewHolder extends RecyclerView.ViewHolder {
                public CallLogListSingleItemBinding binding;

                public ViewHolder(@NonNull CallLogListSingleItemBinding binding) {
                super(binding.getRoot());
                this.binding = binding;
                }
                }

                private static DiffUtil.ItemCallback<CallLogItem> DIFF_CALLBACK =
                new DiffUtil.ItemCallback<CallLogItem>() {
                @Override
                public boolean areItemsTheSame(CallLogItem oldItem, CallLogItem newItem) {
                return oldItem.getHeaderDateVisibility() == newItem.getHeaderDateVisibility()
                && oldItem.getCallId()!=null && oldItem.getCallId().equals(newItem.getCallId());
                }

                @Override
                public boolean areContentsTheSame(@NonNull CallLogItem oldItem, @NonNull CallLogItem newItem) {
                return areItemsTheSame(oldItem, newItem);
                }
                };
                }



                Modified Data passing to adapter




                CallLogListViewModel model = ViewModelProviders.of(this).get(CallLogListViewModel.class);
                model.getCallLogList().observe(this, adapter::submitList);





                share|improve this answer













                For paged list adapter there is 2 thing to note.
                1. Data will be handled internally and no need to declare any data structure to handle data manually.
                2. There is a default method called submitList in PagedListAdapter. It is necessary to submit paged list over that method to the adapter.




                Modified adapter




                public class CallLogListAdapter extends PagedListAdapter<CallLogItem, CallLogListAdapter.ViewHolder> {
                private Context context;
                CallLogListAdapter(Context context) {
                super(DIFF_CALLBACK);
                this.context = context;
                }

                @NonNull
                @Override
                public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
                return new ViewHolder(DataBindingUtil.inflate(
                LayoutInflater.from(parent.getContext()),
                R.layout.call_log_list_single_item,
                parent, false
                ));
                }

                @Override
                public void onBindViewHolder(@NonNull ViewHolder holder, int position) {
                CallLogItem item = getItem(position);
                if (item != null) {
                holder.binding.setCallLog(item);
                ImageUtil.setImage(holder.binding.ivProfileImage, item.getImageUrl(), item.getName());
                } else {
                holder.binding.invalidateAll();
                }
                }


                class ViewHolder extends RecyclerView.ViewHolder {
                public CallLogListSingleItemBinding binding;

                public ViewHolder(@NonNull CallLogListSingleItemBinding binding) {
                super(binding.getRoot());
                this.binding = binding;
                }
                }

                private static DiffUtil.ItemCallback<CallLogItem> DIFF_CALLBACK =
                new DiffUtil.ItemCallback<CallLogItem>() {
                @Override
                public boolean areItemsTheSame(CallLogItem oldItem, CallLogItem newItem) {
                return oldItem.getHeaderDateVisibility() == newItem.getHeaderDateVisibility()
                && oldItem.getCallId()!=null && oldItem.getCallId().equals(newItem.getCallId());
                }

                @Override
                public boolean areContentsTheSame(@NonNull CallLogItem oldItem, @NonNull CallLogItem newItem) {
                return areItemsTheSame(oldItem, newItem);
                }
                };
                }



                Modified Data passing to adapter




                CallLogListViewModel model = ViewModelProviders.of(this).get(CallLogListViewModel.class);
                model.getCallLogList().observe(this, adapter::submitList);






                share|improve this answer












                share|improve this answer



                share|improve this answer










                answered Dec 2 '18 at 7:38









                IftaIfta

                19339




                19339






























                    draft saved

                    draft discarded




















































                    Thanks for contributing an answer to Stack Overflow!


                    • Please be sure to answer the question. Provide details and share your research!

                    But avoid



                    • Asking for help, clarification, or responding to other answers.

                    • Making statements based on opinion; back them up with references or personal experience.


                    To learn more, see our tips on writing great answers.




                    draft saved


                    draft discarded














                    StackExchange.ready(
                    function () {
                    StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53297726%2ffailing-to-load-next-data-with-android-paging-library%23new-answer', 'question_page');
                    }
                    );

                    Post as a guest















                    Required, but never shown





















































                    Required, but never shown














                    Required, but never shown












                    Required, but never shown







                    Required, but never shown

































                    Required, but never shown














                    Required, but never shown












                    Required, but never shown







                    Required, but never shown







                    Popular posts from this blog

                    Xamarin.iOS Cant Deploy on Iphone

                    Glorious Revolution

                    Dulmage-Mendelsohn matrix decomposition in Python