안 드 로 이 드 위 챗 연락처 색인 목록 기능 모방
자신 이 만 든 작은 소프트웨어 에 A-Z 에서 순 위 를 매 기 는 ListView 를 사용 해 야 하기 때문에 자 연 스 럽 게 위 챗 의 연락 처 를 떠 올 렸 다.내 가 원 하 는 것 은 바로 그런 효과 다.원래 스스로 쓰 려 고 하지 않 았 는데 제3자 가 쓴 것 을 원 했다.몇 개 를 찾 아 보 니 어떤 것 은 너무 복잡 하고 어떤 것 은 간단 하지만 나의 요구 에 부합 되 지 않 았 다.그래서 나 는 통합 시 켜 복잡성 과 단순 성 을 하나 로 합 쳤 다.
이루어지다
『8195』효과 도 를 먼저 살 펴 보 자.
요점 분석
『8195』이러한 효 과 를 실현 하려 면 다음 과 같은 몇 가지 문 제 를 고려 해 야 한다.
[첫걸음]
우 리 는 먼저 하나의 종 류 를 사용자 정의 해 야 합 니 다.SlideBar 라 고 합 니 다.Button 을 계승 한 다음 에 onDraw 방법 을 덮어 서 알파벳 a-z 를 그리 면 오른쪽 알파벳 표시 줄 의 효 과 를 나 타 낼 수 있 습 니 다.
원본 코드 보기:
public class SlideBar extends Button{
public interface OnTouchAssortListener{
public void onTouchAssortListener(String s);
}
//
private static final String[] ASSORT_TEXT = {"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 Paint mPaint = new Paint();
private int mSelectIndex = -1;
private OnTouchAssortListener mListener = null;
private Activity mAttachActivity;
PopupWindow mPopupWindow = null;
View layoutView;
TextView text;
public SlideBar(Context context){
this(context,null);
}
public SlideBar(Context context, AttributeSet attrs) {
this(context, attrs,0);
}
public SlideBar(Context context, AttributeSet attrs, int defStyle){
super(context, attrs, defStyle);
mAttachActivity = (Activity)context;
init(context);
}
private void init(Context context) {
layoutView = LayoutInflater.from(context).inflate(R.layout.alert_dialog_menu_layout, null);
text = (TextView) layoutView.findViewById(R.id.content);
}
public void setOnTouchAssortListener(OnTouchAssortListener listener) {
this.mListener = listener;
}
@Override
protected void onDraw(Canvas canvas){
super.onDraw(canvas);
int nHeight = getHeight();
int hWidth = getWidth();
int nAssortCount = ASSORT_TEXT.length;
int nInterval = nHeight / nAssortCount;
for (int i = 0; i < nAssortCount; i++){
mPaint.setAntiAlias(true); //
mPaint.setTypeface(Typeface.DEFAULT_BOLD); //
mPaint.setColor(Color.parseColor("#5f5f5f")); //
if (i == mSelectIndex){
//
mPaint.setColor(Color.parseColor("#3399ff"));
mPaint.setFakeBoldText(true);
mPaint.setTextSize(30);
}
float xPos = hWidth / 2 - mPaint.measureText(ASSORT_TEXT[i]) / 2; // X
float yPos = nInterval * i + nInterval; // Y
canvas.drawText(ASSORT_TEXT[i], xPos, yPos, mPaint);
mPaint.reset();
}
}
@Override
public boolean dispatchTouchEvent(MotionEvent event) {
//
int nIndex = (int) (event.getY() / getHeight() * ASSORT_TEXT.length);
if (nIndex >= 0 && nIndex < ASSORT_TEXT.length){
switch (event.getAction()){
case MotionEvent.ACTION_MOVE:
//
if (mSelectIndex != nIndex){
mSelectIndex = nIndex;
showCharacter(ASSORT_TEXT[mSelectIndex]);
if (mListener != null){
mListener.onTouchAssortListener(ASSORT_TEXT[mSelectIndex]);
}
}
break;
case MotionEvent.ACTION_DOWN:
mSelectIndex = nIndex;
showCharacter(ASSORT_TEXT[mSelectIndex]);
if (mListener != null){
mListener.onTouchAssortListener(ASSORT_TEXT[mSelectIndex]);
}
break;
case MotionEvent.ACTION_UP:
disShowCharacter();
mSelectIndex = -1;
break;
}
} else {
mSelectIndex = -1;
disShowCharacter();
}
invalidate();
return true;
}
private void disShowCharacter() {
if (mPopupWindow != null) {
mPopupWindow.dismiss();
mPopupWindow=null;
}
}
/**
*
* @param string
*/
private void showCharacter(String string){
if (mPopupWindow != null){
text.setText(string);
} else{
mPopupWindow = new PopupWindow(layoutView, 100, 100, false);
mPopupWindow.showAtLocation(mAttachActivity.getWindow().getDecorView(), Gravity.CENTER, 0, 0);
}
text.setText(string);
}
}
는 onDraw 방법 을 먼저 보고 다른 내용 은 먼저 보지 않 으 며 먼저 컨트롤 의 너비 와 높이 를 얻 은 다음 에 모든 자모 가 차지 해 야 할 높이 가 얼마 인지 계산 한 다음 에 모든 자모 가 차지 하 는 공간의 중간 에 이 자 모 를 그리 면 된다.코드 가 비교적 간단 하 므 로 이 부분 은 상세 하 게 설명 할 필요 가 없다.[두 번 째 단계]
우 리 는 클릭 이 벤트 를 추가 해 야 합 니 다.SlideBar 를 클릭 할 때 먼저 오른쪽 칸 에 클릭 된 알파벳 이 커지 는 것 을 볼 수 있 습 니 다.클릭 되 지 않 은 알파벳 과 구별 되 고 Dialog 와 유사 한 것 을 팝 업 하여 피 점 중의 알파벳 을 표시 합 니 다.이 효과 도 잘 이 루어 집 니 다.
SlideBar 에서 우리 가 덮어 야 할 방법 중 하 나 는 dispatchTouchEvent()입 니 다.우리 가 SlideBar 를 누 르 면 다음 동작 은 미 끄 러 지고 들 어 올 릴 수 있 습 니 다.클릭 한 동작 에 응답 해 야 합 니 다.들 어 올 리 면 dialog 와 유사 한 것 이 사라 지고 커 진 자모 도 그대로 돌아 가 야 합 니 다.계속 미 끄 러 지면...어떤 자모 로 미 끄 러 질 때 대응 하 는 자모 가 커지 고 표 시 됩 니 다.
위 에 있 는 소스 코드 를 보면 알파벳 이 커지 는 효과 가 잘 이 루어 집 니 다.선 택 된 알파벳 을 그린 Paint 대상 의 textsize 값 을 크게 만 들 면 됩 니 다.그리고 dialog 와 유사 한 것 은 PopupWindow 로 이 루어 집 니 다.클릭 하고 미 끄 러 질 때 PopupWindow 를 표시 하고 SlideBar 범 위 를 올 리 거나 미 끄 러 질 때 PopupWindow 를 사라 지게 합 니 다.마지막 으로 주의해 야 할 것 은 invalidate()라 는 방법 입 니 다.이 방법 은 화면 을 다시 그 리 는 데 사용 되 는 것 입 니 다.
[세 번 째 단계]
저 는 가장 중요 하고 가장 어 려 운 것 은 한자 가 A-Z 의 순 서 를 따 르 는 것 이 라 고 생각 합 니 다.다행히 이것 은 이미 누군가가 실현 되 었 으 니,우 리 는 이른바'가 져 오기 주의'를 하 자.프로젝트 안에 CharacterParser 류 가 있 습 니 다.이 종 류 는 한자 병 음 을 바 꾸 는 작업 을 봉 인 했 습 니 다.그 중에서 getSelling(String s)방법 은 한자 문자열 을 들 여 한자 의 병 음 을 얻 는 역할 을 합 니 다.역시 좋 은 방법 입 니 다.마음 에 듭 니 다!!이렇게 해서 우 리 는 표시 할 한자 문자열 의 병 음 자 모 를 얻 은 다음 에 모든 문자열 을 자모 에 따라 정렬 하면 A-Z 에서 질서 있 는 목록 을 얻 을 수 있다.ListView 는 일반적으로 하나의 List 대상 을 연결 한 다음 에 List 대상 에 일련의 대상 을 저장 하기 때문에 여 기 는 제 가 하나의 대상 으로 말 하 겠 습 니 다.
public class DataBean {
public static final int TYPE_CHARACTER = 0;
public static final int TYPE_DATA = 1;
private int item_type;
private String item_en;
private String name;
private String phone;
/* */
public DataBean(String name,String phone,int type){
CharacterParser parser = CharacterParser.getInstance();
this.name = name;
this.phone = phone;
this.item_type = type;
this.item_en = parser.getSelling(name).toUpperCase().trim();
if(!item_en.matches("[A-Z]+")){
item_en = "#"+item_en;
}
}
/*
* geter seter
*/
}
이 대상 에서 주의해 야 할 것 은 두 구성원 변수 입 니 다.itemtype 과 itemn,이 대상 이 표시 할 정상 적 인 대상 인지 알파벳 구분자 대상 인지,item 에 따라type 에 따라 Adapter 의 getView 방법 을 쓸 때 서로 다른 View 대상 을 되 돌려 주 고 효과 그림 의 정상 적 인 Item 과 알파벳 분할 자 Item 을 실현 할 수 있 습 니 다.item_n 은 name 변수,즉 한자 문자열 의 병 음 문자열 을 나타 내 는데 주로 이니셜 을 가 져 오고 문자열 간 의 비 교 를 하 는 데 사 용 됩 니 다.현재 List 대상 이 있다 고 가정 하면 그 안에 DataBean 이 저장 되 어 있 습 니 다.그러면 문제 가 생 겼 습 니 다.이 DataBean 대상 을 병 음 문자열 에 따라 정렬 하고 List 대상 에 알파벳 구분 자 를 나타 내 는 DataBean 대상 을 어떻게 추가 합 니까?
우선 정렬 문 제 를 해결 합 니 다.이것 은 비교적 간단 합 니 다.
여 기 는 Collections 의 sort 방법 을 사 용 했 습 니 다.이 방법 은 두 가지 매개 변수 가 있 습 니 다.하 나 는 정렬 이 있 는 List 대상 이 고 다른 하 나 는 Comparator 인터페이스의 유형 을 실현 하 는 대상 입 니 다.정렬 을 어떻게 하 는 지,어떤 구성원 변수 로 정렬 하 는 지 설명 합 니 다.
PinyinComparator 라 는 종 류 는 Comparator 를 실현 했다.
public class PinyinComparator implements Comparator<DataBean>{
public int compare(DataBean o1, DataBean o2){
if (o1.getItem_en().equals("@")
|| o2.getItem_en().equals("#")){
return -1;
} else if (o1.getItem_en().equals("#")
|| o2.getItem_en().equals("@")) {
return 1;
} else {
return o1.getItem_en().compareTo(o2.getItem_en());
}
}
}
볼 수 있 습 니 다.두 DataBean 대상 은 변수 itemn.즉,병 음 문자열 로 정렬 을 하 는 것 입 니 다.이렇게 하면 실현 하기에 비교적 편리 합 니 다.스스로 정렬 하 는 알고리즘 을 쓸 필요 가 없습니다.물론 여러분 이 스스로 정렬 하 는 것 도 반대 하지 않 습 니 다.Collections 의 sort 함 수 를 거 쳐 정렬 한 후에 현재 List 대상 에 저 장 된 DataBean 대상 은 A-Z 에 따라 정렬 되 었 습 니 다.지금 우리 가 해 야 할 일 은 바로 이 대상 에 알파벳 구분자 DataBean 을 나타 내 는 대상 을 삽입 하 는 것 입 니 다.이 실현 은 비교적 간단 해 야 합 니 다.제 가 사용 하 는 방법 은 비교적 멍청 합 니 다/(ㄒ o ㄒ)/~
public class ListUtil {
public static void sortList(List<DataBean> list){
List<DataBean> _List = new ArrayList<DataBean>();
Collections.sort(list, new PinyinComparator());
DataBean dataBean = new DataBean(getFirstCharacter(list.get(0).getItem_en()), "",DataBean.TYPE_CHARACTER);
String currentCharacter = getFirstCharacter(list.get(0).getItem_en());
_List.add(dataBean);
_List.add(list.get(0));
for(int i=1;i<list.size();i++){
if(getFirstCharacter(list.get(i).getItem_en()).compareTo(currentCharacter)!=0){
currentCharacter = getFirstCharacter(list.get(i).getItem_en());
dataBean = new DataBean(currentCharacter, "",DataBean.TYPE_CHARACTER);
_List.add(dataBean);
}
_List.add(list.get(i));
}
list.clear();
for(DataBean bean:_List){
list.add(bean);
}
}
public static String getFirstCharacter(String str){
return str.substring(0, 1);
}
}
이런 종 류 는 List 대상 에 알파벳 구분 자 를 나타 내 는 대상 을 추가 하고 item 설정 을 통 해type 변수의 값 이 다 르 기 때문에 Adapter 에서 이 값 에 따라 서로 다른 View 를 되 돌려 주면 서로 다른 Item 디 스 플레이 를 실현 할 수 있 습 니 다.자,이제 질문 하나만 남 았 습 니 다.바로 알파벳 을 클릭 한 후에 ListView 는 이 알파벳 에 대응 하 는 Item 을 첫 번 째 로 표시 합 니 다.이 실현 도 어렵 지 않 습 니 다.점 에 있 는 알파벳 을 얻 은 후에 모든 DataBean 대상 을 옮 겨 다 니 고 현재 자모 와 일치 하 는 첫 번 째 알파벳 구분자 대상 을 찾 은 다음 에 이 Item 의 position 값 을 얻 습 니 다.ListView 에서 선 택 된 Item 의 position 을 찾 은 Item 의 position 으로 설정 하면 됩 니 다.
드디어 모든 문제 가 해결 되 었 습 니 다.지금 자신 이 이런 효 과 를 실현 할 수 있 는 지 보 세 요.만약 안 된다 면 나의 소스 코드 를 참고 할 수 있다.
작은 매듭
원래 저도 이것 에 대해 잘 모 르 지만 자신 에 게 소스 코드 를 보 여 달라 고 강 요 했 습 니 다.인터넷 에 있 는 큰 신 이 쓴 것 이 100%자신의 요 구 를 만족 시 키 는 것 이 아니 기 때문에 소스 코드 를 알 아 볼 수 있 으 면 스스로 수정 할 수 있 습 니 다.
원본 코드 다운로드여기,이곳.
이상 이 바로 본 고의 모든 내용 입 니 다.여러분 의 학습 에 도움 이 되 고 저 희 를 많이 응원 해 주 셨 으 면 좋 겠 습 니 다.
이 내용에 흥미가 있습니까?
현재 기사가 여러분의 문제를 해결하지 못하는 경우 AI 엔진은 머신러닝 분석(스마트 모델이 방금 만들어져 부정확한 경우가 있을 수 있음)을 통해 가장 유사한 기사를 추천합니다:
Kotlin의 기초 - 2부지난 글에서는 Kotlin이 무엇인지, Kotlin의 특징, Kotlin에서 변수 및 데이터 유형을 선언하는 방법과 같은 Kotlin의 기본 개념에 대해 배웠습니다. 유형 변환은 데이터 변수의 한 유형을 다른 데이터...
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
CC BY-SA 2.5, CC BY-SA 3.0 및 CC BY-SA 4.0에 따라 라이센스가 부여됩니다.