Android中的图形图像

一、在Android中访问图片

在Android中操作图片是通过使用Drawable类来完成的。Drawable类有很多个子类,如BitmapDrawable用来操作位图;ColorDrawable用来操作颜色;ShapeDrawable用来操作各种形状。

有三种方法实例化Drawable对象:一是使用保存在工程中的一个图片文件;二是使用XML定义Drawable属性;三是构造方法实例化,这种方法在实际开发中一般用不到。

1、使用图片文件创建Drawable对象

1)、在工程的资源文件夹下放入一个image1.jpg图片文件

2)、创建布局文件main.xml并在其中添加一个ImageView组件

3)、创建Activity,并实例化ImageView组件

4)、调用ImageView的setImageResource()方法,引用资源id

  1. public class MainActivity extends Activity {  
  2.     private ImageView imageView;  
  3.     @Override  
  4.     public void onCreate(Bundle savedInstanceState) {  
  5.         super.onCreate(savedInstanceState);  
  6.         setContentView(R.layout.main);  
  7.         imageView = (ImageView) findViewById(R.id.ImageView01);  
  8.         //为ImageView设置图片源  
  9.         imageView.setImageResource(R.drawable.image1);  
  10.     }  
  11. }  

main.xml

  1. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"  
  2.     android:layout_width="fill_parent"  
  3.     android:layout_height="fill_parent"  
  4.     android:orientation="vertical" >  
  5.   
  6.     <TextView  
  7.         android:layout_width="fill_parent"  
  8.         android:layout_height="wrap_content"  
  9.         android:text="Drawable Test" />  
  10.       
  11.     <ImageView   
  12.         android:id="@+id/ImageView01"  
  13.         android:layout_width="wrap_content"  
  14.         android:layout_height="wrap_content" />  
  15.   
  16. </LinearLayout>  

2、使用XML文件定义Drawable属性

下面的代码演示了如何在AndroidManifest.xml配置文件中引用资源图标

  1. <application android:icon="@drawable/ic_launcher" android:label="@string/app_name" />  

上一个例子也可以通过这种方式来配置ImageView资源

  1. <ImageView   
  2.         android:id="@+id/ImageView01"  
  3.         android:layout_width="wrap_content"  
  4.         android:layout_height="wrap_content"  
  5.         <strong><u>android:src="@drawable/image1"</u></strong> />  

3、Bitmap和BitmapFactory

当文件保存在SDCard中时,通过这两个类来读取文件

下面的代码演示了如何从SDCard中读取图片文件斌将其设置为壁纸

1)、在SDCard中添加一个名称为image2.jpg的图片文件

2)、创建Activity

3)、在onCreate()方法中通过BitmapFactory的decodeFile()方法传递文件路径,获得Bitmap对象

4)、调用setWallpaper()方法设置桌面

  1. public class MainActivity extends Activity {  
  2.     @Override  
  3.     protected void onCreate(Bundle savedInstanceState) {  
  4.         super.onCreate(savedInstanceState);  
  5.         setContentView(R.layout.main);  
  6.           
  7.         String path = "/sdcard/image2.jpg";  
  8.         //通过BitmapFactory获得Bitmap实例  
  9.         Bitmap bm = BitmapFactory.decodeFile(path);  
  10.         try {  
  11.             //设置桌面  
  12.             setWallpaper(bm);  
  13.         } catch (Exception e) {  
  14.             e.printStackTrace();  
  15.         }  
  16.     }  
  17. }  

二、Android中的动画

在Android中提供了两种动画实现方式:一种是Tween动画,这种实现方式可以使视图组件移动、放大、缩小以及产生透明度的变化;另一种是Frame动画,这是一种传统的动画方法,通过顺序播放排好的图片来实现,类似电影。

1、Tween动画

Tween动画能完成一系列简单的变化(如位置、尺寸、透明度和旋转等)。Tween动画类位于android.view.animation包中,该在包中包含了一些常用的动画实现类。

  • Animation:动画抽象类,其他几个实现类继承该类
  • ScaleAnimation:控制尺寸变化的动画类
  • AlphaAnimation:控制透明度变化的动画类
  • RotateAnimation:控制旋转变化的动画类
  • TranslateAnimation:控制位置变化的动画类
  • AnimationSet:定义动画属性集合类
  • AnimationUtils:动画工具类

总体来讲,Android系统Tween动画提供了四种实现方式

名称 实现类 常用构造方法 参数说明

Alpha

(渐变动画)

AlphaAnimation

AlphaAnimation

