安卓圆形头像
1、上效果图
2、源码地址:
http://yun.baidu.com/pcloud/album/file?album_id=2372756882992388602&uk=1077182200&fsid=2792621442
3、用法:
先说缺点:只能在xml中用src属性有效。用代码动态定义控件无效。
就说一点吧,因为用到自定义属性,所以需引用自定义的xmlns:
- xmlns:app="http://schemas.android.com/apk/res/de.hdodenhof.circleimageview.sample"
如果没有此句,则会报错:error: Error parsing XML: unbound prefix。
对于该控件用法:
- <de.hdodenhof.circleimageview.sample.CircleImageView
- android:layout_width="160dp"
- android:layout_height="160dp"
- android:src="@drawable/hugh"
- app:border_color="@color/light" //边框颜色
- app:border_width="2dp" /> //边框宽度
贴下源码吧,不用下载了,就用到这个类和values包下的attrs.xml文件:
- <?xml version="1.0" encoding="utf-8"?>
- <resources>
- <declare-styleable name="CircleImageView">
- <attr name="border_width" format="dimension" />
- <attr name="border_color" format="color" />
- </declare-styleable>
- </resources>
- package de.hdodenhof.circleimageview.sample;
- import android.content.Context;
- import android.content.res.TypedArray;
- import android.graphics.Bitmap;
- import android.graphics.BitmapShader;
- import android.graphics.Canvas;
- import android.graphics.Color;
- import android.graphics.Matrix;
- import android.graphics.Paint;
- import android.graphics.RectF;
- import android.graphics.Shader;
- import android.graphics.drawable.BitmapDrawable;
- import android.graphics.drawable.ColorDrawable;
- import android.graphics.drawable.Drawable;
- import android.util.AttributeSet;
- import android.widget.ImageView;
- public class CircleImageView extends ImageView {
- private static final ScaleType SCALE_TYPE = ScaleType.CENTER_CROP;
- private static final Bitmap.Config BITMAP_CONFIG = Bitmap.Config.ARGB_8888;
- private static final int COLORDRAWABLE_DIMENSION = 1;
- private static final int DEFAULT_BORDER_WIDTH = 0;
- private static final int DEFAULT_BORDER_COLOR = Color.BLACK;
- private final RectF mDrawableRect = new RectF();
- private final RectF mBorderRect = new RectF();
- private final Matrix mShaderMatrix = new Matrix();
- private final Paint mBitmapPaint = new Paint();
- private final Paint mBorderPaint = new Paint();
- private int mBorderColor = DEFAULT_BORDER_COLOR;
- private int mBorderWidth = DEFAULT_BORDER_WIDTH;
- private Bitmap mBitmap;
- private BitmapShader mBitmapShader;
- private int mBitmapWidth;
- private int mBitmapHeight;
- private float mDrawableRadius;
- private float mBorderRadius;
- private boolean mReady;
- private boolean mSetupPending;
- public CircleImageView(Context context) {
- super(context);
- }
- public CircleImageView(Context context, AttributeSet attrs) {
- this(context, attrs, 0);
- }
- public CircleImageView(Context context, AttributeSet attrs, int defStyle) {
- super(context, attrs, defStyle);
- super.setScaleType(SCALE_TYPE);
- TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.CircleImageView, defStyle, 0);
- mBorderWidth = a.getDimensionPixelSize(R.styleable.CircleImageView_border_width, DEFAULT_BORDER_WIDTH);
- mBorderColor = a.getColor(R.styleable.CircleImageView_border_color, DEFAULT_BORDER_COLOR);
- a.recycle();
- mReady = true;
- if (mSetupPending) {
- setup();
- mSetupPending = false;
- }
- }
- @Override
- public ScaleType getScaleType() {
- return SCALE_TYPE;
- }
- @Override
- public void setScaleType(ScaleType scaleType) {
- if (scaleType != SCALE_TYPE) {
- throw new IllegalArgumentException(String.format("ScaleType %s not supported.", scaleType));
- }
- }
- @Override
- protected void onDraw(Canvas canvas) {
- if (getDrawable() == null) {
- return;
- }
- canvas.drawCircle(getWidth() / 2, getHeight() / 2, mDrawableRadius, mBitmapPaint);
- canvas.drawCircle(getWidth() / 2, getHeight() / 2, mBorderRadius, mBorderPaint);
- }
- @Override
- protected void onSizeChanged(int w, int h, int oldw, int oldh) {
- super.onSizeChanged(w, h, oldw, oldh);
- setup();
- }
- public int getBorderColor() {
- return mBorderColor;
- }
- public void setBorderColor(int borderColor) {
- if (borderColor == mBorderColor) {
- return;
- }
- mBorderColor = borderColor;
- mBorderPaint.setColor(mBorderColor);
- invalidate();
- }
- public int getBorderWidth() {
- return mBorderWidth;
- }
- public void setBorderWidth(int borderWidth) {
- if (borderWidth == mBorderWidth) {
- return;
- }
- mBorderWidth = borderWidth;
- setup();
- }
- @Override
- public void setImageBitmap(Bitmap bm) {
- super.setImageBitmap(bm);
- mBitmap = bm;
- setup();
- }
- @Override
- public void setImageDrawable(Drawable drawable) {
- super.setImageDrawable(drawable);
- mBitmap = getBitmapFromDrawable(drawable);
- setup();
- }
- @Override
- public void setImageResource(int resId) {
- super.setImageResource(resId);
- mBitmap = getBitmapFromDrawable(getDrawable());
- setup();
- }
- private Bitmap getBitmapFromDrawable(Drawable drawable) {
- if (drawable == null) {
- return null;
- }
- if (drawable instanceof BitmapDrawable) {
- return ((BitmapDrawable) drawable).getBitmap();
- }
- try {
- Bitmap bitmap;
- if (drawable instanceof ColorDrawable) {
- bitmap = Bitmap.createBitmap(COLORDRAWABLE_DIMENSION, COLORDRAWABLE_DIMENSION, BITMAP_CONFIG);
- } else {
- bitmap = Bitmap.createBitmap(drawable.getIntrinsicWidth(), drawable.getIntrinsicHeight(), BITMAP_CONFIG);
- }
- Canvas canvas = new Canvas(bitmap);
- drawable.setBounds(0, 0, canvas.getWidth(), canvas.getHeight());
- drawable.draw(canvas);
- return bitmap;
- } catch (OutOfMemoryError e) {
- return null;
- }
- }
- private void setup() {
- if (!mReady) {
- mSetupPending = true;
- return;
- }
- if (mBitmap == null) {
- return;
- }
- mBitmapShader = new BitmapShader(mBitmap, Shader.TileMode.CLAMP, Shader.TileMode.CLAMP);
- mBitmapPaint.setAntiAlias(true);
- mBitmapPaint.setShader(mBitmapShader);
- mBorderPaint.setStyle(Paint.Style.STROKE);
- mBorderPaint.setAntiAlias(true);
- mBorderPaint.setColor(mBorderColor);
- mBorderPaint.setStrokeWidth(mBorderWidth);
- mBitmapHeight = mBitmap.getHeight();
- mBitmapWidth = mBitmap.getWidth();
- mBorderRect.set(0, 0, getWidth(), getHeight());
- mBorderRadius = Math.min((mBorderRect.height() - mBorderWidth) / 2, (mBorderRect.width() - mBorderWidth) / 2);
- mDrawableRect.set(mBorderWidth, mBorderWidth, mBorderRect.width() - mBorderWidth, mBorderRect.height() - mBorderWidth);
- mDrawableRadius = Math.min(mDrawableRect.height() / 2, mDrawableRect.width() / 2);
- updateShaderMatrix();
- invalidate();
- }
- private void updateShaderMatrix() {
- float scale;
- float dx = 0;
- float dy = 0;
- mShaderMatrix.set(null);
- if (mBitmapWidth * mDrawableRect.height() > mDrawableRect.width() * mBitmapHeight) {
- scale = mDrawableRect.height() / (float) mBitmapHeight;
- dx = (mDrawableRect.width() - mBitmapWidth * scale) * 0.5f;
- } else {
- scale = mDrawableRect.width() / (float) mBitmapWidth;
- dy = (mDrawableRect.height() - mBitmapHeight * scale) * 0.5f;
- }
- mShaderMatrix.setScale(scale, scale);
- mShaderMatrix.postTranslate((int) (dx + 0.5f) + mBorderWidth, (int) (dy + 0.5f) + mBorderWidth);
- mBitmapShader.setLocalMatrix(mShaderMatrix);
- }
- }