android九宫格可分页加载控件

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/qq_31433525/article/details/82252232

这里写图片描述
github地址
基本思路是viewpager+gridview,每一页viewpager视图有一个gridview,gridview加载九格。所以要保证数据的准确性。数据以List< List < T>>的形式。控件实现了高度自适应,根据控件的个数,计算控件的高度。内部的viewpager和gridview视图都以动态创建,无需新建一个xml文件,整个控件只需要一个item的布局文件。
使用方法
使用时可以先请求一个接口,需初始化数据,数据初始化需要根据总个数初始化所有数据,在每次分页加载的时候,再通过请求当页的数据,更改数据,刷新页面。

  viewPager = findViewById(R.id.ninePages);
       //数据初始化
        List<List<TestEntity>> lists = new ArrayList<>();
        for (int i = 0; i < 6; i++) {//页数
            List<TestEntity> list1 = new ArrayList<>();
            for (int j = 0; j < 9; j++) {//每页个数
                TestEntity entity = new TestEntity();
                entity.setText("j=" + j + "/i=" + i);
                list1.add(entity);
            }
            lists.add(list1);
        }
        //设置不每页重复加载
        viewPager.setEveryRequest(false);
        //设置分页加载
        viewPager.setPagingLoad(true);
        viewPager.setListener(new RequestDataListener<TestEntity>() {
            @Override
            public void request(int position) {//分页加载
                List<TestEntity> changeList =new ArrayList<>();
                for (int i = 0; i < 9; i++) {
                    TestEntity testEntity = new TestEntity();
                    testEntity.setText("change" + i);
                    changeList.add(testEntity);
                }
                //数据刷新
                viewPager.dataInvalidate(position,changeList);
            }

            @Override
            public int gridViewColumn() {//gridview列数
                return 3;
            }

            @Override
            public View getView(LayoutInflater inflater, int position, View convertView, ViewGroup parent, List<TestEntity> list) {
                ViewHolder viewHolder  = null;
                if(convertView == null){
                    convertView = inflater.inflate(R.layout.item_gridview,parent,false);
                    viewHolder = new ViewHolder();
                    viewHolder.textView = convertView.findViewById(R.id.textview);
                    convertView.setTag(viewHolder);
                }else{
                    viewHolder = (ViewHolder) convertView.getTag();
                }
                viewHolder.textView.setText(list.get(position).getText());
                return convertView;
            }
        });
         viewPager.setList(lists);
class ViewHolder{
        private TextView textView;
    }

注意:viewPager.setList(lists);要在最后调用
视图控件:

public class NinePagesPagination<T> extends LinearLayout {
    private View mView;
    private ViewPager viewPager;
    private Context context;
    private List<List<T>> list = new ArrayList<>();
    //已经请求过的,不在重复请求
    private List<Integer> hasAdded = new ArrayList<>();
    //是否每次请求
    private boolean isEveryRequest;
    //是否进行分页加载
    private boolean isPagingLoad;
    private RequestDataListener listener;
    private MyViewPagerAdapter adapter;
    private ViewPager.OnPageChangeListener pageChangeListener;
    public NinePagesPagination(Context context, @Nullable AttributeSet attrs) {
        super(context, attrs);
        this.context = context;
        viewPager = new ViewPager(context);
        LayoutParams params = new LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT);
        viewPager.setLayoutParams(params);
        mView = viewPager;
        addView(mView);
    }

    @Override
    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
        super.onMeasure(widthMeasureSpec, heightMeasureSpec);
        if(listener!=null && listener.gridViewColumn() != 0){
            int column = listener.gridViewColumn();
            int row = (int) Math.ceil((double) list.get(0).size()/column);
            int heightMeasureSpec2 = MeasureSpec.makeMeasureSpec(row*getWidth()/column,
                    MeasureSpec.AT_MOST);
            setMeasuredDimension(widthMeasureSpec,heightMeasureSpec2);
        }
    }

    public void setListener(RequestDataListener listener) {
        this.listener = listener;
    }

    public void setPageChangeListener(ViewPager.OnPageChangeListener pageChangeListener) {
        this.pageChangeListener = pageChangeListener;
    }

    public void setEveryRequest(boolean everyRequest) {
        isEveryRequest = everyRequest;
    }

    public void setPagingLoad(boolean pagingLoad) {
        isPagingLoad = pagingLoad;
    }

    public void setList(List<List<T>> list) {
        this.list = list;
        initView();
        invalidate();
    }

    private void initView() {
        adapter = new MyViewPagerAdapter(context, list,listener);
        viewPager.setAdapter(adapter);
        viewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() {
            @Override
            public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
                if(pageChangeListener != null){
                    pageChangeListener.onPageScrolled(position,positionOffset,positionOffsetPixels);
                }
            }

            @Override
            public void onPageSelected(int position) {
                if(pageChangeListener != null){
                    pageChangeListener.onPageSelected(position);
                }
                if (isPagingLoad) {//分页加载
                    if (isEveryRequest) {//每次都请求
                        adapter.setCurrentPosition(position);
                        listener.request(position);
                    } else {//请求过一次将不在重复请求
                        if (!hasAdded.contains(position)) {
                            hasAdded.add(position);
                            adapter.setCurrentPosition(position);
                            listener.request(position);
                        }
                    }
                }
            }


            @Override
            public void onPageScrollStateChanged(int state) {
                if(pageChangeListener != null){
                    pageChangeListener.onPageScrollStateChanged(state);
                }
            }
        });
    }
    //数据刷新
    public void dataInvalidate(int position,List<T> changeList){
        list.set(position, changeList);
        adapter.notifyDataSetChanged();
    }
}

