为实时计算机视觉处理获得高FPS的方法

时间:2011-12-27 22:01:58

标签: android camera frame-rate

我的目标是获得尽可能高的FPS。我会很满意BW小帧,但FPS应该是最大的。 HTC WildFire S上的getSupportedPreviewFpsRange返回(9,30)。但是当我尝试用最简单的处理绘制预览图像时,它在视觉上最大可达到12-15 FPS。 设置参数和startPreview()方法调用后,我执行以下操作:

camera.setPreviewCallback(new Camera.PreviewCallback() {
          @Override
          public void onPreviewFrame(byte[] bytes, Camera camera) {
            Bitmap bitmap = Bitmap.createBitmap(size.width, size.height, Bitmap.Config.ARGB_8888);
            int[] colors = new int[size.width * size.height];
            for (int i=0; i < colors.length; i++){
              colors[i] = getBWColor(bytes[i]);
            }
            bitmap.setPixels(colors, 0, size.width, 0, 0, size.width, size.height);
            secondView.setImageBitmap(bitmap);
          }
        });
      }

private static int getBWColor(byte b){
    int res = 255;
    for(int i=0;i<3;i++){
      res = (res << 8) + b;
    }
    return res;
  }

有没有办法尽可能快地获得它? =(

3 个答案:

答案 0 :(得分:5)

首先,使用setPreviewCallbackWithBuffer(),它重用一个缓冲区,而不必在每个帧上分配新的缓冲区。检查我的older answer,有一个示例如何使用它。

比,不要在onPreviewFrame()中做任何昂贵的操作,数据的时间有限,它会在每个新帧上重写。你应该在另一个线程中进行处理。

当然,不要在每个帧上创建一个颜色数组的新位图,只做一次。

答案 1 :(得分:3)

我真的不明白你在做什么,但我猜你在处理过程中会自杀。

1)每次都不要创建新的位图。重用1位图。 2)使用NDK在C / C ++中处理您的位图。看看“等离子”的例子。它比Java快得多。不是因为它的C ++真的,而是因为每当你推入像素的数据数组时,API的Java版本往往会改变整个事物。在C ++版本中,您可以直接操作像素值。

答案 2 :(得分:1)

我不确定你的目标是什么,但我添加了相机功能的方式创建了一个自定义的SurfaceView类并在那里设置我的相机。在我选择正面(如果可用)或背面后,我设置参数然后调用setPreviewDisplay并传入我创建的SurfaceHolder(下面的代码)。之后只需调用startpreview(),一切都很美妙。我有很好的帧率,一切都很好。如果您希望我详细说明或发布一些代码,请告诉我。

SufaceHolder mHolder;
mHolder = getHolder();
mHolder.addCallback(this); // this is the SurfaceView class
mHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);
mHolder.setKeepScreenOn(true);