I am trying to implement Endless Infinite Scrolling with RecyclerView, but I am only getting first 10 records, not getting next 10 records and even not getting any progress while trying to scroll at bottom.
Whereas I was suppose to get next 10 records on scroll and so on... But getting only first 10 records
Here I have uploaded copy of my JSON - But i am not able to fetch data from same url, that's why i am using client's url and local host.
I am following this tutorial
Here is my complete code, May I know where I am doing mistake ?
JSON :
{ "names": [ { "name": "Name 1" }, { "name": "Name 2" }, .... { "name": "Name 60" } ] }
Log:
D/name -(13759): Name 1 D/name -(13759): Name 2 ....................... D/name -(13759): Name 60
Here is my updated code, which i am using to parse JSON data
MainActivity.java: UPDATED
public class MainActivity extends AppCompatActivity { private Toolbar toolbar; private TextView tvEmptyView; private RecyclerView mRecyclerView; private DataAdapter mAdapter; private LinearLayoutManager mLayoutManager; private ArrayList<Student> studentList; protected Handler handler; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); toolbar = (Toolbar) findViewById(R.id.toolbar); tvEmptyView = (TextView) findViewById(R.id.empty_view); mRecyclerView = (RecyclerView) findViewById(R.id.my_recycler_view); studentList = new ArrayList<Student>(); handler = new Handler(); if (toolbar != null) { setSupportActionBar(toolbar); getSupportActionBar().setTitle("Android Students"); } loadData(); } // load initial data private void loadData() { new Parser().execute("http://10.0.2.2/jsons/mytest.txt"); } class Parser extends AsyncTask<String, Void, Boolean> { ProgressDialog dialog; @Override protected void onPreExecute() { super.onPreExecute(); dialog = new ProgressDialog(MainActivity.this); dialog.show(); dialog.setCancelable(false); } @Override protected Boolean doInBackground(String... urls) { try { //------------------>> HttpGet httppost = new HttpGet(urls[0]); HttpClient httpclient = new DefaultHttpClient(); HttpResponse response = httpclient.execute(httppost); // StatusLine stat = response.getStatusLine(); int status = response.getStatusLine().getStatusCode(); if (status == 200) { HttpEntity entity = response.getEntity(); String data = EntityUtils.toString(entity); JSONObject jsono = new JSONObject(data); JSONArray jarray = jsono.getJSONArray("names"); for (int i = 0; i < jarray.length(); i++) { JSONObject object = jarray.getJSONObject(i); Student actor = new Student(); actor.setName(object.getString("name")); Log.d("name - ", object.getString("name")); studentList.add(actor); } Log.d("MainActivity:StudentList ", "The size "+studentList.size()); return true; } //------------------>> } catch (ParseException e1) { e1.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } catch (JSONException e) { e.printStackTrace(); } return false; } protected void onPostExecute(Boolean result) { dialog.cancel(); Log.d("MainActivity:StudentList ", "The size "+studentList.size()); ArrayList< Student > temArray = new ArrayList< Student >(studentList.subList(0, 10)); mAdapter = new DataAdapter(temArray, mRecyclerView); Log.d("MainActivity:TempList ", "The size "+temArray.size()); // set the adapter object to the Recyclerview mRecyclerView.setAdapter(mAdapter); // use this setting to improve performance if you know that changes // in content do not change the layout size of the RecyclerView mRecyclerView.setHasFixedSize(true); mLayoutManager = new LinearLayoutManager(MainActivity.this); // use a linear layout manager mRecyclerView.setLayoutManager(mLayoutManager); if (studentList.isEmpty()) { mRecyclerView.setVisibility(View.GONE); tvEmptyView.setVisibility(View.VISIBLE); } else { mRecyclerView.setVisibility(View.VISIBLE); tvEmptyView.setVisibility(View.GONE); } mAdapter.setOnLoadMoreListener(new OnLoadMoreListener() { @Override public void onLoadMore() { //add null , so the adapter will check view_type and show progress bar at bottom studentList.add(null); mAdapter.notifyItemInserted(studentList.size() - 1); handler.postDelayed(new Runnable() { @Override public void run() { // remove progress item studentList.remove(studentList.size() - 1); mAdapter.notifyItemRemoved(studentList.size()); //add items one by one int start = studentList.size(); int end = start + 10; for (int i = start + 1; i < end; i++) { mAdapter.notifyItemInserted(studentList.size()); } mAdapter.setLoaded(); //or you can add all at once but do not forget to call mAdapter.notifyDataSetChanged(); } }, 2000); } }); } } }
DataAdapter.java:
public class DataAdapter extends RecyclerView.Adapter { private final int VIEW_ITEM = 1; private final int VIEW_PROG = 0; private List<Student> studentList; // The minimum amount of items to have below your current scroll position // before loading more. private int visibleThreshold = 5; private int lastVisibleItem, totalItemCount; private boolean loading; private OnLoadMoreListener onLoadMoreListener; public DataAdapter(List<Student> students, RecyclerView recyclerView) { studentList = students; if (recyclerView.getLayoutManager() instanceof LinearLayoutManager) { final LinearLayoutManager linearLayoutManager = (LinearLayoutManager) recyclerView .getLayoutManager(); recyclerView .addOnScrollListener(new RecyclerView.OnScrollListener() { @Override public void onScrolled(RecyclerView recyclerView, int dx, int dy) { super.onScrolled(recyclerView, dx, dy); totalItemCount = linearLayoutManager.getItemCount(); lastVisibleItem = linearLayoutManager .findLastVisibleItemPosition(); if (!loading && totalItemCount <= (lastVisibleItem + visibleThreshold)) { // End has been reached // Do something if (onLoadMoreListener != null) { onLoadMoreListener.onLoadMore(); } loading = true; } } }); } } @Override public int getItemViewType(int position) { return studentList.get(position) != null ? VIEW_ITEM : VIEW_PROG; } @Override public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) { RecyclerView.ViewHolder vh; if (viewType == VIEW_ITEM) { View v = LayoutInflater.from(parent.getContext()).inflate( R.layout.list_row, parent, false); vh = new StudentViewHolder(v); } else { View v = LayoutInflater.from(parent.getContext()).inflate( R.layout.progress_item, parent, false); vh = new ProgressViewHolder(v); } return vh; } @Override public void onBindViewHolder(RecyclerView.ViewHolder holder, int position) { if (holder instanceof StudentViewHolder) { Student singleStudent= (Student) studentList.get(position); ((StudentViewHolder) holder).tvName.setText(singleStudent.getName()); ((StudentViewHolder) holder).student= singleStudent; } else { ((ProgressViewHolder) holder).progressBar.setIndeterminate(true); } } public void setLoaded() { loading = false; } @Override public int getItemCount() { return studentList.size(); } public void setOnLoadMoreListener(OnLoadMoreListener onLoadMoreListener) { this.onLoadMoreListener = onLoadMoreListener; } // public static class StudentViewHolder extends RecyclerView.ViewHolder { public TextView tvName; public Student student; public StudentViewHolder(View v) { super(v); tvName = (TextView) v.findViewById(R.id.tvName); v.setOnClickListener(new OnClickListener() { @Override public void onClick(View v) { Toast.makeText(v.getContext(), "OnClick :" + student.getName(), Toast.LENGTH_SHORT).show(); } }); } } public static class ProgressViewHolder extends RecyclerView.ViewHolder { public ProgressBar progressBar; public ProgressViewHolder(View v) { super(v); progressBar = (ProgressBar) v.findViewById(R.id.progressBar1); } } }
OnLoadMoreListener.java:
public interface OnLoadMoreListener { void onLoadMore(); }
I had the same issue once an I solve it using this code ... First .. create this class
public abstract class EndlessOnScrollListener extends OnScrollListener { public static String TAG = EndlessOnScrollListener.class.getSimpleName(); // use your LayoutManager instead private LinearLayoutManager llm; public EndlessOnScrollListener(LinearLayoutManager sglm) { this.lm = llm; } @Override public void onScrolled(RecyclerView recyclerView, int dx, int dy) { super.onScrolled(recyclerView, dx, dy); if (!recyclerView.canScrollVertically(1)) { onScrolledToEnd(); } } public abstract void onScrolledToEnd(); }
Second .. in you activity use this
recyclerView.addOnScrollListener(new EndlessOnScrollListener() { @Override public void onScrolledToEnd() { if (!loading) { loading = true; // add 10 by 10 to tempList then notify changing in data } loading = false; } });
This works for me .... I hope it works for you to.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With