您当前的位置: 首页 >  ui

命运之手

暂无认证

  • 1浏览

    0关注

    747博文

    0收益

  • 0浏览

    0点赞

    0打赏

    0留言

私信
关注
热门博文

【高级UI】【011】Canvas和Paint常用API

命运之手 发布时间:2021-10-27 21:17:49 ,浏览量:1

前言

Canvas(画布)是用来画图形的,而Paint(画笔)则是用来指定画图形时用的颜色,宽度等样式信息

这里我们列举一些常用的API,方便新手快速上手

至于不常用的,和比较复杂的API,我们后面的课程用到时在详解

一来篇幅有限,复杂的难以讲清楚,二来也没必要将博客写成百科全书,比较偏的知识大家用到时百度即可

这篇博客建议大家快速扫一遍,有个印象后,直接看下篇教程

Paint常用API


	//画笔API
	Paint paint = new Paint();
	paint.setAntiAlias(true); //抗锯齿,可以让图形边缘更平滑
	paint.setColor(Colors.RED); //设置画笔颜色
	paint.setStyle(Paint.Style.FILL); //填充
	paint.setStyle(Paint.Style.STROKE); //描边
	paint.setStyle(Paint.Style.FILL_AND_STROKE); //填充并描边
	paint.setStrokeWidth(5); //画笔宽度
	paint.setStrokeCap(Paint.Cap.ROUND); //线条端点形状
	paint.setStrokeJoin(Paint.Join.ROUND); //线条连接处形状
	paint.setPathEffect(new DashPathEffect(new float[]{20, 10, 50, 100}, 15)); //设置线条路径效果
	paint.setTextSize(50); //设置文字大小
	paint.setTextAlign(Paint.Align.LEFT); //设置文字对齐方式
	paint.setTypeface(Typeface.DEFAULT); //设置字体
	paint.setLetterSpacing(0.1F); //设置字符间距
	paint.measureText("Hello"); //获取字符串宽度
	paint.getTextBounds("Hello", 0, 5, new Rect()); //获取字符串位置区域
	paint.setShader(new LinearGradient(0, 0, 0, 0, 0, 0, Shader.TileMode.MIRROR)); //设置渲染器,Shader决定了图形和特效如何组合成最终图像
	paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_IN)); //设置图形叠加模式,Xfermode决定了两个图形如何叠加
	paint.setColorFilter(new LightingColorFilter(Colors.RED, 0)); //设置颜色过滤器,ColorFilter决定了图形和颜色如何叠加
	paint.setMaskFilter(new BlurMaskFilter(10, BlurMaskFilter.Blur.NORMAL)); //设置滤镜效果
	paint.setShadowLayer(5, 2, 2, Colors.RED); //设置阴影效果
	paint.set(new Paint()); //将一个画笔的属性,拷贝到当前画笔
	paint.reset(); //重置画笔所有设置

