android 自定義ListView顯示微信聊天好友列表
阿新 • • 發佈:2018-12-31
我們使用listView實現顯示微信好友列表,如下圖所示
這是MainActivity的程式碼如下:
下面我們來自定義adpater實現好友列表介面佈局<span style="font-size:18px;">package com.listviewdodo; import java.util.ArrayList; import java.util.List; import com.listviewdodo.R; import com.listviewdodo.myadapter.Myadapter; import com.listviewdodo.util.GetDataType; import android.os.Bundle; import android.app.Activity; import android.view.Menu; import android.widget.ListView; import android.widget.Toast; public class MainActivity extends Activity { private ListView lv_friend; private Myadapter adapter; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); lv_friend=(ListView) findViewById(R.id.lv_friend); adapter=new Myadapter(this, getdatas()); lv_friend.setAdapter(adapter); } private List<GetDataType> getdatas() { List<GetDataType> list=new ArrayList<GetDataType>(); GetDataType data1=new GetDataType(); data1.setIv_portrait(R.drawable.a1); data1.setName("楊冪"); data1.setSignature("喜歡我就來找我啊"); list.add(data1); GetDataType data2=new GetDataType(); data2.setIv_portrait(R.drawable.a2); data2.setName("范冰冰"); data2.setSignature("我在這裡等你哦"); list.add(data2); GetDataType data3=new GetDataType(); data3.setIv_portrait(R.drawable.a3); data3.setName("唐嫣"); data3.setSignature("來追我呀,呵呵"); list.add(data3); GetDataType data4=new GetDataType(); data4.setIv_portrait(R.drawable.a4); data4.setName("李小璐"); data4.setSignature("386562,加我好友呀"); list.add(data4); GetDataType data5=new GetDataType(); data5.setIv_portrait(R.drawable.a5); data5.setName("柳巖"); data5.setSignature("帥哥,過來一下"); list.add(data5); return list; } }</span>
<span style="font-size:18px;">/*需求:實現微信好友列表 * 自定義ListView控制元件 * 作者:Keep moving */ package com.listviewdodo.myadapter; import java.util.List; import com.listviewdodo.R; import com.listviewdodo.util.GetDataType; import android.content.Context; import android.view.View; import android.view.ViewGroup; import android.widget.BaseAdapter; import android.widget.ImageView; import android.widget.TextView; public class Myadapter extends BaseAdapter{ private List<GetDataType> mData; private Context mcontext; private int mid; public Myadapter(Context context,List data){ this.mcontext=context; this.mData=data; } //獲取列表列的數量 @Override public int getCount() { return mData.size(); } //根據postion獲取item的資料 @Override public Object getItem(int position) { return mData.get(position); } //獲取position對應的id @Override public long getItemId(int position) { return position; } //建立item的檢視 @Override public View getView(int position, View convertView, ViewGroup parent) { View view=View.inflate(mcontext, R.layout.item_list, null); //獲取item對應的資料物件 GetDataType getdata=mData.get(position); //初始化view ImageView iv_portrait= (ImageView) view.findViewById(R.id.iv_portrait); TextView txt_name=(TextView) view.findViewById(R.id.txt_name); TextView signature=(TextView) view.findViewById(R.id.txt_signature); //邦定資料到view iv_portrait.setImageResource(getdata.getIv_portrait()); txt_name.setText(getdata.getName()); signature.setText(getdata.getSignature()); return view; } } </span>
接下來我們用ImageView控制元件來自定義一個圓圈的頭像
<span style="font-size:18px;">package com.listviewdodo.myview; import com.listviewdodo.R; import android.content.Context; import android.content.res.TypedArray; import android.graphics.Bitmap; import android.graphics.Bitmap.Config; import android.graphics.Canvas; import android.graphics.Paint; import android.graphics.PorterDuff.Mode; import android.graphics.PorterDuffXfermode; import android.graphics.Rect; import android.graphics.drawable.BitmapDrawable; import android.graphics.drawable.Drawable; import android.graphics.drawable.NinePatchDrawable; import android.util.AttributeSet; import android.widget.ImageView; /** * 圓形ImageView,可設定最多兩個寬度不同且顏色不同的圓形邊框。 * * @author */ public class RoundImageView extends ImageView { private int mBorderThickness = 0; private Context mContext; private int defaultColor = 0xFFFFFFFF; // 如果只有其中一個有值,則只畫一個圓形邊框 private int mBorderOutsideColor = 0; private int mBorderInsideColor = 0; // 控制元件預設長、寬 private int defaultWidth = 0; private int defaultHeight = 0; public RoundImageView(Context context) { super(context); mContext = context; } public RoundImageView(Context context, AttributeSet attrs) { super(context, attrs); mContext = context; setCustomAttributes(attrs); } public RoundImageView(Context context, AttributeSet attrs, int defStyle) { super(context, attrs, defStyle); mContext = context; setCustomAttributes(attrs); } private void setCustomAttributes(AttributeSet attrs) { TypedArray a = mContext.obtainStyledAttributes(attrs, R.styleable.roundedimageview); mBorderThickness = a.getDimensionPixelSize( R.styleable.roundedimageview_border_thickness, 0); mBorderOutsideColor = a .getColor(R.styleable.roundedimageview_border_outside_color, defaultColor); mBorderInsideColor = a.getColor( R.styleable.roundedimageview_border_inside_color, defaultColor); } @Override protected void onDraw(Canvas canvas) { Drawable drawable = getDrawable(); if (drawable == null) { return; } if (getWidth() == 0 || getHeight() == 0) { return; } this.measure(0, 0); if (drawable.getClass() == NinePatchDrawable.class) return; Bitmap b = ((BitmapDrawable) drawable).getBitmap(); Bitmap bitmap = b.copy(Bitmap.Config.ARGB_8888, true); if (defaultWidth == 0) { defaultWidth = getWidth(); } if (defaultHeight == 0) { defaultHeight = getHeight(); } // 保證重新讀取圖片後不會因為圖片大小而改變控制元件寬、高的大小(針對寬、高為wrap_content佈局的imageview,但會導致margin無效) // if (defaultWidth != 0 && defaultHeight != 0) { // LinearLayout.LayoutParams params = new LinearLayout.LayoutParams( // defaultWidth, defaultHeight); // setLayoutParams(params); // } int radius = 0; if (mBorderInsideColor != defaultColor && mBorderOutsideColor != defaultColor) {// 定義畫兩個邊框,分別為外圓邊框和內圓邊框 radius = (defaultWidth < defaultHeight ? defaultWidth : defaultHeight) / 2 - 2 * mBorderThickness; // 畫內圓 drawCircleBorder(canvas, radius + mBorderThickness / 2, mBorderInsideColor); // 畫外圓 drawCircleBorder(canvas, radius + mBorderThickness + mBorderThickness / 2, mBorderOutsideColor); } else if (mBorderInsideColor != defaultColor && mBorderOutsideColor == defaultColor) {// 定義畫一個邊框 radius = (defaultWidth < defaultHeight ? defaultWidth : defaultHeight) / 2 - mBorderThickness; drawCircleBorder(canvas, radius + mBorderThickness / 2, mBorderInsideColor); } else if (mBorderInsideColor == defaultColor && mBorderOutsideColor != defaultColor) {// 定義畫一個邊框 radius = (defaultWidth < defaultHeight ? defaultWidth : defaultHeight) / 2 - mBorderThickness; drawCircleBorder(canvas, radius + mBorderThickness / 2, mBorderOutsideColor); } else {// 沒有邊框 radius = (defaultWidth < defaultHeight ? defaultWidth : defaultHeight) / 2; } Bitmap roundBitmap = getCroppedRoundBitmap(bitmap, radius); canvas.drawBitmap(roundBitmap, defaultWidth / 2 - radius, defaultHeight / 2 - radius, null); } /** * 獲取裁剪後的圓形圖片 * * @param radius * 半徑 */ public Bitmap getCroppedRoundBitmap(Bitmap bmp, int radius) { Bitmap scaledSrcBmp; int diameter = radius * 2; // 為了防止寬高不相等,造成圓形圖片變形,因此擷取長方形中處於中間位置最大的正方形圖片 int bmpWidth = bmp.getWidth(); int bmpHeight = bmp.getHeight(); int squareWidth = 0, squareHeight = 0; int x = 0, y = 0; Bitmap squareBitmap; if (bmpHeight > bmpWidth) {// 高大於寬 squareWidth = squareHeight = bmpWidth; x = 0; y = (bmpHeight - bmpWidth) / 2; // 擷取正方形圖片 squareBitmap = Bitmap.createBitmap(bmp, x, y, squareWidth, squareHeight); } else if (bmpHeight < bmpWidth) {// 寬大於高 squareWidth = squareHeight = bmpHeight; x = (bmpWidth - bmpHeight) / 2; y = 0; squareBitmap = Bitmap.createBitmap(bmp, x, y, squareWidth, squareHeight); } else { squareBitmap = bmp; } if (squareBitmap.getWidth() != diameter || squareBitmap.getHeight() != diameter) { scaledSrcBmp = Bitmap.createScaledBitmap(squareBitmap, diameter, diameter, true); } else { scaledSrcBmp = squareBitmap; } Bitmap output = Bitmap.createBitmap(scaledSrcBmp.getWidth(), scaledSrcBmp.getHeight(), Config.ARGB_8888); Canvas canvas = new Canvas(output); Paint paint = new Paint(); Rect rect = new Rect(0, 0, scaledSrcBmp.getWidth(), scaledSrcBmp.getHeight()); paint.setAntiAlias(true); paint.setFilterBitmap(true); paint.setDither(true); canvas.drawARGB(0, 0, 0, 0); canvas.drawCircle(scaledSrcBmp.getWidth() / 2, scaledSrcBmp.getHeight() / 2, scaledSrcBmp.getWidth() / 2, paint); paint.setXfermode(new PorterDuffXfermode(Mode.SRC_IN)); canvas.drawBitmap(scaledSrcBmp, rect, rect, paint); // bitmap回收(recycle導致在佈局檔案XML看不到效果) // bmp.recycle(); // squareBitmap.recycle(); // scaledSrcBmp.recycle(); bmp = null; squareBitmap = null; scaledSrcBmp = null; return output; } /** * 邊緣畫圓 */ private void drawCircleBorder(Canvas canvas, int radius, int color) { Paint paint = new Paint(); /* 去鋸齒 */ paint.setAntiAlias(true); paint.setFilterBitmap(true); paint.setDither(true); paint.setColor(color); /* 設定paint的 style 為STROKE:空心 */ paint.setStyle(Paint.Style.STROKE); /* 設定paint的外框寬度 */ paint.setStrokeWidth(mBorderThickness); canvas.drawCircle(defaultWidth / 2, defaultHeight / 2, radius, paint); } } </span>
最後我們來寫一個類,實現好友頭像、好友名稱、好友個性簽名。程式碼如下
<span style="font-size:18px;">package com.listviewdodo.util;
public class GetDataType {
private int iv_portrait;
private String name;
private String signature;
public int getIv_portrait() {
return iv_portrait;
}
public void setIv_portrait(int iv_portrait) {
this.iv_portrait = iv_portrait;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getSignature() {
return signature;
}
public void setSignature(String signature) {
this.signature = signature;
}
}
</span>