viewpager适配器:

public class MyViewPagerAdapter<T> extends PagerAdapter {
    private Context context;
    private List<List<T>> list;
    private LayoutInflater inflater;
    private MyGridViewAdapter adapter;
    private int currentPosition;
    private RequestDataListener listener;
    public MyViewPagerAdapter(Context context, List<List<T>> list,RequestDataListener listener) {
        this.context = context;
        this.list = list;
        this.listener = listener;
        inflater = LayoutInflater.from(context);
    }

    @Override
    public int getCount() {
        return list.size();
    }

    @Override
    public boolean isViewFromObject(@NonNull View view, @NonNull Object object) {
        return view == object;
    }

    @NonNull
    @Override
    public Object instantiateItem(@NonNull ViewGroup container, int position) {
        GridView view = new GridView(context);
        ViewGroup.LayoutParams params = new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT);
        view.setLayoutParams(params);
        view.setTag(position);
        if(listener!=null && listener.gridViewColumn() != 0){
            view.setNumColumns(listener.gridViewColumn());
        }
        adapter = new MyGridViewAdapter(context, list.get(position),listener);
        view.setAdapter(adapter);
        container.addView(view);
        return view;
    }

    @Override
    public void destroyItem(@NonNull ViewGroup container, int position, @NonNull Object object) {
        container.removeView((View) object);
    }

    @Override
    public int getItemPosition(@NonNull Object object) {
        //viewpager立即刷新页面
        if (list != null && list.size() == 0) {
            return POSITION_NONE;
        }
        View view = (View) object;
        if (currentPosition == (Integer) view.getTag()) {
            return POSITION_NONE;
        } else {
            return POSITION_UNCHANGED;
        }
    }

    @Override
    public void notifyDataSetChanged() {
        super.notifyDataSetChanged();
        if(adapter != null){
            adapter.notifyDataSetChanged();
        }
    }

    public void setCurrentPosition(int currentPosition) {
        this.currentPosition = currentPosition;
    }
}

gridview适配器

public class MyGridViewAdapter<T> extends BaseAdapter{
    private Context context;
    private List<T> list;
    private LayoutInflater inflater;
    private RequestDataListener listener;
    public MyGridViewAdapter(Context context, List<T> list,RequestDataListener listener){
        this.context = context;
        this.list = list;
        this.listener = listener;
        inflater = LayoutInflater.from(context);
    }
    @Override
    public int getCount() {
        return list.size();
    }

    @Override
    public Object getItem(int position) {
        return list.get(position);
    }

    @Override
    public long getItemId(int position) {
        return position;
    }

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        convertView = listener.getView(inflater,position,convertView,parent,list);
        int width;
        //计算item的宽
        if(listener != null &listener.gridViewColumn() != 0){
             width = parent.getWidth()/listener.gridViewColumn();
        }else{
             width = parent.getWidth()/3;
        }
        //设置item的宽高相等
        convertView.setLayoutParams(new AbsListView.LayoutParams(width,width));
        return convertView;
    }
}

暴露的接口

public interface RequestDataListener<T> {
   void request(int position);
    //gridView列数
    int gridViewColumn();
    View getView(LayoutInflater inflater, int position, View convertView, ViewGroup parent, List<T> list);
}

猜你喜欢

转载自blog.csdn.net/qq_31433525/article/details/82252232