在android中的recyclerview中分页

时间:2016-07-20 11:34:28

标签: java android pagination android-recyclerview

我正在尝试在recyclerview中实施分页。 以下是我的java课程:

MyAdapter.java

    package com.example.opinion;

import android.support.v7.widget.RecyclerView;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.TextView;

import java.util.ArrayList;
import java.util.List;


/**
 * Created by manish on 7/18/2016.
 */
public class MyAdapter extends RecyclerView.Adapter<MyAdapter.ViewHolder> {
    private ArrayList<String> movieName = new ArrayList();


    public MyAdapter(ArrayList film)
    {
        this.movieName = film;
    }

    @Override
    public MyAdapter.ViewHolder onCreateViewHolder(ViewGroup parent,
                                                   int viewType) {
        // create a new view
        View v = LayoutInflater.from(parent.getContext()).inflate(R.layout.list_items, null);
        // set the view's size, margins, paddings and layout parameters
        ViewHolder vh = new ViewHolder(v);
        return vh;
    }
    @Override
    public void onBindViewHolder(ViewHolder holder, int position) {
        // - get element from your dataset at this position
        // - replace the contents of the view with that element
        holder.movieText.setText(movieName.get(position));



    }

    // Return the size of your dataset (invoked by the layout manager)
    @Override
    public int getItemCount()
    {
        System.out.print(movieName.size());
        return movieName.size();
    }

    public class ViewHolder extends RecyclerView.ViewHolder {
        // each data item is just a string in this case
        public TextView movieText;

        public ViewHolder(View v) {
            super(v);
            movieText = (TextView) v.findViewById(R.id.movieName);
        }
    }

}

viewfragment.java:这里我正在本地网络上获取数据。在此文件中,loadMore(current_page)函数仅在时间获取3个值。第一次调用它时,这三个值仅在recyclerview内的cardview中可见。我不知道问题出在哪里!

package com.example.opinion;



import java.lang.reflect.Type;
import java.util.ArrayList;
import java.util.List;

import org.w3c.dom.Text;

import android.content.Context;
import android.content.Intent;
import android.content.SharedPreferences;
import android.os.AsyncTask;
import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.util.Log;
import android.view.Gravity;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.content.Intent;
import android.widget.Button;
import android.widget.TextView;
import android.widget.Toast;

import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
import retrofit2.Retrofit;
import retrofit2.converter.gson.GsonConverterFactory;
import retrofit2.http.GET;
import retrofit2.http.Path;


public class ViewFragment extends Fragment {

    private static final String PREFS_NAME = "Prefname";



    public int j =0;
    static String quesText;


    //public static final String BASE_URL = "http://192.168.0.104/";

    public interface PostquesApi{
        @GET("ques/{i}")
        Call<quesGetResponse> quesget(@Path("i") String i);
    }

    static class quesGetResponse {

        String ques1;
        String ques2;
        String ques3;
        String quid1;
        String quid2;
        String quid3;

        public quesGetResponse(String ques1, String ques2, String ques3, String u1, String u2,String u3){
            this.ques1 = ques1;
            this.ques2 = ques2;
            this.ques3 = ques3;
            this.quid1 = u1;
            this.quid2 = u2;
            this.quid3 = u3;
            }
    }
    //View rootView;
    private RecyclerView mRecyclerView;
    private RecyclerView.Adapter mAdapter;

