Android仿微信通讯录

Android仿微信通讯录

分3部:

1、listview实现显示头像、名字(太简单,这里就不写了)

通讯录页面xml布局代码:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
   >

    <FrameLayout
        android:id="@+id/fl"
        android:layout_width="match_parent"
        android:layout_height="wrap_content">


        <ListView

            android:id="@+id/school_friend_member"

            android:layout_width="match_parent"

            android:layout_height="match_parent"

            android:cacheColorHint="@android:color/transparent"

            android:dividerHeight="1px"

            android:fadingEdge="none"

            android:listSelector="@android:color/transparent"

            android:scrollbars="none"></ListView>


        <TextView

            android:id="@+id/school_friend_dialog"

            android:layout_width="80dp"

            android:layout_height="80dp"

            android:layout_gravity="center"

            android:background="@color/green_light"

            android:gravity="center"

            android:textColor="#ffffffff"

            android:textSize="30dp"

            android:visibility="invisible" />


        <com.diancanwang.dell.diancanwang.chat.bean.SideBar

            android:id="@+id/school_friend_sidrbar"

            android:layout_width="30dp"

            android:layout_height="match_parent"

            android:layout_gravity="right|center" />

    </FrameLayout>

</LinearLayout>

2、实现A——Z的好友分类

首先 导入拼音依赖

compile files('libs/pinyin4j-2.5.0.jar')  (依赖可以到网上搜索一个,添加到app下面的libs文件夹里,我这里给出的是我添加好后app build.gradle里面的)

其次

import net.sourceforge.pinyin4j.PinyinHelper;
import net.sourceforge.pinyin4j.format.HanyuPinyinCaseType;
import net.sourceforge.pinyin4j.format.HanyuPinyinOutputFormat;
import net.sourceforge.pinyin4j.format.HanyuPinyinToneType;
import net.sourceforge.pinyin4j.format.HanyuPinyinVCharType;
import net.sourceforge.pinyin4j.format.exception.BadHanyuPinyinOutputFormatCombination;

import java.util.Comparator;

/**
 * 2018/4/22.
 */

public class PinyinComparator implements Comparator<SortModel> {
    public int compare(SortModel o1, SortModel o2) {
        if (o1.getSortLetters().equals("@")
                || o2.getSortLetters().equals("#")) {
            return -1;
        } else if (o1.getSortLetters().equals("#")
                || o2.getSortLetters().equals("@")) {
            return 1;
        } else {
            return o1.getSortLetters().compareTo(o2.getSortLetters());
        }
    }

    public static String getPingYin(String inputString) {
        HanyuPinyinOutputFormat format = new HanyuPinyinOutputFormat();
        format.setCaseType(HanyuPinyinCaseType.LOWERCASE);
        format.setToneType(HanyuPinyinToneType.WITHOUT_TONE);
        format.setVCharType(HanyuPinyinVCharType.WITH_V);
        char[] input = inputString.trim().toCharArray();
        String output = "";
        try {
            for (char curchar : input) {
                if (java.lang.Character.toString(curchar).matches("[\u4e00-\u9fa5]+")) {
                    String[] temp = PinyinHelper.toHanyuPinyinStringArray(curchar, format);
                    output += temp[0];
                } else
                    output += java.lang.Character.toString(curchar);
            }
        } catch (BadHanyuPinyinOutputFormatCombination e) {
            e.printStackTrace();
        }
        return output;
    }

}

实体类

扫描二维码关注公众号,回复: 8554071 查看本文章
/**
 *  2018/4/22.
 * 实体类
 */

public class SortModel {
    private int img;//头像
    private String name;   //显示的数据
    private String sortLetters;  //显示数据拼音的首字母

    public SortModel(int img, String name, String sortLetters) {
        this.img = img;
        this.name = name;
        this.sortLetters = sortLetters;
    }

    public SortModel() {
    }

    public int getImg() {
        return img;
    }