Canvas常用API


	//画布API
	Canvas canvas = null;
	Paint paint = null;
	Bitmap bitmap = null;
	//给整个画布填充颜色
	canvas.drawColor(Color.RED);
	//以指定混合模式给整个画布填充颜色
	canvas.drawColor(Color.RED, PorterDuff.Mode.ADD);
	//通过Color清空画布
	canvas.drawColor(Color.TRANSPARENT, PorterDuff.Mode.CLEAR);
	//通过Xfermode清空画布
	paint.setColor(Color.TRANSPARENT);
	paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.CLEAR));
	canvas.drawRect(new Rect(0, 0, 999, 999), paint);
	//画点
	canvas.drawPoint(100, 100, paint);
	//画多条线,每2个float为一个点,每4个float为一条线
	//4表示跳过前4个float,8表示连续画8个float,即画两条线
	//数组、offset、count的值,都应当是4的整数倍
	canvas.drawLines(new float[]{
	        100, 100, 300, 250,
	        0, 0, 400, 400,
	        200, 300, 500, 500,
	        100, 100, 300, 250
	}, 4, 8, paint);
	//画一条线,相当于canvas.drawLines(pointArray, 0, 4, paint)
	canvas.drawLine(100, 100, 400, 400, paint);
	//画两条线,相当于canvas.drawLines(pointArray, 0, 8, paint)
	canvas.drawLines(new float[]{
	        100, 100, 300, 250,
	        0, 0, 400, 400
	}, paint);
	//画矩形
	canvas.drawRect(100, 100, 600, 600, paint);
	//画圆角矩形
	canvas.drawRoundRect(100, 100, 600, 600, 20, 20, paint);
	//画圆
	canvas.drawCircle(350, 350, 250, paint);
	//画椭圆
	canvas.drawOval(100, 100, 600, 300, paint);
	//画弧,false表示只画弧,true表示画包括半径在内的封闭扇形
	canvas.drawArc(100, 100, 600, 600, 0, -90, false, paint);
	//画任意几何路径
	Path path = new Path();
	path.addArc(100, 100, 500, 300, -180, 180); //在[100,100]-[500,300]的椭圆上,截取[-180°,0°]的弧
	path.arcTo(600, 600, 1000, 800, -180, 180, true); //画一条新的弧,为true时是一条新的路径,为false时强制通过直线连接两条路径
	path.lineTo(500, 1500); //画一条到指定位置的直线
	canvas.drawPath(path, paint);
	//画贝塞尔曲线
	Path path2 = new Path();
	path2.moveTo(300, 300); //移动画笔到[300,300]
	path2.quadTo(500, 400, 700, 300); //以[300,300]为起点,[700,300]为终点,[500,400]为控制点,画二阶贝塞尔曲线
	path2.moveTo(300, 300);
	path2.rQuadTo(500, 400, 700, 300); //还是画二阶塞尔曲线,但这里的坐标,都是相对于[300,300]的相对位置
	path2.moveTo(300, 300);
	path2.cubicTo(500, 400, 600, 800, 700, 300); //画三阶贝塞尔曲线,比二阶多一个控制点
	canvas.drawPath(path2, paint);
	//画文字
	canvas.drawText("Hello", 300, 300, paint);
	//沿指定曲线路径画文字
	Path path3 = new Path();
	path3.moveTo(300, 300);
	path3.quadTo(500, 400, 700, 300);
	canvas.drawTextOnPath("Hello Hello Hello", path3, 0, 0, paint);
	//画位图
	canvas.drawBitmap(bitmap, 300, 300, paint);
	//画位图的指定部分,到指定的Rect位置
	canvas.drawBitmap(bitmap, new Rect(0, 0, bitmap.getWidth(), bitmap.getHeight()), new Rect(0, 0, 800, 400), paint);
	//通过Picture绘制
	//Picture对象不存储实际像素,只保存绘制过程
	Picture picture = new Picture();
	Canvas c = picture.beginRecording(400, 400);
	c.drawLine(100, 100, 400, 400, paint);
	picture.endRecording();
	canvas.drawPicture(picture);
	canvas.drawPicture(picture, new Rect(0, 0, 400, 400));
	//通过PictureDrawable绘制
	PictureDrawable pd = new PictureDrawable(picture);
	pd.setBounds(new Rect(0, 0, 400, 400));
	pd.draw(canvas);
	//平移旋转画布
	//本来在[0,0]处绘制的图形,将会被绘制到[100,100]处
	//本来横向绘制的图形,将变为竖向
	canvas.translate(100, 100);
	canvas.rotate(90);
	canvas.drawBitmap(bitmap, 0, 0, paint);
	//通过矩阵画平移,缩放,旋转后的图像
	Matrix matrix = new Matrix();
	matrix.reset();
	matrix.postTranslate(100, 200);
	matrix.postScale(3, 3);
	matrix.postRotate(20);
	canvas.drawBitmap(bitmap, matrix, paint);
	//裁剪绘制区域
	//canvas默认的绘制区域是整个View范围
	//当通过INTERSECT模式进行裁剪时,则只保留旧的区域与Rect相交的区域,作为新的绘制区域
	//当通过DIFFERENCE模式进行裁剪时,则从旧的区域去除与Rect相交的区域,作为新的绘制区域
	//clipRect可以调用多次,并且每次都是在上次结果之上,继续裁剪,范围只会越来越小,绝对不会变大
	//想要回到最初的绘制区域,则需要通过save和restore来保存、还原画布状态
	canvas.clipRect(new Rect(300, 300, 600, 600), Region.Op.INTERSECT);
	canvas.clipRect(new Rect(300, 300, 600, 600), Region.Op.DIFFERENCE);
	canvas.clipRect(new Rect(300, 300, 600, 600)); //相当于clipRect(Region.Op.INTERSECT)
	canvas.clipOutRect(new Rect(300, 300, 600, 600)); //相当于clipRect(Region.Op.DIFFERENCE)
	//通过Path裁剪绘制区域
	//和clipRect功能一样,只是用Path区域代替Rect区域
	Path path4 = new Path();
	path4.moveTo(300, 300);
	path4.lineTo(600, 300);
	path4.lineTo(600, 600);
	path4.lineTo(300, 600);
	canvas.clipPath(path4);
	//保存和还原画布状态
	//saveLayer和save的功能一样,但saveLayer会同时生成一个新图层
	//新操作将只会在这个图层图层上面操作,比如XferMode等操作,将不会影响到旧的图层
	int saveCount = canvas.save(); //保存画布状态
	saveCount = canvas.saveLayer(new RectF(0, 0, 1000, 1000), paint); //保存画布状态,同时生成一个新图层
	canvas.restore(); //还原到最近一次保存的状态
	canvas.restoreToCount(saveCount); //还原至指定的保存状态

关注
打赏
1654938663
查看更多评论
立即登录/注册

微信扫码登录

0.0398s