(float fromAlpha,float toAlpha)

fromAlpha:动画开始透明度

toAlpha:动画结束透明度

(取值范围0.0~1.0)

Scale

(尺寸变化动画)

ScaleAnimation

public ScaleAnimation

(float fromX, float toX, float fromY, float toY,

int pivotXType, float pivotXValue,

int pivotYType, float pivotYValue)

fromX:起始X坐标上的伸缩尺寸

toX:结束X坐标上的伸缩尺寸

fromY:起始Y坐标上的伸缩尺寸

toY:结束Y坐标上的伸缩尺寸

pivotXType:X坐标伸缩模式(取值有

Animation.ABSOLUTE、

Animation.RELATIVE_TO_SELF、

Animation.RELATIVE_TO_PARENT)

pivotXValue:相当于X坐标伸缩值

pivotYType:Y坐标伸缩模式

pivotYValue:相当于Y坐标伸缩值

Translate

(位置变化动画)

TranslateAnimation

TranslateAnimation

(float fromXDelta, float toXDelta,

float fromYDelta, float toYDelta)

fromXDelta:起始X坐标

toXDelta:结束X坐标

fromYDelta:起始Y坐标

toYDelta:结束Y坐标

Rotate

(旋转动画)

RotateAnimation

RotateAnimation

(float fromDegrees, float toDegrees,

int pivotXType, float pivotXValue,

int pivotYType, float pivotYValue)

fromDegrees:旋转开始角度

toDegrees:旋转结束角度

pivotXType:X坐标伸缩模式

pivotXValue:相当于X坐标伸缩值

pivotYType:Y坐标伸缩模式

pivotYValue:相当于Y坐标伸缩值

Tween动画的实现方式有两种:一种是直接通过硬编码的方式在程序代码中实现;另一种是在配置文件中定义。Android系统推荐使用配置文件的方法,这种方式可扩展性较高

  1. /** 
  2.  * Tween动画 
  3.  * 实现方式:硬编码 
  4.  */  
  5. public class MainActivity extends Activity {  
  6.     private Button b1,b2,b3,b4;  
  7.     private ImageView imageView;  
  8.     @Override  
  9.     protected void onCreate(Bundle savedInstanceState) {  
  10.         super.onCreate(savedInstanceState);  
  11.         setContentView(R.layout.main);  
  12.         b1 = (Button) findViewById(R.id.tween_Button01);  
  13.         b2 = (Button) findViewById(R.id.tween_Button02);  
  14.         b3 = (Button) findViewById(R.id.tween_Button03);  
  15.         b4 = (Button) findViewById(R.id.tween_Button04);  
  16.         imageView = (ImageView) findViewById(R.id.tween_ImageView);  
  17.         //尺寸  
  18.         b1.setOnClickListener(new OnClickListener() {  
  19.             @Override  
  20.             public void onClick(View v) {  
  21.                 //创建Scale(尺寸)变化动画  
  22.                 Animation scaleAnimation = new ScaleAnimation(0f, 1f, 0f, 1f,  
  23.                         Animation.RELATIVE_TO_SELF,0.5f,  
  24.                         Animation.RELATIVE_TO_SELF,0.5f);  
  25.                   
  26.                 Animation scaleAnimation2 = new ScaleAnimation(0f, 1f, 0f, 1f,  
  27.                         Animation.RELATIVE_TO_SELF,0.5f,  
  28.                         Animation.RELATIVE_TO_PARENT,0.5f);  
  29.                   
  30.                 //设置动画持续时间  
  31.                 scaleAnimation.setDuration(2000);  
  32.                 //开始动画  
  33.                 imageView.startAnimation(scaleAnimation);  
  34.             }  
  35.         });  
  36.         //渐变  
  37.         b2.setOnClickListener(new OnClickListener() {  
  38.             @Override  
  39.             public void onClick(View v) {  
  40.                 Animation alphaAnimation = new AlphaAnimation(0.1f,0.1f);  
  41.                 alphaAnimation.setDuration(2000);  
  42.                 imageView.startAnimation(alphaAnimation);  
  43.             }  
  44.         });  
  45.         //位置变化  
  46.         b3.setOnClickListener(new OnClickListener() {  
  47.             @Override  
  48.             public void onClick(View v) {  
  49.                 Animation translateAnimation = new TranslateAnimation(1010010100);  
  50.                 translateAnimation.setDuration(2000);  
  51.                 imageView.startAnimation(translateAnimation);  
  52.             }  
  53.         });  
  54.         //旋转  
  55.         b4.setOnClickListener(new OnClickListener() {  
  56.             @Override  
  57.             public void onClick(View v) {  
  58.                 Animation rotateAnimation = new RotateAnimation(0f, +360f,  
  59.                         Animation.RELATIVE_TO_SELF,0.5f,  
  60.                         Animation.RELATIVE_TO_SELF,0.5f);  
  61.                 rotateAnimation.setDuration(2000);  
  62.                 imageView.startAnimation(rotateAnimation);  
  63.             }  
  64.         });  
  65.     }  
  66. }  

