融合了A~Z快速索引和侧滑菜单的ListVeiw的demo

本demo技术要点

  • 自定义快速索引控件
  • ViewPager有效的禁止左右滑动
  • Fragment抽取懒加载基类,且只加载一次
  • 感谢开源库SwipeMenuListView

效果图

效果图

快速索引控件.

package cn.evun.view;

import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Rect;
import android.util.AttributeSet;
import android.view.MotionEvent;
import android.view.View;

import cn.evun.javebean.Cheeses;

/**
 * 自定义快速索引
 */
public class QuickIndexBar extends View {

    private Paint paint;
    private float cellWidth;
    private float cellHeight;

    public QuickIndexBar(Context context, AttributeSet attrs) {
        super(context, attrs);
        init();
    }

    private void init() {
        paint = new Paint();
        paint.setColor(Color.GRAY);
        paint.setTextSize(30);
    }

    @Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);
//      canvas.drawText("#",10f,20f,paint);
//      canvas.drawText("#",10f,50f,paint);
//      canvas.drawText("#",10f,80f,paint);
//      canvas.drawText("#",10f,110f,paint);
//      canvas.drawText("#",10f,140f,paint);
        for (int i = 0; i < Cheeses.LETTERS.length; i++) {
            String letter = Cheeses.LETTERS[i];
            Rect rect = new Rect();
            //获取不同的字母的宽高
            //将字母放入一个矩形容器中,矩形容器的宽高就是字母的宽高
            //获取文字边界
            paint.getTextBounds(letter, 0, 1, rect);
            //矩形的宽高就是文本的宽高
            int textWidth = rect.width();
            int textHeight = rect.height();
            float x = cellWidth * 0.5f - textWidth * 0.5f;
            float y = cellHeight * 0.5f + textHeight * 0.5f + i * cellHeight;
            canvas.drawText(letter, x, y, paint);
        }

    }

    //获取cellWidth和cellHeight
    @Override
    protected void onSizeChanged(int w, int h, int oldw, int oldh) {
        super.onSizeChanged(w, h, oldw, oldh);
        //获取当前控件的测量宽高
        cellWidth = this.getMeasuredWidth();
        cellHeight = this.getMeasuredHeight() * 1.0f / Cheeses.LETTERS.length;
    }

    //当前索引
    private int currentIndex = -1;
    //上一个索引
    private int lastIndex = -1;

    @Override
    public boolean onTouchEvent(MotionEvent event) {
        switch (event.getAction()) {
            case MotionEvent.ACTION_DOWN:
            case MotionEvent.ACTION_MOVE:
                if (listener != null) {
                    //每次滑动前,将当前索引赋值给上一个索引
                    lastIndex = currentIndex;
                    //目的:找到触摸的位置对应的letter
                    float y = event.getY();
                    //修改当前索引
                    currentIndex = (int) (y / cellHeight);
                    if (currentIndex > Cheeses.LETTERS.length - 1) {
                        currentIndex = Cheeses.LETTERS.length - 1;
                    } else if (currentIndex < 0) {
                        currentIndex = 0;
                    }
                    if (lastIndex != currentIndex) {
                        String letter = Cheeses.LETTERS[currentIndex];
//                  Log.i("test", "letter:" + letter);
                        listener.onLetterChanged(letter);
                    }
                }
                break;
            case MotionEvent.ACTION_UP:
                if(listener!=null){
                    listener.onLetterDismiss();
                }
                break;
        }
        //想要处理事件
        return true;
    }

    private OnLetterChangedListener listener;

    public interface OnLetterChangedListener {
        void onLetterChanged(String letter);
        void onLetterDismiss();
    }

    public void setOnLetterChangedListener(OnLetterChangedListener listener) {
        this.listener = listener;
    }
}

ViewPager有效的禁止左右滑动

package cn.evun.view;

import android.content.Context;
import android.support.v4.view.ViewPager;
import android.util.AttributeSet;
import android.view.MotionEvent;

/**
 */

public class NoScrollViewPager extends ViewPager {

    private boolean canScroll =true;

    public NoScrollViewPager(Context context) {
        super(context);
    }

    public NoScrollViewPager(Context context, AttributeSet attrs) {
        super(context, attrs);
    }

    @Override
    public boolean onTouchEvent(MotionEvent ev) {
        return this.canScroll&&super.onTouchEvent(ev);
    }

    @Override
    public boolean onInterceptTouchEvent(MotionEvent ev) {
        return this.canScroll&&super.onInterceptTouchEvent(ev);
    }

    public void isCanScroll(boolean b){
        this.canScroll =b;
    }
}

源码传送

CSDN下载
Github源码

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值