    public void setImg(int img) {
        this.img = img;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getSortLetters() {
        return sortLetters;
    }

    public void setSortLetters(String sortLetters) {
        this.sortLetters = sortLetters;
    }

    @Override
    public String toString() {
        return "SortModel{" +
                "img=" + img +
                ", name='" + name + '\'' +
                ", sortLetters='" + sortLetters + '\'' +
                '}';
    }
}
import android.widget.ListView;
import android.widget.TextView;

import com.diancanwang.dell.diancanwang.R;
import com.diancanwang.dell.diancanwang.base.BaseFragment;
import com.diancanwang.dell.diancanwang.chat.adapter.SortAdapter;
import com.diancanwang.dell.diancanwang.chat.bean.PinyinComparator;
import com.diancanwang.dell.diancanwang.chat.bean.SideBar;
import com.diancanwang.dell.diancanwang.chat.bean.SortModel;

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

import butterknife.Bind;

/**
 * 通讯录页面
 */
public class AddBookFragment extends BaseFragment {

    @Bind(R.id.school_friend_member)
    ListView mListView;
    @Bind(R.id.school_friend_dialog)
    TextView mDialog;
    @Bind(R.id.school_friend_sidrbar)
    SideBar mSideBar;
    private List<SortModel> list;

    @Override
    protected int getLayoutId() {
        return R.layout.fragment_add_book;
    }

    @Override
    protected void initView() {

    }

    @Override
    protected void initData() {
        list = new ArrayList<>();
//        for (int i = 0; i < 10; i++) {
        SortModel sortModel = new SortModel();
        SortModel sortModel1 = new SortModel();
        SortModel sortModel2 = new SortModel();
        SortModel sortModel3 = new SortModel();
        SortModel sortModel4 = new SortModel();
        SortModel sortModel5 = new SortModel();


        sortModel.setImg(R.mipmap.ic_launcher);
        sortModel1.setImg(R.mipmap.ic_launcher);
        sortModel2.setImg(R.mipmap.ic_launcher);
        sortModel3.setImg(R.mipmap.ic_launcher);
        sortModel4.setImg(R.mipmap.ic_launcher);
        sortModel5.setImg(R.mipmap.ic_launcher);
        sortModel2.setName("华为");
        sortModel.setName("阿里巴巴");
        sortModel1.setName("百度");
        sortModel3.setName("xiaoxue");
        sortModel4.setName("……%¥#¥%#");
        sortModel5.setName("百家姓");

        String pingYin = PinyinComparator.getPingYin("阿里巴巴");
        String pingYin1 = PinyinComparator.getPingYin("百度");
        String pingYin2 = PinyinComparator.getPingYin("华为");
        String pingYin3 = PinyinComparator.getPingYin("xiaoxue");
        String pingYin4 = PinyinComparator.getPingYin("……%¥#¥%#");
        String pingYin5 = PinyinComparator.getPingYin("百家姓");

        sortModel3.setSortLetters(pingYin3);
        sortModel.setSortLetters(pingYin);
        sortModel1.setSortLetters(pingYin1);
        sortModel2.setSortLetters(pingYin2);
        sortModel4.setSortLetters(pingYin4);
        sortModel5.setSortLetters(pingYin5);



        list.add(sortModel2);
        list.add(sortModel1);
        list.add(sortModel3);
        list.add(sortModel);
        list.add(sortModel4);
        list.add(sortModel5);

//        }
    }

    @Override
    protected void initAdapter() {
        SortAdapter adapter = new SortAdapter(list, getActivity());
        mListView.setAdapter(adapter);
    }


}

适配器

import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseAdapter;
import android.widget.ImageView;
import android.widget.SectionIndexer;
import android.widget.TextView;

import com.bumptech.glide.Glide;
import com.diancanwang.dell.diancanwang.R;
import com.diancanwang.dell.diancanwang.chat.bean.PinyinComparator;
import com.diancanwang.dell.diancanwang.chat.bean.SortModel;

import java.util.Collections;
import java.util.List;

/**
 * 2018/4/22.
 */

public class SortAdapter extends BaseAdapter implements SectionIndexer {
    private List<SortModel> list;
    private Context mContext;

    public SortAdapter(List<SortModel> list, Context mContext) {
        this.list = list;
        this.mContext = mContext;
    }

