【问题标题】:Android camera: very low preview FPSAndroid 相机:预览 FPS 非常低
【发布时间】:2014-10-14 09:24:10
【问题描述】:

一周前,我开始研究 Android 相机 API。我已成功启动相机并开始预览,效果很好。然后我发现我没有正确初始化和释放相机,所以我对代码进行了一些检查,现在我遇到了一个最初没有出现的问题:FPS 极低。大约 0.5,即每帧 2 秒。有趣的是,我得到了 1 帧的延迟,然后在(1-15 毫秒)之后立即获得了第二帧,然后在下一帧之前再次延迟了 2 秒。

这是我的相机初始化代码:

    m_openedCamera = Camera.open(id);
    m_surfaceHolder = new SurfaceView(MyApplication.instance().getApplicationContext()).getHolder();
    Assert.assertNotNull(m_openedCamera);

    // This is required on A500 for some reason
    Camera.Parameters params = m_openedCamera.getParameters();
    params.setPreviewFormat(ImageFormat.NV21);
    params.setPreviewSize(320, 240);
    if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.ICE_CREAM_SANDWICH)
    {
        params.setRecordingHint(true);
        params.setAutoExposureLock(true);
        params.setAutoWhiteBalanceLock(true);
    }

    m_openedCamera.setParameters(params);

    int bitsPerPx  = ImageFormat.getBitsPerPixel(ImageFormat.NV21);
    int width       = params.getPreviewSize().width;
    int height      = params.getPreviewSize().height;
    int size        = (int)(width * height * bitsPerPx / 8.0);
    m_openedCamera.addCallbackBuffer( new byte[size] );
    m_openedCamera.addCallbackBuffer( new byte[size] );
    m_openedCamera.addCallbackBuffer( new byte[size] );
    m_openedCamera.addCallbackBuffer( new byte[size] );

    m_openedCamera.setErrorCallback(this);
    m_openedCamera.setPreviewDisplay(m_surfaceHolder);
    m_openedCameraFacing = facing;
    m_openedCamera.setPreviewCallback(this);
    m_openedCamera.startPreview();

我刚刚添加了回调缓冲区 - 没有改变任何东西。在我一周前的初始代码中,我没有表面视图,但现在删除它也没有效果。 这也发生在我的第二个更新的平板电脑上,即使那里的 FPS 更高(8-10),并且那里没有双帧,帧间隔均匀。 FPS 过去至少为 20。顺便说一句,光照条件从现在到现在都没有改变。

更新:尝试按照here 所述在单独的线程中打开相机 - 没有变化。

【问题讨论】:

  • 如果消除回调缓冲区,性能会提高吗?类似于stackoverflow.com/questions/7790566/… ?
  • @fadden:不。无论有没有缓冲区,性能都完全相同。
  • 这里缺少的一个电话是Camera.Parameters.setPreviewFrameRate()setPreviewFpsRange()。请注意仅选择支持的 FPS。
  • 请注意,没有setPreviewCallbackWithBuffer()addCallbackBuffer() 是无关紧要的。如果您的处理涉及工作线程等,预分配的回调缓冲区可能会非常有用。如果垃圾收集是即时的(例如,所有处理都在回调内完成),这将无济于事。
  • @AlexCohn:错过了那个。至于 FPS 范围 - 此设备的相机仅支持一个范围,我已尝试明确设置它,但没有任何区别。

标签: android camera android-camera


【解决方案1】:

params.setRecordingHint(true);用于开始录像开始。

请用“params.setRecordingHint(false)”再次检查

【讨论】:

  • setRecordingHint 是 Android 4.0,我正在尝试 3.1。
【解决方案2】:

请自己制作previewcallbak函数,然后

私有 PreviewCallback mPreviewCallback = new PreviewCallback();

.... setPreviewCallback(mPreviewCallback);

PreviewCallback()可以参考cts目录下的CameraTest.Java:cts/tests/tests/hawdware/src/android/hardware/cts

【讨论】:

  • 答案如何?显然,我确实有一个回调。使用空主体(更具体地说,回调仅测量和记录经过的 FPS,仅此而已)。
【解决方案3】:

来自您下面的评论 "我已成功初始化相机并开始预览,效果很好。然后我发现我没有正确初始化和释放相机"

我猜你一开始是在使用相机 HAL 中定义的默认相机参数。虽然不清楚“初始化”是什么意思,但我认为它们很可能是相机参数设置。

所以,我建议您删除 params 的代码,然后再次测试。 或者,你可以一个一个测试一下

  1. 仅删除“params.setPreviewSize(320, 240);”
  2. 仅删除“params.setPreviewFormat(ImageFormat.NV21);”
  3. 删除 1 和 2。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-11-03
    • 1970-01-01
    相关资源
    最近更新 更多