4

クライアントがカメラを使用して写真を撮るアプリがあります。画像のプレビューは、ユーザーが「クリック」ボタンを押す前に、SurfaceView を使用してタブレットに表示されています。ユーザーがクリック ボタンを押すと、onPictureTaken メソッドが呼び出され、そのメソッドで画像を保存し、camera.stopPreview() メソッドも呼び出します (これにより、ユーザーは撮影された写真を見ることができます)。

ただし、問題があります...写真が撮られた瞬間にユーザーがタブレットの周りを移動している場合、stopPreviewメソッドが呼び出された後に実際に表示される静止画は、バイト配列で取得したものと一致しませんonPictureTaken メソッドの。数ミリ秒の遅延があり、ユーザーが写真を撮る直前にタブレットを動かしているときにその違いが際立ちます (私は、99% の人が写真を撮っている間タブレットを動かさないことを知っています。しかし、私のクライアントは実際にこの問題に気づき、修正を望んでいます...)。以下に示すように、保存操作を別のスレッドに移動しようとしたため、onPictureTaken メソッドはできるだけ高速に実行できます。それでも全然効果がなかった…

private PictureCallback pictureCallback = new PictureCallback() {

    public void onPictureTaken(byte[] data, Camera camera) {

        camera.stopPreview();
        reference = data;

        new PictureCallbackHeavy().execute();
    }
};

また、takePicture メソッドを呼び出す直前に camera.stopPreview() を呼び出してみました (onPictureTaken() メソッド内ではありません)。しかし、結果は同じです。

撮影された画像を onPictureTaken() コールバックのバイト配列に正確に表示できるように、stopPreview メソッドを同期するにはどうすればよいですか?

前もって感謝します!!=)

4

1 に答える 1

2

残念ながら、stopPreview() を呼び出すだけでは適切なプレビュー画像を取得することはできません。これは、写真が撮影された瞬間と onPictureTaken() が呼び出される瞬間の間に、次のように動作するため、かなりの時間が経過する可能性があるためです。

  • カメラが実際に写真を撮ります (それがプレビューしたいものです)
  • onShutter() が呼び出されます
  • 生の画像データの onPictureTaken() が呼び出されます (一部のデバイスで)
  • スケーリングされたプレビュー画像の onPictureTaken() が呼び出されます (一部のデバイスで)
  • 最終的な圧縮画像データの onPictureTaken() が呼び出されます (ここで話しているもの)

そのため、onPictureTaken() コールバックをビットマップに変換し、byte[] dataそのビットマップを ImageView にマップして、SurfaceView の上に配置し、静止プレビュー イメージを表示する必要があります。コードはおそらく次のようになります。

public void onPictureTaken(byte[] data, Camera camera) {
    camera.stopPreview();
    final Bitmap image = BitmapFactory.decodeByteArray(data, 0, data.length);
    surfaceView.setVisibility(SurfaceView.GONE);
    imageView.setVisibility(ImageView.VISIBLE);
    imageView.setImageBitmap(image);
    reference = data;
    new PictureCallbackHeavy().execute();
}
于 2012-06-19T11:32:24.573 に答える