main.xml

  1. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"  
  2.     android:layout_width="fill_parent"  
  3.     android:layout_height="fill_parent"  
  4.     android:orientation="vertical" >  
  5.       
  6.     <ImageView   
  7.         android:id="@+id/tween_ImageView"  
  8.         android:layout_width="wrap_content"  
  9.         android:layout_height="wrap_content"  
  10.         android:src="@drawable/image1" />  
  11.       
  12.     <Button   
  13.         android:id="@+id/tween_Button01"  
  14.         android:text="Test Scale...尺寸"  
  15.         android:layout_width="wrap_content"  
  16.         android:layout_height="wrap_content" />  
  17.       
  18.     <Button   
  19.         android:id="@+id/tween_Button02"  
  20.         android:text="Test Alpha...透明度"  
  21.         android:layout_width="wrap_content"  
  22.         android:layout_height="wrap_content" />  
  23.       
  24.     <Button   
  25.         android:id="@+id/tween_Button03"  
  26.         android:text="Test Translate...位置变化"  
  27.         android:layout_width="wrap_content"  
  28.         android:layout_height="wrap_content" />  
  29.       
  30.     <Button   
  31.         android:id="@+id/tween_Button04"  
  32.         android:text="Test Rotate...旋转"  
  33.         android:layout_width="wrap_content"  
  34.         android:layout_height="wrap_content" />  
  35.   
  36. </LinearLayout>  

下面演示如何通过配置文件实现

首先在res\anim\目录下创建各种动画的XML配置文件

my_alpha.xml

  1. <set xmlns:android="http://schemas.android.com/apk/res/android">      
  2.     <alpha android:fromAlpha="0.1"  
  3.         android:toAlpha="1.0"  
  4.         android:duration="5000" />     
  5. </set>  

my_translate.xml

  1. <set xmlns:android="http://schemas.android.com/apk/res/android">  
  2.     <translate android:fromXDelta="10"  
  3.         android:toXDelta="100"  
  4.         android:fromYDelta="10"  
  5.         android:toYDelta="100" />  
  6. </set>  

my_scale.xml

  1. <set xmlns:android="http://schemas.android.com/apk/res/android">  
  2.     <scale android:fromXScale="0.0"  
  3.         android:toXScale="1.0"  
  4.         android:fromYScale="0.0"  
  5.         android:toYScale="1.0"  
  6.           
  7.         android:pivotX="50%"  
  8.         android:pivotY="50%"  
  9.         android:duration="5000" />  
  10. </set>  

my_rotate.xml

  1. <set xmlns:android="http://schemas.android.com/apk/res/android">  
  2.     <rotate android:fromDegrees="10"  
  3.         android:toDegrees="-180"  
  4.           
  5.         android:pivotX="50%"  
  6.         android:pivotY="50%"  
  7.         android:duration="5000" />  
  8. </set>  
  1. /** 
  2.  * Tween动画 
  3.  * 实现方式:配置文件 
  4.  */  
  5. public class MainActivity extends Activity {  
  6.     private Button b1,b2,b3,b4;  
  7.     private ImageView imageView;  
  8.     @Override  
  9.     protected void onCreate(Bundle savedInstanceState) {  
  10.         super.onCreate(savedInstanceState);  
  11.         setContentView(R.layout.main);  
  12.         b1 = (Button) findViewById(R.id.tween_Button01);  
  13.         b2 = (Button) findViewById(R.id.tween_Button02);  
  14.         b3 = (Button) findViewById(R.id.tween_Button03);  
  15.         b4 = (Button) findViewById(R.id.tween_Button04);  
  16.         imageView = (ImageView) findViewById(R.id.tween_ImageView);  
  17.         //尺寸  
  18.         b1.setOnClickListener(new OnClickListener() {  
  19.             @Override  
  20.             public void onClick(View v) {  
  21.                 //创建Scale(尺寸)变化动画  
  22.                 Animation scaleAnimation = AnimationUtils.loadAnimation(Main3_2Activity.this, R.anim.my_scale);  
  23.                 //开始动画  
  24.                 imageView.startAnimation(scaleAnimation);  
  25.             }  
  26.         });  
  27.         //渐变  
  28.         b2.setOnClickListener(new OnClickListener() {  
  29.             @Override  
  30.             public void onClick(View v) {  
  31.                 Animation alphaAnimation = AnimationUtils.loadAnimation(Main3_2Activity.this, R.anim.my_alpha);  
  32.                 imageView.startAnimation(alphaAnimation);  
  33.             }  
  34.         });  
  35.         //位置变化  
  36.         b3.setOnClickListener(new OnClickListener() {  
  37.             @Override  
  38.             public void onClick(View v) {  
  39.                 Animation translateAnimation = AnimationUtils.loadAnimation(Main3_2Activity.this, R.anim.my_translate);  
  40.                 imageView.startAnimation(translateAnimation);  
  41.             }  
  42.         });  
  43.         //旋转  
  44.         b4.setOnClickListener(new OnClickListener() {  
  45.             @Override  
  46.             public void onClick(View v) {  
  47.                 Animation rotateAnimation = AnimationUtils.loadAnimation(Main3_2Activity.this, R.anim.my_rotate);  
  48.                 rotateAnimation.setDuration(2000);  
  49.                 imageView.startAnimation(rotateAnimation);  
  50.             }  
  51.         });  
  52.     }  
  53. }  

