• Android应用开发基础篇(8)-----SurfaceView


    链接地址:http://www.cnblogs.com/lknlfy/archive/2012/02/25/2368069.html

    一、概述

          SurfaceView也是一个用来画图的部件,不过由于它的效率比较高,因此一般多用在游戏编程中,在摄像头编程中也会用到,还有它和View比较大的不同是它可以在非UI线程里画图。下面的实现中会提到使用SurfaceView来画图需要注意的几个地方。

     

    二、要求

         会使用SurfaceView来画图。

     

    三、实现

         新建工程MySurface,修改/res/layout/main.xml文件,在里面添加一个Button和一个SurfaceView,完整的main.xml文件如下:

    复制代码
     1 <?xml version="1.0" encoding="utf-8"?>
    2 <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    3 android:layout_width="fill_parent"
    4 android:layout_height="fill_parent"
    5 android:orientation="vertical" >
    6
    7
    8 <Button
    9 android:id="@+id/button"
    10 android:layout_width="fill_parent"
    11 android:layout_height="wrap_content"
    12 android:text="画线"
    13 />
    14
    15 <SurfaceView
    16 android:id="@+id/surface"
    17 android:layout_width="fill_parent"
    18 android:layout_height="fill_parent"
    19 />
    20
    21 </LinearLayout>
    复制代码

    修改MySurfaceActivity.java文件,主要实现Button的监听和SurfaceHolder.Callback的接口,完整的内容如下:

    复制代码
     1 package com.nan.surface;
    2
    3
    4 import android.app.Activity;
    5 import android.graphics.Canvas;
    6 import android.graphics.Color;
    7 import android.graphics.Paint;
    8 import android.graphics.Rect;
    9 import android.os.Bundle;
    10 import android.view.SurfaceHolder;
    11 import android.view.SurfaceView;
    12 import android.view.View;
    13 import android.widget.Button;
    14
    15
    16 public class MySurfaceActivity extends Activity
    17 {
    18 private int OldX = 0;
    19 private int OldY = 0;
    20 private Button mButton = null;
    21 private SurfaceView mSurfaceView = null;
    22 private SurfaceHolder mSurfaceHolder = null;
    23 private Paint mPaint = null;
    24
    25 @Override
    26 public void onCreate(Bundle savedInstanceState)
    27 {
    28 super.onCreate(savedInstanceState);
    29 setContentView(R.layout.main);
    30
    31 mButton = (Button)findViewById(R.id.button);
    32 mSurfaceView = (SurfaceView)findViewById(R.id.surface);
    33 mSurfaceHolder = mSurfaceView.getHolder();
    34 mSurfaceHolder.addCallback(new MyHolder());
    35
    36 mPaint = new Paint();
    37 //画笔的颜色
    38 mPaint.setColor(Color.RED);
    39 //画笔的粗细
    40 mPaint.setStrokeWidth(10.0f);
    41 //按钮监听
    42 mButton.setOnClickListener(new View.OnClickListener()
    43 {
    44
    45 public void onClick(View v)
    46 {
    47 // TODO Auto-generated method stub
    48 //锁定整个SurfaceView
    49 Canvas mCanvas = mSurfaceHolder.lockCanvas();
    50 mCanvas.drawLine(OldX, OldY, OldX+10, OldY+10, mPaint);
    51 //横坐标增加
    52 OldX = OldX + 10;
    53 //纵坐标增加
    54 OldY = OldY + 10;
    55 // 绘制完成,释放画布,提交修改
    56 mSurfaceHolder.unlockCanvasAndPost(mCanvas);
    57 //重新锁一次
    58 //mSurfaceHolder.lockCanvas(new Rect(0, 0, 0, 0));
    59 //mSurfaceHolder.unlockCanvasAndPost(mCanvas);
    60 }
    61 });
    62 }
    63
    64 //定义一个类,实现Callback接口
    65 public class MyHolder implements SurfaceHolder.Callback
    66 {
    67
    68 public void surfaceChanged(SurfaceHolder holder, int format, int width,
    69 int height)
    70 {
    71 // TODO Auto-generated method stub
    72 //add your code
    73 }
    74
    75 public void surfaceCreated(SurfaceHolder holder)
    76 {
    77 // TODO Auto-generated method stub
    78 //add your code
    79 }
    80
    81 public void surfaceDestroyed(SurfaceHolder holder)
    82 {
    83 // TODO Auto-generated method stub
    84 //add your code
    85 }
    86
    87 }
    88
    89 }
    复制代码

    此时运行该程序,并点击几下“画线”按钮,效果如下所示:

    可以看到,画出来的线是断断续续的,把上面程序的第58,59行的注释去掉,再运行一次,效果如下:

    可以看到,线已经没有断开的现象了。

    还有一点需要注意的是,如果希望程序在后台运行时还能画图且不报程序出错的问题,就要修改成以下这样的形式:

    复制代码
     1                 //锁定整个SurfaceView
    2 Canvas mCanvas = mSurfaceHolder.lockCanvas();
    3 try
    4 {
    5 if(mCanvas!=null)
    6 {
    7 mCanvas.drawLine(OldX, OldY, OldX+10, OldY+10, mPaint);
    8 //横坐标增加
    9 OldX = OldX + 10;
    10 //纵坐标增加
    11 OldY = OldY + 10;
    12 //绘制完成,释放画布,提交修改
    13 mSurfaceHolder.unlockCanvasAndPost(mCanvas);
    14 }
    15 }
    16 catch(Exception e)
    17 {
    18 e.printStackTrace();
    19 }
    20 finally
    21 {
    22 if(mCanvas!=null)
    23 {
    24 //重新锁一次
    25 mSurfaceHolder.lockCanvas(new Rect(0, 0, 0, 0));
    26 mSurfaceHolder.unlockCanvasAndPost(mCanvas);
    27 }
    28 }
    复制代码

    再运行,效果同第2幅图的一样。

    如果一件事情你觉得难的完不成,你可以把它分为若干步,并不断寻找合适的方法。最后你发现你会是个超人。不要给自己找麻烦,但遇到麻烦绝不怕,更不要退缩。 电工查找电路不通点的最快方法是:分段诊断排除,快速定位。你有什么启示吗? 求知若饥,虚心若愚。 当你对一个事情掌控不足的时候,你需要做的就是“梳理”,并制定相应的规章制度,并使资源各司其职。
  • 相关阅读:
    2018-8-18 训练神经网络笔记
    ffmpeg解码视频为图片和将图片合成一个MP4视频
    minikube start error
    按顺序将目录下的所有文件的绝对路径写入文件中
    ssh远程免密登录
    Ubuntu默认的awk一直报语法错误
    ffmpeg常用操作
    ssh免密登录server
    cv::namedWindow是非线程安全的
    lingcrypt源码安装undefined reference to ...
  • 原文地址:https://www.cnblogs.com/wvqusrtg/p/5179033.html
Copyright © 2020-2023  润新知