Android Graphics之PathEffect
#本文基于android sdk 22
在android graphics模块中有一类特效类叫做“path effect”,他们有一个共同的基类“PathEffect”。这些path effect的唯一目的就是给path增加特效,换句话话说只有当paint的style为“STROKE”或者“FILL_AND_STROKE”时,path effect才会生效。添加path effect的方式很简单,只需要调用Paint.setPathEffect()即可。
截止到android sdk 22,共有6中内置的PathEffect。下面表格列出这六种path effect,并给出基本说明。
下面是各种path effect的实例代码和运行结果。
CornerPathEffect
核心代码:
packagecom.zlsam.learngraphics.patheffect;
importandroid.content.Context;
importandroid.graphics.Canvas;
importandroid.graphics.Color;
importandroid.graphics.CornerPathEffect;
importandroid.graphics.Paint;
importandroid.graphics.Path;
importandroid.util.AttributeSet;
importandroid.view.View;
/**
*Createdbyzhanglongon16/8/18.
*/
publicclassCornerPathEffectViewextendsView{
privateintmCornerRadius=5;
privatePathmPath;
privatePaintmPaint;
publicCornerPathEffectView(Contextcontext){
this(context,null);
}
publicCornerPathEffectView(Contextcontext,AttributeSetattrs){
this(context,attrs,0);
}
publicCornerPathEffectView(Contextcontext,AttributeSetattrs,intdefStyleAttr){
super(context,attrs,defStyleAttr);
if(isInEditMode()){
//Initpath
mPath=newPath();
mPath.moveTo(10,100);
mPath.lineTo(60,10);
mPath.lineTo(120,190);
mPath.lineTo(180,40);
mPath.lineTo(240,160);
mPath.lineTo(300,10);
mPath.lineTo(360,190);
mPath.lineTo(420,40);
mPath.lineTo(480,160);
//Initpaint
mPaint=newPaint();
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeWidth(2);
mPaint.setColor(Color.CYAN);
mPaint.setPathEffect(newCornerPathEffect(mCornerRadius));
return;
}
//Initpath
mPath=newPath();
mPath.moveTo(10,100);
mPath.lineTo(60,10);
mPath.lineTo(120,190);
mPath.lineTo(180,40);
mPath.lineTo(240,160);
mPath.lineTo(300,10);
mPath.lineTo(360,190);
mPath.lineTo(420,40);
mPath.lineTo(480,160);
//Initpaint
mPaint=newPaint();
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeWidth(2);
mPaint.setColor(Color.CYAN);
mPaint.setPathEffect(newCornerPathEffect(mCornerRadius));
}
@Override
protectedvoidonDraw(Canvascanvas){
super.onDraw(canvas);
canvas.drawPath(mPath,mPaint);
}
publicvoidsetCornerRadius(intradius){
mCornerRadius=radius;
mPaint.setPathEffect(newCornerPathEffect(mCornerRadius));
invalidate();
}
publicintgetCornerRadius(){
returnmCornerRadius;
}
}
运行效果:
DashPathEffect
核心代码:
packagecom.zlsam.learngraphics.patheffect;
importandroid.content.Context;
importandroid.graphics.Canvas;
importandroid.graphics.Color;
importandroid.graphics.DashPathEffect;
importandroid.graphics.Paint;
importandroid.graphics.Path;
importandroid.util.AttributeSet;
importandroid.view.View;
/**
*Createdbyzhanglongon16/8/18.
*/
publicclassDashPathEffectViewextendsView{
privatefloatmSolidLength=1F;
privatefloatmVirtualLength=1F;
privatefloatmPhase=0;
privatePathmPath;
privatePaintmPaint;
publicDashPathEffectView(Contextcontext){
this(context,null);
}
publicDashPathEffectView(Contextcontext,AttributeSetattrs){
this(context,attrs,0);
}
publicDashPathEffectView(Contextcontext,AttributeSetattrs,intdefStyleAttr){
super(context,attrs,defStyleAttr);
if(isInEditMode()){
//Initpath
mPath=newPath();
mPath.moveTo(10,100);
mPath.lineTo(60,10);
mPath.lineTo(120,190);
mPath.lineTo(180,40);
mPath.lineTo(240,160);
mPath.lineTo(300,10);
mPath.lineTo(360,190);
mPath.lineTo(420,40);
mPath.lineTo(480,160);
//Initpaint
mPaint=newPaint();
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeWidth(2);
mPaint.setColor(Color.CYAN);
mPaint.setPathEffect(newDashPathEffect(newfloat[]{mSolidLength,mVirtualLength},mPhase));
return;
}
//Initpath
mPath=newPath();
mPath.moveTo(10,100);
mPath.lineTo(60,10);
mPath.lineTo(120,190);
mPath.lineTo(180,40);
mPath.lineTo(240,160);
mPath.lineTo(300,10);
mPath.lineTo(360,190);
mPath.lineTo(420,40);
mPath.lineTo(480,160);
//Initpaint
mPaint=newPaint();
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeWidth(2);
mPaint.setColor(Color.CYAN);
mPaint.setPathEffect(newDashPathEffect(newfloat[]{mSolidLength,mVirtualLength},mPhase));
}
@Override
protectedvoidonDraw(Canvascanvas){
super.onDraw(canvas);
canvas.drawPath(mPath,mPaint);
}
publicvoidsetSolidLength(floatlength){
mSolidLength=length;
mPaint.setPathEffect(newDashPathEffect(newfloat[]{mSolidLength,mVirtualLength},mPhase));
invalidate();
}
publicfloatgetSolidLength(){
returnmSolidLength;
}
publicvoidsetVirtualLength(floatlength){
mVirtualLength=length;
mPaint.setPathEffect(newDashPathEffect(newfloat[]{mSolidLength,mVirtualLength},mPhase));
invalidate();
}
publicfloatgetVirtualLength(){
returnmVirtualLength;
}
publicvoidsetPhase(floatphase){
mPhase=phase;
mPaint.setPathEffect(newDashPathEffect(newfloat[]{mSolidLength,mVirtualLength},mPhase));
invalidate();
}
publicfloatgetPhase(){
returnmPhase;
}
}
运行效果:
PathDashPathEffect
核心代码:
packagecom.zlsam.learngraphics.patheffect;
importandroid.content.Context;
importandroid.graphics.Canvas;
importandroid.graphics.Color;
importandroid.graphics.Paint;
importandroid.graphics.Path;
importandroid.graphics.PathDashPathEffect;
importandroid.graphics.RectF;
importandroid.util.AttributeSet;
importandroid.view.View;
/**
*Createdbyzhanglongon16/8/18.
*/
publicclassPathDashPathEffectViewextendsView{
privatePathmPath;
privatePaintmPaint;
publicPathDashPathEffectView(Contextcontext){
this(context,null);
}
publicPathDashPathEffectView(Contextcontext,AttributeSetattrs){
this(context,attrs,0);
}
publicPathDashPathEffectView(Contextcontext,AttributeSetattrs,intdefStyleAttr){
super(context,attrs,defStyleAttr);
if(isInEditMode()){
//Initpath
mPath=newPath();
mPath.moveTo(10,100);
mPath.lineTo(60,10);
mPath.lineTo(120,190);
mPath.lineTo(180,40);
mPath.lineTo(240,160);
mPath.lineTo(300,10);
mPath.lineTo(360,190);
mPath.lineTo(420,40);
mPath.lineTo(480,160);
//Initpaint
mPaint=newPaint();
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeWidth(2);
mPaint.setColor(Color.CYAN);
Pathpath=newPath();
path.addOval(newRectF(0,0,10,20),Path.Direction.CCW);
mPaint.setPathEffect(newPathDashPathEffect(path,20,0,PathDashPathEffect.Style.ROTATE));
return;
}
//Initpath
mPath=newPath();
mPath.moveTo(10,100);
mPath.lineTo(60,10);
mPath.lineTo(120,190);
mPath.lineTo(180,40);
mPath.lineTo(240,160);
mPath.lineTo(300,10);
mPath.lineTo(360,190);
mPath.lineTo(420,40);
mPath.lineTo(480,160);
//Initpaint
mPaint=newPaint();
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeWidth(2);
mPaint.setColor(Color.CYAN);
Pathpath=newPath();
path.addOval(newRectF(0,0,10,20),Path.Direction.CCW);
mPaint.setPathEffect(newPathDashPathEffect(path,20,0,PathDashPathEffect.Style.ROTATE));
}
@Override
protectedvoidonDraw(Canvascanvas){
super.onDraw(canvas);
canvas.drawPath(mPath,mPaint);
}
}
运行结果:
DiscretePathEffect
核心代码:
packagecom.zlsam.learngraphics.patheffect;
importandroid.content.Context;
importandroid.graphics.Canvas;
importandroid.graphics.Color;
importandroid.graphics.DiscretePathEffect;
importandroid.graphics.Paint;
importandroid.graphics.Path;
importandroid.util.AttributeSet;
importandroid.view.View;
/**
*Createdbyzhanglongon16/8/18.
*/
publicclassDiscretePathEffectViewextendsView{
privatefloatmSegmentLength=1.0F;
privatefloatmDeviation=1.0F;
privatePathmPath;
privatePaintmPaint;
publicDiscretePathEffectView(Contextcontext){
this(context,null);
}
publicDiscretePathEffectView(Contextcontext,AttributeSetattrs){
this(context,attrs,0);
}
publicDiscretePathEffectView(Contextcontext,AttributeSetattrs,intdefStyleAttr){
super(context,attrs,defStyleAttr);
if(isInEditMode()){
//Initpath
mPath=newPath();
mPath.moveTo(10,100);
mPath.lineTo(60,10);
mPath.lineTo(120,190);
mPath.lineTo(180,40);
mPath.lineTo(240,160);
mPath.lineTo(300,10);
mPath.lineTo(360,190);
mPath.lineTo(420,40);
mPath.lineTo(480,160);
//Initpaint
mPaint=newPaint();
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeWidth(2);
mPaint.setColor(Color.CYAN);
mPaint.setPathEffect(newDiscretePathEffect(mSegmentLength,mDeviation));
return;
}
//Initpath
mPath=newPath();
mPath.moveTo(10,100);
mPath.lineTo(60,10);
mPath.lineTo(120,190);
mPath.lineTo(180,40);
mPath.lineTo(240,160);
mPath.lineTo(300,10);
mPath.lineTo(360,190);
mPath.lineTo(420,40);
mPath.lineTo(480,160);
//Initpaint
mPaint=newPaint();
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeWidth(2);
mPaint.setColor(Color.CYAN);
mPaint.setPathEffect(newDiscretePathEffect(mSegmentLength,mDeviation));
}
@Override
protectedvoidonDraw(Canvascanvas){
super.onDraw(canvas);
canvas.drawPath(mPath,mPaint);
}
publicvoidsetSegmentLength(floatlength){
mSegmentLength=length;
mPaint.setPathEffect(newDiscretePathEffect(mSegmentLength,mDeviation));
invalidate();
}
publicfloatgetSegmentLength(){
returnmSegmentLength;
}
publicvoidsetDeviation(floatdeviation){
mDeviation=deviation;
mPaint.setPathEffect(newDiscretePathEffect(mSegmentLength,mDeviation));
invalidate();
}
publicfloatgetDeviation(){
returnmDeviation;
}
}
运行结果:
ComposePathEffect
核心代码:
packagecom.zlsam.learngraphics.patheffect;
importandroid.content.Context;
importandroid.graphics.Canvas;
importandroid.graphics.Color;
importandroid.graphics.ComposePathEffect;
importandroid.graphics.CornerPathEffect;
importandroid.graphics.DashPathEffect;
importandroid.graphics.Paint;
importandroid.graphics.Path;
importandroid.util.AttributeSet;
importandroid.view.View;
/**
*Createdbyzhanglongon16/8/18.
*/
publicclassComposePathEffectViewextendsView{
privateintmCornerRadius=0;
privatefloatmSolidLength=1F;
privatefloatmVirtualLength=1F;
privatefloatmPhase=0;
privatePathmPath;
privatePaintmPaint;
publicComposePathEffectView(Contextcontext){
this(context,null);
}
publicComposePathEffectView(Contextcontext,AttributeSetattrs){
this(context,attrs,0);
}
publicComposePathEffectView(Contextcontext,AttributeSetattrs,intdefStyleAttr){
super(context,attrs,defStyleAttr);
if(isInEditMode()){
//Initpath
mPath=newPath();
mPath.moveTo(10,100);
mPath.lineTo(60,10);
mPath.lineTo(120,190);
mPath.lineTo(180,40);
mPath.lineTo(240,160);
mPath.lineTo(300,10);
mPath.lineTo(360,190);
mPath.lineTo(420,40);
mPath.lineTo(480,160);
//Initpaint
mPaint=newPaint();
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeWidth(2);
mPaint.setColor(Color.CYAN);
mPaint.setPathEffect(newComposePathEffect(newDashPathEffect(newfloat[]{mSolidLength,mVirtualLength},mPhase),newCornerPathEffect(mCornerRadius)));
return;
}
//Initpath
mPath=newPath();
mPath.moveTo(10,100);
mPath.lineTo(60,10);
mPath.lineTo(120,190);
mPath.lineTo(180,40);
mPath.lineTo(240,160);
mPath.lineTo(300,10);
mPath.lineTo(360,190);
mPath.lineTo(420,40);
mPath.lineTo(480,160);
//Initpaint
mPaint=newPaint();
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeWidth(2);
mPaint.setColor(Color.CYAN);
mPaint.setPathEffect(newComposePathEffect(newDashPathEffect(newfloat[]{mSolidLength,mVirtualLength},mPhase),newCornerPathEffect(mCornerRadius)));
}
@Override
protectedvoidonDraw(Canvascanvas){
super.onDraw(canvas);
canvas.drawPath(mPath,mPaint);
}
publicvoidsetCornerRadius(intradius){
mCornerRadius=radius;
mPaint.setPathEffect(newComposePathEffect(newDashPathEffect(newfloat[]{mSolidLength,mVirtualLength},mPhase),newCornerPathEffect(mCornerRadius)));
invalidate();
}
publicintgetCornerRadius(){
returnmCornerRadius;
}
publicvoidsetSolidLength(floatlength){
mSolidLength=length;
mPaint.setPathEffect(newComposePathEffect(newDashPathEffect(newfloat[]{mSolidLength,mVirtualLength},mPhase),newCornerPathEffect(mCornerRadius)));
invalidate();
}
publicfloatgetSolidLength(){
returnmSolidLength;
}
publicvoidsetVirtualLength(floatlength){
mVirtualLength=length;
mPaint.setPathEffect(newComposePathEffect(newDashPathEffect(newfloat[]{mSolidLength,mVirtualLength},mPhase),newCornerPathEffect(mCornerRadius)));
invalidate();
}
publicfloatgetVirtualLength(){
returnmVirtualLength;
}
publicvoidsetPhase(floatphase){
mPhase=phase;
mPaint.setPathEffect(newComposePathEffect(newDashPathEffect(newfloat[]{mSolidLength,mVirtualLength},mPhase),newCornerPathEffect(mCornerRadius)));
invalidate();
}
publicfloatgetPhase(){
returnmPhase;
}
}
运行结果:
SumPathEffect
核心代码:
packagecom.zlsam.learngraphics.patheffect;
importandroid.content.Context;
importandroid.graphics.Canvas;
importandroid.graphics.Color;
importandroid.graphics.CornerPathEffect;
importandroid.graphics.DashPathEffect;
importandroid.graphics.Paint;
importandroid.graphics.Path;
importandroid.graphics.SumPathEffect;
importandroid.util.AttributeSet;
importandroid.view.View;
/**
*Createdbyzhanglongon16/8/18.
*/
publicclassSumPathEffectViewextendsView{
privateintmCornerRadius=0;
privatefloatmSolidLength=1F;
privatefloatmVirtualLength=1F;
privatefloatmPhase=0;
privatePathmPath;
privatePaintmPaint;
publicSumPathEffectView(Contextcontext){
this(context,null);
}
publicSumPathEffectView(Contextcontext,AttributeSetattrs){
this(context,attrs,0);
}
publicSumPathEffectView(Contextcontext,AttributeSetattrs,intdefStyleAttr){
super(context,attrs,defStyleAttr);
if(isInEditMode()){
//Initpath
mPath=newPath();
mPath.moveTo(10,100);
mPath.lineTo(60,10);
mPath.lineTo(120,190);
mPath.lineTo(180,40);
mPath.lineTo(240,160);
mPath.lineTo(300,10);
mPath.lineTo(360,190);
mPath.lineTo(420,40);
mPath.lineTo(480,160);
//Initpaint
mPaint=newPaint();
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeWidth(2);
mPaint.setColor(Color.CYAN);
mPaint.setPathEffect(newSumPathEffect(newDashPathEffect(newfloat[]{mSolidLength,mVirtualLength},mPhase),newCornerPathEffect(mCornerRadius)));
return;
}
//Initpath
mPath=newPath();
mPath.moveTo(10,100);
mPath.lineTo(60,10);
mPath.lineTo(120,190);
mPath.lineTo(180,40);
mPath.lineTo(240,160);
mPath.lineTo(300,10);
mPath.lineTo(360,190);
mPath.lineTo(420,40);
mPath.lineTo(480,160);
//Initpaint
mPaint=newPaint();
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeWidth(2);
mPaint.setColor(Color.CYAN);
mPaint.setPathEffect(newSumPathEffect(newDashPathEffect(newfloat[]{mSolidLength,mVirtualLength},mPhase),newCornerPathEffect(mCornerRadius)));
}
@Override
protectedvoidonDraw(Canvascanvas){
super.onDraw(canvas);
canvas.drawPath(mPath,mPaint);
}
publicvoidsetCornerRadius(intradius){
mCornerRadius=radius;
mPaint.setPathEffect(newSumPathEffect(newDashPathEffect(newfloat[]{mSolidLength,mVirtualLength},mPhase),newCornerPathEffect(mCornerRadius)));
invalidate();
}
publicintgetCornerRadius(){
returnmCornerRadius;
}
publicvoidsetSolidLength(floatlength){
mSolidLength=length;
mPaint.setPathEffect(newSumPathEffect(newDashPathEffect(newfloat[]{mSolidLength,mVirtualLength},mPhase),newCornerPathEffect(mCornerRadius)));
invalidate();
}
publicfloatgetSolidLength(){
returnmSolidLength;
}
publicvoidsetVirtualLength(floatlength){
mVirtualLength=length;
mPaint.setPathEffect(newSumPathEffect(newDashPathEffect(newfloat[]{mSolidLength,mVirtualLength},mPhase),newCornerPathEffect(mCornerRadius)));
invalidate();
}
publicfloatgetVirtualLength(){
returnmVirtualLength;
}
publicvoidsetPhase(floatphase){
mPhase=phase;
mPaint.setPathEffect(newSumPathEffect(newDashPathEffect(newfloat[]{mSolidLength,mVirtualLength},mPhase),newCornerPathEffect(mCornerRadius)));
invalidate();
}
publicfloatgetPhase(){
returnmPhase;
}
}
运行结果:
本文的示例×××地址:https://github.com/zhanglong1/AndroidGraphicsDemo
声明:本站所有文章资源内容,如无特殊说明或标注,均为采集网络资源。如若本站内容侵犯了原著者的合法权益,可联系本站删除。