2、Frame动画

Frame动画是顺序播放图片来产生动画效果的,类似电影。

Frame动画是通过AnimationDrawable类实现的,该类中的两个重要方法是start()和stop()分别用来开始和停止动画。动画一般通过XML配置文件来进行配置,在工程的res\anim\目录下创建一个XML配置文件,该配置文件中有一个<animation-list>根元素和若干个<item>子元素。

下面演示Frame动画的实现,该实例顺序播放4张图片。

res\anim\dance.xml

  1. <animation-list xmlns:android="http://schemas.android.com/apk/res/android"  
  2.     android:oneshot="true">  
  3.           
  4.     <item android:drawable="@drawable/d101" android:duration="500" />  
  5.     <item android:drawable="@drawable/d102" android:duration="500" />  
  6.     <item android:drawable="@drawable/d103" android:duration="500" />  
  7.     <item android:drawable="@drawable/d104" android:duration="500" />  
  8.       
  9. </animation-list>  

main.xml

  1. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"  
  2.     android:layout_width="fill_parent"  
  3.     android:layout_height="fill_parent"  
  4.     android:orientation="vertical" >  
  5.       
  6.     <ImageView   
  7.         android:id="@+id/d_ImageView01"  
  8.         android:layout_width="wrap_content"  
  9.         android:layout_height="wrap_content"   
  10.         android:background="@anim/dance" />  
  11.       
  12.     <Button   
  13.         android:id="@+id/d_Button01"  
  14.         android:text="Start"  
  15.         android:layout_width="wrap_content"  
  16.         android:layout_height="wrap_content" />  
  17.       
  18.     <Button   
  19.         android:id="@+id/d_Button02"  
  20.         android:text="Stop"  
  21.         android:layout_width="wrap_content"  
  22.         android:layout_height="wrap_content" />  
  23.   
  24. </LinearLayout>  
  1. public class MainActivity extends Activity {  
  2.     private Button b1,b2;  
  3.     private ImageView imageView;  
  4.     //声明AnimationDrawable  
  5.     private AnimationDrawable danceAnimation;  
  6.     @Override  
  7.     protected void onCreate(Bundle savedInstanceState) {  
  8.         super.onCreate(savedInstanceState);  
  9.         setContentView(R.layout.main);  
  10.         b1 = (Button) findViewById(R.id.d_Button01);  
  11.         b2 = (Button) findViewById(R.id.d_Button02);  
  12.         imageView = (ImageView) findViewById(R.id.d_ImageView01);  
  13.         //获取背景色,并转换为AnimationDrawable对象  
  14.         danceAnimation = (AnimationDrawable) imageView.getBackground();  
  15.         b1.setOnClickListener(new OnClickListener() {  
  16.             @Override  
  17.             public void onClick(View arg0) {  
  18.                 //开始动画  
  19.                 danceAnimation.start();  
  20.             }  
  21.         });  
  22.         b2.setOnClickListener(new OnClickListener() {  
  23.             @Override  
  24.             public void onClick(View arg0) {  
  25.                 danceAnimation.stop();  
  26.             }  
  27.         });  
  28.     }  
  29. }  

