原文:https://blog.csdn.net/uyy203/article/details/54912969
先上動(dòng)態(tài)效果圖
利用一個(gè)自定義View 虫蝶,和其中的dispatchTouchEvent 攔截觸摸事件實(shí)現(xiàn)
SideBar.java
package xyz.slideviewgettext;
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Paint;
import android.graphics.Typeface;
import android.util.AttributeSet;
import android.view.MotionEvent;
import android.view.View;
import java.util.List;
/**
* Created by xyz on 2017/2/5.
*/
public class SideBar extends View {
private List<String> letterList;
private Paint paint;
public SideBar(Context context,List<String> list){
this(context,(AttributeSet) null);
this.letterList=list;
}
public SideBar(Context context, AttributeSet attributeSet){
this(context,attributeSet,0);
}
public SideBar(Context context,AttributeSet attributeSet,int defStyle){
super(context,attributeSet,defStyle);
init();
}
private void init(){
setBackgroundColor(0x000000);
}
@Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
int height=getHeight();//獲取view的高度
int width=getWidth();//獲取view的寬度
int singleHeight=height/letterList.size();//獲取每一個(gè)字母所占的高度
int textHight= getFontAboveBaseLineHeight(35);
paint=new Paint();
for(int i=0;i<letterList.size();i++){
paint.setColor(0xff606060);
paint.setTypeface(Typeface.DEFAULT_BOLD);
paint.setAntiAlias(true);
paint.setTextSize(35);
//文字x軸坐標(biāo)
float xPos=width/2-paint.measureText(letterList.get(i))/2;
//文字y軸坐標(biāo)
// float yPos=(singleHeight*(i)) + (2*singleHeight/3);
float yPos=(singleHeight*i)+((singleHeight+textHight)/2);
canvas.drawText(letterList.get(i),xPos,yPos,paint);
paint.reset();//重置畫(huà)筆
}
}
@Override
public boolean dispatchTouchEvent(MotionEvent event) {
int action=event.getAction();
final float x=event.getX();
final float y=event.getY();
// 點(diǎn)擊y坐標(biāo)所占總高度的比例*b數(shù)組的長(zhǎng)度就等于點(diǎn)擊b中的個(gè)數(shù).
final int index=(int)((y/getHeight())*letterList.size());
if(x<0||x>getWidth()||y<0||y>getHeight()) {
action = MotionEvent.ACTION_UP;
}
switch (action) {
case MotionEvent.ACTION_UP:
setBackgroundColor(0x000000);
if (onTouchBarListener != null) {
onTouchBarListener.onTouch(null, -1, false);
}
invalidate();
break;
default:
setBackgroundColor(0xffffffff);
if (onTouchBarListener != null) {
onTouchBarListener.onTouch(letterList.get(index), index, true);
}
invalidate();
break;
}
return true;//要實(shí)現(xiàn)觸摸式的動(dòng)態(tài)效果,必須返回true裕寨,使得事件能夠被攔截
}
//獲得字體baseLine以上的高度
//若需要了解關(guān)于單行文本高度分析詳情請(qǐng)看 http://blog.csdn.net/uyy203/article/details/54926753
public int getFontAboveBaseLineHeight(float fontSize)
{
Paint paint = new Paint();
paint.setTextSize(fontSize);
Paint.FontMetrics fm = paint.getFontMetrics();
return (int)(Math.ceil(- fm.ascent));
}
//外部設(shè)置列表數(shù)據(jù)方法攒读,重繪view
public void setLetterList(List<String> list){
this.letterList=list;
invalidate();
}
//外部調(diào)用接口廓旬,以便讓外部獲得當(dāng)前觸摸到的字母
private OnTouchBarListener onTouchBarListener;
public interface OnTouchBarListener{
void onTouch(String letter,int pos,boolean state);
}
public void setOnTouchBarLisstener(OnTouchBarListener l){
this.onTouchBarListener=l;
}
}
MainActivity.java
package xyz.slideviewgettext;
import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.view.ViewGroup;
import android.view.Window;
import android.widget.Button;
import android.widget.RelativeLayout;
import android.widget.TextView;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
public class MainActivity extends Activity {
public List<String> letterList;
public static String[] INDEX_STRING = {
"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",
"#"
};
public static String[] Afterstring = {
"1", "2", "3", "4", "5", "6", "7", "8", "9",
"@"
};
private RelativeLayout rlayout;
private static int WC= ViewGroup.LayoutParams.WRAP_CONTENT;
private static int MP=ViewGroup.LayoutParams.MATCH_PARENT;
private SideBar sideBar;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
requestWindowFeature(Window.FEATURE_NO_TITLE);
// setContentView(R.layout.activity_main);
letterList=new ArrayList<String>();
letterList= Arrays.asList(INDEX_STRING);
//整體布局
rlayout=new RelativeLayout(getBaseContext());
RelativeLayout.LayoutParams rp=new RelativeLayout.LayoutParams(MP,MP);
setContentView(rlayout,rp);
//屏幕中間顯示的文本凿蒜,會(huì)將當(dāng)前觸摸到的字母顯示出來(lái)
final TextView text=new TextView(getBaseContext());
rp=new RelativeLayout.LayoutParams(WC,WC);
rp.addRule(RelativeLayout.CENTER_IN_PARENT);
text.setTextSize(100);
text.setTextColor(0xff606060);
rlayout.addView(text,rp);
//包裹側(cè)邊導(dǎo)航欄view的布局
final RelativeLayout sideLayout=new RelativeLayout(getBaseContext());
rp=new RelativeLayout.LayoutParams(80,letterList.size()*60);
rp.addRule(RelativeLayout.ALIGN_PARENT_RIGHT);
rp.addRule(RelativeLayout.CENTER_VERTICAL);
rlayout.addView(sideLayout,rp);
//包裹側(cè)邊導(dǎo)航欄view
sideBar=new SideBar(getBaseContext(),letterList);
rp=new RelativeLayout.LayoutParams(WC,WC);
sideLayout.addView(sideBar,rp);
sideBar.setOnTouchBarLisstener(new SideBar.OnTouchBarListener() {
@Override
public void onTouch(String letter, int pos,boolean state) {
if(state)
text.setText(letter);
else
text.setText("");
}
});
//改變list內(nèi)容 重繪view
Button button =new Button(getBaseContext());
rp=new RelativeLayout.LayoutParams(WC,WC);
button.setText("點(diǎn)我");
rlayout.addView(button,rp);
button.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
letterList= Arrays.asList(Afterstring);
sideBar.setLetterList(letterList);
}
});
}
}
若需要了解關(guān)于單行文本高度分析詳情請(qǐng)看 http://www.reibang.com/p/aab850e29b6c