    public void updateListView(List<SortModel> list) {
        this.list = list;
        notifyDataSetChanged();
    }


    @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) {
        ViewHolder viewHolder = null;
        if (convertView == null) {
            viewHolder = new ViewHolder();
            convertView = LayoutInflater.from(mContext).inflate(R.layout.item, null);
            //头像
            viewHolder.imgHead = (ImageView) convertView.findViewById(R.id.book_head);
            //昵称
            viewHolder.tvTitle = (TextView) convertView.findViewById(R.id.book_name);
            //索引字母
            viewHolder.tvLetter = (TextView) convertView.findViewById(R.id.catalog);
            convertView.setTag(viewHolder);
        } else {
            viewHolder = (ViewHolder) convertView.getTag();
        }


        //// 获取首字母的assii值
        int section = getSectionForPosition(position);
        //通过首字母的assii值来判断是否显示字母
        int positionForSelection = getPositionForSection(section);

        viewHolder.tvLetter.setOnClickListener(null);

        if (position == positionForSelection) {

            viewHolder.tvLetter.setVisibility(View.VISIBLE);
            //把拼音转成大写字母,并取首字母    toUpperCase()  转换为大写字母
            String firstLetter = list.get(position).getSortLetters().substring(0, 1).toUpperCase();
            // 正则表达式,判断首字母是否是英文字母
            if (firstLetter.matches("[A-Z]")) {
//              给通讯录好友排序(按照从A-Z的顺序)
                Collections.sort(list, new PinyinComparator());
                //给控件设置值
                viewHolder.tvLetter.setText(firstLetter);
            } else {
                viewHolder.tvLetter.setText("#");
            }


        } else {
            viewHolder.tvLetter.setVisibility(View.GONE);
        }

        Glide.with(mContext).load(list.get(position).getImg()).into(viewHolder.imgHead);
        viewHolder.tvTitle.setText(list.get(position).getName());

        return convertView;
    }

    final static class ViewHolder {
        ImageView imgHead;
        TextView tvLetter;
        TextView tvTitle;
    }

    @Override
    public Object[] getSections() {
        return null;
    }

    @Override
    public int getPositionForSection(int section) {
        for (int i = 0; i < getCount(); i++) {
            String sortStr = list.get(i).getSortLetters();
            char firstChar = sortStr.toUpperCase().charAt(0);
            if (firstChar == section) {
                return i;
            }
        }

        return -1;

    }

    @Override
    public int getSectionForPosition(int position) {

        return list.get(position).getSortLetters().toUpperCase().charAt(0);
    }
}

适配器里的xml布局

<?xml version="1.0" encoding="utf-8"?>

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:gravity="center_vertical"
    android:orientation="vertical">


    <TextView
        android:id="@+id/catalog"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:background="#F9F9F9"
        android:paddingBottom="5dp"
        android:paddingLeft="20dp"
        android:paddingTop="5dp"
        android:text="A"
        android:textColor="#454545" />

<!--

    <TextView

        android:id="@+id/line"
        android:layout_width="match_parent"
        android:layout_height="1px"
        android:background="@color/green_light" />
-->


    <LinearLayout
        android:id="@+id/content"
        android:layout_width="match_parent"
        android:layout_height="60dp"
        android:background="@color/white"
        android:orientation="horizontal"
        android:paddingBottom="5dp"
        android:paddingLeft="10dp"
        android:paddingRight="10dp"
        android:paddingTop="5dp">


        <ImageView
            android:id="@+id/book_head"
            android:layout_width="45dp"
            android:layout_height="45dp"
            android:layout_gravity="center_vertical"
            android:layout_marginLeft="10dp"
            android:src="@color/green_light" />


        <TextView
            android:id="@+id/book_name"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_gravity="center_vertical"
            android:layout_marginLeft="10dip"
            android:ellipsize="end"
            android:gravity="center_vertical"
            android:singleLine="true"
            android:text="xxxx"
            android:textColor="#323232"
            android:textSize="16sp" />

    </LinearLayout>


</LinearLayout>

3.实现右侧的字母导航

import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.drawable.ColorDrawable;
import android.support.annotation.Nullable;
import android.util.AttributeSet;
import android.view.MotionEvent;
import android.view.View;
import android.widget.TextView;

