Java学习者论坛

 找回密码
 立即注册

QQ登录

只需一步,快速开始

手机号码,快捷登录

恭喜Java学习者论坛(https://www.javaxxz.com)已经为数万Java学习者服务超过8年了!积累会员资料超过10000G+
成为本站VIP会员,下载本站10000G+会员资源,购买链接:点击进入购买VIP会员
JAVA高级面试进阶视频教程Java架构师系统进阶VIP课程

分布式高可用全栈开发微服务教程

Go语言视频零基础入门到精通

Java架构师3期(课件+源码)

Java开发全终端实战租房项目视频教程

SpringBoot2.X入门到高级使用教程

大数据培训第六期全套视频教程

深度学习(CNN RNN GAN)算法原理

Java亿级流量电商系统视频教程

互联网架构师视频教程

年薪50万Spark2.0从入门到精通

年薪50万!人工智能学习路线教程

年薪50万!大数据从入门到精通学习路线年薪50万!机器学习入门到精通视频教程
仿小米商城类app和小程序视频教程深度学习数据分析基础到实战最新黑马javaEE2.1就业课程从 0到JVM实战高手教程 MySQL入门到精通教程
查看: 200|回复: 0

[默认分类] Android自定义圆形图片

[复制链接]
  • TA的每日心情
    开心
    2021-12-13 21:45
  • 签到天数: 15 天

    [LV.4]偶尔看看III

    发表于 2018-5-27 13:34:39 | 显示全部楼层 |阅读模式


    Android自定义圆形图片,可设置最多两个的外边框。包括从网络获取图片显示。
    解决图片锯齿问题。
    解决图片变形问题。




    原始图片:








    核心代码:

    1. /**
    2. * 圆形ImageView,可设置最多两个宽度不同且颜色不同的圆形边框。
    3. *
    4. * @author Alan
    5. */
    6. public class RoundImageView extends ImageView {
    7.         private int mBorderThickness = 0;
    8.         private Context mContext;
    9.         private int defaultColor = 0xFFFFFFFF;
    10.         // 如果只有其中一个有值,则只画一个圆形边框
    11.         private int mBorderOutsideColor = 0;
    12.         private int mBorderInsideColor = 0;
    13.         // 控件默认长、宽
    14.         private int defaultWidth = 0;
    15.         private int defaultHeight = 0;
    16.         public RoundImageView(Context context) {
    17.                 super(context);
    18.                 mContext = context;
    19.         }
    20.         public RoundImageView(Context context, AttributeSet attrs) {
    21.                 super(context, attrs);
    22.                 mContext = context;
    23.                 setCustomAttributes(attrs);
    24.         }
    25.         public RoundImageView(Context context, AttributeSet attrs, int defStyle) {
    26.                 super(context, attrs, defStyle);
    27.                 mContext = context;
    28.                 setCustomAttributes(attrs);
    29.         }
    30.         private void setCustomAttributes(AttributeSet attrs) {
    31.                 TypedArray a = mContext.obtainStyledAttributes(attrs,
    32.                                 R.styleable.roundedimageview);
    33.                 mBorderThickness = a.getDimensionPixelSize(
    34.                                 R.styleable.roundedimageview_border_thickness, 0);
    35.                 mBorderOutsideColor = a
    36.                                 .getColor(R.styleable.roundedimageview_border_outside_color,
    37.                                                 defaultColor);
    38.                 mBorderInsideColor = a.getColor(
    39.                                 R.styleable.roundedimageview_border_inside_color, defaultColor);
    40.         }
    41.         @Override
    42.         protected void onDraw(Canvas canvas) {
    43.                 Drawable drawable = getDrawable();
    44.                 if (drawable == null) {
    45.                         return;
    46.                 }
    47.                 if (getWidth() == 0 || getHeight() == 0) {
    48.                         return;
    49.                 }
    50.                 this.measure(0, 0);
    51.                 if (drawable.getClass() == NinePatchDrawable.class)
    52.                         return;
    53.                 Bitmap b = ((BitmapDrawable) drawable).getBitmap();
    54.                 Bitmap bitmap = b.copy(Bitmap.Config.ARGB_8888, true);
    55.                 if (defaultWidth == 0) {
    56.                         defaultWidth = getWidth();
    57.                 }
    58.                 if (defaultHeight == 0) {
    59.                         defaultHeight = getHeight();
    60.                 }
    61.                 // 保证重新读取图片后不会因为图片大小而改变控件宽、高的大小(针对宽、高为wrap_content布局的imageview,但会导致margin无效)
    62.                 // if (defaultWidth != 0 && defaultHeight != 0) {
    63.                 // LinearLayout.LayoutParams params = new LinearLayout.LayoutParams(
    64.                 // defaultWidth, defaultHeight);
    65.                 // setLayoutParams(params);
    66.                 // }
    67.                 int radius = 0;
    68.                 if (mBorderInsideColor != defaultColor
    69.                                 && mBorderOutsideColor != defaultColor) {// 定义画两个边框,分别为外圆边框和内圆边框
    70.                         radius = (defaultWidth < defaultHeight ? defaultWidth
    71.                                         : defaultHeight) / 2 - 2 * mBorderThickness;
    72.                         // 画内圆
    73.                         drawCircleBorder(canvas, radius + mBorderThickness / 2,
    74.                                         mBorderInsideColor);
    75.                         // 画外圆
    76.                         drawCircleBorder(canvas, radius + mBorderThickness
    77.                                         + mBorderThickness / 2, mBorderOutsideColor);
    78.                 } else if (mBorderInsideColor != defaultColor
    79.                                 && mBorderOutsideColor == defaultColor) {// 定义画一个边框
    80.                         radius = (defaultWidth < defaultHeight ? defaultWidth
    81.                                         : defaultHeight) / 2 - mBorderThickness;
    82.                         drawCircleBorder(canvas, radius + mBorderThickness / 2,
    83.                                         mBorderInsideColor);
    84.                 } else if (mBorderInsideColor == defaultColor
    85.                                 && mBorderOutsideColor != defaultColor) {// 定义画一个边框
    86.                         radius = (defaultWidth < defaultHeight ? defaultWidth
    87.                                         : defaultHeight) / 2 - mBorderThickness;
    88.                         drawCircleBorder(canvas, radius + mBorderThickness / 2,
    89.                                         mBorderOutsideColor);
    90.                 } else {// 没有边框
    91.                         radius = (defaultWidth < defaultHeight ? defaultWidth
    92.                                         : defaultHeight) / 2;
    93.                 }
    94.                 Bitmap roundBitmap = getCroppedRoundBitmap(bitmap, radius);
    95.                 canvas.drawBitmap(roundBitmap, defaultWidth / 2 - radius, defaultHeight
    96.                                 / 2 - radius, null);
    97.         }
    98.         /**
    99.          * 获取裁剪后的圆形图片
    100.          *
    101.          * @param radius
    102.          *            半径
    103.          */
    104.         public Bitmap getCroppedRoundBitmap(Bitmap bmp, int radius) {
    105.                 Bitmap scaledSrcBmp;
    106.                 int diameter = radius * 2;
    107.                 // 为了防止宽高不相等,造成圆形图片变形,因此截取长方形中处于中间位置最大的正方形图片
    108.                 int bmpWidth = bmp.getWidth();
    109.                 int bmpHeight = bmp.getHeight();
    110.                 int squareWidth = 0, squareHeight = 0;
    111.                 int x = 0, y = 0;
    112.                 Bitmap squareBitmap;
    113.                 if (bmpHeight > bmpWidth) {// 高大于宽
    114.                         squareWidth = squareHeight = bmpWidth;
    115.                         x = 0;
    116.                         y = (bmpHeight - bmpWidth) / 2;
    117.                         // 截取正方形图片
    118.                         squareBitmap = Bitmap.createBitmap(bmp, x, y, squareWidth,
    119.                                         squareHeight);
    120.                 } else if (bmpHeight < bmpWidth) {// 宽大于高
    121.                         squareWidth = squareHeight = bmpHeight;
    122.                         x = (bmpWidth - bmpHeight) / 2;
    123.                         y = 0;
    124.                         squareBitmap = Bitmap.createBitmap(bmp, x, y, squareWidth,
    125.                                         squareHeight);
    126.                 } else {
    127.                         squareBitmap = bmp;
    128.                 }
    129.                 if (squareBitmap.getWidth() != diameter
    130.                                 || squareBitmap.getHeight() != diameter) {
    131.                         scaledSrcBmp = Bitmap.createScaledBitmap(squareBitmap, diameter,
    132.                                         diameter, true);
    133.                 } else {
    134.                         scaledSrcBmp = squareBitmap;
    135.                 }
    136.                 Bitmap output = Bitmap.createBitmap(scaledSrcBmp.getWidth(),
    137.                                 scaledSrcBmp.getHeight(), Config.ARGB_8888);
    138.                 Canvas canvas = new Canvas(output);
    139.                 Paint paint = new Paint();
    140.                 Rect rect = new Rect(0, 0, scaledSrcBmp.getWidth(),
    141.                                 scaledSrcBmp.getHeight());
    142.                 paint.setAntiAlias(true);
    143.                 paint.setFilterBitmap(true);
    144.                 paint.setDither(true);
    145.                 canvas.drawARGB(0, 0, 0, 0);
    146.                 canvas.drawCircle(scaledSrcBmp.getWidth() / 2,
    147.                                 scaledSrcBmp.getHeight() / 2, scaledSrcBmp.getWidth() / 2,
    148.                                 paint);
    149.                 paint.setXfermode(new PorterDuffXfermode(Mode.SRC_IN));
    150.                 canvas.drawBitmap(scaledSrcBmp, rect, rect, paint);
    151.                 // bitmap回收(recycle导致在布局文件XML看不到效果)
    152.                 // bmp.recycle();
    153.                 // squareBitmap.recycle();
    154.                 // scaledSrcBmp.recycle();
    155.                 bmp = null;
    156.                 squareBitmap = null;
    157.                 scaledSrcBmp = null;
    158.                 return output;
    159.         }
    160.         /**
    161.          * 边缘画圆
    162.          */
    163.         private void drawCircleBorder(Canvas canvas, int radius, int color) {
    164.                 Paint paint = new Paint();
    165.                 /* 去锯齿 */
    166.                 paint.setAntiAlias(true);
    167.                 paint.setFilterBitmap(true);
    168.                 paint.setDither(true);
    169.                 paint.setColor(color);
    170.                 /* 设置paint的 style 为STROKE:空心 */
    171.                 paint.setStyle(Paint.Style.STROKE);
    172.                 /* 设置paint的外框宽度 */
    173.                 paint.setStrokeWidth(mBorderThickness);
    174.                 canvas.drawCircle(defaultWidth / 2, defaultHeight / 2, radius, paint);
    175.         }
    176. }
    复制代码


    布局文件:

    1. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    2.     xmlns:tools="http://schemas.android.com/tools"
    3.     xmlns:imagecontrol="http://schemas.android.com/apk/res-auto"
    4.     android:layout_width="match_parent"
    5.     android:layout_height="match_parent"
    6.     android:background="#fffffdfa"
    7.     android:orientation="vertical"
    8.     android:paddingBottom="@dimen/activity_vertical_margin"
    9.     android:paddingLeft="@dimen/activity_vertical_margin"
    10.     android:paddingRight="@dimen/activity_vertical_margin"
    11.     android:paddingTop="@dimen/activity_vertical_margin"
    12.     tools:context=".MainActivity" >
    13.     <LinearLayout
    14.         android:layout_width="match_parent"
    15.         android:layout_height="wrap_content"
    16.         android:orientation="horizontal" >
    17.         <com.alan.roundimageview.RoundImageView
    18.             android:id="@+id/roundImage_network"
    19.             android:layout_width="60dp"
    20.             android:layout_height="60dp"
    21.             android:src="@drawable/default_portrait" />
    22.         <com.alan.roundimageview.RoundImageView
    23.             android:id="@+id/roundImage_one_border"
    24.             android:layout_width="80dp"
    25.             android:layout_height="80dp"
    26.             android:layout_marginLeft="10dp"
    27.             android:layout_marginRight="10dp"
    28.             imagecontrol:border_outside_color="#FFFF0000"
    29.             imagecontrol:border_thickness="2dp"
    30.             android:src="@drawable/default_portrait" />
    31.         <com.alan.roundimageview.RoundImageView
    32.             android:id="@+id/roundImage_two_border"
    33.             android:layout_width="120dp"
    34.             android:layout_height="120dp"
    35.             android:scaleType="centerCrop"
    36.             imagecontrol:border_inside_color="#fff7f2e9"
    37.             imagecontrol:border_outside_color="#ffd5d1c8"
    38.             imagecontrol:border_thickness="2dp"
    39.             android:src="@drawable/default_portrait"/>
    40.     </LinearLayout>
    41.     <LinearLayout
    42.         android:layout_width="match_parent"
    43.         android:layout_height="wrap_content"
    44.         android:layout_marginTop="10dp"
    45.         android:orientation="horizontal" >
    46.         <com.alan.roundimageview.RoundImageView
    47.             android:layout_width="60dp"
    48.             android:layout_height="60dp"
    49.             android:src="@drawable/default_portrait" />
    50.         <com.alan.roundimageview.RoundImageView
    51.             android:layout_width="80dp"
    52.             android:layout_height="80dp"
    53.             android:layout_marginLeft="10dp"
    54.             android:layout_marginRight="10dp"
    55.             imagecontrol:border_outside_color="#FFFF0000"
    56.             imagecontrol:border_thickness="2dp"
    57.             android:src="@drawable/default_portrait"/>
    58.         <com.alan.roundimageview.RoundImageView
    59.             android:layout_width="120dp"
    60.             android:layout_height="120dp"
    61.             android:scaleType="centerCrop"
    62.             imagecontrol:border_inside_color="#fff7f2e9"
    63.             imagecontrol:border_outside_color="#ffd5d1c8"
    64.             imagecontrol:border_thickness="2dp"
    65.             android:src="@drawable/default_portrait" />
    66.     </LinearLayout>
    67. </LinearLayout>
    复制代码






    源代码下载


    回复

    使用道具 举报

    您需要登录后才可以回帖 登录 | 立即注册

    本版积分规则

    QQ|手机版|Java学习者论坛 ( 声明:本站资料整理自互联网,用于Java学习者交流学习使用,对资料版权不负任何法律责任,若有侵权请及时联系客服屏蔽删除 )

    GMT+8, 2024-6-12 07:43 , Processed in 0.388866 second(s), 37 queries .

    Powered by Discuz! X3.4

    © 2001-2017 Comsenz Inc.

    快速回复 返回顶部 返回列表