三、动态图形绘制

1、动态图形绘制的基本思路

创建一个类继承View类(或者继承SurfaceView类)。覆盖onDraw()方法,使用Canvas对象在界面上绘制不同的图形,使用invalidate()方法刷新界面。

下面通过一个弹球实例来讲述动态图形绘制的基本思路,该实例是在界面上动态绘制一个小球,当小球触顶时自动改变方向继续运行。

  1. public class MainActivity extends Activity {  
  2.     @Override  
  3.     protected void onCreate(Bundle savedInstanceState) {  
  4.         super.onCreate(savedInstanceState);  
  5.         MyView v = new MyView(thisnull);  
  6.         setContentView(v);  
  7.           
  8.     }  
  9.     //自定义视图类  
  10.     class MyView extends View implements Runnable{  
  11.         //图形当前坐标  
  12.         private int x = 20,y = 20;  
  13.         //构造方法  
  14.         public MyView(Context context,AttributeSet attrs) {  
  15.             super(context, attrs);  
  16.             //获得焦点  
  17.             setFocusable(true);  
  18.             //启动线程  
  19.             new Thread(this).start();  
  20.         }  
  21.         @Override  
  22.         public void run() {  
  23.             Looper.prepare();  
  24.             RefreshHandler mRedrawHandler = new RefreshHandler();  
  25.             while(!Thread.currentThread().isInterrupted()){  
  26.                 //通过发送消息更新界面  
  27.                 Message m = new Message();  
  28.                 m.what = 0x101;  
  29.                 mRedrawHandler.sendMessage(m);  
  30.                 try {  
  31.                     Thread.sleep(100);  
  32.                 } catch (Exception e) {  
  33.                     e.printStackTrace();  
  34.                 }  
  35.             }  
  36.         }  
  37.         @Override  
  38.         protected void onDraw(Canvas canvas) {  
  39.             super.onDraw(canvas);  
  40.             //实例化画笔  
  41.             Paint p = new Paint();  
  42.             //设置画笔颜色  
  43.             p.setColor(Color.GREEN);  
  44.             //画圆  
  45.             canvas.drawCircle(x, y, 10, p);  
  46.         }  
  47.         //更新界面处理器         
  48.         class RefreshHandler extends Handler{  
  49.             @Override  
  50.             public void handleMessage(Message msg) {  
  51.                 if(msg.what == 0x101){  
  52.                     MyView.this.update();  
  53.                     MyView.this.invalidate();  
  54.                 }  
  55.                 super.handleMessage(msg);  
  56.             }  
  57.         }  
  58.         //更新坐标  
  59.         private void update(){  
  60.             int h = getHeight();  
  61.             y += 5;  
  62.             if(y >= h)  
  63.                 y = 20;  
  64.         }  
  65.     }  
  66. }  

2、动态图形绘制类简介

1)、Canvas

画布,位于android.graphics包中,提供了一些画各种图形的方法,例如矩形、圆、椭圆等

方法名称 方法描述
drawText(String text, float x, float y, Paint paint) 在屏幕上写字
drawPoint(float x, float y, Paint paint) 画点
drawLine(float startX, float startY, float stopX, float stopY, Paint paint) 画线
drawCircle(float cx, float cy, float radius, Paint paint) 画圆
drawOval(RectF oval, Paint paint) 画椭圆
drawRect(RectF rect, Paint paint) 画矩形
drawRoundRect(RectF rect, float rx, float ry, Paint paint) 画圆角矩形
clipRect(float left, float top, float right, float bottom) 剪辑矩形
clipRegion(Region region) 剪辑区域

2)、Paint

涂料,用来描述图形颜色和风格,如线宽、颜色、字体等信息。位于android.graphics包中

方法名称 方法描述
Paint() 构造方法,使用默认设置
setColor(int color) 设置颜色
setStrokeWidth(float width) 设置线宽
setTextAlign(Align align) 设置文字对齐
setTextSize(float textSize) 设置文字尺寸
setShader(Shader shader) 设置渐变
setAlpha(int a) 设置alpha值
reset() 复位Paint默认设置

3)、Color

此类定义了一些颜色常量和一些创建颜色的方法。颜色的定义一般使用RGB三原色来定义。Color位于android.graphics包中。

方法或者属性名称 方法描述
BLACK 黑色
BLUE 蓝色
CYAN 青色
DKGRAY 深灰色
GRAY 灰色
GREEN 绿色
LTGRAY 浅灰色
MAGENTA 紫色
RED 红色
TRANSPARENT 透明
WHITE 白色
YELLOW 黄色


