
前言
在实际项目中,用户头像,音乐专辑都有可能用到圆形,菱形等无规则图像,需要自己自定义View实现相应的功能。
思路
需求:制作圆角菱形的图片
思路:
1、绘制出圆角矩形的遮罩层;
2、将矩形旋转45°;
3、使用画笔的PorterDuffXfermode的SRC_IN属性;
4、将图片绘制遮罩层上。
PorterDuffXfermode
PorterDuffXfermode在网上有许多讲解它的文章,这里只讲解最常用的两种模式SRC_IN和DST_IN。
SRC_IN:【本文所用的模式】显示底层图像和上方图像的相交区域,且 显示的是上方图像 。如图所示,先绘制出黄色的底层图像,再绘制出蓝色的图像,设置的模式为SRC_IN,则显示的是两张图像相交的扇形区域,且为上层蓝色图像。


DST_IN:显示底层图像和上方图像的相交区域,且 显示的是底层图像。如图所示,先绘制出黄色的底层图像,再绘制出蓝色的图像,设置的模式为DST_IN,则显示的是两张图像相交的扇形区域,且为底层黄色图像。
实现
1、根据图片的大小绘制出圆角矩形的遮罩层;
1 | // 创建图片 |
2、设置两张图像的显示模式为SRC_IN;
1 | mPaint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_IN)); |
3、这里需要注意的是因为使用的是同一个画布Canvas,在绘制圆角矩形时已经将画布旋转45°并且平移,这里就需要将画布旋转平移回到初始状态,不然图片就会跟着旋转,就会如下图所示。
1 | // 画布先旋转后平移,防止图片也跟着旋转 |
4、绘制上层图片
1 | maskCanvas.drawBitmap(mImageBitmap, 0, 0, mPaint); |
5、最后在onDraw方法中绘制出最后的图片;
1 | @Override |
总结
设计无规则图形,方法大同小异,可使用PorterDuffXfermode的不同模式实现不同的效果。需要注意的是由于底层和上层的图像都是同一个Canvas绘制,绘制底层时已经改变了方向,后面绘制上层时需要回复到初始状态。另外也可以另写方法创建新的Canvas绘制上层图像,就不必恢复。
源码
1 | public class CustomDiamondImage extends View { |