How to implement load more recyclerview in android

前端 未结 8 1740
盖世英雄少女心
盖世英雄少女心 2020-12-30 06:23

I want to implement load more in Recyclerview. Here is the code. The code is from github. https://gist.github.com/ssinss/e06f12ef66c51252563e

MainActivity code:

相关标签:
8条回答
  • 2020-12-30 06:36

    I found an answer here that, I believe, is much better than most I've seen on SO and elsewhere.

    The idea is simple: in onScrolled in your RecyclerView's ScrollListener, check if the last completely visible item is the last item in your data set.

            if(llm.findLastCompletelyVisibleItemPosition() == data.length() -1){
                //bottom of list!
                loadMoreData();
            }
    

    This happens with a method in the LinearLayoutManager. Calling LinearLayoutManager#findLastCompletelyVisibleItemPosition() can comparing it to the position of the last item in your dataset let's you know when you can load more.

    I haven't tried this for the GridLayoutManager.

    UPDATE

    LinearLayoutManager#findLastVisibleItemPosition() is a better alternative to LinearLayoutManager#findLastCompletelyVisibleItemPosition(), especially when your items are longer than the window height.

    0 讨论(0)
  • 2020-12-30 06:43

    Check do you currently have items to scroll down -

    if (! recyclerView.canScrollVertically(1))
    

    If yes - load more items, for example, using HTTP client.

    Full code:

    recyclerView.addOnScrollListener(new RecyclerView.OnScrollListener() {
                @Override
                public void onScrolled(@NonNull RecyclerView recyclerView, int dx, int dy) {
                    super.onScrolled(recyclerView, dx, dy);
                    if (! recyclerView.canScrollVertically(1)){ //1 for down
                        loadMore();
                    }
                }
            });
    
    0 讨论(0)
  • 2020-12-30 06:43
    public abstract class LoadMoreAdapter extends RecyclerView.Adapter{
    private LoadMoreListner loadMoreListner;
    private boolean isLoading;
    int vissibleThreshold = 5;
    
    public LoadMoreAdapter(final LoadMoreListner loadMoreListner, RecyclerView recyclerView) {
        this.loadMoreListner = loadMoreListner;
        final LinearLayoutManager linearLayoutManager = (LinearLayoutManager) recyclerView.getLayoutManager();
        recyclerView.addOnScrollListener(new RecyclerView.OnScrollListener() {
            @Override
            public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
                super.onScrollStateChanged(recyclerView, newState);
            }
    
            @Override
            public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
                super.onScrolled(recyclerView, dx, dy);
                int totalItemCOunt = linearLayoutManager.getItemCount();
                int lastVissibleItemPOs = linearLayoutManager.findLastVisibleItemPosition();
                if (!isLoading && totalItemCOunt<= lastVissibleItemPOs+vissibleThreshold){
                    if (loadMoreListner!=null){
                        isLoading = true;
                        loadMoreListner.onLoadMore();
                    }
                }
            }
        });
    }
    public void setLoaded(){
        isLoading =false;
    }
    

    }

    Your adapter will extends to this LoadmoreAdapter

    public interface LoadMoreListner {
    void onLoadMore();
    

    }

    And in your activity

    @Override
    public void onLoadMore() {
        items.add(null);
        nameLoadMoreAdapter.notifyItemInserted(items.size()-1);
        loadNewData();
    }
    

    After populating list and here your loadnewData() will have this

    items.remove(items.size()-1);
                nameLoadMoreAdapter.notifyItemRemoved(items.size());
                items.addAll(itemsArrayList);
                nameLoadMoreAdapter.notifyItemInserted(items.size());
                nameLoadMoreAdapter.setLoaded();
    

    where itemsArrayList are of newdata

    0 讨论(0)
  • 2020-12-30 06:43

    You can check this link for Load More RecyclerView and Bottom ProgressBar.

    0 讨论(0)
  • 2020-12-30 06:45

    I have created a commonAdapter to handle loadMore

    public abstract class CommonModelAdapter<T,V extends BaseModelViewHolder<T>> extends RecyclerView.Adapter<V>{
    
        public abstract V setViewHolder(ViewGroup parent);
    
        private Context mContext;
        private List<T> items;
        private List<T> copyItems;
    
        public static final int VIEW_TYPE_PROGRESS = 0;
        public static final int VIEW_TYPE_ITEM = 1;
    
        public CommonModelAdapter(Context mContext,List<T> items){
            this.mContext = mContext;
            this.items = items;
            copyItems = new ArrayList<>();
            copyItems.addAll(items);
        }
    
        @Override
        public V onCreateViewHolder(ViewGroup parent, int viewType) {
            if(viewType == VIEW_TYPE_ITEM){
                return setViewHolder(parent);
            }
            else{
                return (V) new ProgressViewHolder(parent ,R.layout.item_progress_loader);
            }
        }
    
        @Override
        public void onBindViewHolder(V holder, int position) {
            if (holder instanceof ProgressViewHolder) {
                ((ProgressViewHolder) holder).showProgressLoader();
            }
            else{
                try {
                    holder.onBindData(items.get(position));
                } catch (Exception e) {
                    e.printStackTrace();
                }
            }
        }
    
        @Override
        public int getItemCount() {
            return items.size();
        }
    
        @Override
        public int getItemViewType(int position) {
            if(items.get(position) == null)
                return VIEW_TYPE_PROGRESS;
            else
                return VIEW_TYPE_ITEM;
        }
    
        public T getItemAt(int position){
            return items.get(position);
        }
    
        public void setItems(List<T> newItems){
            this.items = newItems;
        }
    }
    

    Where BaseModelViewHolder

    public abstract class BaseModelViewHolder<T extends BaseModelBO> extends RecyclerView.ViewHolder {
    
        public abstract void onBindData(T data);
    
        public BaseModelViewHolder(ViewGroup parent, int layoutId) {
            super(LayoutInflater.from(parent.getContext()).inflate(layoutId, parent, false));
        }
    
        public <T extends View> T findViewById(@IdRes int resId) {
            return (T) itemView.findViewById(resId);
        }
    }
    

    LoadMoreRecyclerView

    public class LoadMoreRecyclerView extends RecyclerView  {
    
        private boolean loading = true;
        int pastVisiblesItems, visibleItemCount, totalItemCount;
        //WrapperLinearLayout is for handling crash in RecyclerView
        private WrapperLinearLayout mLayoutManager;
        private Context mContext;
        private OnLoadMoreListener onLoadMoreListener;
    
        public LoadMoreRecyclerView(Context context) {
            super(context);
            mContext = context;
            init();
        }
    
        public LoadMoreRecyclerView(Context context, @Nullable AttributeSet attrs) {
            super(context, attrs);
            mContext = context;
            init();
        }
    
        public LoadMoreRecyclerView(Context context, @Nullable AttributeSet attrs, int defStyle) {
            super(context, attrs, defStyle);
            mContext = context;
            init();
        }
    
        private void init(){
            mLayoutManager = new WrapperLinearLayout(mContext,LinearLayoutManager.VERTICAL,false);
            this.setLayoutManager(mLayoutManager);
            this.setItemAnimator(new DefaultItemAnimator());
            this.setHasFixedSize(true);
        }
    
        @Override
        public void onScrolled(int dx, int dy) {
            super.onScrolled(dx, dy);
    
            if(dy > 0) //check for scroll down
            {
                visibleItemCount = mLayoutManager.getChildCount();
                totalItemCount = mLayoutManager.getItemCount();
                pastVisiblesItems = mLayoutManager.findFirstVisibleItemPosition();
    
                if (loading)
                {
                    if ( (visibleItemCount + pastVisiblesItems) >= totalItemCount)
                    {
                        loading = false;
                        Log.v("...", "Call Load More !");
                        if(onLoadMoreListener != null){
                            onLoadMoreListener.onLoadMore();
                        }
                        //Do pagination.. i.e. fetch new data
                    }
                }
            }
        }
    
        @Override
        public void onScrollStateChanged(int state) {
            super.onScrollStateChanged(state);
        }
    
        public void enableLoadingMore(boolean moreLoading){
            loading = moreLoading;
        }
    
        public void setOnLoadMoreListener(OnLoadMoreListener onLoadMoreListener) {
            this.onLoadMoreListener = onLoadMoreListener;
        }
    
        public void setScrolling(boolean enable){
            mLayoutManager.setScrollEnabled(enable);
        }
    }
    

    When you want to show progress...

     mLoadMoreRecyclerView.setOnLoadMoreListener(new OnLoadMoreListener() {
            @Override
            public void onLoadMore() {
    
                {
                    overAllItems.add(null); //to show ProgressDialog
                    mAdapter.notifyDataSetChanged();
    
                    callYourService();
                }
                /*else{
                    //for reEnable calling it...
                    mLoadMoreRecyclerView.enableLoadingMore(true);
                }*/
    
            }
        });
    
    0 讨论(0)
  • 2020-12-30 06:52
    import android.support.v7.widget.OrientationHelper;
    import android.support.v7.widget.RecyclerView;
    import android.view.View;
    
    /**
     * Created by CRAFT BOX on 9/7/2016.
     */
    public class RecyclerViewPositionHelper {
    
        final RecyclerView recyclerView;
        final RecyclerView.LayoutManager layoutManager;
    
        RecyclerViewPositionHelper(RecyclerView recyclerView) {
            this.recyclerView = recyclerView;
            this.layoutManager = recyclerView.getLayoutManager();
        }
    
        public static RecyclerViewPositionHelper createHelper(RecyclerView recyclerView) {
            if (recyclerView == null) {
                throw new NullPointerException("Recycler View is null");
            }
            return new RecyclerViewPositionHelper(recyclerView);
        }
    
        /**
         * Returns the adapter item count.
         *
         * @return The total number on items in a layout manager
         */
        public int getItemCount() {
            return layoutManager == null ? 0 : layoutManager.getItemCount();
        }
    
        /**
         * Returns the adapter position of the first visible view. This position does not include
         * adapter changes that were dispatched after the last layout pass.
         *
         * @return The adapter position of the first visible item or {@link RecyclerView#NO_POSITION} if
         * there aren't any visible items.
         */
        public int findFirstVisibleItemPosition() {
            final View child = findOneVisibleChild(0, layoutManager.getChildCount(), false, true);
            return child == null ? RecyclerView.NO_POSITION : recyclerView.getChildAdapterPosition(child);
        }
    
        /**
         * Returns the adapter position of the first fully visible view. This position does not include
         * adapter changes that were dispatched after the last layout pass.
         *
         * @return The adapter position of the first fully visible item or
         * {@link RecyclerView#NO_POSITION} if there aren't any visible items.
         */
        public int findFirstCompletelyVisibleItemPosition() {
            final View child = findOneVisibleChild(0, layoutManager.getChildCount(), true, false);
            return child == null ? RecyclerView.NO_POSITION : recyclerView.getChildAdapterPosition(child);
        }
    
        /**
         * Returns the adapter position of the last visible view. This position does not include
         * adapter changes that were dispatched after the last layout pass.
         *
         * @return The adapter position of the last visible view or {@link RecyclerView#NO_POSITION} if
         * there aren't any visible items
         */
        public int findLastVisibleItemPosition() {
            final View child = findOneVisibleChild(layoutManager.getChildCount() - 1, -1, false, true);
            return child == null ? RecyclerView.NO_POSITION : recyclerView.getChildAdapterPosition(child);
        }
    
        /**
         * Returns the adapter position of the last fully visible view. This position does not include
         * adapter changes that were dispatched after the last layout pass.
         *
         * @return The adapter position of the last fully visible view or
         * {@link RecyclerView#NO_POSITION} if there aren't any visible items.
         */
        public int findLastCompletelyVisibleItemPosition() {
            final View child = findOneVisibleChild(layoutManager.getChildCount() - 1, -1, true, false);
            return child == null ? RecyclerView.NO_POSITION : recyclerView.getChildAdapterPosition(child);
        }
    
        View findOneVisibleChild(int fromIndex, int toIndex, boolean completelyVisible,
                                 boolean acceptPartiallyVisible) {
            OrientationHelper helper;
            if (layoutManager.canScrollVertically()) {
                helper = OrientationHelper.createVerticalHelper(layoutManager);
            } else {
                helper = OrientationHelper.createHorizontalHelper(layoutManager);
            }
    
            final int start = helper.getStartAfterPadding();
            final int end = helper.getEndAfterPadding();
            final int next = toIndex > fromIndex ? 1 : -1;
            View partiallyVisible = null;
            for (int i = fromIndex; i != toIndex; i += next) {
                final View child = layoutManager.getChildAt(i);
                final int childStart = helper.getDecoratedStart(child);
                final int childEnd = helper.getDecoratedEnd(child);
                if (childStart < end && childEnd > start) {
                    if (completelyVisible) {
                        if (childStart >= start && childEnd <= end) {
                            return child;
                        } else if (acceptPartiallyVisible && partiallyVisible == null) {
                            partiallyVisible = child;
                        }
                    } else {
                        return child;
                    }
                }
            }
            return partiallyVisible;
        }
    }
    
    /* NearbyModel */
    
    
    
    /**
     * Created by CRAFT BOX on 8/23/2016.
     */
    public class NearbyModel {
    
        public String getId() {
            return id;
        }
    
        public void setId(String id) {
            this.id = id;
        }
    
        public String getName() {
            return name;
        }
    
        public void setName(String name) {
            this.name = name;
        }
    
        public String getRate() {
            return rate;
        }
    
        public void setRate(String rate) {
            this.rate = rate;
        }
        public String getAddress() {
            return address;
        }
    
        public void setAddress(String address) {
            this.address = address;
        }
    
        public String getImage_path() {
            return image_path;
        }
    
        public void setImage_path(String image_path) {
            this.image_path = image_path;
        }
    
        String id;
        String name;
        String rate;
    
        public String getDistance() {
            return distance;
        }
    
        public void setDistance(String distance) {
            this.distance = distance;
        }
    
        String distance;
    
    
        public String getReview() {
            return review;
        }
    
        public void setReview(String review) {
            this.review = review;
        }
    
        String review;
        String address;
    
        public String getCategory_name() {
            return category_name;
        }
    
        public void setCategory_name(String category_name) {
            this.category_name = category_name;
        }
    
        String category_name;
        String image_path;
        public NearbyModel()
        {
    
        }
        public NearbyModel(String id,String name,String rate,String distance,String review,String address,String category_name,String image_path)
        {
            this.id=id;
            this.name=name;
            this.rate=rate;
            this.distance=distance;
            this.review=review;
            this.address=address;
            this.category_name=category_name;
            this.image_path=image_path;
        }
    
    }
    
    
    
     /* My activity */
    
     public class Search_by_shop extends Fragment {
    
    
        private RecyclerView recyclerView;
        ArrayList<NearbyModel> near_data;
        NearAdapter adapter;
    
        int firstVisibleItem, visibleItemCount, totalItemCount,count=0;
        protected int m_PreviousTotalCount;
        RecyclerViewPositionHelper mRecyclerViewHelper;
    
    
         @Override
        public View onCreateView(LayoutInflater inflater, ViewGroup container,Bundle savedInstanceState)
        {
            View rootView = inflater.inflate(R.layout.search_by_shop_fragment, container, false);
            recyclerView = (RecyclerView) rootView.findViewById(R.id.search_by_recycleview);
    
            recyclerView.setOnScrollListener(new RecyclerView.OnScrollListener() {
                @Override
                public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
                    super.onScrollStateChanged(recyclerView, newState);
    
                    mRecyclerViewHelper = RecyclerViewPositionHelper.createHelper(recyclerView);
                    visibleItemCount = recyclerView.getChildCount();
                    totalItemCount = mRecyclerViewHelper.getItemCount();
                    firstVisibleItem = mRecyclerViewHelper.findFirstVisibleItemPosition();
    
                    if (totalItemCount == 0 || adapter == null)
                        return;
                    if (m_PreviousTotalCount == totalItemCount)
                    {
                        return;
                    }
                    else
                    {
                        boolean loadMore = firstVisibleItem + visibleItemCount >= totalItemCount;
                        if (loadMore)
                        {
                            m_PreviousTotalCount = totalItemCount;
                            new GetAllrestaurant().execute();
                        }
                    }
                }
            });
    
            new GetAllrestaurant().execute();
    
            return rootView;
       }
    
       public class GetAllrestaurant extends AsyncTask<String, Void, JSONObject> {
            ProgressDialog pd;
            @Override
            protected void onPreExecute() {
                super.onPreExecute();
                pd = new ProgressDialog(getActivity());
                pd.setTitle("Please Wait");
                pd.setMessage("Loading");
                pd.setCancelable(false);
                pd.show();
            }
    
            @Override
            protected JSONObject doInBackground(String... strings) {
                UserFunction uf = new UserFunction();
                JSONObject json = uf.getAllrestaurunt();
                return json;
            }
    
            @Override
            protected void onPostExecute(JSONObject json) {
                super.onPostExecute(json);
                pd.dismiss();
                try {
                    if (json.getInt("ack") == 1) {
                        JSONArray json_users = json.getJSONArray("result");
                        // looping through All Products
                        for (int i = 0; i < json_users.length(); i++) {
                            JSONObject c = json_users.getJSONObject(i);
                            String id = c.getString("id");
                            String name = c.getString("name");
                            String distance = c.getString("distance");
                            String category = c.getString("serving_category");
                            String rate = c.getString("rate");
                            String address = c.getString("address");
                            String count_review = c.getString("count_review");
                            String image_path = c.getString("image_path");
                            NearbyModel da=new NearbyModel(id,name,rate,distance,count_review,address,category,image_path);
                            near_data.add(da);
                        }
    
                        if(count==0)
                        {
                            adapter = new NearAdapter(getActivity(), near_data);
                            recyclerView.setAdapter(adapter);
                            recyclerView.setLayoutManager(new LinearLayoutManager(getActivity()));
                        }
                        else
                        {
                            adapter.notifyDataSetChanged();
                        }
                        if(json_users.length()==0)
                        {
                            count=0;
                        }
                        else
                        {
                            count+=json_users.length();
                        }
    
                    }
                } catch (Exception e) {
                    Log.e("<-SubjectActException->", e.toString());
                }
            }
        }
    
        public class NearAdapter extends RecyclerView.Adapter<NearAdapter.ViewHolder> {
            private ArrayList<NearbyModel> data;
            private Context context;
            public NearAdapter(Context context,ArrayList<NearbyModel> data) {
                this.data = data;
                this.context = context;
            }
    
            @Override
            public ViewHolder onCreateViewHolder(ViewGroup viewGroup, final int i) {
                View view = LayoutInflater.from(viewGroup.getContext()).inflate(R.layout.list_near_by, viewGroup, false);
                return new ViewHolder(view);
            }
    
            @Override
            public void onBindViewHolder(ViewHolder viewHolder, final int i) {
                viewHolder.name.setText(data.get(i).getName());
                viewHolder.distince.setText(data.get(i).getDistance());
                viewHolder.review.setText(data.get(i).getReview());
                viewHolder.category.setText(data.get(i).getCategory_name());
                viewHolder.address.setText(data.get(i).getAddress());
                viewHolder.rat.setRating(Integer.parseInt(data.get(i).getRate()));
                viewHolder.vi_click.setOnClickListener(new View.OnClickListener() {
                    @Override
                    public void onClick(View v) {
                        GlobalVariable.position=i;
                        Intent ik=new Intent(context,Restaurant_detail.class);
                        ik.putExtra("rid",""+data.get(i).getId());
                        startActivity(ik);
                    }
                });
                if(data.get(i).getImage_path().equals(""))
                {
                    Picasso.with(context).load("abc").placeholder(R.drawable.load_240).into(viewHolder.img);
                }
                else
                {
                    Picasso.with(context).load(data.get(i).getImage_path()).placeholder(R.drawable.load_240).into(viewHolder.img);
                }
            }
    
            @Override
            public int getItemCount() {
                return data.size();
            }
    
            public class ViewHolder extends RecyclerView.ViewHolder{
                private TextView name,distince,review,category,address;
                private ImageView img;
                private RatingBar rat;
                CardView vi_click;
    
                public ViewHolder(View view) {
                    super(view);
                    name = (TextView)view.findViewById(R.id.list_near_by_name);
                    distince = (TextView)view.findViewById(R.id.list_near_by_distince);
                    review = (TextView)view.findViewById(R.id.list_near_by_review);
                    category = (TextView)view.findViewById(R.id.list_near_by_category);
                    address = (TextView)view.findViewById(R.id.list_near_by_address);
                    img = (ImageView) view.findViewById(R.id.list_near_by_img);
                    rat = (RatingBar)view.findViewById(R.id.list_near_by_ratbar);
                    vi_click = (CardView)view.findViewById(R.id.list_near_card);
                }
            }
        }
    
    0 讨论(0)
提交回复
热议问题