4)、Path

当我们想要画一个圆的时候,我们只需要指定圆心(点)和半径就可以了。那么,如果要画一个梯形呢?这里需要有点和连线。Path一般用来从某个点移动到另一个点连线。Path位于android.graphics包中。

方法或者属性名称 方法描述
lineTo(float x , float y) 从最后点到指定点画线
moveTo(float x, float y) 移动到指定点
reset() 复位

3、绘制几何图形

  1. public class MainActivity extends Activity {  
  2.     @Override  
  3.     protected void onCreate(Bundle savedInstanceState) {  
  4.         super.onCreate(savedInstanceState);  
  5.         setContentView(new MyView(this));  
  6.     }  
  7.     //自定义视图类  
  8.     private class MyView extends View{  
  9.         public MyView(Context context) {  
  10.             super(context);  
  11.         }  
  12.         @Override  
  13.         protected void onDraw(Canvas canvas) {  
  14.             super.onDraw(canvas);  
  15.             canvas.drawColor(Color.WHITE);//设置Canvas颜色  
  16.             Paint paint = new Paint();//实例化Paint  
  17.             paint.setAntiAlias(true);             
  18.             paint.setColor(Color.RED);//设置颜色  
  19.             paint.setStyle(Paint.Style.STROKE);//设置样式  
  20.             paint.setStrokeWidth(3);//设置笔画粗细  
  21.             canvas.drawCircle(404030, paint);//画圆  
  22.             canvas.drawRect(109070150, paint);//画矩形  
  23.             canvas.drawRect(1017070200, paint);//画矩形  
  24.             RectF re = new RectF(10,220,70,250);//声明矩形  
  25.             canvas.drawOval(re, paint);//画椭圆  
  26.             Path path = new Path();//实例化路径  
  27.             path.moveTo(10330);//移动到指定点  
  28.             path.lineTo(70330);//画线  
  29.             path.lineTo(40270);//画线  
  30.             path.close();//关闭路径  
  31.             canvas.drawPath(path, paint);//画路径  
  32.             Path path1 = new Path();//实例化路径  
  33.             path1.moveTo(10410);//移动到指定点  
  34.             path1.lineTo(70410);//画线  
  35.             path1.lineTo(55350);//画线  
  36.             path1.lineTo(25350);//画线  
  37.             path1.close();//关闭路径  
  38.             canvas.drawPath(path1, paint);//画路径  
  39.             paint.setStyle(Paint.Style.FILL);//设置样式  
  40.             paint.setColor(Color.BLUE);//设置颜色  
  41.             canvas.drawCircle(1204030, paint);//画圆  
  42.             canvas.drawRect(9090150150, paint);//画矩形  
  43.             canvas.drawRect(90170,150,200,paint);//画矩形  
  44.             RectF re2 = new RectF(90,220,150,250);//实例化矩形  
  45.             canvas.drawOval(re2, paint);//画椭圆  
  46.             Path path2 = new Path();//实例化路径  
  47.             path2.moveTo(90330);//移动到指定点  
  48.             path2.lineTo(150330);//画线  
  49.             path2.lineTo(120270);  
  50.             path2.close();  
  51.             canvas.drawPath(path2, paint);  
  52.             Path path3 = new Path();  
  53.             path3.moveTo(90410);  
  54.             path3.lineTo(150410);  
  55.             path3.lineTo(135350);  
  56.             path3.lineTo(105350);  
  57.             path3.close();  
  58.             canvas.drawPath(path3, paint);  
  59.             //线性渲染  
  60.             Shader mShader = new LinearGradient(00100100,   
  61.                     new int[]{Color.RED,Color.GREEN,Color.BLUE,Color.YELLOW},   
  62.                     null,Shader.TileMode.REPEAT);  
  63.             paint.setShader(mShader);//为Paint设置线性渲染  
  64.             canvas.drawCircle(2004030, paint);  
  65.             canvas.drawRect(17090230,150, paint);  
  66.             canvas.drawRect(170170230200, paint);  
  67.             RectF re3 = new RectF(170220230250);  
  68.             canvas.drawOval(re3, paint);  
  69.             Path path4 = new Path();  
  70.             path4.moveTo(170330);  
  71.             path4.lineTo(230330);  
  72.             path4.lineTo(200270);  
  73.             path4.close();  
  74.             canvas.drawPath(path4, paint);  
  75.             Path path5 = new Path();  
  76.             path5.moveTo(170410);  
  77.             path5.lineTo(230410);  
  78.             path5.lineTo(215350);  
  79.             path5.lineTo(185350);  
  80.             path5.close();  
  81.             canvas.drawPath(path5, paint);  
  82.             paint.setTextSize(24);//设置文本大小  
  83.             //写文字  
  84.             canvas.drawText(getResources().getString(R.string.str_text1), 24050, paint);  
  85.             canvas.drawText(getResources().getString(R.string.str_text2), 240120, paint);  
  86.             canvas.drawText(getResources().getString(R.string.str_text3), 240190, paint);  
  87.             canvas.drawText(getResources().getString(R.string.str_text4), 240250, paint);  
  88.             canvas.drawText(getResources().getString(R.string.str_text5), 240320, paint);  
  89.             canvas.drawText(getResources().getString(R.string.str_text6), 240390, paint);  
  90.         }  
  91.     }   
  92. }  

