1:畫(huà)圓
canvas.drawCircle(width / 2, height / 2, radius, mPaint);//繪制圓形镰禾,第一個(gè)參數(shù)是圓心的x坐標(biāo)所灸,第二個(gè)參數(shù)是圓心的y坐標(biāo),第三個(gè)參數(shù)是半徑魔熏,單位都是像素
2:畫(huà)矩形canvas.drawRect(0,0,getMeasuredWidth(),getMeasuredHeight(),paint);//這里繪制出來(lái)的矩形是實(shí)心的矩形砾淌,而不是空心的矩形線條稼钩,因?yàn)閜aint設(shè)置的style是Paint.Style.FILL篱瞎,前四個(gè)參數(shù)的具體含義請(qǐng)看下圖
3:canvas.save()和canvas.restore()的區(qū)別
@Override
protected void onDraw(Canvas canvas) {
canvas.drawRect(0,0,getMeasuredWidth(),getMeasuredHeight(),paint);
canvas.drawRect(10,10,getMeasuredWidth()-10,getMeasuredHeight()-10,paint1);
canvas.save();
canvas.translate(10,0);
canvas.restore();
super.onDraw(canvas);
}
區(qū)別是:當(dāng)調(diào)用save方法后苟呐,就將canvas的位置和角度記錄下來(lái)了,然后接下來(lái)就可以進(jìn)行畫(huà)布的平移俐筋,旋轉(zhuǎn)之類(lèi)的位置變化操作牵素,也可以進(jìn)行畫(huà)圖操作,不過(guò)此時(shí)所畫(huà)的圖是在進(jìn)行了位置變化操作之后的canvas上進(jìn)行的澄者,如果要還原上一次保存的canvas的位置的話笆呆,就調(diào)用restore方法,這時(shí)canvas的位置就回到了上一次save時(shí)的狀態(tài)了粱挡。
4赠幕,畫(huà)圓弧:drawArc(RectF oval, float startAngle, float sweepAngle, boolean useCenter, Paint paint)
oval :指定圓弧的外輪廓矩形區(qū)域询筏。
startAngle: 圓弧起始角度(x軸的正右的方向榕堰,是0度的位置),單位為度嫌套。
sweepAngle: 圓弧掃過(guò)的角度逆屡,順時(shí)針?lè)较驗(yàn)檎嵌然迹瑔挝粸槎?br> useCenter: 如果為T(mén)rue時(shí),用來(lái)繪制扇形魏蔗,如果為false時(shí)砍的,用來(lái)繪制弧形。
paint: 繪制圓弧的畫(huà)板屬性莺治,如顏色挨约,是否填充等。
paint.setStyle(Paint.Style.FILL);
canvas.drawArc(200,100,800,500,180,60,false,paint);
以上兩句代碼畫(huà)出的形狀是
5产雹,畫(huà)筆的一些方法
1:用paint的時(shí)候有三種Style,分別是
Paint.Style.STROKE 只繪制圖形輪廓(描邊)
Paint.Style.FILL 只繪制圖形內(nèi)容 翁锡,默認(rèn)是Paint.Style.FILL
Paint.Style.FILL_AND_STROKE 既繪制輪廓也繪制內(nèi)容
image.png
2:mPaint.setStrokeWidth(40);//用來(lái)設(shè)置畫(huà)筆的寬度
6,設(shè)置畫(huà)布的顏色蔓挖,這類(lèi)顏色填充方法一般用于在繪制之前設(shè)置底色,或者在繪制之后為界面設(shè)置半透明蒙版馆衔。
canvas.drawColor(Color.RED);
canvas.drawARGB(100,100,100,100);
canvas.drawRGB(100,100,100);
7,設(shè)置線條的寬度瘟判,在STROKE和FILL_AND_STROKE下使用
paint.setStrokeWidth(10);//設(shè)置線條寬度為10像素
8,在繪制的時(shí)候,往往需要開(kāi)啟抗鋸齒來(lái)讓圖形和文字的邊緣更加平滑
paint=new Paint(Paint.ANTI_ALIAS_FLAG);//靜態(tài)開(kāi)啟抗鋸齒
paint.setAntiAlias(true);//動(dòng)態(tài)開(kāi)啟抗鋸齒
9,繪制一個(gè)點(diǎn)角溃,前兩個(gè)參數(shù)是x,y坐標(biāo)拷获,點(diǎn)的大小可以通過(guò)paint.setStrokeWidth來(lái)設(shè)置,點(diǎn)的形狀可以通過(guò)paint.setStrokeCap來(lái)設(shè)置减细,其中匆瓜,SQUARE或BUTT畫(huà)出來(lái)是方形的點(diǎn),ROUND畫(huà)出來(lái)是圓形的點(diǎn)未蝌。
canvas.drawPoint(100,100,paint);
10,畫(huà)橢圓
canvas.drawOval(100,100,200,500,paint);
11,畫(huà)線,由于直線不是封閉圖形驮吱,所以paint.setStyle對(duì)直線沒(méi)有影響,canvas.drawLine是畫(huà)一條線,可以用canvas.drawLines批量畫(huà)線
canvas.drawLine(200,200,400,400,paint);
12,畫(huà)圓角矩形萧吠,第五個(gè)和第六個(gè)參數(shù)是矩形的每個(gè)圓角的橫向半徑和縱向半徑
canvas.drawRoundRect(200,300,400,500,80,80,paint);
13,根據(jù)path畫(huà)圖形
canvas.drawPath(path, paint);
其中左冬,Path對(duì)象有如下
第一組,add...方法(添加完整封閉圖形纸型,除了addPath())
path.addCircle(300,300,200, Path.Direction.CW);//添加圓
//path.addOval();//添加橢圓
//path.addRect();//添加矩形
//path.addRoundRect();添加圓角矩形
//path.addPath();添加path
第二組拇砰,...To方法(畫(huà)直線或者曲線)
//lineTo和rLineTo畫(huà)直線
paint.setStyle(Paint.Style.STROKE);//如果參數(shù)是Paint.Style.FILL,那么畫(huà)出來(lái)的是個(gè)三角形狰腌,和上面的那個(gè)畫(huà)圓弧的一樣除破,將畫(huà)筆style設(shè)置為FILL
path.lineTo(100,100);//參數(shù)是絕對(duì)坐標(biāo),由當(dāng)前位置(0,0)向(100,100)畫(huà)一條直線
path.rLineTo(100,0);//參數(shù)是相對(duì)坐標(biāo),由當(dāng)前位置(100,100)向正右方100像素的位置畫(huà)一條直線
canvas.drawPath(path, paint);
//moveTo移動(dòng)原點(diǎn)位置
paint.setStyle(Paint.Style.STROKE);
path.lineTo(100,100);//相對(duì)于原點(diǎn)(0,0)畫(huà)直線到點(diǎn)(100,100)
path.moveTo(200,100);//此時(shí)原點(diǎn)坐標(biāo)為(200,100)
path.lineTo(200,0);//相對(duì)于原點(diǎn)(200,100)畫(huà)直線到點(diǎn)(200,0)癌别,注意這個(gè)(200,0)點(diǎn)還是以(0,0)為原點(diǎn)的(200,0)點(diǎn)皂岔,因?yàn)橛玫氖莑ineTo,如果是rLineTo()則原點(diǎn)為(200,100)
canvas.drawPath(path, paint);
//arcTo畫(huà)弧線
paint.setStyle(Paint.Style.STROKE);
path.lineTo(100,100);
path.arcTo(100,100,300,300,-90,90,false);//第七個(gè)參數(shù)為直線連線連到弧形起點(diǎn)展姐,true為無(wú)痕跡躁垛,false為有痕跡剖毯,如果沒(méi)有path.lineTo(100,100);這句
//代碼的話,true和false的效果是一樣的
canvas.drawPath(path, paint);
//addArc畫(huà)弧線
paint.setStyle(Paint.Style.STROKE);
path.lineTo(100,100);
path.addArc(100,100,300,300,-90,90);//path.addArc(100,100,300,300,-90,90)相當(dāng)于path.arcTo(100,100,300,300,-90,90,true)教馆,addArc()相當(dāng)于arcTo()的第七個(gè)參數(shù)為true的簡(jiǎn)化版
canvas.drawPath(path, paint);
第三逊谋,Path的close方法,不是所有的子圖形都需要使用path的close()來(lái)封閉的土铺,當(dāng)paint的style是FILL或者是FILL_AND_STROKE時(shí)胶滋,Path會(huì)自動(dòng)封閉子圖形,這就是上面畫(huà)弧和畫(huà)兩條線悲敷,如果設(shè)置為FILL究恤,畫(huà)出來(lái)的是填充的弧和三角形的原因。
paint.setStyle(Paint.Style.FILL);
path.moveTo(100,100);
path.lineTo(200,100);
path.lineTo(150,150);
canvas.drawPath(path, paint);//這里只繪制了兩條邊后德,但由于style是FILL,所以繪制時(shí)會(huì)自動(dòng)封口
第四部宿,Path的setFillType方法,對(duì)于添加子圖形類(lèi)方法(如path.addCircle(),path.addRect())的方向瓢湃,由方法的dir參數(shù)來(lái)控制理张,而對(duì)于畫(huà)線類(lèi)的方法(如path.lineTo(),path.arcTo())的方向就是圖形的方向
paint.setStyle(Paint.Style.FILL);
path.addCircle(300,300,200, Path.Direction.CCW);//CW順時(shí)針,CCW逆時(shí)針
path.addCircle(300,300,100, Path.Direction.CW);
path.setFillType(Path.FillType.INVERSE_WINDING);//EVEN_ODD是如果是奇數(shù)就繪制绵患,也就是說(shuō)如果兩個(gè)圖形有部分重合雾叭,那么重合的那部分就不繪制,繪制剩下的
//WINDING是按方向進(jìn)行相加的落蝙,順時(shí)針?lè)较?1织狐,逆時(shí)針?lè)较?1,最后為0的那部分不繪制掘殴,繪制剩下的
//INVERSE_EVEN_ODD就是將EVEN_ODD反過(guò)來(lái)
//INVERSE_WINDING就是將WINDING反過(guò)來(lái)
canvas.drawPath(path,paint);
來(lái)個(gè)圖片赚瘦,通俗易懂
14,畫(huà)Bitmap
Bitmap bitmap=BitmapFactory.decodeResource(getResources(),R.mipmap.ic_launcher);
...
canvas.drawBitmap(bitmap,100,100,paint);
15奏寨,繪制文字
paint.setTextSize(100);//設(shè)置文字的大小
canvas.drawText("你好啊",200,200,paint);
以前記錄過(guò)的
Paint a=new Paint();
a.setColor(Color.RED);
//a.setAlpha(100);
//a.setStyle(Style.FILL_AND_STROKE);//設(shè)置畫(huà)筆的風(fēng)格
//a.setStrokeWidth(33);//設(shè)置空心線寬
a.setTextSize(34);//設(shè)置畫(huà)筆字體的大小
//a.setTypeface(Typeface.DEFAULT_BOLD);//設(shè)置字體樣式
//a.setTextScaleX(55);//設(shè)置比例因子起意,以一為標(biāo)準(zhǔn)
//a.setARGB(40, 45, 88, 66);//設(shè)置字體的顏色
//a.setUnderlineText(true);//設(shè)置下劃線
//a.setTextSkewX(3);//設(shè)置傾斜因子,以零為標(biāo)準(zhǔn)
canvas.drawColor(Color.GREEN);//設(shè)置背景顏色
//canvas.drawText("n好啊", 70, 90, a);
///canvas.drawCircle(33, 22, 44, a);
//canvas.drawLine(33, 44, 11, 22, a);
//canvas.drawPoint(44, 55, a);
//canvas.drawRoundRect(new RectF(55,277,488,499), 35, 22, a);//繪制圓角矩形
//canvas.drawOval(new RectF(33,333,222,444), a);//繪制橢圓形
//Path ab=new Path();
//ab.moveTo(33, 44);
//ab.lineTo(77, 88);
//ab.lineTo(76, 55);
//canvas.drawPath(ab, a);//繪制任意多邊形
//canvas.drawArc(new RectF(33,44,333,444), 66, 55, true, a);//繪制圓弧
//Bitmap ac=((BitmapDrawable)getResources().getDrawable(R.drawable.ic_launcher)).getBitmap();
//canvas.drawBitmap(ac, 444, 44, a);//繪制圖像
//canvas.clipRect(44, 66, 222, 330);//裁剪指定的區(qū)域
//canvas.drawColor(Color.BLUE);
//canvas.drawText("旋轉(zhuǎn)字", 43, 333, a);
//canvas.save();
//canvas.rotate(60,43,333);
//canvas.drawText("旋轉(zhuǎn)字", 43, 333, a);
//canvas.restore();//關(guān)于畫(huà)布鎖定和解鎖病瞳,旋轉(zhuǎn)的例子
-----------------------------------------------------------------------------------
android群英傳中對(duì)canvas的介紹
1:Canvas.save()揽咕,Canvas.restore(),Canvas.translate()套菜,Canvas.rotate()這四個(gè)方法的介紹如下:
Canvas.save()這個(gè)方法亲善,從字面上可以理解為保存畫(huà)布,它的作用就是將之前的所有已繪制圖像保存起來(lái)逗柴,讓后續(xù)的操作就好像在一個(gè)新的圖層上操作一樣蛹头,這一點(diǎn)點(diǎn)與photoshop中的圖層理解基本一致。
Canvas.restore()這個(gè)方法,則可以理解為photoshop中的合并圖層操作渣蜗,它的作用是將我們?cè)趕ave()之后繪制的所有圖像與save()之前的圖像進(jìn)行合并屠尊。
translate()和rotate()方法,就是在調(diào)用translate(x,y)方法之后耕拷,將原點(diǎn)(0,0)移動(dòng)到(x,y)讼昆。之后的所有繪圖操作都將以(x,y)為原點(diǎn)執(zhí)行。同理totate()方法也是一樣的骚烧,它將坐標(biāo)系旋轉(zhuǎn)了一定的角度浸赫。
2:Layer圖層
在android中通過(guò)調(diào)用saveLayer()方法,saveLayerAlpha()方法創(chuàng)建一個(gè)圖層赃绊,使用restore()方法既峡,restoreToCount()方法合并所有圖層。創(chuàng)建圖層的時(shí)候碧查,后面所有的操作都發(fā)生在這個(gè)圖層上涧狮。saveLayerAlpha()的第五個(gè)參數(shù)的取值如果是0比表示完全透明,127表示半透明么夫,255表示完全不透明。示例代碼如下:
canvas.drawCircle(300,300,200,paint);
canvas.saveLayerAlpha(0,0,600,600,127);
paint.setColor(Color.GREEN);
canvas.drawCircle(300,300,300,paint);
canvas.restore();
圖如下所示:
3:PorterDuffXfermode(參考文章:http://www.reibang.com/p/0f64daf202f2)
示例代碼如下:
...
canvas.saveLayer(0,0,canvas.getWidth(),canvas.getHeight(),paint);//必須要新建一個(gè)圖層才能看到混合后的效果了
canvas.drawCircle(0,0,bitmap.getWidth()/2,paint);
paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_IN));
canvas.drawBitmap(bitmap,0,0,paint);
paint.setXfermode(null);// 還原混合模式
canvas.restore();//合并圖層
...
效果如下:
4:Shader肤视,著色器档痪,渲染器,Shader包括:BitmapShader(位圖Shader)邢滑,LinearGradient(線性Shader)腐螟,RadialGradient(光速Shader),SweepGradient(梯度Shader)困后,ComposeShader(混合Shader)
4.1:BitmapShader的使用乐纸,填充模式有三種CLAMP(拉伸),REPEAT(重復(fù))摇予,MIRROR(鏡像)汽绢,示例代碼如下:
paint.setShader(new BitmapShader(bitmap, Shader.TileMode.CLAMP, Shader.TileMode.CLAMP));
canvas.drawCircle(canvas.getWidth() / 2, canvas.getHeight() / 2, canvas.getWidth() / 2 > canvas.getHeight() / 2 ? canvas.getHeight() / 2 : canvas.getWidth() / 2, paint);
結(jié)果如下所示:
4.2:LinearGradient的使用,示例代碼如下:
paint.setShader(new LinearGradient(0,0,canvas.getWidth(),canvas.getHeight(),Color.BLUE,Color.GREEN, Shader.TileMode.CLAMP));
canvas.drawCircle(canvas.getWidth() / 2, canvas.getHeight() / 2, canvas.getWidth() / 2 > canvas.getHeight() / 2 ? canvas.getHeight() / 2 : canvas.getWidth() / 2, paint);
結(jié)果如下所示:
小技巧:Marix.setScale(1F,-1F)可以實(shí)現(xiàn)圖片的垂直翻轉(zhuǎn)侧戴。
5:PathEffect
5.1:DiscretePathEffect宁昭,使用這個(gè)效果之后,線段上就會(huì)產(chǎn)生許多雜點(diǎn)
paint.setPathEffect(new DiscretePathEffect(3f,5f));
Path path=new Path();
path.moveTo(0,canvas.getHeight()/2);
path.lineTo(canvas.getWidth()/3,0);
path.lineTo(canvas.getWidth()/3*2,canvas.getHeight());
path.lineTo(canvas.getWidth(),0);
canvas.drawPath(path,paint);
效果圖如下:
5.2:DashPathEffect酗宋,這個(gè)效果可以用來(lái)繪制虛線积仗,用一個(gè)數(shù)組來(lái)設(shè)置各個(gè)點(diǎn)之間的間隔,此后繪制虛線時(shí)就重復(fù)這樣的間隔進(jìn)行繪制蜕猫,另一個(gè)參數(shù)則用來(lái)控制繪制時(shí)數(shù)組的一個(gè)偏移量寂曹,通常可以通過(guò)設(shè)置值來(lái)實(shí)現(xiàn)路徑的動(dòng)態(tài)效果。
paint.setPathEffect(new DashPathEffect(new float[]{20,10,5,10},0));
效果圖如下:
5.3:PathDashPathEffect隆圆,這個(gè)效果和DashPathEffect效果類(lèi)似漱挚,只不過(guò)它的功能更加強(qiáng)大,可以設(shè)置顯示點(diǎn)的圖形匾灶,即方形點(diǎn)的虛線棱烂,圓形點(diǎn)的虛線。
Path path1=new Path();
path1.addRect(0,0,8,8,Path.Direction.CCW);
paint.setPathEffect(new PathDashPathEffect(path1,12f,0,PathDashPathEffect.Style.ROTATE));
效果圖如下:
5.4:CornerPathEffect阶女,就是將拐角處變得圓滑颊糜,具體圓滑的程度,則由參數(shù)決定秃踩。
paint.setPathEffect(new CornerPathEffect(30));
效果圖如下:
5.5:ComposePathEffect衬鱼,將任意兩種路徑特效組合起來(lái)形成一個(gè)新的效果。
PathEffect pathEffect=new CornerPathEffect(30);
PathEffect pathEffect1=new DashPathEffect(new float[]{20,10,5,10},0);
paint.setPathEffect(new ComposePathEffect(pathEffect,pathEffect1));
效果圖如下:
5.6:SumPathEffect憔杨,將任意兩種路徑特效組合起來(lái)形成一個(gè)新的效果鸟赫。
PathEffect pathEffect=new CornerPathEffect(30);
PathEffect pathEffect1=new DashPathEffect(new float[]{20,10,5,10},0);
paint.setPathEffect(new SumPathEffect(pathEffect,pathEffect1));
效果圖如下: