关于SurfaceView
来源:互联网 发布:js调用api接口代码 编辑:程序博客网 时间:2024/06/02 02:12
SurfaceView 是在子线程中更新画面的组件, View是 在 UI 的主线程中更新画面, 适合于做动画.
使用SurfaceView 通常要实现 SurfaceHolder.Callback接口,SurfaceView 类的生命周期有3个回调函数,分别为:
public abstract void surfaceCreated(SurfaceHolder holder) 在SurfaceView 创建时调用
public abstract void surfaceChanged(SurfaceHolder holder, int format, int width, int height) 在SurfaceView 改变时调用
public abstract void surfaceDestroyed(SurfaceHolder holder)在SurfaceView 销毁前调用
此外, 还有一个重要方法:
protected void onDraw(Canvas c) 用来绘制SurfaceView 画面, 每一次SurfaceView 中画面改变都是调用此方法.
通常实现动画效果原理是:
新建一个线程类,每隔一段时间调用SurfaceView 的onDraw(), 在onDraw() 方法中的画面也有一个线程类在时刻改变,这样后一个线程类实现了onDraw() 画面中显示内容的变化, 前一个线程类 时刻刷新画面,这样就形成了动画.
具体代码请参见 SufaceView_3_7 工程, 讲解一下两个线程类
使用SurfaceView 通常要实现 SurfaceHolder.Callback接口,SurfaceView 类的生命周期有3个回调函数,分别为:
public abstract void surfaceCreated(SurfaceHolder holder) 在SurfaceView 创建时调用
public abstract void surfaceChanged(SurfaceHolder holder, int format, int width, int height) 在SurfaceView 改变时调用
public abstract void surfaceDestroyed(SurfaceHolder holder)在SurfaceView 销毁前调用
此外, 还有一个重要方法:
protected void onDraw(Canvas c) 用来绘制SurfaceView 画面, 每一次SurfaceView 中画面改变都是调用此方法.
通常实现动画效果原理是:
新建一个线程类,每隔一段时间调用SurfaceView 的onDraw(), 在onDraw() 方法中的画面也有一个线程类在时刻改变,这样后一个线程类实现了onDraw() 画面中显示内容的变化, 前一个线程类 时刻刷新画面,这样就形成了动画.
具体代码请参见 SufaceView_3_7 工程, 讲解一下两个线程类
public class OnDrawThread extends Thread {MySurfaceView msv; // 得到MySurfaceView的引用SurfaceHolder sh; // SurfaceHolder引用public OnDrawThread(MySurfaceView msv) { super(); this.msv = msv; // 构造方法中,将msv引用指向调用了该类的MySurfaceView的对象 sh = msv.getHolder();}@Overridepublic void run() { super.run(); Canvas canvas = null; while (true) { // 这个循环用于时刻刷新界面 try { canvas = sh.lockCanvas(null); // 将canvas的引用指向surfaceView的canvas的对象 synchronized (this.sh) { // 绘制过程,可能带来同步方面的问题,加锁 if (canvas != null) { msv.onDraw(canvas); // 这里调用onDraw(),时刻刷新画面 } } } finally { try { if (sh != null) { sh.unlockCanvasAndPost(canvas); // 绘制完后解锁 } } catch (Exception e) { e.printStackTrace(); } }try { Thread.sleep(Constant.ONDRAWSPEED); // 休息1秒钟 } catch (Exception e) { e.printStackTrace(); } }}}----------------------------------//该类是控制duke图片运动的类public class PicRunThread extends Thread{MySurfaceView msv; //MySurfaceView的引用private float picX=0; //图片x坐标private float picY=Constant.SCREENHEIGHT-Constant.PICHEIGHT; //图片y坐标boolean yRunFlag=false; //y方向上的运动标记,false时y=y+speed,true时y=y-speedint picAlphaNum=0; //图片变暗效果中画笔的alpha值public PicRunThread(MySurfaceView msv) { super(); this.msv = msv; //将该线程类的引用指向调用其的MySurfaceView的对象}@Overridepublic void run() { super.run(); while(true){ //这个循环用于显示内容变化,实现重复显示, 如果没有则画面只显示一遍 //控制duke图片的运动 while(this.picX<Constant.SCREENWIDTH){ //当图片的左边完全超过屏幕的右边时,循环结束 msv.setPicX(picX); msv.setPicY(picY); picX=picX+Constant.PICXSPEED; if(yRunFlag){//应该向上运动,自减 picY=picY-Constant.PICYSPEED; }else{//应该向下运动,自加 picY=picY+Constant.PICYSPEED; } if(picY<=0){ //到达屏幕上沿 yRunFlag=false; }else if(picY>Constant.SCREENHEIGHT-Constant.PICHEIGHT){ //到达屏幕下沿yRunFlag=true; } try{ Thread.sleep(Constant.PICRUNSPEED); }catch(Exception e){e.printStackTrace();} } //图片变暗效果演示 msv.picAlphaFlag=true; //开启图片变暗效果 for(picAlphaNum=100;picAlphaNum<=200;picAlphaNum++){ if(picAlphaNum==200){ msv.picAlphaFlag=false; //当图片变暗效果结束,标记重置 picX=0; //图片x坐标 picY=Constant.SCREENHEIGHT-Constant.PICHEIGHT; //图片y坐标 System.out.println(msv.picAlphaFlag+"picX:"+picX+"picY:"+picY); } msv.setPicAlphaNum(picAlphaNum); try{ Thread.sleep(Constant.PICALPHASPEED); }catch(Exception e){e.printStackTrace();} } }}}
效果图示意如下:
- 关于SurfaceView
- 关于SurfaceView
- 关于SurfaceView类
- 关于SurfaceView的问题
- 关于SurfaceView的问题
- 关于surfaceview的理解
- 关于SurfaceView学习.
- 关于SurfaceView的使用
- 关于surfaceview的使用
- 关于Android之SurfaceView
- 关于android surfaceview
- 关于SurfaceView的截图问题
- 关于SurfaceView控件设置透明
- surfaceview
- SurfaceView
- surfaceview
- surfaceview
- SurfaceView
- 学习腾讯的产品管理之道
- 图片显示
- 辞职的程序员那些事儿
- 如何准确看清用户需求?
- UPnP簡析
- 关于SurfaceView
- andengine
- 开启win7的虚拟WiFi 热点
- awk中时间戳转换
- ok6410学习笔记(8.mmap地址映射之linux内存管理)
- Hibernate缓存(一)
- 动态编译 C#
- 逻辑思维题
- linux ping 命令的实现和分析