四、图形特效

1、使用Matrix实现旋转、缩放和平移

该类具有3×3的矩阵坐标,通过该类可以实现图形的旋转、平移和缩放。使用日reset()方法来初始化矩阵类,使用setScale()、setTranslate()、setRotate()方法来设置矩阵缩放、平移和旋转属性。

  1. public class MainActivity extends Activity {  
  2.     @Override  
  3.     protected void onCreate(Bundle savedInstanceState) {  
  4.         super.onCreate(savedInstanceState);  
  5.         MyView myView = new MyView(Main7Activity.this);  
  6.         setContentView(myView);  
  7.     }  
  8.     class MyView extends View{  
  9.         private Bitmap bm;//位图实例  
  10.         private Matrix matrix = new Matrix();//Matrix实例  
  11.         private float angle = 0.0f;//旋转角度  
  12.         private int w,h;//位图宽和高  
  13.         private float scale = 1.0f;//缩放比例  
  14.         private boolean isScale = false;//判断缩放还是旋转  
  15.         //构造方法  
  16.         public MyView(Context context) {  
  17.             super(context);  
  18.             //获得位图  
  19.             bm = BitmapFactory.decodeResource(this.getResources(), R.drawable.image1);  
  20.             w = bm.getWidth();//获得位图宽  
  21.             h = bm.getHeight();//获得位图高  
  22.             //使当前视图获得焦点  
  23.             this.setFocusable(true);  
  24.         }  
  25.         @Override  
  26.         protected void onDraw(Canvas canvas) {  
  27.             super.onDraw(canvas);  
  28.             //重置Matrix  
  29.             matrix.reset();  
  30.             if(!isScale){  
  31.                 //旋转Matrix  
  32.                 matrix.setRotate(angle);  
  33.             }else{  
  34.                 //缩放Matrix  
  35.                 matrix.setScale(scale, scale);  
  36.             }  
  37.             //根据原始位图和Matrix创建新视图  
  38.             Bitmap bm2 = Bitmap.createBitmap(bm, 00,w,h, matrix,true);  
  39.             //绘制新视图  
  40.             canvas.drawBitmap(bm2, matrix, null);  
  41.         }  
  42.         @Override  
  43.         public boolean onKeyDown(int keyCode, KeyEvent event) {  
  44.             //向左旋转  
  45.             if(keyCode == KeyEvent.KEYCODE_DPAD_LEFT){//键盘←  
  46.                 isScale = false;  
  47.                 angle++;  
  48.                 postInvalidate();  
  49.             }  
  50.             //向右旋转  
  51.             if(keyCode == KeyEvent.KEYCODE_DPAD_RIGHT){//键盘→  
  52.                 isScale = false;  
  53.                 angle--;  
  54.                 postInvalidate();  
  55.             }  
  56.             //放大  
  57.             if(keyCode == KeyEvent.KEYCODE_DPAD_UP){//键盘↑  
  58.                 isScale = true;  
  59.                 if(scale < 2.0)  
  60.                     scale += 0.1;  
  61.                 postInvalidate();  
  62.             }  
  63.             //缩小  
  64.             if(keyCode == KeyEvent.KEYCODE_DPAD_DOWN){//键盘↓  
  65.                 isScale = true;  
  66.                 if(scale > 0.5)  
  67.                     scale -= 0.1;  
  68.                 postInvalidate();  
  69.             }  
  70.             return super.onKeyDown(keyCode, event);  
  71.         }  
  72.     }  
  73. }  

2、使用Shader类渲染图形

