Android 향상 의 SurfaceView 와 다 중 스 레 드 의 혼합 인 스 턴 스

7110 단어 AndroidSurfaceView
앞에서 간단하게 소개 했다Android 에서 Surface View 의 기본 사용본 고 는 Surface View 와 다 중 스 레 드 의 혼합 을 소개 한다.Surface View 와 다 중 스 레 드 가 혼 합 된 것 은 애니메이션 의 반 짝 임 을 방지 하기 위 한 다 중 스 레 드 응용 입 니 다.안 드 로 이 드 의 다 중 스 레 드 용법 은 JAVA 의 다 중 스 레 드 용법 과 똑 같 습 니 다.본 고 는 다 중 스 레 드 방면 의 소 개 를 하지 않 습 니 다.SurfaceView 와 다 중 스 레 드 의 혼합 사용 을 직접 설명 합 니 다.즉,하나의 스 레 드 를 열 어 그림 을 읽 고 다른 스 레 드 는 그림 을 전문 적 으로 그립 니 다.
본 프로그램 은 캡 처 를 다음 과 같이 실행 합 니 다.왼쪽 은 하나의 스 레 드 를 열 어 읽 고 그림 을 그립 니 다.오른쪽 은 두 개의 스 레 드 를 엽 니 다.하 나 는 그림 을 읽 고 하 나 는 그림 을 전문 적 으로 그립 니 다.

비교 해 보면 오른쪽 애니메이션 의 프레임 속 도 는 왼쪽 보다 현저히 빠 르 고 좌우 둘 다 Thread.sleep()를 사용 하지 않 았 다.왜 두 개의 스 레 드 를 열 고 한 사람 은 그림 을 읽 어야 합 니까?두 개의 스 레 드 를 열지 않 고 왼쪽 처럼 모두'읽 으 면서 그리 기'를 해 야 합 니까?Surface View 는 그림 을 그 릴 때마다 Canvas 를 잠 그 기 때 문 입 니 다.즉,같은 구역 을 이번에 다 그리 지 못 하면 다음 에 그 릴 수 없 기 때문에 애니메이션 재생 의 효율 을 높이 려 면 스 레 드 를 열 어 그림 을 전문 적 으로 그리고 다른 스 레 드 를 열 어 예비 처 리 를 해 야 합 니 다.
main.xml 의 원본 코드 는 다음 과 같 습 니 다.

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
 android:layout_width="fill_parent" android:layout_height="fill_parent"
 android:orientation="vertical">

 <LinearLayout android:id="@+id/LinearLayout01"
 android:layout_width="wrap_content" android:layout_height="wrap_content">
 <Button android:id="@+id/Button01" android:layout_width="wrap_content"
  android:layout_height="wrap_content" android:text="      "></Button>
 <Button android:id="@+id/Button02" android:layout_width="wrap_content"
  android:layout_height="wrap_content" android:text="      "></Button>
 </LinearLayout>
 <SurfaceView android:id="@+id/SurfaceView01"
 android:layout_width="fill_parent" android:layout_height="fill_parent"></SurfaceView>
</LinearLayout>

자바 프로그램의 원본 코드 는 다음 과 같 습 니 다.

package com.testSurfaceView;
import java.lang.reflect.Field;
import java.util.ArrayList;
import android.app.Activity;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Canvas;
import android.graphics.Paint;
import android.graphics.Rect;
import android.os.Bundle;
import android.util.Log;
import android.view.SurfaceHolder;
import android.view.SurfaceView;
import android.view.View;
import android.widget.Button;

public class testSurfaceView extends Activity {
 /** Called when the activity is first created. */
 Button btnSingleThread, btnDoubleThread;
 SurfaceView sfv;
 SurfaceHolder sfh;
 ArrayList<Integer> imgList = new ArrayList<Integer>();
 int imgWidth, imgHeight;
 Bitmap bitmap;//      ,      