    private ArrayList movieList = new ArrayList();
    private static int current_page = 1;




    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
            Bundle savedInstanceState) {

        final View rootView = inflater.inflate(R.layout.fragment_view, container, false);

        for(int k=0; k<2; k++) {
            loadData(current_page);
        }
        System.out.println("contents of movie list: "+ movieList);

        mRecyclerView = (RecyclerView) rootView.findViewById(R.id.my_recycler_view);

        // 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);

        // use a linear layout manager
        LinearLayoutManager feedLayoutManager = new LinearLayoutManager(getActivity());
        mAdapter = new MyAdapter(movieList);
        mRecyclerView.setAdapter(mAdapter);
        mRecyclerView.setLayoutManager(feedLayoutManager);

        // specify an adapter (see also next example)

        mRecyclerView.addOnScrollListener(new EndlessRecyclerOnScrollListener(
                feedLayoutManager) {
            @Override
            public void onLoadMore(int current_page) {
                // do somthing...

                loadMoreData(current_page);

            }

        });

        /*qt2.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Intent comm = new Intent(getActivity(), Comments.class);
                quesText = qt2.getText().toString();

                //comm.putExtra(quesText, Text );
                startActivity(comm);
            }
        });
        qt3.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Intent comm = new Intent(getActivity(), Comments.class);
                quesText = qt3.getText().toString();

                //comm.putExtra(quesText, Text );
                startActivity(comm);
            }
        });*/

        return rootView;

    }
    public void loadData(int page) {
        // Send an API request to retrieve appropriate data using the offset value as a parameter.
        //  --> Deserialize API response and then construct new objects to append to the adapter
        //  --> Notify the adapter of the changes
        Retrofit retrofit = new Retrofit.Builder()
                .baseUrl(Login.BASE_URL)
                .addConverterFactory(GsonConverterFactory.create())
                .build();

        PostquesApi apiService = retrofit.create(PostquesApi.class);
        Call<quesGetResponse> call = apiService.quesget(Integer.toString(j));
        call.enqueue(new Callback<quesGetResponse>() {
            @Override
            public void onResponse(Call<quesGetResponse> call, Response<quesGetResponse> response) {
                quesGetResponse decodedResponse = response.body();
                if (decodedResponse != null) {
                    if (decodedResponse.ques1 != null && decodedResponse.quid1.compareTo(Login.user_id) != 0)
                    {
                        movieList.add(decodedResponse.ques1);
                    }
                    if (decodedResponse.ques2 != null && decodedResponse.quid2.compareTo(Login.user_id) != 0)
                    {
                        movieList.add(decodedResponse.ques2);
                    }
                    if (decodedResponse.ques3 != null && decodedResponse.quid3.compareTo(Login.user_id) != 0)
                    {
                        movieList.add(decodedResponse.ques3);
                    }
                }

                if (decodedResponse.ques1 == null || decodedResponse.ques2 == null || decodedResponse.ques3 == null) {
                    Context context = getActivity().getApplicationContext();
                    CharSequence text = "Sorry!! no more questions in the database...";
                    int duration = Toast.LENGTH_SHORT;

                    Toast toast = Toast.makeText(context, text, duration);
                    toast.show();
                }

                j = j + 3;
            }

            @Override
            public void onFailure(Call<quesGetResponse> call, Throwable t) {

            }
        });
    }
    private void loadMoreData(int current_page) {

        Retrofit retrofit = new Retrofit.Builder()
                .baseUrl(Login.BASE_URL)
                .addConverterFactory(GsonConverterFactory.create())
                .build();

        PostquesApi apiService = retrofit.create(PostquesApi.class);
        Call<quesGetResponse> call = apiService.quesget(Integer.toString(j));
        call.enqueue(new Callback<quesGetResponse>() {
            @Override
            public void onResponse(Call<quesGetResponse> call, Response<quesGetResponse> response) {
                quesGetResponse decodedResponse = response.body();
                if (decodedResponse != null) {
                    if (decodedResponse.ques1 != null && decodedResponse.quid1.compareTo(Login.user_id) != 0)
                    {
                        movieList.add(decodedResponse.ques1);
                    }
                    if (decodedResponse.ques2 != null && decodedResponse.quid2.compareTo(Login.user_id) != 0)
                    {
                        movieList.add(decodedResponse.ques2);
                    }
                    if (decodedResponse.ques3 != null && decodedResponse.quid3.compareTo(Login.user_id) != 0)
                    {
                        movieList.add(decodedResponse.ques3);
                    }
                }

                if (decodedResponse.ques1 == null || decodedResponse.ques2 == null || decodedResponse.ques3 == null) {
                    Context context = getActivity().getApplicationContext();
                    CharSequence text = "Sorry!! no more questions in the database...";
                    int duration = Toast.LENGTH_SHORT;

                    Toast toast = Toast.makeText(context, text, duration);
                    toast.show();
                }

                j = j + 3;
            }

            @Override
            public void onFailure(Call<quesGetResponse> call, Throwable t) {

            }
        });



        mAdapter.notifyDataSetChanged();

    }

}

EndlessRecyclerOnScrollListener.java:实现分页逻辑的文件。

package com.example.opinion;

import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;

/**
 * Created by manish on 7/20/2016.
 */

public abstract class EndlessRecyclerOnScrollListener extends
        RecyclerView.OnScrollListener {
    public static String TAG = EndlessRecyclerOnScrollListener.class
            .getSimpleName();

    private int previousTotal = 0;
    private boolean loading = true;
    private int visibleThreshold = 3;
    int firstVisibleItem, visibleItemCount, totalItemCount;

    private int current_page = 1;

    private LinearLayoutManager mLinearLayoutManager;

    public EndlessRecyclerOnScrollListener(
            LinearLayoutManager linearLayoutManager) {
        this.mLinearLayoutManager = linearLayoutManager;
    }

    @Override
    public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
        super.onScrolled(recyclerView, dx, dy);

        visibleItemCount = recyclerView.getChildCount();
        totalItemCount = mLinearLayoutManager.getItemCount();
        firstVisibleItem = mLinearLayoutManager.findFirstVisibleItemPosition();

        if (loading) {
            if (totalItemCount > previousTotal) {
                loading = false;
                previousTotal = totalItemCount;
            }
        }
        if (!loading
                && (totalItemCount - visibleItemCount) <= (firstVisibleItem + visibleThreshold)) {
            // End has been reached

            // Do something
            current_page++;

            onLoadMore(current_page);

            loading = true;
        }
    }

    public abstract void onLoadMore(int current_page);
}

如果有人可以查看并告诉我上述文件中所需的更正,或者可以将我引导到某些资源,我们将非常感激。

1 个答案:

答案 0 :(得分:2)

我建议您不要使用EndlessRecyclerOnScrollListener类并听取Recyclerview的滚动事件,您应该在MyAdapter类中观看。

<强> 1 即可。首先添加一个界面

public interface GetNewDataEvents {
        void getNewAdapterData();
    }

<强> 2 即可。在MyAdapter类中初始化该接口,通过实现它来添加数据。

第3 即可。您可以在bindViewHolder中轻松找到当前正在加载的项目 使用

if(position==(movieName.size()-1)

在其中您可以轻松调用该接口方法并在其中加载新数据。

这件事表示当前正在加载第二个项目,你应该添加新数据。

如果您获得了新数据,您可以轻松地将其加载到适配器中并使用它来调用notifyItemRangeChanged以获得性能并实现最佳实践,方法是不加载整个适配器,只更改少量项目。

如果你想参考它,你可以去here