Shader是一个抽象父类,其子类有多个,如BitmapShader(位图渲染)、ComposeShader(混合渲染)、LinearGradient(线性渲染)、RadialGradient(光束渲染)、SweepGradient(梯度渲染)等。通过Paint对象的paint.setShader(shader)方法来说使用Shader。

    1. public class Main8Activity extends Activity {  
    2.     @Override  
    3.     protected void onCreate(Bundle savedInstanceState) {  
    4.         super.onCreate(savedInstanceState);  
    5.         MyView myView = new MyView(this);  
    6.         setContentView(myView);  
    7.     }  
    8.     class MyView extends View{  
    9.         //声明Bitmap对象  
    10.         private Bitmap bm;  
    11.         //声明位图渲染对象  
    12.         private Shader bitmapShader;  
    13.         //声明线性渲染对象  
    14.         private Shader linearGradient;  
    15.         //声明光束渲染对象  
    16.         private Shader radiaGradient;  
    17.         //声明梯度渲染对象  
    18.         private Shader sweepGradient;  
    19.         //声明混合渲染对象  
    20.         private Shader composeShader;  
    21.         //声明画笔  
    22.         private Paint paint;  
    23.         //声明颜色数组  
    24.         private int[] colors;  
    25.         private boolean isFirst = true;  
    26.           
    27.         public MyView(Context context) {  
    28.             super(context);  
    29.             //获得Bitmap实例  
    30.             bm = BitmapFactory.decodeResource(getResources(), R.drawable.d101);  
    31.             //实例化画笔  
    32.             paint = new Paint();  
    33.             colors = new int[]{Color.RED,Color.GREEN,Color.BLUE};  
    34.             //实例化位图渲染对象,X坐标方向重复图形,Y坐标方向镜像图形  
    35.             bitmapShader = new BitmapShader(bm, TileMode.REPEAT, TileMode.MIRROR);  
    36.             //实例化线性渲染  
    37.             linearGradient = new LinearGradient(0,0100100, colors, null, TileMode.REPEAT);  
    38.             //实例化光束渲染  
    39.             radiaGradient = new RadialGradient(10010080, colors, null, TileMode.REPEAT);  
    40.             //实例化梯度渲染  
    41.             sweepGradient = new SweepGradient(200200, colors, null);  
    42.             //实例化混合渲染  
    43.             composeShader = new ComposeShader(linearGradient, radiaGradient,PorterDuff.Mode.DARKEN);  
    44.             //使其获得焦点  
    45.             setFocusable(true);  
    46.         }  
    47.         @Override  
    48.         protected void onDraw(Canvas canvas) {  
    49.             super.onDraw(canvas);  
    50.             if(isFirst){  
    51.                 //写字,用来提示用户操作  
    52.                 String content = "按上/下/左/右/中间键测试!";  
    53.                 paint.setColor(Color.BLUE);  
    54.                 canvas.drawText(content, 0, content.length()-120,20,paint);                 
    55.             }else{  
    56.                 //全屏画矩形  
    57.                 canvas.drawRect(00, getWidth(), getHeight(), paint);  
    58.             }  
    59.         }  
    60.         @Override  
    61.         public boolean onKeyDown(int keyCode, KeyEvent event) {  
    62.             isFirst = false;  
    63.             if(keyCode == KeyEvent.KEYCODE_DPAD_UP){  
    64.                 //将画笔渲染设置为位图渲染  
    65.                 paint.setShader(bitmapShader);  
    66.             }  
    67.             if(keyCode == KeyEvent.KEYCODE_DPAD_DOWN){  
    68.                 //将画笔渲染设置为线性渲染  
    69.                 paint.setShader(linearGradient);  
    70.             }  
    71.             if(keyCode == KeyEvent.KEYCODE_DPAD_LEFT){  
    72.                 //将画笔渲染设置为光束渲染  
    73.                 paint.setShader(radiaGradient);  
    74.             }  
    75.             if(keyCode == KeyEvent.KEYCODE_DPAD_RIGHT){  
    76.                 //将画笔渲染设置为梯度渲染  
    77.                 paint.setShader(sweepGradient);  
    78.             }  
    79.             if(keyCode == KeyEvent.KEYCODE_DPAD_CENTER){  
    80.                 //将画笔渲染设置为混合渲染  
    81.                 paint.setShader(composeShader);  
    82.             }  
    83.             //重绘界面  
    84.             postInvalidate();  
    85.             return super.onKeyDown(keyCode, event);  
    86.         }  
    87.     }  
    88. }  
原文地址:https://www.cnblogs.com/renyuan/p/2660512.html