android 自定义圆角头像以及使用declare-styleable进行配置属性解析
android屏幕圆角实现方法的示例代码
android屏幕圆⾓实现⽅法的⽰例代码现在很多全⾯屏⼿机的屏幕四⾓做成圆的,其圆润的感觉给⼈带来别样的视觉体验。
先来⼀张我⼤锤⼦镇楼(不是⼴告呀,锤⼦没给钱),⼤家来直观感受⼀下圆⾓的魅⼒。
锤⼦.jpg当然这种是硬件上实现的,我怀疑也是⽅的显⽰屏,然后做了个圆⾓遮蔽。
那对于我们这些脸⽅的⼿机,就不能笑嘻嘻的圆⼀回吗?答案是肯定的,no picture say ...效果图(应该能看出来我⽤的是神马⼿机吧)圆⾓实现:那我们就应该思考了,软件层⾯怎样实现这种效果呢。
相信很多朋友⽴马会想到——使⽤悬浮窗。
实现原理:利⽤WindowManager将我们的圆⾓加到屏幕的四个⾓,圆⾓颜⾊设置为⿊⾊,形成视觉圆⾓屏幕。
1.⾃定义圆⾓view很显然,⾸先我们需要实现⼀个形状如下图的圆⾓,怎么做呢?⽤path(不熟悉的⼩伙伴可以百度⼀下哈),这⾥我们以左上⾓为例实现这个圆⾓。
圆⾓// top leftcase Gravity.TOP | Gravity.LEFT:path.moveTo(0.0f, 0.0f);path.lineTo(0.0f, (float) h);path.arcTo(new RectF(0.0f, 0.0f,((float) w) * 2.0f, ((float) h) * 2.0f), 180.0f, 90.0f, true);path.lineTo((float) w, 0.0f);path.lineTo(0.0f, 0.0f);path.close();break;为了能让⽤户⾃定义圆⾓颜⾊,⼤⼩,透明度,各个⾓是否显⽰,我在⾥⾯加了对应的控制变量,当⽤户设置的时候更新view就可以了。
public void setCornerSize(int size){this.cornerSize = size;requestLayout();invalidate();}是不是很简单,这样⼀个圆⾓view就实现了。
自定义view实现圆角图片
自定义view实现圆角图片前两天想实现一个圆角图片的效果,通过网络搜索后找到一些答案。
这里自己再记录一下,加深一下自己的认识和知识理解。
?实现圆角图片的思路是自定义一个ImageView,然后通过Ondraw()重绘的功能,将drawable和一个圆形进行重叠绘制,这样就可以达到圆角的效果了。
?下面开始具体实现圆角图片的过程。
第一步:写自定义属性文件首先我们需要定义一个属性。
在values目录下面新建一个xml文件,这个文件用来自定义一些属性,这样我们就可以写出自己的控件了。
我来简单解释一下,declare-styleable这个标签就是用来自定义属性的,attr标签用来定义具体的属性,format可以指定很多种格式,具体有哪些属性,这里不做过多介绍了,请看博客中的介绍:本来图片修改为圆形,其他地方都是透明2.只是让显示的时候,动态的裁剪到一些部分,然后让图片变圆。
这两种方法的优劣我想大家一眼就能看明白。
直接修改图片,带来的后果是,我如果换了一种方式了,不再是圆角,而是星型,那么我们的图片已经毁掉了,没办法在重用了。
而第二种方式就可以,无论我们换什么样的表现方式,我们是需要换一种裁剪的算法,就可以实现不同的形状的图片了,那么很显然,第二种方法是以不变应万变的。
那么现在,我们选定了第二种方式,那怎么实现呢有人说我们自己写一个类,直接继承自view,然后所有的绘图和大小的计算我们都自己来搞,这样行吗当然可行,但是我们可能是在重复造轮子,因为我们已经有了一个ImageView,而且它里面给我们做了很多关于图片的操作,我们何不继承自ImageView,然后做少量的工作,就可以实现圆角效果呢。
方案确定,好,那我们就开始实现自己的类。
我们定义一个RoundImageView 继承自ImageView?然后两个成员变量,分别对应于自定义属性文件中的BorderRadius和RoundType。
?接下来我们重写构造函数首先是mPaint的初始化,这是一个画刷,用来画图形的,后面会说。
Android-解析自定义view之圆形头像的各类方案
Android-解析自定义view之圆形头像的各类方案我们可以看到很多app都采用了圆形头像,那么怎么绘制圆形头像才是性能最好?代码复用性最强?也最方便呢?本博主做了一些探究。
文章结构:1.利用shape来制作圆形头像(一种死方案,要求是美工愿意配合你) 2.结合一个会导致oom的实现圆形头像方案进行性能分析 3.最优的圆形头像方案一、利用shape来制作圆形头像(要求是美工愿意配合你)为什么要求美工配合你呢??因为这个方案是在ImageView直接调用资源文件的,也就是直接用了ImageView的LayoutParams的match_parent模式。
不能按照那个圆的大小来适配。
给出代码讲解:drawable文件的shape标签<?xml version="1.0" encoding="utf-8"?><shape xmlns:android="/apk/res/android"android:shape="oval"><!-- Corner的属性是设置圆角的半径的--><solid android:color="#FFFFFF" /><strokeandroid:width="2dp"android:color="#777777"></stroke><sizeandroid:width="120dp"android:height="120dp" /></shape>在xml文件中的调用:<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="/apk/res/android"xmlns:app="/apk/res-auto"xmlns:tools="/tools"android:layout_width="match_parent"android:layout_height="match_parent"android:orientation="vertical"tools:context="com.demo.fuzhucheng.someShapesImageview.ImageViewActivity"><!--第一种方案--><ImageViewandroid:id="@+id/shapecircle"android:layout_width="150dp"android:layout_height="150dp"android:background="@drawable/activity_circle_circleimageview"android:src="@drawable/activity_imageview_photo" /><!--最优方案,也就是本文的第三种方案--><com.demo.fuzhucheng.someShapesImageview.CircleImageview android:id="@+id/mycircle"android:layout_width="180dp"android:layout_height="180dp"android:background="@color/white"android:src="@drawable/timg"app:backgroundHeadColor="@color/yellow"app:circleBorderHeadWidth="5dp"app:ringHeadColor="@color/colorAccent" /></LinearLayout>二、对一种容易导致OOM的方案进行分析:给出代码分析:下面这个是别人的代码,由于点评就不给链接的。
Android对控件设置边框样式(边框颜色,圆角)和图片样式(圆角)
Android对控件设置边框样式(边框颜⾊,圆⾓)和图⽚样式(圆⾓)1、设置边框、圆⾓、背景⾊案例在drawable中新建⼀个edge.xml⽂件<?xml version="1.0" encoding="utf-8"?><shape xmlns:android="/apk/res/android"><!-- 这⾥是设置背景⾊--><solid android:color="@color/colorGrey"/><!-- 这⾥是设置为四周也可以单独设置某个位置为圆⾓--><corners android:topLeftRadius="5dp"android:topRightRadius="5dp"android:bottomRightRadius="5dp"android:bottomLeftRadius="5dp"/><!-- 这⾥设置边框 --><stroke android:width="1dp" android:color="#000000"/></shape>Activity页⾯引⽤:android:background="@drawable/edge"如下案例所⽰:<ScrollViewandroid:id="@+id/scrollView2"android:layout_width="0dp"android:layout_height="0dp"android:layout_marginStart="8dp"android:layout_marginTop="8dp"android:layout_marginEnd="8dp"android:layout_marginBottom="8dp"app:layout_constraintBottom_toTopOf="@+id/guideline"app:layout_constraintEnd_toEndOf="parent"app:layout_constraintHorizontal_bias="0.0"app:layout_constraintStart_toStartOf="parent"app:layout_constraintTop_toTopOf="parent"app:layout_constraintVertical_bias="0.0"android:background="@drawable/edge"><LinearLayoutandroid:layout_width="match_parent"android:layout_height="wrap_content"android:orientation="vertical"><TextViewandroid:id="@+id/et"android:layout_width="match_parent"android:layout_height="wrap_content"android:minLines="8"android:text="123456789"/></LinearLayout></ScrollView>说明: solid为填充⾊即内部的背景填充⾊,stroke 为边框可以设置颜⾊和宽度效果如下:2、设置边框颜⾊案例:在drawable中新建⼀个button_edge.xml⽂件<?xml version="1.0" encoding="utf-8"?><layer-list xmlns:android="/apk/res/android"><!-- 边框颜⾊值 --><item><shape><solid android:color="#3bbaff"/></shape></item><!--这个是按钮边框设置为四周并且宽度为1--><itemandroid:right="1dp"android:left="1dp"android:top="1dp"android:bottom="1dp"><shape><!--这个是背景颜⾊--><solid android:color="#ffffff"/><!--这个是按钮中的字体与按钮内的四周边距--><padding android:bottom="5dp"android:left="5dp"android:right="5dp"android:top="5dp"/></shape></item></layer-list>使⽤:android:background="@drawable/button_edge"3、设置圆⾓按钮案例:(其实按钮还是⽅形的,只是将外围部分隐藏了⽽已)在drawable中:新建⼀个 button_circle_shape.xml⽂件<?xml version="1.0" encoding="UTF-8"?><shapexmlns:android="/apk/res/android"android:shape="rectangle"><!-- 填充的颜⾊ --><solid android:color="#FFFFFF"/><!-- android:radius 弧形的半径 --><!-- 设置按钮的四个⾓为弧形 --><cornersandroid:radius="5dip"/><!--也可单独设置--><!-- <corners --><!-- android:topLeftRadius="10dp"--><!-- android:topRightRadius="10dp"--><!-- android:bottomRightRadius="10dp"--><!-- android:bottomLeftRadius="10dp"--><!-- /> -->**设置⽂字padding**<!-- padding:Button⾥⾯的⽂字与Button边界的间隔 --><paddingandroid:left="10dp"android:top="10dp"android:right="10dp"android:bottom="10dp"/></shape>使⽤:android:background="@drawable/shape"4、设置圆⾓图⽚案例1 简单的设置:(不能添加⾃定义图⽚只能设置颜⾊和字体)在drawable中创建⼀个image_circle.xml图⽚<?xml version="1.0" encoding="utf-8"?><shape xmlns:android="/apk/res/android"><solid android:color="#FFFFFF"/><corners android:topLeftRadius="10dp"android:topRightRadius="10dp"android:bottomRightRadius="10dp"android:bottomLeftRadius="10dp"/></shape>使⽤:android:background="@drawable/image_circle"5、真实案例:edge.xml<?xml version="1.0" encoding="utf-8"?><layer-list xmlns:android="/apk/res/android"><!-- 边框颜⾊值 --><item><shape><solid android:color="#3bbaff"/></shape></item><!--这个是按钮边框设置为四周并且宽度为1--><itemandroid:right="1dp"android:left="1dp"android:top="1dp"android:bottom="1dp"><shape><!--这个是背景颜⾊--><solid android:color="#ffffff"/><!--这个是按钮中的字体与按钮内的四周边距--><padding android:bottom="5dp"android:left="5dp"android:right="5dp"android:top="5dp"/></shape></item></layer-list>布局⽂件 LeftFragment.xml:<?xml version="1.0" encoding="utf-8"?><FrameLayout xmlns:android="/apk/res/android" xmlns:tools="/tools"android:layout_width="match_parent"android:layout_height="match_parent"tools:context=".LeftFragment"><LinearLayoutandroid:layout_width="match_parent"android:layout_height="match_parent"android:layout_gravity="center"android:orientation="vertical"><LinearLayoutandroid:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_gravity="center_horizontal"android:orientation="horizontal"android:padding="10dp"><ImageViewandroid:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_gravity="center_horizontal"android:src="@mipmap/user"/><TextViewandroid:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_gravity="center_horizontal"android:text="⼿⼯登录"android:textSize="20sp"/></LinearLayout><LinearLayoutandroid:layout_width="match_parent"android:layout_height="wrap_content"android:padding="10dp"android:background="@drawable/edge"android:layout_marginLeft="5dp"android:layout_marginRight="5dp"><TextViewandroid:layout_width="wrap_content"android:layout_height="wrap_content"android:paddingLeft="20dp"android:text="账号"android:textSize="15sp"/><EditTextandroid:layout_width="match_parent"android:layout_height="wrap_content"android:hint="请输⼊⼯⼚管理系统账号"android:background="@null"android:paddingLeft="10dp"android:textSize="15sp"/></LinearLayout><LinearLayoutandroid:layout_width="match_parent"android:layout_height="wrap_content"android:padding="10dp"android:background="@drawable/edge"android:layout_marginLeft="5dp"android:layout_marginRight="5dp"><TextViewandroid:layout_width="wrap_content"android:layout_height="wrap_content"android:paddingLeft="20dp"android:textSize="15sp"android:text="密码"/><EditTextandroid:layout_width="match_parent"android:layout_height="wrap_content"android:hint="请输⼊⼯⼚管理系统登录密码" android:background="@null"android:paddingLeft="10dp"android:textSize="15sp"/></LinearLayout><CheckBoxandroid:layout_width="match_parent"android:layout_height="wrap_content"android:padding="10dp"android:text="记住密码"/><Buttonandroid:layout_width="match_parent"android:layout_height="wrap_content"android:padding="10dp"android:text="登录"/><TextViewandroid:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_gravity="center"android:text="登录出现问题?"/></LinearLayout></FrameLayout>。
Android自定义Drawable实现圆角效果
Android⾃定义Drawable实现圆⾓效果Drawable是⼀种可绘制资源的载体,如图形、图像等。
在实际开发中可以作为view的背景。
主要有静态和动态两种⽅式,静态通过xml描述使⽤,动态即⾃定义Drawable。
本⽂实现⼀个圆形和圆⾓的背景图⽚效果。
效果图:实现⽅式:1.初始化⼀个BitmapShader着⾊器对象;2.将着⾊器对象set给画笔;3.在画布上绘制圆或圆⾓即可;4.使⽤,view.setBackgroundDrawable或者 ImageView.setImageDrawablepackage com.mydrawable.musk;import android.graphics.Bitmap;import android.graphics.BitmapShader;import android.graphics.Canvas;import android.graphics.ColorFilter;import android.graphics.Paint;import android.graphics.PixelFormat;import android.graphics.Shader;import android.graphics.drawable.Drawable;/*** Created by musk.*/public class CircleDrawable extends Drawable {private Paint mPaint;private int mWidth;private Bitmap mBitmap;public CircleDrawable(Bitmap bitmap) {mBitmap = bitmap;//着⾊器,设置横向和纵向的着⾊模式为平铺BitmapShader bitmapShader = new BitmapShader(mBitmap,Shader.TileMode.CLAMP, Shader.TileMode.CLAMP);mPaint = new Paint();mPaint.setAntiAlias(true);mPaint.setDither(true);mPaint.setShader(bitmapShader);mWidth = Math.min(mBitmap.getWidth(), mBitmap.getHeight());}//绘制@Overridepublic void draw(Canvas canvas) {canvas.drawCircle(mWidth / 2, mWidth / 2, mWidth / 2, mPaint);}//设置透明度值@Overridepublic void setAlpha(int alpha) {mPaint.setAlpha(alpha);}//设置颜⾊过滤器@Overridepublic void setColorFilter(ColorFilter colorFilter) {mPaint.setColorFilter(colorFilter);}//返回不透明度@Overridepublic int getOpacity() {return PixelFormat.TRANSLUCENT;}//返回图⽚实际的宽⾼@Overridepublic int getIntrinsicWidth() {return mWidth;}@Overridepublic int getIntrinsicHeight() {return mWidth;}}⾃定义Drawable有五个⽅法必须覆写,draw()、setAlpha()、setColorFilter()、getOpacity(),另外的getIntrinsicWidth()和getIntrinsicHeight()是在view设置wrap_content时设置drawable的宽度和⾼度。
自定义view实现圆角图片(终审稿)
?
到现在为止我们完成了万里长征第一步,获取到了我们自定义控件的属性了。
接下来就是我们的重头戏,重绘图片。下面我们重写了OnDraw函数
那么现在,我们选定了第二种方式,那怎么实现呢有人说我们自己写一个类,直接继承自view,然后所有的绘图和大小的计算我们都自己来搞,这样行吗当然可行,但是我们可能是在重复造轮子,因为我们已经有了一个ImageView,而且它里面给我们做了很多关于图片的操作,我们何不继承自ImageView,然后做少量的工作,就可以实现圆角效果呢。方案确定,好,那我们就开始实现自己的类。
{
(getWidth()/2, getHeight()/2, mBorderRadius, pa);
}
return bit;
}
看看上面的代码,是不是很熟悉,我们之前已经接触过基本的画图方法了。想必,不用解释了,一眼都能看明白。这里我只实现了画圆的,大家可以各自发挥想想,画出各种各样的形状,哈哈,是不是很容易,我们自己实现了圆角图像,同时对于android自定义view的绘制也有了大致了解。
1
(mMashBitmap, 0,0, mPaint); 此时,bitmap中保存的就是叠加之后的图片了,也就是我们最终需要的圆角图片了。最后我们将这个bitmap绘制到OnDraw函数给我们传递进来的<br>canvas上,所有工作就基本做完了。(bitmap, 0,0, null);<br>最后将绘制好的图片保存起来。<em id="__mceDel">mWeakBitmap = new WeakReference<Bitmap>(bitmap);<br><br></em>下一次执行ondraw 的时候,我们就直接用保存好的bitmap进行绘制了,也就是我们代码中else的部分。<br><br>最艰难的部分说完了,哈哈,如果不理解还是得多看几遍。接下来的工作就轻松了很多,对了,我们还没有实现之前那个绘制形状的函数呢。我们来绘制把。很容易的。<br><br>
Android自定义ViewGroup实现带箭头的圆角矩形菜单
Android⾃定义ViewGroup实现带箭头的圆⾓矩形菜单本⽂和⼤家⼀起做⼀个带箭头的圆⾓矩形菜单,⼤概长下⾯这个样⼦:要求顶上的箭头要对准菜单锚点,菜单项按压反⾊,菜单背景⾊和按压⾊可配置。
最简单的做法就是让UX给个三⾓形的图⽚往上⼀贴,但是转念⼀想这样是不是太low了点,⽽且不同分辨率也不太好适配,⼲脆⾃定义⼀个ViewGroup吧!⾃定义ViewGroup其实很简单,基本都是按⼀定的套路来的。
⼀、定义⼀个attrs.xml就是声明⼀下你的这个⾃定义View有哪些可配置的属性,将来使⽤的时候可以⾃由配置。
这⾥声明了7个属性,分别是:箭头宽度、箭头⾼度、箭头⽔平偏移、圆⾓半径、菜单背景⾊、阴影⾊、阴影厚度。
<resources><declare-styleable name="ArrowRectangleView"><attr name="arrow_width" format="dimension" /><attr name="arrow_height" format="dimension" /><attr name="arrow_offset" format="dimension" /><attr name="radius" format="dimension" /><attr name="background_color" format="color" /><attr name="shadow_color" format="color" /><attr name="shadow_thickness" format="dimension" /></declare-styleable></resources>⼆、写⼀个继承ViewGroup的类,在构造函数中初始化这些属性这⾥需要⽤到⼀个obtainStyledAttributes()⽅法,获取⼀个TypedArray对象,然后就可以根据类型获取相应的属性值了。
glide设置圆角方法
glide设置圆角方法(原创实用版3篇)目录(篇1)1.Glide 简介2.设置圆角的方法3.示例代码正文(篇1)1.Glide 简介Glide 是一个流行的 Android 图像加载库,它提供了高效的图片加载和缓存功能。
Glide 旨在简化图片加载的过程,并提供更好的性能和用户体验。
在 Glide 中,我们可以通过设置圆角来改变图片的显示效果,使图片更加圆润。
2.设置圆角的方法要在 Glide 中设置圆角,我们可以使用`setCircleClip()`方法。
这个方法接受一个布尔值,当为`true`时,图片将显示为圆形,当为`false`时,图片将显示为矩形。
此外,我们还可以通过`setRadius()`方法设置圆角的半径。
3.示例代码下面是一个使用 Glide 设置圆角的示例代码:```javaimport com.bumptech.glide.Glide;import com.bumptech.glide.load.ImageResource;public class MainActivity extends AppCompatActivity {@Overrideprotected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState);setContentView(yout.activity_main);// 加载图片并设置圆角Glide.with(this).load(R.drawable.image).circleClip(true) // 设置图片为圆形.radius(50) // 设置圆角半径.into(imageView);}}```在这个示例中,我们使用`Glide.with()`方法加载`R.drawable.image`中的图片,并使用`circleClip(true)`方法设置图片为圆形,同时使用`radius(50)`方法设置圆角半径。
Android实现圆形图片或者圆角图片
Android实现圆形图⽚或者圆⾓图⽚Android圆形图⽚或者圆⾓图⽚的快速实现,具体内容如下话不多说直接上codexml⽂件布局<LinearLayoutandroid:id="@+id/ll_headpict"android:layout_width="match_parent"android:layout_height="97dp"android:layout_margin="13dp"android:background="@drawable/shape_white_radius10_solid"android:gravity="center_vertical"android:orientation="horizontal"android:paddingLeft="25dp"><TextViewandroid:layout_width="0dp"android:layout_height="wrap_content"android:layout_weight="1"android:text="头像"android:textColor="@color/color4A4A4A"android:textSize="14sp"android:textStyle="bold" /><ImageViewandroid:id="@+id/iv_headpict"android:layout_width="60dp"android:layout_height="60dp"android:layout_marginRight="37dp"android:scaleType="fitXY"android:src="@mipmap/ic_headview_demo" /></LinearLayout>初始化控件之后⽤⼯具类加载//第⼀个参数上下⽂,第⼆个控件名称,第三个图⽚url地址,第四个参数圆⾓⼤⼩ViewUtils.loadImageRadius(this, mIvpict, stringUrl, 15);//头像ViewUtils.java⼯具类/*** Created by wjw on 2016/11/28* 倒圆⾓⼯具类*/public class ViewUtils {/*** 图⽚加载* @param context* @param iv* @param url*/public static void loadImage(Context context, ImageView iv, String url) {if(null ==context || null==iv){return;}if(Utils.isTxtEmpty(url)){try {Glide.with(context).load(R.mipmap.placeholder_icon) .dontAnimate().diskCacheStrategy(DiskCacheStrategy.ALL).into(iv);}catch (Exception e){}}else {try {Glide.with(context).load(url) .dontAnimate().diskCacheStrategy(DiskCacheStrategy.ALL).placeholder(R.mipmap.placeholder_icon).into(iv); } catch (Exception e) {}}}public static void loadImage(Context context, ImageView iv, int id) {if(null ==context || null==iv){return;}try {Glide.with(context).load(id) .dontAnimate().diskCacheStrategy(DiskCacheStrategy.ALL).placeholder(R.mipmap.placeholder_icon).into(iv); }catch (Exception e){}}/*** 本地图⽚* @param context* @param iv* @param id* @param radius*/public static void loadImage(Context context, ImageView iv, int id,int radius) {if(null ==context || null==iv){return;}try {Glide.with(context).load(id) .dontAnimate().diskCacheStrategy(DiskCacheStrategy.ALL).transform(new GlideRoundTransform(context, radius)).into(iv);}catch (Exception e){}}public static void setImageResource(ImageView iv, int id) {if(null!=iv){iv.setImageResource(id);}}/*** 加载⽹络图⽚(带圆⾓)* @param context* @param iv* @param url* @param radius*/public static void loadImageRadius(Context context, ImageView iv, String url, int radius) {if(null ==context || null==iv){return;}if(Utils.isTxtEmpty(url)){try {Glide.with(context).load(R.mipmap.placeholder_icon) .dontAnimate().diskCacheStrategy(DiskCacheStrategy.ALL).transform(new GlideRoundTransform(context, radius)).into(iv);}catch (Exception e){}}else{try {Glide.with(context).load(url) .dontAnimate().diskCacheStrategy(DiskCacheStrategy.ALL).transform(new GlideRoundTransform(context, radius)).placeholder(R.mipmap.placeholder_icon).into(iv);}catch (Exception e){}}}/*** 加载⽹络图⽚(圆形)* @param context* @param iv* @param url*/public static void loadImageCircle(Context context, ImageView iv, String url) {if(null ==context || null==iv){return;}if (Utils.isTxtEmpty(url)) {try {Glide.with(context).load(R.mipmap.placeholder_icon) .dontAnimate().diskCacheStrategy(DiskCacheStrategy.ALL).transform(new GlideCircleTransform(context)).into(iv);}catch (Exception e){}} else {try {Glide.with(context).load(url) .dontAnimate().diskCacheStrategy(DiskCacheStrategy.ALL).transform(new GlideCircleTransform(context)). placeholder(R.mipmap.placeholder_icon).into(iv);}catch (Exception e){}}}}效果如图圆⾓图⽚以上就是本⽂的全部内容,希望对⼤家的学习有所帮助,也希望⼤家多多⽀持。
android自定义圆角button效果的实例代码(自定义viewDemo)
android⾃定义圆⾓button效果的实例代码(⾃定义viewDemo)概述在平时开发过程中经常会碰到需要使⽤圆⾓button的情况,⼀般也会包括很多其他⼩功能,⽐如要在⾥⾯添加img,设置不同的圆⾓⼤⼩等。
针对这样的场景,直接使⽤创建多个shape,定义多个xml⽂件也是可以实现的。
但是如果使⽤⾮常频繁,那么直接⾃定义⼀个就会来的⾮常⽅便。
甚⾄在⼀些情况下,不是可以⽤shape定义的规则图形,⽐如需要⽤到贝塞尔曲线等。
如果全局需要这样风格的view,那么⾃定义⼀个View是⾮常必要的。
本⽂主要是个demo记录,如有需要的读者可以借鉴学习。
Demo主要实现功能:1. ⾃定义圆⾓⼤⼩2. ⽀持设置leftDrawable,和⾃定义⽂字内容(⽂字和img默认居中)3. ⽀持点击效果源码RoundRadiusButton.java/*** author: xujiajia* description:* 1、drawable只有在设置textString的时候才会⽣效(居中效果两个⼀起测量)*/public class RoundRadiusButton extends View {//dataprivate int width = 0;private int height = 0;private int roundRadius = 16;private int bgColor = Color.LTGRAY;private boolean isTouching = false;//img and textprivate Drawable leftDrawable = null;private int drawableWidth = 20;private int drawableHeight = 20;private int leftDrawablePaddingRight = 0;private String textString;private int textSize = 30;private int textColor = Color.BLACK;//onDrawPaint paint;Path path;RectF rectF;Rect rect;public RoundRadiusButton(Context context, int width, int height) {super(context);this.width = width;this.height = height;this.setLayoutParams(new youtParams(width, height));this.setClickable(true);}public RoundRadiusButton(Context context, AttributeSet attrs) {super(context, attrs);getDataFromAttrs(context, attrs);this.setClickable(true);}public RoundRadiusButton(Context context, AttributeSet attrs, int defStyleAttr) {super(context, attrs, defStyleAttr);getDataFromAttrs(context, attrs);this.setClickable(true);}private void getDataFromAttrs(Context context, AttributeSet attrs) {if (attrs == null) {return;}TypedArray ta = context.obtainStyledAttributes(attrs, R.styleable.RoundRadiusButton);roundRadius = ta.getDimensionPixelOffset(R.styleable.RoundRadiusButton_roundRadius, 16);bgColor = ta.getColor(R.styleable.RoundRadiusButton_bgColor, Color.LTGRAY);leftDrawable = ta.getDrawable(R.styleable.RoundRadiusButton_leftDrawable);drawableWidth = ta.getDimensionPixelOffset(R.styleable.RoundRadiusButton_drawableWidth, 0); drawableHeight = ta.getDimensionPixelOffset(R.styleable.RoundRadiusButton_drawableHeight, 0); leftDrawablePaddingRight =ta.getDimensionPixelOffset(R.styleable.RoundRadiusButton_leftDrawablePaddingRight, 0);textString = ta.getString(R.styleable.RoundRadiusButton_textString);textSize = ta.getDimensionPixelOffset(R.styleable.RoundRadiusButton_textSize, 0);textColor = ta.getColor(R.styleable.RoundRadiusButton_textColor, Color.BLACK);ta.recycle();}public void setRoundRadius(int roundRadius) {this.roundRadius = roundRadius;invalidate();}public void setBgColor(int bgColor) {this.bgColor = bgColor;invalidate();}public void setLeftDrawable(Drawable leftDrawable, int drawableWidth, int drawableHeight,int paddingRight) {this.leftDrawable = leftDrawable;this.drawableWidth = drawableWidth;this.drawableHeight = drawableHeight;this.leftDrawablePaddingRight = paddingRight;invalidate();}public void setTextString(String textString) {this.textString = textString;invalidate();}public void setTextColor(int textColor) {this.textColor = textColor;invalidate();}public void setTextSize(int textSize) {this.textSize = textSize;invalidate();}@Override public boolean onTouchEvent(MotionEvent event) {if (isClickable()) {switch (event.getAction()) {case MotionEvent.ACTION_DOWN:isTouching = true;invalidate();break;case MotionEvent.ACTION_UP:isTouching = false;invalidate();break;}}return super.onTouchEvent(event);}@Override protected void onDraw(Canvas canvas) {super.onDraw(canvas);if (width == 0 || height == 0) {width = getWidth();height = getHeight();}if (paint == null) {paint = new Paint();}if (path == null) {path = new Path();}if (rectF == null) {rectF = new RectF();if (rect == null) {rect = new Rect();}paint.setColor(bgColor);paint.setAntiAlias(true);//抗锯齿paint.setStrokeWidth(0);//线的宽度设为0,避免画圆弧的时候部分圆弧与边界相切paint.setStyle(Paint.Style.FILL_AND_STROKE);path.setFillType(Path.FillType.WINDING);//左上圆⾓path.moveTo(0, roundRadius);rectF.set(0, 0, 2 * roundRadius,2 * roundRadius);path.addArc(rectF, 180, 90);//上边path.lineTo(width - roundRadius, 0);//右上圆⾓rectF.set(width - roundRadius * 2, 0, width, roundRadius * 2);path.addArc(rectF, -90, 90);//右边path.lineTo(width, height - roundRadius);//右下圆⾓rectF.set(width - roundRadius * 2, height - roundRadius * 2, width,height);path.addArc(rectF, 0, 90);//下边path.lineTo(roundRadius, height);//左下圆⾓rectF.set(0, height - roundRadius * 2, 2 * roundRadius,height);path.addArc(rectF, 90, 90);//左边path.lineTo(0, roundRadius);path.close();canvas.drawPath(path, paint);if (isTouching) {paint.setColor(getContext().getResources().getColor(R.color.black_tran_30));canvas.drawPath(path, paint);}//填充背景中间空⽩的部分path.moveTo(0, roundRadius);path.lineTo(width - roundRadius, 0);path.lineTo(width, height - roundRadius);path.lineTo(roundRadius, height);path.close();canvas.drawPath(path, paint);if (isTouching) {paint.setColor(getContext().getResources().getColor(R.color.black_tran_30));canvas.drawPath(path, paint);}//text, drawable两个⼀起计算位置if (!TextUtils.isEmpty(textString)) {paint.setStrokeWidth(1.5f);paint.setColor(textColor);paint.setTextSize(textSize);rect.setEmpty();paint.getTextBounds(textString, 0, textString.length(), rect);float leftBitmap = 0;float topBitmap = 0;if (leftDrawable != null) {if (leftDrawable != null) {leftBitmap = (1.0f * width - drawableWidth - rect.width() - leftDrawablePaddingRight) / 2; topBitmap = (1.0f * height - drawableHeight) / 2;leftDrawable.setBounds((int) leftBitmap, (int) topBitmap,(int) (leftBitmap + drawableWidth),(int) (topBitmap + drawableHeight));leftDrawable.draw(canvas);}}float textX = 0;float textY =1.0f * height / 2 + paint.getTextSize() / 2 - paint.getFontMetrics().descent / 2;if (leftBitmap == 0 && topBitmap == 0) {textX = width / 2 - rect.width() / 2;} else {textX = leftBitmap + drawableWidth + leftDrawablePaddingRight;canvas.drawText(textString, textX, textY, paint);}}}MainActivity.javapublic class MainActivity extends AppCompatActivity {private LinearLayout llContainer;@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(yout.activity_main);initView();}private void initView() {llContainer = findViewById(R.id.ll_container);RoundRadiusButton roundRadiusButton = new RoundRadiusButton(this, 500, 200);roundRadiusButton.setBgColor(Color.LTGRAY);roundRadiusButton.setRoundRadius(40);//textroundRadiusButton.setTextString("testtesttest");roundRadiusButton.setTextColor(Color.WHITE);roundRadiusButton.setTextSize(40);//drawableroundRadiusButton.setLeftDrawable(getResources().getDrawable(R.mipmap.ic_launcher), 60, 60, 80); roundRadiusButton.setOnClickListener(new View.OnClickListener() {@Override public void onClick(View v) {Toast.makeText(MainActivity.this, "testest", Toast.LENGTH_LONG).show();}});roundRadiusButton.setClickable(false);llContainer.addView(roundRadiusButton);}}activity_main.xml<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="/apk/res/android"xmlns:app="/apk/res-auto"xmlns:tools="/tools"android:id="@+id/ll_container"android:layout_width="match_parent"android:layout_height="match_parent"android:background="#868684"android:gravity="center"android:orientation="vertical"tools:context=".MainActivity"><com.example.newbuttiontest.RoundRadiusButtonandroid:layout_width="300dp"android:layout_height="200dp"app:bgColor="#FFEB3B"app:drawableHeight="18dp"app:drawableWidth="18dp"app:leftDrawable="@mipmap/ic_launcher"app:leftDrawablePaddingRight="5dp"app:roundRadius="30dp"app:textColor="#FF4329"app:textSize="16dip"app:textString="testtesttest"/></LinearLayout>attrs.xml<?xml version="1.0" encoding="utf-8"?><resources><declare-styleable name="RoundRadiusButton"><attr name="roundRadius" format="dimension" /><attr name="bgColor" format="color" /><attr name="leftDrawable" format="reference" /><attr name="leftDrawablePaddingRight" format="dimension" /><attr name="drawableWidth" format="dimension" /><attr name="drawableHeight" format="dimension" /><attr name="textString" format="string" /><attr name="textSize" format="dimension" /><attr name="textColor" format="color" /></declare-styleable></resources>colors.xml<resources><color name="black_tran_30">#30000000</color></resources>总结以上所述是⼩编给⼤家介绍的android ⾃定义圆⾓button效果的实例代码,希望对⼤家有所帮助,如果⼤家有任何疑问请给我留⾔,⼩编会及时回复⼤家的。
Android特效专辑(五)——自定义圆形头像和仿MIUI卸载动画—粒子爆炸
Android特效专辑(五)——自定义圆形头像和仿MIUI卸载动画—粒子爆炸好的,各位亲爱的朋友,今天讲的特效还是比较炫的,首先,我们会讲一个自定义圆形的imageView,接着,我们会来实现粒子爆炸的特效,按照国际惯例,无图无真相的没这个效果也是模仿大神的,现在应用在了我的《Only》上截图好的,我们新建一个工程——AnimView,我们要用到的图片一.自定义圆形头像——直接开写了,要实现的东西都在注释上了1.编写自定义属性attr.xml<?xml version="1.0" encoding="utf-8"?><resources><declare-styleable name="roundedimageview"><attr name="border_thickness" format="dimension" /><attr name="border_inside_color" format="color" /><attr name="border_outside_color" format="color"></attr></declare-styleable></resources>2.自定义View紧接着我们就可以编写这个类了package com.lgl.animview;/*** 圆形头像* Created by LGL on 2016/1/12.*/import android.content.Context;import android.content.res.TypedArray;import android.graphics.Bitmap;import android.graphics.Canvas;import android.graphics.Paint;import android.graphics.PorterDuff;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,可设置最多两个宽度不同且颜色不同的圆形边框。
Android关于Glide的使用(高斯模糊、加载监听、圆角图片)
Android关于Glide的使⽤(⾼斯模糊、加载监听、圆⾓图⽚)⾼斯模糊、加载监听、圆⾓图⽚这些相信⼤家都很熟悉,那如何实现这些效果,请⼤家参考本⽂进⾏学习。
1、引⽤compile 'com.github.bumptech.glide:glide:3.7.0'2、加载图⽚2.1 基本加载Glide.with(context).load(url).into(imageView);2.2 设置加载中和加载失败的情况Glide.with(context).load(url).placeholder(R.drawable.loading) //占位符也就是加载中的图⽚,可放个gif.error(R.drawable.failed) //失败图⽚.into(view);2.3 只加载动画Glide.with(context).load(url).asGif() // 只能加载gif⽂件.into(imageView);2.4 添加图⽚淡⼊加载的效果Glide.with(context).load(url).placeholder(R.drawable.loading).error(R.drawable.failed).crossFade(1000) // 可设置时长,默认“300ms”.into(view);2.5 加载⾼斯模糊图Glide.with(context).load(url).placeholder(R.drawable.loading).error(R.drawable.failed).crossFade(1000).bitmapTransform(new BlurTransformation(context,23,4)) // “23”:设置模糊度(在0.0到25.0之间),默认”25";"4":图⽚缩放⽐例,默认“1”。
.into(view);2.6 加载监听器RequestListenerGlide.with(this).load(internetUrl).listener(new RequestListener<String, GlideDrawable>() {@Overridepublic boolean onException(Exception e, String model, Target<GlideDrawable> target, boolean isFirstResource) {Toast.makeText(getApplicationContext(),"资源加载异常",Toast.LENGTH_SHORT).show();return false;}//这个⽤于监听图⽚是否加载完成@Overridepublic boolean onResourceReady(GlideDrawable resource, String model, Target<GlideDrawable> target, boolean isFromMemoryCache, boolean isFirstResource) { Toast.makeText(getApplicationContext(),"图⽚加载完成",Toast.LENGTH_SHORT).show();return false;}}).into(imageView);注意:如果需要加载完成后设置图⽚透明度为0,则不能设置.placeholder(R.drawable.url),否则达不到你想要的效果。
android实现简单圆弧效果
android实现简单圆弧效果最近项⽬完成就开始搞⼀些有⽤没⽤的东西,以前⾯试的时候有⼈问我那种圆弧效果怎么做,还问我翻牌效果,我只看过,没有做过,现在有空了,⽽且想到可能会⽤到就做个简单的圆弧很简单,⾃定义个View,创建个Paint,设置 arcPaint.setStyle(Paint.Style.STROKE)再设置圆弧的宽,再在onDraw内调⽤canvas.drawArc()就好了现在只做⼀个带刻度的圆弧和⼀个开⼝地⽅是圆⾓的圆弧。
其他各种效果以后再摸索ArcView.javapublic class ArcView extends View {private Paint textPaint;private Paint arcPaint;private Shader backGradient;private Xfermode xfermode;private RectF oval = new RectF();public ArcView(Context context) {super(context);init();}public ArcView(Context context, @Nullable AttributeSet attrs) {super(context, attrs);init();}private int type = 0;public void setType(int type) {this.type = type;if(type == 1){start = 10;}}private void init(){arcPaint = new Paint();arcPaint.setAntiAlias(true);if(type == 0){xfermode = new PorterDuffXfermode(PorterDuff.Mode.CLEAR);}textPaint = new Paint();textPaint.setAntiAlias(true);textPaint.setColor(Color.WHITE);textPaint.setTextSize(50);textPaint.setStyle(Paint.Style.FILL);textPaint.setTextAlign(Paint.Align.CENTER);}private int strokeWidth = 40;public void setStrokeWidth(int strokeWidth) {this.strokeWidth = strokeWidth;}private int max = 100;public void setMax(int max) {this.max = max;}private int progress;public void setProgress(int progress) {this.progress = progress;postInvalidate();}private int start = 0;public void setStart(int start) {if(type == 1){if(start < 10){start = 10;}}else{if(start < 0){start = 0;}}this.start = start;}@Overrideprotected void onDraw(Canvas canvas) {super.onDraw(canvas);if(getWidth() != 0){int width = getWidth();int height = getHeight();int cx = width/2;int cy = height/2;if(backGradient == null){oval.set( strokeWidth/2, strokeWidth/2,width - strokeWidth/2, height - strokeWidth/2);int colorStart = getResources().getColor(R.color.colorPrimary);int color2 = Color.GREEN;int colorEnd = Color.RED;backGradient = new SweepGradient(cx,cy,new int[]{color2 ,colorStart, colorEnd},new float[]{0.1f,0.4f,0.9f}); postInvalidate();}else{int sc = 0;if(type == 0){sc = canvas.saveLayer(0, 0, canvas.getWidth(), canvas.getHeight(), null, Canvas.ALL_SAVE_FLAG); }else{canvas.save();}canvas.rotate(90,cx,cy);arcPaint.setColor(Color.GRAY);arcPaint.setStyle(Paint.Style.STROKE);arcPaint.setStrokeWidth(strokeWidth);if(type == 1){arcPaint.setStrokeCap(Paint.Cap.ROUND);}int s =start;int e = start*2;//底⾊canvas.drawArc(oval,s,360 - e,false,arcPaint);arcPaint.setShader(backGradient);//渐变int sweep = (int) (progress*1.0f/max*(360 - e));canvas.drawArc(oval,s,sweep,false,arcPaint);arcPaint.setShader(null);if(type == 0){//刻度arcPaint.setXfermode(xfermode);arcPaint.setStyle(Paint.Style.STROKE);arcPaint.setStrokeWidth(5);for (int i = 0; i < 36;i++){canvas.drawLine(0,cy,getWidth(),cy,arcPaint);canvas.rotate(5,cx,cy);}arcPaint.setXfermode(null);canvas.restoreToCount(sc);}else{canvas.restore();}Paint.FontMetrics fontMetrics = textPaint.getFontMetrics();float top = fontMetrics.top;float bottom = fontMetrics.bottom;int baseLineY = (int) (cy - top/2 - bottom/2);canvas.drawText(progress+"%",cx,baseLineY,textPaint);//⼗字线,⽤来参考的,可删除canvas.drawLine(cx,0,cx,height,textPaint);canvas.drawLine(0,cy,width,cy,textPaint);}}}}activity_main.xml<?xml version="1.0" encoding="utf-8"?><android.support.constraint.ConstraintLayout xmlns:android="/apk/res/android" xmlns:tools="/tools"android:layout_width="match_parent"android:layout_height="match_parent"tools:context="com.hyq.hm.testdraw.MainActivity"><LinearLayoutandroid:layout_width="match_parent"android:layout_height="match_parent"android:orientation="vertical"android:gravity="center_horizontal"><SeekBarandroid:id="@+id/seek_bar"android:layout_width="match_parent"android:layout_height="wrap_content"android:layout_margin="20dp"android:max="100"/><LinearLayoutandroid:layout_width="wrap_content"android:layout_height="wrap_content"android:orientation="horizontal"><com.hyq.hm.testdraw.ArcViewandroid:id="@+id/arc_view_0"android:layout_width="100dp"android:layout_height="100dp"android:layout_margin="5dp"android:background="#885453"/><com.hyq.hm.testdraw.ArcViewandroid:id="@+id/arc_view_1"android:layout_width="100dp"android:layout_height="100dp"android:layout_margin="5dp"/></LinearLayout></LinearLayout></android.support.constraint.ConstraintLayout>MainActivity.javapublic class MainActivity extends AppCompatActivity {private SeekBar seekBar;private ArcView arcView0;private ArcView arcView1;@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(yout.activity_main);arcView0 = findViewById(R.id.arc_view_0);arcView1 = findViewById(R.id.arc_view_1);arcView0.setType(0);arcView1.setType(1);arcView0.setStart(10);arcView1.setStart(0);seekBar = findViewById(R.id.seek_bar);seekBar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {@Overridepublic void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {arcView0.setProgress(progress);arcView1.setProgress(progress);}@Overridepublic void onStartTrackingTouch(SeekBar seekBar) {}@Overridepublic void onStopTrackingTouch(SeekBar seekBar) {}});}}以上就是本⽂的全部内容,希望对⼤家的学习有所帮助,也希望⼤家多多⽀持。
Android开发使用Drawable绘制圆角与圆形图案功能示例
Android开发使⽤Drawable绘制圆⾓与圆形图案功能⽰例本⽂实例讲述了Android开发使⽤Drawable绘制圆⾓与圆形图案功能。
分享给⼤家供⼤家参考,具体如下:1. 创建类RoundCircleDrawable继承Drawable/*** 圆⾓矩形* @Project App_View* @Package com.android.view.drawable* @author chenlin* @version 1.0* @Date 2016年4⽉21⽇* @Note TODO*/public class RoundCircleDrawable extends Drawable{private Paint mPaint;//画笔private int mWidth;//图⽚宽与长度的最⼩值private int mRadius;//半径private int mRound;//圆⾓private RectF mRectF;//矩形private Bitmap mBitmap;//图⽚private Type mType = Type.TYPE_ROUND;//默认是矩形//设置类型enum Type{TYPE_ROUND, TYPE_CICLE;}public RoundCircleDrawable(Bitmap bitmap){this.mBitmap = bitmap;//初始化画笔mPaint = new Paint();mPaint.setAntiAlias(true);BitmapShader shader = new BitmapShader(mBitmap, TileMode.CLAMP, TileMode.CLAMP);mPaint.setShader(shader);mWidth = Math.min(mBitmap.getWidth(), mBitmap.getHeight());mRadius = mWidth / 2;}/*** 向外提供设置图⽚类型的⽅法* @param type*/public void setType(Type type){this.mType = type;}/*** 暴露给外⾯设置圆⾓的⼤⼩** @param round*/public void setRound(int round) {this.mRound = round;}@Overridepublic void setBounds(int left, int top, int right, int bottom) {super.setBounds(left, top, right, bottom);mRectF = new RectF(left, top, right, bottom);}@Overridepublic void draw(Canvas canvas) {if (mType == Type.TYPE_ROUND) {canvas.drawRoundRect(mRectF, mRound, mRound, mPaint);}else {canvas.drawCircle(mWidth / 2, mWidth / 2, mRadius, mPaint);}}@Overridepublic int getIntrinsicWidth() {if (mType == Type.TYPE_CICLE) {return mWidth;}else {return mBitmap.getWidth();}}@Overridepublic int getIntrinsicHeight() {if (mType == Type.TYPE_CICLE) {return mWidth;}else {return mBitmap.getHeight();}}@Overridepublic void setAlpha(int alpha) {mPaint.setAlpha(alpha);}@Overridepublic void setColorFilter(ColorFilter cf) {mPaint.setColorFilter(cf);}@Overridepublic int getOpacity() {return PixelFormat.TRANSLUCENT;}}2. 实现⽅法public class RoundActivity extends Activity {private ImageView mImageView;@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(yout.activity_round_drawable);mImageView = (ImageView) findViewById(R.id.iv_round);Bitmap bitmap = BitmapFactory.decodeResource(getResources(), R.drawable.aa);//RoundImageDrawable drawable = new RoundImageDrawable(bitmap);//drawable.setRound(30);RoundCircleDrawable drawable = new RoundCircleDrawable(bitmap);drawable.setRound(50);mImageView.setImageDrawable(drawable);}}更多关于Android相关内容感兴趣的读者可查看本站专题:《》、《》、《》、《》、《》、《》及《》希望本⽂所述对⼤家Android程序设计有所帮助。
AndroidGradientDrawable(shape标签定义)静态使用和动态使用(圆。。。
AndroidGradientDrawable(shape标签定义)静态使⽤和动态使⽤(圆。
Android GradientDrawable使⽤优势: 1. 快速实现⼀些基本图形(线,矩形,圆,椭圆,圆环) 2. 快速实现⼀些圆⾓,渐变,阴影等效果 3. 代替图⽚设置为View的背景 4. 可以减少apk⼤⼩,提升⽤户下载意愿 5. 还可以减少内存占⽤ 6. ⽅便修改与维护 基于上⾯⼏种优势,我们很多时候都会选择使⽤android的shape,下⾯分别介绍shape的静态使⽤和动态使⽤1. GradientDrawable的静态使⽤(xml中使⽤shape标签定义) 在drawable中创建⼀个xml⽂件,在布局⽂件中直接引⽤这个xml⽂件即可<?xml version="1.0" encoding="utf-8"?><!--android:shape=["rectangle" | "oval" | "line" | "ring"]shape的形状,默认为矩形,可以设置为矩形(rectangle)、椭圆形(oval)、线(line)、环形(ring)下⾯的属性只有在android:shape="ring时可⽤:android:innerRadius 内环的半径。
android:innerRadiusRatio 浮点型,以环的宽度⽐率来表⽰内环的半径,例如,如果android:innerRadiusRatio,表⽰内环半径等于环的宽度除以5,这个值是可以被覆盖的,默认为9.android:thickness 环的厚度android:thicknessRatio 浮点型,以环的宽度⽐率来表⽰环的厚度,例如,如果android:thicknessRatio="2",那么环的厚度就等于环的宽度除以2。
Android自定义ImageView实现圆角功能
Android⾃定义ImageView实现圆⾓功能使⽤⾃定义ImageView,实现圆⾓功能,供⼤家参考,具体内容如下1.⾃定义属性attrs.xml<?xml version="1.0" encoding="utf-8"?><resources><declare-styleable name="RoundCornerImageView"><attr name="radius" format="dimension" /><attr name="left_top_radius" format="dimension" /><attr name="right_top_radius" format="dimension" /><attr name="right_bottom_radius" format="dimension" /><attr name="left_bottom_radius" format="dimension" /></declare-styleable></resources>2.⾃定义RoundCornerImageView,继承AppCompatImageViewpublic class RoundCornerImageView extends AppCompatImageView {private float width, height;private int defaultRadius = 0;private int radius;private int leftTopRadius;private int rightTopRadius;private int rightBottomRadius;private int leftBottomRadius;public RoundCornerImageView(Context context) {this(context, null);init(context, null);}public RoundCornerImageView(Context context, AttributeSet attrs) {this(context, attrs, 0);init(context, attrs);}public RoundCornerImageView(Context context, AttributeSet attrs, int defStyleAttr) {super(context, attrs, defStyleAttr);init(context, attrs);}private void init(Context context, AttributeSet attrs) {if (Build.VERSION.SDK_INT < 18) {setLayerType(YER_TYPE_SOFTWARE, null);}// 读取配置TypedArray array = context.obtainStyledAttributes(attrs, R.styleable.RoundCornerImageView);radius = array.getDimensionPixelOffset(R.styleable.RoundCornerImageView_radius, defaultRadius);leftTopRadius = array.getDimensionPixelOffset(R.styleable.RoundCornerImageView_left_top_radius, defaultRadius);rightTopRadius = array.getDimensionPixelOffset(R.styleable.RoundCornerImageView_right_top_radius, defaultRadius);rightBottomRadius = array.getDimensionPixelOffset(R.styleable.RoundCornerImageView_right_bottom_radius, defaultRadius); leftBottomRadius = array.getDimensionPixelOffset(R.styleable.RoundCornerImageView_left_bottom_radius, defaultRadius); //如果四个⾓的值没有设置,那么就使⽤通⽤的radius的值。
android自定义环形对比图效果
android⾃定义环形对⽐图效果本⽂实例为⼤家分享了android⾃定义环形对⽐图的具体代码,供⼤家参考,具体内容如下1.⾸先在res/values⾥创建⼀个attr.xml的⽂件。
<?xml version="1.0" encoding="utf-8"?><resources><declare-styleable name="AnswerChartView"><attr name="radius" format="dimension"/><attr name="strokeWidth" format="dimension"/><attr name="circleColor" format="color"/><attr name="innerringColor" format="color"/><attr name="outringColor" format="color"/><attr name="textSize" format="dimension"/></declare-styleable></resources>2.然后为⾃定义对⽐图Viewpackage com.jsle.ebag.answer.view;import com.jsle.ebag.answer.R;import android.content.Context;import android.content.res.TypedArray;import android.graphics.Canvas;import android.graphics.Paint;import android.graphics.RectF;import android.graphics.Paint.FontMetrics;import android.util.AttributeSet;import android.view.View;/*** 弧线对⽐图* @param* @return* @author LH* @data 2016年1⽉25⽇下午6:17:34**/public class AnswerChartView extends View {// 圆画笔private Paint mCirclePaint;// 圆环画笔private Paint mRingPaint;// 百分数画笔private Paint mTextPaint;// ⽂本画笔private Paint mTextPaint2;// ⾥⾯圆颜⾊private int mCircleColor;// ⾥⾯弧颜⾊private int mInnerRingColor;// 外⾯弧颜⾊private int mOutRingColor;// 空⽩的圆半径private float mRadius;// ⾥⾯的弧半径private float mRingRadius;// 最外弧半径private float mRingRadius2;// 圆环的宽度private float mStrokeWidth;// ⽂本的中⼼x轴位置private int mXCenter;// ⽂本的中⼼y轴位置private int mYCenter;// 百分⽐⽂本的宽度private float mTxtWidth;// 描述⽂本的宽度private float mTxtWidth2;// ⽂本的⾼度private float mTxtHeight;// 百分数⽂本的⼤⼩private float mTxtSize;// 总成绩private int mTotalProgress = 100;// 个⼈的正确率private double mInnerProgress;// 班级的正确率private double mOutProgress;public AnswerChartView(Context context, AttributeSet attrs) {super(context, attrs);initAttrs(context, attrs);initVariable();}private void initAttrs(Context context, AttributeSet attrs) {TypedArray typeArray = context.getTheme().obtainStyledAttributes(attrs,R.styleable.AnswerChartView, 0, 0);mRadius = typeArray.getDimension(R.styleable.AnswerChartView_radius, 80);mTxtSize=typeArray.getDimension(R.styleable.AnswerChartView_textSize, 20);mStrokeWidth = typeArray.getDimension(R.styleable.AnswerChartView_strokeWidth, 10);mCircleColor = typeArray.getColor(R.styleable.AnswerChartView_circleColor, 0xFFFFFFFF);mOutRingColor = typeArray.getColor(R.styleable.AnswerChartView_innerringColor, 0xFFFFFFFF); mInnerRingColor = typeArray.getColor(R.styleable.AnswerChartView_outringColor, 0xFFFFFFFF); mRingRadius = mRadius + mStrokeWidth / 2;mRingRadius2 = mRadius + mStrokeWidth/2*3;}private void initVariable() {mCirclePaint = new Paint();mCirclePaint.setAntiAlias(true);mCirclePaint.setStyle(Paint.Style.FILL);mRingPaint = new Paint();mRingPaint.setAntiAlias(true);mRingPaint.setColor(mInnerRingColor);mRingPaint.setStyle(Paint.Style.STROKE);mRingPaint.setStrokeWidth(mStrokeWidth);mTextPaint = new Paint();mTextPaint.setAntiAlias(true);mTextPaint.setStyle(Paint.Style.FILL);mTextPaint.setARGB(255, 32, 207, 152);mTextPaint.setTextSize(mTxtSize);mTextPaint2 = new Paint();mTextPaint2.setAntiAlias(true);mTextPaint2.setStyle(Paint.Style.FILL);mTextPaint2.setARGB(255, 0, 0, 0);mTextPaint2.setTextSize(20);FontMetrics fm = mTextPaint.getFontMetrics();mTxtHeight = (int) Math.ceil(fm.descent - fm.ascent);}@Overrideprotected void onDraw(Canvas canvas) {mXCenter = getWidth() / 2;mYCenter = getHeight() / 2;mCirclePaint.setColor(getResources().getColor(R.color.gray));canvas.drawCircle(mXCenter,mYCenter, mRadius + mStrokeWidth*2, mCirclePaint);RectF oval1 = new RectF();oval1.left = (mXCenter - mRingRadius);oval1.top = (mYCenter - mRingRadius);oval1.right = mRingRadius * 2 + (mXCenter - mRingRadius);oval1.bottom = mRingRadius * 2 + (mYCenter - mRingRadius);mRingPaint.setColor(mOutRingColor);canvas.drawArc(oval1, -90, ((float)mOutProgress / mTotalProgress) * 360, false, mRingPaint); mCirclePaint.setColor(mCircleColor);canvas.drawCircle(mXCenter, mYCenter, mRadius, mCirclePaint);if (mInnerProgress > 0 ) {RectF oval = new RectF();oval.left = (mXCenter - mRingRadius2);oval.top = (mYCenter - mRingRadius2);oval.right = mRingRadius2 * 2 + (mXCenter - mRingRadius2);oval.bottom = mRingRadius2 * 2 + (mYCenter - mRingRadius2);mRingPaint.setColor(mInnerRingColor);canvas.drawArc(oval, -90, ((float)mInnerProgress / mTotalProgress) * 360, false, mRingPaint); // // canvas.drawCircle(mXCenter, mYCenter, mRadius + mStrokeWidth / 2, mRingPaint);String txt = mInnerProgress + "%";String txt2 = "正确率";mTxtWidth = mTextPaint.measureText(txt, 0, txt.length());mTxtWidth2 = mTextPaint2.measureText(txt2, 0, txt2.length());canvas.drawText(txt, mXCenter - mTxtWidth / 2, mYCenter+mTxtWidth / 8, mTextPaint);canvas.drawText(txt2 ,mXCenter - mTxtWidth2 / 2, mYCenter + mTxtWidth / 2, mTextPaint2); }else if(mInnerProgress==0){String txt = mInnerProgress + "%";String txt2 = "正确率";mTxtWidth = mTextPaint.measureText(txt, 0, txt.length());mTxtWidth2 = mTextPaint2.measureText(txt2, 0, txt2.length());canvas.drawText(txt, mXCenter - mTxtWidth / 2, mYCenter+mTxtWidth / 8, mTextPaint);canvas.drawText(txt2 ,mXCenter - mTxtWidth2 / 2, mYCenter + mTxtWidth / 2, mTextPaint2); }}public void setOutProgress(double progress){mOutProgress=progress;}public void setInnerProgress(double progress) {mInnerProgress = progress;// invalidate();postInvalidate();}}3.使⽤⾃定义View<com.jsle.ebag.answer.view.AnswerChartViewandroid:id="@+id/tasks_view"android:layout_width="160dp"android:layout_height="160dp"android:layout_centerHorizontal="true"tc:circleColor="@color/circle_color"tc:innerringColor="@color/dark_yellow"tc:outringColor="@color/green"tc:radius="60dip"tc:strokeWidth="6dip"tc:textSize="32sp" />4.最后可已在AnswerChartActivity中设置内环和外环的百分⽐和属性package com.jsle.ebag.answer.activity;import java.text.DecimalFormat;import com.jsle.ebag.answer.R;import yout;import com.jsle.ebag.answer.view.AnswerChartView;import android.app.Activity;import android.content.Intent;import android.os.Bundle;import android.view.Menu;import android.view.MenuItem;import android.view.View;import android.view.View.OnClickListener;import android.widget.Button;import android.widget.LinearLayout;import android.widget.TextView;public class AnswerChartActivity extends BaseActivity implements OnClickListener { private AnswerChartView mTasksView;private double mAccuracy;//个⼈的正确率private double cAccuracy;//班级的正确率private double mCurrentProgress;private LinearLayout btn_black;private TextView tv_title,tv_subjectcount,tv_submit,tv_accuracy;private String title;private double maccuracy,caccuracy;private int subjectcount,submit;@Overrideprotected int getID() {// TODO Auto-generated method stubreturn R.id.Activity_ID_AnswerChart;}@Overrideprotected String getTag() {// TODO Auto-generated method stubreturn "AnswerChart_Acitivity";}@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(yout.activity_answer_chart);btn_black=(LinearLayout) findViewById(R.id.btn_black);tv_title=(TextView) findViewById(_title);tv_subjectcount=(TextView) findViewById(_subjectcount);tv_submit=(TextView) findViewById(_submit);tv_accuracy=(TextView) findViewById(_accuracy);btn_black.setOnClickListener(this);getData();initVariable();initView();new Thread(new ProgressRunable()).start();}private void getData() {// TODO Auto-generated method stubIntent intent = getIntent();title=intent.getStringExtra("title");maccuracy = intent.getDoubleExtra("maccuracy", 0);caccuracy = intent.getDoubleExtra("caccuracy", 0);subjectcount=intent.getIntExtra("subjectcount", 0);submit=intent.getIntExtra("submit", 0);}private void initVariable() {tv_title.setText(title);tv_subjectcount.setText("共"+subjectcount+"道题");tv_submit.setText(submit+"");tv_accuracy.setText(caccuracy+"%");mAccuracy =maccuracy;cAccuracy=caccuracy;mCurrentProgress = 0;}private void initView() {mTasksView = (AnswerChartView) findViewById(R.id.tasks_view);mTasksView.setOutProgress(cAccuracy);}/***进度动画效果* @author LH* @data 2016年1⽉29⽇下午3:43:31**/class ProgressRunable implements Runnable {@Overridepublic void run() {while (mCurrentProgress < mAccuracy) {mCurrentProgress += 1;if(mCurrentProgress>mAccuracy){mCurrentProgress=mAccuracy;}mTasksView.setInnerProgress(mCurrentProgress);try {Thread.sleep(15);} catch (Exception e) {e.printStackTrace();}}}}@Overridepublic void onClick(View v) {// TODO Auto-generated method stubswitch (v.getId()) {case R.id.btn_black:finish();break;default:break;}}}以上就是本⽂的全部内容,希望对⼤家的学习有所帮助,也希望⼤家多多⽀持。
Android自定义View圆形图片控件代码详解
Android⾃定义View圆形图⽚控件代码详解前⾔在⽇常开发中,圆形的图⽚效果还是很常见的。
可以通过给Paint设置Xfermode来实现,这⾥简单记录如下。
实现实现圆形效果的核⼼是PorterDuffXfermode,对于PorterDuffXfermode,这⾥不展开,可以查询相关资料。
核⼼代码//绘制背景canvas.drawCircle(mSize / 2, mSize / 2, mSize / 2, mPaint);//设置模式为:显⽰背景层和上层的交集,且显⽰上层图像mPaint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_IN));//绘制要显⽰的图像canvas.drawBitmap(mSrcBitmap, 0, 0, mPaint);//重置XfermodemPaint.setXfermode(null);⾃定义属性<?xml version="1.0" encoding="utf-8"?><resources><declare-styleable name="CircleView"><!--定义资源--><attr name="src" format="reference" /><!--定义类型--><attr name="type" format="enum"><!--圆形--><enum name="round" value="1" /><!--矩形--><enum name="rect" value="2" /></attr></declare-styleable></resources>⾃定义控件public class CircleView extends View {private static final int DEFAULT_SIZE = 200;private static final int DEFAULT_RADIUS = 20;private static final int TYPE_ROUND = 1;private static final int TYPE_RECT = 2;private int mSize;private int mResourceId;private int mType;private Paint mPaint;private Bitmap mSrcBitmap;public CircleView(Context context) {this(context, null);}public CircleView(Context context, AttributeSet attrs) {this(context, attrs, 0);}public CircleView(Context context, AttributeSet attrs, int defStyleAttr) {super(context, attrs, defStyleAttr);TypedArray ta = context.obtainStyledAttributes(attrs, R.styleable.CircleView);mResourceId = ta.getResourceId(R.styleable.CircleView_src, R.mipmap.ic_launcher);mType = ta.getInt(R.styleable.CircleView_type, TYPE_ROUND);ta.recycle();init();}@Overrideprotected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {int width = getMeasureSize(widthMeasureSpec);int height = getMeasureSize(heightMeasureSpec);mSize = Math.min(width, height);setMeasuredDimension(mSize, mSize);}@RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)@Overrideprotected void onDraw(Canvas canvas) {super.onDraw(canvas);//绘制背景if (mSrcBitmap == null) {mSrcBitmap = getScaleBitmap();}if (mType == TYPE_ROUND) {canvas.drawCircle(mSize / 2, mSize / 2, mSize / 2, mPaint);} else if (mType == TYPE_RECT) {canvas.drawRoundRect(0, 0, mSize, mSize, DEFAULT_RADIUS, DEFAULT_RADIUS, mPaint); }//设置模式为:显⽰背景层和上层的交集,且显⽰上层图像mPaint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_IN));//绘制要显⽰的图像canvas.drawBitmap(mSrcBitmap, 0, 0, mPaint);//重置XfermodemPaint.setXfermode(null);}private void init() {//禁⽤硬件加速,否则可能⽆法绘制圆形setLayerType(LAYER_TYPE_HARDWARE, null);mPaint = new Paint();mPaint.setAntiAlias(true);mPaint.setStyle(Paint.Style.FILL);}private int getMeasureSize(int measureSpec) {int mode = MeasureSpec.getMode(measureSpec);int size = MeasureSpec.getSize(measureSpec);return mode == MeasureSpec.EXACTLY ? size : DEFAULT_SIZE;}/*** 获取缩放后的Bitmap** @return*/private Bitmap getScaleBitmap() {BitmapFactory.Options options = new BitmapFactory.Options();options.inJustDecodeBounds = true;BitmapFactory.decodeResource(getResources(), mResourceId, options);options.inSampleSize = calcSampleSize(options, mSize, mSize);options.inJustDecodeBounds = false;return BitmapFactory.decodeResource(getResources(), mResourceId, options);}/*** 计算缩放⽐例** @param option* @param width* @param height* @return*/private int calcSampleSize(BitmapFactory.Options option, int width, int height) {int originWidth = option.outWidth;int originHeight = option.outHeight;int sampleSize = 1;while ((originWidth = originWidth >> 1) > width && (originHeight = originHeight >> 1) > height) { sampleSize = sampleSize << 1;}return sampleSize;}}注意:如果没有圆形的效果,那么可能需要禁⽤硬件加速:setLayerType(LAYER_TYPE_HARDWARE, null)布局<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="/apk/res/android"xmlns:app="/apk/res-auto"xmlns:tools="/tools"android:layout_width="match_parent"android:layout_height="match_parent"android:gravity="center_horizontal"android:orientation="vertical"tools:context=".MainActivity"><com.wangyz.custom.CircleViewandroid:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_margin="10dp"app:src="@drawable/image" /><com.wangyz.custom.CircleViewandroid:layout_width="100dp"android:layout_height="100dp"android:layout_margin="10dp"app:src="@drawable/image" /><com.wangyz.custom.CircleViewandroid:layout_width="100dp"android:layout_height="100dp"android:layout_margin="10dp"app:src="@drawable/image"app:type="rect" /></LinearLayout>效果以上就是本⽂的全部内容,希望对⼤家的学习有所帮助,也希望⼤家多多⽀持。
android 自定义圆角头像以及使用declare-styleable进行配置属性解析
android 自定义圆角头像以及使用declare-styleable进行配置属性解析由于最新项目中正在检查UI是否与效果图匹配,结果关于联系人模块给的默认图片是四角稍带弧度的圆角,而我们截取的图片是正方形的,现在要给应用统一替换。
应用中既用到大圆角头像(即整个头像是圆的)又用到四角稍带弧度的圆角头像,封装一下以便重用。
以下直接见代码[java] view plain copy 在CODE上查看代码片派生到我的代码片package com.test.demo;import com.test.demo.R;import android.content.Context;import android.content.res.TypedArray;import android.graphics.Bitmap;import android.graphics.BitmapShader;import android.graphics.Canvas;import android.graphics.Matrix;import android.graphics.Paint;import android.graphics.RectF;import android.graphics.Shader.TileMode;import android.graphics.drawable.BitmapDrawable;import android.graphics.drawable.Drawable;import android.os.Bundle;import android.os.Parcelable;import android.util.AttributeSet;import android.util.Log;import android.util.TypedValue;import android.widget.ImageView;/*** 圆角imageview*/public class RoundImageView extends ImageView {private static final String TAG = "RoundImageView";/*** 图片的类型,圆形or圆角*/private int type;public static final int TYPE_CIRCLE = 0;public static final int TYPE_ROUND = 1;/*** 圆角大小的默认值*/private static final int CORNER_RADIUS_DEFAULT = 10;/*** 圆角的大小*/private int mCornerRadius;/*** 绘图的Paint*/private Paint mBitmapPaint;// 按下状态颜色private Paint mPressedColorPaint;private int pressedColor;/*** 圆角的半径*/private int mRadius;/*** 3x3 矩阵,主要用于缩小放大*/private Matrix mMatrix;/*** view的宽度*/private int mWidth;private RectF mRoundRect;public RoundImageView(Context context, AttributeSet attrs) {super(context, attrs);mMatrix = new Matrix();mBitmapPaint = new Paint();mBitmapPaint.setAntiAlias(true);TypedArray a = context.obtainStyledAttributes(attrs,R.styleable.RoundImageView);pressedColor = a.getColor(R.styleable.RoundImageView_pressed_color, -1);if (pressedColor != -1) {mPressedColorPaint = new Paint();mPressedColorPaint.setAntiAlias(true);mPressedColorPaint.setColor(pressedColor);}mCornerRadius = a.getDimensionPixelSize(R.styleable.RoundImageView_corner_radius, (int) TypedValue.applyDimension(PLEX_UNIT_DIP,CORNER_RADIUS_DEFAULT, getResources().getDisplayMetrics()));// 默认为10dp type = a.getInt(R.styleable.RoundImageView_type, TYPE_CIRCLE);// 默认为Circlea.recycle();}public RoundImageView(Context context) {this(context, null);}@Overrideprotected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { super.onMeasure(widthMeasureSpec, heightMeasureSpec);/*** 如果类型是圆形,则强制改变view的宽高一致,以小值为准*/if (type == TYPE_CIRCLE) {mWidth = Math.min(MeasureSpec.getSize(widthMeasureSpec),MeasureSpec.getSize(heightMeasureSpec));mRadius = mWidth / 2;}}/*** 初始化BitmapShader*/private void setUpShader() {Drawable drawable = getDrawable();if (drawable == null) {return;}Bitmap bmp = drawableToBitamp(drawable);// 将bmp作为着色器,就是在指定区域内绘制bmp// 渲染图像,使用图像为绘制图形着色BitmapShader mBitmapShader = new BitmapShader(bmp, TileMode.CLAMP,TileMode.CLAMP);float scale = 1.0f;if (type == TYPE_CIRCLE) {// 拿到bitmap宽或高的小值int bSize = Math.min(bmp.getWidth(), bmp.getHeight());scale = mWidth * 1.0f / bSize;} else if (type == TYPE_ROUND) {if (!(bmp.getWidth() == getWidth() && bmp.getHeight() == getHeight())) {// 如果图片的宽或者高与view的宽高不匹配,计算出需要缩放的比例;缩放后的图片的宽高,一定要大于我们view的宽高;所以我们这里取大值;scale = Math.max(getWidth() * 1.0f / bmp.getWidth(),getHeight() * 1.0f / bmp.getHeight());}}// shader的变换矩阵,我们这里主要用于放大或者缩小mMatrix.setScale(scale, scale);// 设置变换矩阵mBitmapShader.setLocalMatrix(mMatrix);// 设置shadermBitmapPaint.setShader(mBitmapShader);}@Overrideprotected void onDraw(Canvas canvas) {if (getDrawable() == null) {return;}setUpShader();if (type == TYPE_ROUND) {canvas.drawRoundRect(mRoundRect, mCornerRadius, mCornerRadius,mBitmapPaint);if (isPressed() && mPressedColorPaint != null) {canvas.drawRoundRect(mRoundRect, mCornerRadius, mCornerRadius,mPressedColorPaint);}} else {canvas.drawCircle(mRadius, mRadius, mRadius, mBitmapPaint);if (isPressed() && mPressedColorPaint != null) {canvas.drawCircle(mRadius, mRadius, mRadius, mPressedColorPaint);}}}@Overrideprotected void onSizeChanged(int w, int h, int oldw, int oldh) {super.onSizeChanged(w, h, oldw, oldh);Log.d(TAG, "onSizeChanged,w=" + w + ",h=" + h + ",oldw=" + oldw+ ",oldh=" + oldh);// 圆角图片的范围if (type == TYPE_ROUND) {mRoundRect = new RectF(0, 0, w, h);}}/*** drawable转bitmap*/private Bitmap drawableToBitamp(Drawable drawable) {if (drawable instanceof BitmapDrawable) {BitmapDrawable bd = (BitmapDrawable) drawable;return bd.getBitmap();}int w = drawable.getIntrinsicWidth();int h = drawable.getIntrinsicHeight();Bitmap bitmap = Bitmap.createBitmap(w, h, Bitmap.Config.ARGB_8888);Canvas canvas = new Canvas(bitmap);drawable.setBounds(0, 0, w, h);drawable.draw(canvas);return bitmap;}private static final String STATE_INSTANCE = "state_instance";private static final String STATE_TYPE = "state_type";private static final String STATE_BORDER_RADIUS = "state_border_radius"; private static final String STATE_PRESSED_COLOR = "state_pressed_color";@Overrideprotected Parcelable onSaveInstanceState() {Bundle bundle = new Bundle();bundle.putParcelable(STA TE_INSTANCE, super.onSaveInstanceState());bundle.putInt(STA TE_TYPE, type);bundle.putInt(STA TE_BORDER_RADIUS, mCornerRadius);bundle.putInt(STA TE_PRESSED_COLOR, pressedColor);return bundle;}@Overrideprotected void onRestoreInstanceState(Parcelable state) {if (state instanceof Bundle) {Bundle bundle = (Bundle) state;super.onRestoreInstanceState(((Bundle) state).getParcelable(STATE_INSTANCE));this.type = bundle.getInt(STATE_TYPE);this.mCornerRadius = bundle.getInt(STA TE_BORDER_RADIUS);this.pressedColor = bundle.getInt(STA TE_PRESSED_COLOR);if (pressedColor != -1) {mPressedColorPaint = new Paint();mPressedColorPaint.setAntiAlias(true);mPressedColorPaint.setColor(pressedColor);}} else {super.onRestoreInstanceState(state);}}public void setType(int type) {if (this.type != type) {this.type = type;if (this.type != TYPE_ROUND && this.type != TYPE_CIRCLE) {this.type = TYPE_CIRCLE;}requestLayout();}}@Overrideprotected void dispatchSetPressed(boolean pressed) {// imageView.setClickable(true),或imageView.setOnClickListener时才可触发dispatchSetPressedsuper.dispatchSetPressed(pressed);invalidate();}}declare-styleable:declare-styleable是给自定义控件添加自定义属性用的。
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
android 自定义圆角头像以及使用declare-styleable进行配置属性解析由于最新项目中正在检查UI是否与效果图匹配,结果关于联系人模块给的默认图片是四角稍带弧度的圆角,而我们截取的图片是正方形的,现在要给应用统一替换。
应用中既用到大圆角头像(即整个头像是圆的)又用到四角稍带弧度的圆角头像,封装一下以便重用。
以下直接见代码[java] view plain copy 在CODE上查看代码片派生到我的代码片package com.test.demo;import com.test.demo.R;import android.content.Context;import android.content.res.TypedArray;import android.graphics.Bitmap;import android.graphics.BitmapShader;import android.graphics.Canvas;import android.graphics.Matrix;import android.graphics.Paint;import android.graphics.RectF;import android.graphics.Shader.TileMode;import android.graphics.drawable.BitmapDrawable;import android.graphics.drawable.Drawable;import android.os.Bundle;import android.os.Parcelable;import android.util.AttributeSet;import android.util.Log;import android.util.TypedValue;import android.widget.ImageView;/*** 圆角imageview*/public class RoundImageView extends ImageView {private static final String TAG = "RoundImageView";/*** 图片的类型,圆形or圆角*/private int type;public static final int TYPE_CIRCLE = 0;public static final int TYPE_ROUND = 1;/*** 圆角大小的默认值*/private static final int CORNER_RADIUS_DEFAULT = 10;/*** 圆角的大小*/private int mCornerRadius;/*** 绘图的Paint*/private Paint mBitmapPaint;// 按下状态颜色private Paint mPressedColorPaint;private int pressedColor;/*** 圆角的半径*/private int mRadius;/*** 3x3 矩阵,主要用于缩小放大*/private Matrix mMatrix;/*** view的宽度*/private int mWidth;private RectF mRoundRect;public RoundImageView(Context context, AttributeSet attrs) {super(context, attrs);mMatrix = new Matrix();mBitmapPaint = new Paint();mBitmapPaint.setAntiAlias(true);TypedArray a = context.obtainStyledAttributes(attrs,R.styleable.RoundImageView);pressedColor = a.getColor(R.styleable.RoundImageView_pressed_color, -1);if (pressedColor != -1) {mPressedColorPaint = new Paint();mPressedColorPaint.setAntiAlias(true);mPressedColorPaint.setColor(pressedColor);}mCornerRadius = a.getDimensionPixelSize(R.styleable.RoundImageView_corner_radius, (int) TypedValue.applyDimension(PLEX_UNIT_DIP,CORNER_RADIUS_DEFAULT, getResources().getDisplayMetrics()));// 默认为10dp type = a.getInt(R.styleable.RoundImageView_type, TYPE_CIRCLE);// 默认为Circlea.recycle();}public RoundImageView(Context context) {this(context, null);}@Overrideprotected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { super.onMeasure(widthMeasureSpec, heightMeasureSpec);/*** 如果类型是圆形,则强制改变view的宽高一致,以小值为准*/if (type == TYPE_CIRCLE) {mWidth = Math.min(MeasureSpec.getSize(widthMeasureSpec),MeasureSpec.getSize(heightMeasureSpec));mRadius = mWidth / 2;}}/*** 初始化BitmapShader*/private void setUpShader() {Drawable drawable = getDrawable();if (drawable == null) {return;}Bitmap bmp = drawableToBitamp(drawable);// 将bmp作为着色器,就是在指定区域内绘制bmp// 渲染图像,使用图像为绘制图形着色BitmapShader mBitmapShader = new BitmapShader(bmp, TileMode.CLAMP,TileMode.CLAMP);float scale = 1.0f;if (type == TYPE_CIRCLE) {// 拿到bitmap宽或高的小值int bSize = Math.min(bmp.getWidth(), bmp.getHeight());scale = mWidth * 1.0f / bSize;} else if (type == TYPE_ROUND) {if (!(bmp.getWidth() == getWidth() && bmp.getHeight() == getHeight())) {// 如果图片的宽或者高与view的宽高不匹配,计算出需要缩放的比例;缩放后的图片的宽高,一定要大于我们view的宽高;所以我们这里取大值;scale = Math.max(getWidth() * 1.0f / bmp.getWidth(),getHeight() * 1.0f / bmp.getHeight());}}// shader的变换矩阵,我们这里主要用于放大或者缩小mMatrix.setScale(scale, scale);// 设置变换矩阵mBitmapShader.setLocalMatrix(mMatrix);// 设置shadermBitmapPaint.setShader(mBitmapShader);}@Overrideprotected void onDraw(Canvas canvas) {if (getDrawable() == null) {return;}setUpShader();if (type == TYPE_ROUND) {canvas.drawRoundRect(mRoundRect, mCornerRadius, mCornerRadius,mBitmapPaint);if (isPressed() && mPressedColorPaint != null) {canvas.drawRoundRect(mRoundRect, mCornerRadius, mCornerRadius,mPressedColorPaint);}} else {canvas.drawCircle(mRadius, mRadius, mRadius, mBitmapPaint);if (isPressed() && mPressedColorPaint != null) {canvas.drawCircle(mRadius, mRadius, mRadius, mPressedColorPaint);}}}@Overrideprotected void onSizeChanged(int w, int h, int oldw, int oldh) {super.onSizeChanged(w, h, oldw, oldh);Log.d(TAG, "onSizeChanged,w=" + w + ",h=" + h + ",oldw=" + oldw+ ",oldh=" + oldh);// 圆角图片的范围if (type == TYPE_ROUND) {mRoundRect = new RectF(0, 0, w, h);}}/*** drawable转bitmap*/private Bitmap drawableToBitamp(Drawable drawable) {if (drawable instanceof BitmapDrawable) {BitmapDrawable bd = (BitmapDrawable) drawable;return bd.getBitmap();}int w = drawable.getIntrinsicWidth();int h = drawable.getIntrinsicHeight();Bitmap bitmap = Bitmap.createBitmap(w, h, Bitmap.Config.ARGB_8888);Canvas canvas = new Canvas(bitmap);drawable.setBounds(0, 0, w, h);drawable.draw(canvas);return bitmap;}private static final String STATE_INSTANCE = "state_instance";private static final String STATE_TYPE = "state_type";private static final String STATE_BORDER_RADIUS = "state_border_radius"; private static final String STATE_PRESSED_COLOR = "state_pressed_color";@Overrideprotected Parcelable onSaveInstanceState() {Bundle bundle = new Bundle();bundle.putParcelable(STA TE_INSTANCE, super.onSaveInstanceState());bundle.putInt(STA TE_TYPE, type);bundle.putInt(STA TE_BORDER_RADIUS, mCornerRadius);bundle.putInt(STA TE_PRESSED_COLOR, pressedColor);return bundle;}@Overrideprotected void onRestoreInstanceState(Parcelable state) {if (state instanceof Bundle) {Bundle bundle = (Bundle) state;super.onRestoreInstanceState(((Bundle) state).getParcelable(STATE_INSTANCE));this.type = bundle.getInt(STATE_TYPE);this.mCornerRadius = bundle.getInt(STA TE_BORDER_RADIUS);this.pressedColor = bundle.getInt(STA TE_PRESSED_COLOR);if (pressedColor != -1) {mPressedColorPaint = new Paint();mPressedColorPaint.setAntiAlias(true);mPressedColorPaint.setColor(pressedColor);}} else {super.onRestoreInstanceState(state);}}public void setType(int type) {if (this.type != type) {this.type = type;if (this.type != TYPE_ROUND && this.type != TYPE_CIRCLE) {this.type = TYPE_CIRCLE;}requestLayout();}}@Overrideprotected void dispatchSetPressed(boolean pressed) {// imageView.setClickable(true),或imageView.setOnClickListener时才可触发dispatchSetPressedsuper.dispatchSetPressed(pressed);invalidate();}}declare-styleable:declare-styleable是给自定义控件添加自定义属性用的。