 @Override
 public void onCreate(Bundle savedInstanceState) {
 super.onCreate(savedInstanceState);
 setContentView(R.layout.main);

 btnSingleThread = (Button) this.findViewById(R.id.Button01);
 btnDoubleThread = (Button) this.findViewById(R.id.Button02);
 btnSingleThread.setOnClickListener(new ClickEvent());
 btnDoubleThread.setOnClickListener(new ClickEvent());
 sfv = (SurfaceView) this.findViewById(R.id.SurfaceView01);
 sfh = sfv.getHolder();
 sfh.addCallback(new MyCallBack());//     surfaceCreated  surfaceChanged
 }

 class ClickEvent implements View.OnClickListener {

 @Override
 public void onClick(View v) {

  if (v == btnSingleThread) {
  new Load_DrawImage(0, 0).start();//          
  } else if (v == btnDoubleThread) {
  new LoadImage().start();//       
  new DrawImage(imgWidth + 10, 0).start();//       
  }
 }
 }
 class MyCallBack implements SurfaceHolder.Callback {
 @Override
 public void surfaceChanged(SurfaceHolder holder, int format, int width,
  int height) {
  Log.i("Surface:", "Change");
 }
 @Override
 public void surfaceCreated(SurfaceHolder holder) {
  Log.i("Surface:", "Create");
  //               ID   
  Field[] fields = R.drawable.class.getDeclaredFields();
  for (Field field : fields) {
  if (!"icon".equals(field.getName()))//   icon     
  {
   int index = 0;
   try {
   index = field.getInt(R.drawable.class);
   } catch (IllegalArgumentException e) {
   // TODO Auto-generated catch block
   e.printStackTrace();
   } catch (IllegalAccessException e) {
   // TODO Auto-generated catch block
   e.printStackTrace();
   }
   //     ID
   imgList.add(index);
  }
  }
  //       
  Bitmap bmImg = BitmapFactory.decodeResource(getResources(),
   imgList.get(0));
  imgWidth = bmImg.getWidth();
  imgHeight = bmImg.getHeight();
 }
 @Override
 public void surfaceDestroyed(SurfaceHolder holder) {
  Log.i("Surface:", "Destroy");
 }
 }
 /*
 *           
 */
 class Load_DrawImage extends Thread {
 int x, y;
 int imgIndex = 0;

 public Load_DrawImage(int x, int y) {
  this.x = x;
  this.y = y;
 }
 public void run() {
  while (true) {
  Canvas c = sfh.lockCanvas(new Rect(this.x, this.y, this.x
   + imgWidth, this.y + imgHeight));
  Bitmap bmImg = BitmapFactory.decodeResource(getResources(),
   imgList.get(imgIndex));
  c.drawBitmap(bmImg, this.x, this.y, new Paint());
  imgIndex++;
  if (imgIndex == imgList.size())
   imgIndex = 0;
  sfh.unlockCanvasAndPost(c);//         
  }
 }
 };
 /*
 *         
 */
 class DrawImage extends Thread {
 int x, y;
 public DrawImage(int x, int y) {
  this.x = x;
  this.y = y;
 }
 public void run() {
  while (true) {
  if (bitmap != null) {//      
   Canvas c = sfh.lockCanvas(new Rect(this.x, this.y, this.x
    + imgWidth, this.y + imgHeight));

   c.drawBitmap(bitmap, this.x, this.y, new Paint());

   sfh.unlockCanvasAndPost(c);//         
  }
  }
 }
 };
 /*
 *           
 */
 class LoadImage extends Thread {
 int imgIndex = 0;
 public void run() {
  while (true) {
  bitmap = BitmapFactory.decodeResource(getResources(),
   imgList.get(imgIndex));
  imgIndex++;
  if (imgIndex == imgList.size())//          
   imgIndex = 0;
  }
 }
 };
}

본 고 에서 말 한 예 시 는 여러분 이 안 드 로 이 드 의 Surface View 와 다 중 스 레 드 의 혼합 프로 그래 밍 을 하 는 데 도움 이 되 기 를 바 랍 니 다.

좋은 웹페이지 즐겨찾기