Android Canvas Clip 裁剪
上一章节我们学习了裁剪 API 中的 clipRect()
,本章节我们来讲讲另一个 API clipPath()
clipPath()
clipPath()
按照路径裁剪,可以是开放或闭合的曲线,线构成的复杂的集合图形
clipPath()
只有只有一个方法,使用方式非常简单,自己绘制一个 Path
作为参数即可
boolean clipPath(Path path)
另一个在 API 26+
中被废弃
clipPath(Path path, Region.Op op)
范例
我们使用 clipPath()
来制作一个圆角头像
-
创建一个 空的 Android 项目
cn.twle.android.ClipPath
-
下载 /static/i/android/avatar.png,并把所有的图片拖到
res/drawable
目录下 -
自定义一个 View 类
RoundImageView.java
package cn.twle.android.clippath; import android.content.Context; import android.graphics.Bitmap; import android.graphics.Canvas; import android.graphics.Paint; import android.graphics.PaintFlagsDrawFilter; import android.graphics.Path; import android.graphics.Rect; import android.support.v7.widget.AppCompatImageView; import android.util.AttributeSet; public class RoundImageView extends AppCompatImageView { private Bitmap mBitmap; private Rect mRect = new Rect(); private PaintFlagsDrawFilter pdf = new PaintFlagsDrawFilter(0, Paint.ANTI_ALIAS_FLAG); private Paint mPaint = new Paint(); private Path mPath=new Path(); public RoundImageView(Context context, AttributeSet attrs) { super(context, attrs); init(); } //传入一个Bitmap对象 public void setBitmap(Bitmap bitmap) { this.mBitmap = bitmap; } private void init() { mPaint.setStyle(Paint.Style.STROKE); mPaint.setFlags(Paint.ANTI_ALIAS_FLAG); mPaint.setAntiAlias(true);// 抗锯尺 } @Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); if(mBitmap == null) { return; } mRect.set(0,0,getWidth(),getHeight()); canvas.save(); canvas.setDrawFilter(pdf); mPath.addCircle(getWidth() / 2, getWidth() / 2, getHeight() / 2, Path.Direction.CCW); canvas.clipPath(mPath); canvas.drawBitmap(mBitmap, null, mRect, mPaint); canvas.restore(); } }
-
修改
activity_main.xml
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:gravity="center" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="horizontal"> <cn.twle.android.clippath.RoundImageView android:id="@+id/img_round" android:layout_width="128dp" android:layout_height="128dp" android:layout_margin="5px"/> </LinearLayout>
-
修改
MainActivity.java
设置setContentView(new MsView(MainActivity.this))
package cn.twle.android.clippath; import android.graphics.Bitmap; import android.graphics.BitmapFactory; import android.support.v7.app.AppCompatActivity; import android.os.Bundle; public class MainActivity extends AppCompatActivity { private RoundImageView img_round; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); img_round = (RoundImageView) findViewById(R.id.img_round); Bitmap bitmap = BitmapFactory.decodeResource(getResources(),R.drawable.avatar); img_round.setBitmap(bitmap); } }
这种方式制作的圆角 ImageView
会有锯齿明显,即使为 Paint
,Canvas
设置了 抗锯齿也没用
参考文档
官方 API 文档 : Canvas