/**
 *  2018/4/16.
 * 侧边栏 SideBar
 */

public class SideBar extends View {

    //触摸事件(用的接口回调)
    private OnTouchingLetterChangedListener onTouchingLetterChangedListener;

    //26个字母
    public static String[] b = {"A", "B", "C", "D", "E", "F", "G", "H", "I",
            "J", "K", "L", "M", "N", "O", "P", "Q", "R", "S", "T", "U", "V",
            "W", "X", "Y", "Z", "#"};


    private int choose = -1;// 选中
    private TextView mTextDialog;

    public void setTextView(TextView mTextDialog) {
        this.mTextDialog = mTextDialog;
    }

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

    public SideBar(Context context, @Nullable AttributeSet attrs) {
        super(context, attrs);
    }

    public SideBar(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
    }

    @Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);
        Paint paint = new Paint();
        int height = getHeight();//获取高度
        int width = getWidth();//获取宽度
        int singleHeight = height / b.length;//获取每一个字母的高度

        for (int i = 0; i < b.length; i++) {
            paint.setColor(Color.parseColor("#838383"));//未选中的颜色
            paint.setTextSize(30);
            paint.setAntiAlias(true);//抗锯齿功能
            // 选中的状态
            if (i == choose) {
                paint.setColor(Color.BLACK);//选中的颜色
                paint.setFakeBoldText(false); //true为粗体,false为非粗体            }
            }
            // x坐标等于中间-字符串宽度的一半.
            float xPos = width / 2 - paint.measureText(b[i]) / 2;
            float yPos = singleHeight * i + singleHeight;
            canvas.drawText(b[i], xPos, yPos, paint);
            paint.reset();// 重置画笔


        }
    }

    @Override
    public boolean dispatchTouchEvent(MotionEvent event) {
        final int action = event.getAction();
        final float y = event.getY();// 点击y坐标
        final int oldChoose = choose;
        final OnTouchingLetterChangedListener listener = onTouchingLetterChangedListener;
        final int c = (int) (y / getHeight() * b.length);// 点击y坐标所占总高度的比例*b数组的长度就等于点击b中的个数.

        switch (action) {
            case MotionEvent.ACTION_UP:
                setBackgroundDrawable(new ColorDrawable(0x00000000));
                choose = -1;//
                invalidate();
                if (mTextDialog != null) {
                    mTextDialog.setVisibility(View.INVISIBLE);
                }

                break;

            default:
                setBackgroundColor(Color.TRANSPARENT);
                if (oldChoose != c) {  //判断选中字母是否发生改变
                    if (c >= 0 && c < b.length) {
                        if (listener != null) {
                            listener.onTouchingLetterChangedListener(b[c]);
                        }
                        if (mTextDialog != null) {
                            mTextDialog.setText(b[c]);
                            mTextDialog.setVisibility(View.VISIBLE);
                        }

                        choose = c;
                        invalidate();
                    }
                }

                break;
        }

        return true;
    }

    public void setOnTouchingLetterChangedListener(OnTouchingLetterChangedListener onTouchingLetterChangedListener) {
        this.onTouchingLetterChangedListener = onTouchingLetterChangedListener;
    }

    public interface OnTouchingLetterChangedListener {
        void onTouchingLetterChangedListener(String s);
    }
}

在设置数据的页面把SideBar和Dialog绑定再一起,然后初始化监听

  protected void initView() {
//        把SideBar和Dialog绑定
        mSideBar.setTextView(mDialog);


        mSideBar.setOnTouchingLetterChangedListener(new SideBar.OnTouchingLetterChangedListener() {
            @Override
            public void onTouchingLetterChangedListener(String s) {

                // 该字母首次出现的位置
                int position = adapter.getPositionForSection(s.charAt(0));
                if (position != -1) {
                    mListView.setSelection(position);
                }

            }
        });
    }
发布了154 篇原创文章 · 获赞 36 · 访问量 22万+

猜你喜欢

转载自blog.csdn.net/yijiaodingqiankun/article/details/101267409
今日推荐